Reputation: 81
Ok, so I've seen multiple people with this issue, and I've found to some extent what might be causing the issue, but I can't figure out how to fix it. Basically, I'm trying to send a screenshot from a client to a server via sockets. I take the screenshot on the client application and use this method to convert it to a byte array:
// Convert bitmap to byte method
public static byte[] ImageToByte(Bitmap bitmap)
{
byte[] imageData;
using (var stream = new MemoryStream())
{
bitmap.Save(stream, ImageFormat.Png);
imageData = stream.ToArray();
return imageData;
}
}
I then send the length of the byte array and the byte array to the server. The server, after receiving the length, uses this method to get the actual data (this is part of the method since most of it isn't relevant):
void dataRecieveCallback(IAsyncResult ar)
{
try
{
int rec = sck.EndReceive(ar);
if (rec <= 0)
{
return;
}
recieveBuffer.bufStream.Write(recieveBuffer.buffer, 0, rec);
recieveBuffer.toRecieve -= rec;
if (recieveBuffer.toRecieve > 0)
{
Array.Clear(recieveBuffer.buffer, 0, recieveBuffer.buffer.Length);
recieveBuffer.bufStream.Position = 0;
sck.BeginReceive(recieveBuffer.buffer, 0, recieveBuffer.buffer.Length, SocketFlags.None, dataRecieveCallback, null);
return;
}
// Convert all recieved data in memory stream to a byte array
byte[] finalBuffer = recieveBuffer.bufStream.ToArray();
I then use the finalBuffer
to try to get the image, but whenever I do, using this method:
TypeConverter tc = TypeDescriptor.GetConverter(typeof(Bitmap));
Bitmap screenShot = (Bitmap)tc.ConvertFrom(finalBuffer);
I always get a System.ArgumentException
from System.Drawing.ImageFromStream
: "parameter is invalid". This code has worked fine for sending strings, but whenever I try to send an image it doesn't work. I'm pretty much sure it's an issue with the socket code because I tried doing this locally by taking a screenshot, converting it to a byte array using the same methods, then using the same method to convert it back, and it worked. Does anyone know what's wrong with my code here?
Here is part of the code for the buffer
struct RecBuffer
{
public const int BUFFER_SIZE = 1024;
public byte[] buffer;
public int toRecieve;
public MemoryStream bufStream;
public RecBuffer(int toRec)
{
buffer = new byte[BUFFER_SIZE];
toRecieve = toRec;
bufStream = new MemoryStream(toRecieve);
}
}
I used quite a bit of the code from this tutorial. At least for the receiving parts.
Upvotes: 1
Views: 463
Reputation: 13040
I think the problem is with your dataRecieveCallback
function.
There you reset the bufStream's position to zero:
if (recieveBuffer.toRecieve > 0)
{
Array.Clear(recieveBuffer.buffer, 0, recieveBuffer.buffer.Length);
recieveBuffer.bufStream.Position = 0; // <--Here
sck.BeginReceive(recieveBuffer.buffer, 0, recieveBuffer.buffer.Length, SocketFlags.None, dataRecieveCallback, null);
return;
}
This means that you overwrite the already received bytes the next time the system calls your callback function.
So, just remove the line
recieveBuffer.bufStream.Position = 0;
and your code should work fine.
Upvotes: 1