iasksillyquestions
iasksillyquestions

Reputation: 5689

C# bitmap images, byte arrays and streams!

I have a function which extracts a file into a byte array (data).

        int contentLength = postedFile.ContentLength;
        byte[] data = new byte[contentLength];
        postedFile.InputStream.Read(data, 0, contentLength);

Later I use this byte array to construct an System.Drawing.Image object (where data is the byte array)

       MemoryStream ms = new MemoryStream(data);
       Image bitmap = Image.FromStream(ms);

I get the following exception "ArgumentException: Parameter is not valid."

The original posted file contained a 500k jpeg image...

Any ideas why this isnt working?

Note: I assure you I have a valid reason for converting to a byte array and then to a memorystream!!

Upvotes: 1

Views: 16324

Answers (5)

jrista
jrista

Reputation: 32960

Any reason why you don't simply do this:

Image bitmap = Image.FromStream(postedFile.InputStream);

Upvotes: 1

Guffa
Guffa

Reputation: 700432

That's most likely because you didn't get all the file data into the byte array. The Read method doesn't have to return as many bytes as you request, and it returns the number of bytes actually put in the array. You have to loop until you have gotten all the data:

int contentLength = postedFile.ContentLength;
byte[] data = new byte[contentLength];
for (int pos = 0; pos < contentLength; ) {
   pos += postedFile.InputStream.Read(data, pos, contentLength - pos);
}

This is a common mistake when reading from a stream. I have seen this problem a lot of times.

Edit:
With the check for an early end of stream, as Matthew suggested, the code would be:

int contentLength = postedFile.ContentLength;
byte[] data = new byte[contentLength];
for (int pos = 0; pos < contentLength; ) {
   int len = postedFile.InputStream.Read(data, pos, contentLength - pos);
   if (len == 0) {
      throw new ApplicationException("Upload aborted.");
   }
   pos += len;
}

Upvotes: 5

Kevin Pullin
Kevin Pullin

Reputation: 13327

Have you checked the return value from the Read() call to verify that is actually reading all of the content? Perhaps Read() is only returning a portion of the stream, requiring you to loop the Read() call until all of the bytes are consumed.

Upvotes: 1

Eclipse
Eclipse

Reputation: 45493

I have had problems loading images in .NET that were openable by more robust image libraries. It's possible that the specific jpeg image you have is not supported by .NET. jpeg files are not just one type of encoding, there's a variety of possible compression schemes allowed.

You could try it with another image that you know is in a supported format.

Upvotes: 0

Matthew Flaschen
Matthew Flaschen

Reputation: 284836

You're not checking the return value of postedFile.InputStream.Read. It is not at all guaranteed to fill the array on the first call. That will leave a corrupt JPEG in data (0's instead of file content).

Upvotes: 1

Related Questions