/// <summary>
/// Writes a byte array to the stream. This block of data is compressed and stored in the stream passed as a parameter to the <see cref="ZOutputStream(Stream,int)">class constructor</see>.
/// </summary>
/// <param name="buffer">A byte array to compress.</param>
/// <param name="offset">Offset of the first byte to compress.</param>
/// <param name="count">The number of bytes to compress from the buffer.</param>
/// <example> The following code demonstrates how to use the <c>ZOutputStream</c> to compress data
/// <code>
/// [C#]
/// private void compressFile(string inFile, string outFile)
/// {
/// /* Create a file to store compressed data */
/// System.IO.FileStream compressedFile = new System.IO.FileStream(@"c:\data\compressed.dat", System.IO.FileMode.Create);
/// /* Open a file containing source data */
/// System.IO.FileStream sourceFile = new System.IO.FileStream(@"c:\data\source.dat", System.IO.FileMode.Open);
/// /* Create ZOutputStream for compression */
/// ZOutputStream compressionStream = new ZOutputStream(compressedFile);
///
/// try
/// {
/// byte[] buffer = new byte[2000];
/// int len;
/// /* Read and compress data */
/// while ((len = sourceFile.Read(buffer, 0, 2000)) > 0)
/// {
/// /* Store compressed data */
/// compressionStream.Write(buffer, 0, len);
/// }
/// }
/// finally
/// {
/// compressionStream.Close();
/// sourceFile.Close();
/// compressedFile.Close();
/// }
/// }
/// </code>
/// </example>
public override void Write(byte[] buffer, int offset, int count)
{
if (count == 0)
{
return;
}
if (buffer == null)
{
throw new ArgumentNullException("buffer");
}
int err;
byte[] b = new byte[buffer.Length];
System.Array.Copy(buffer, 0, b, 0, buffer.Length);
z.next_in = b;
z.next_in_index = offset;
z.avail_in = count;
do
{
z.next_out = buf;
z.next_out_index = 0;
z.avail_out = ZLibUtil.zLibBufSize;
err = z.deflate(flush);
if (err != (int)ZLibResultCode.Z_OK && err != (int)ZLibResultCode.Z_STREAM_END)
{
throw new ZStreamException("deflating: " + z.msg);
}
_stream.Write(buf, 0, ZLibUtil.zLibBufSize - z.avail_out);
//fixed infinite loop where z.istate.mode == 12, but z.avail_in != 0.
if (z.istate != null)
{
if (z.istate.mode == InflateMode.DONE)
{
if (z.avail_in > 0)
{
z.avail_in = 0;
}
}
}
}while (z.avail_in > 0 || z.avail_out == 0);
}