I receive a JPEG image from a sever in a char *
buffer. I want to show this picture in a picture box before saving it.All I know is that a picture box can show images from File, Hbitmap and Stream. I don't want to use the file one. and I don't know how to use the other ones.
我从char *缓冲区中的服务器接收JPEG图像。我想在保存之前在图片框中显示这张图片。我所知道的是一个图片框可以显示来自File,Hbitmap和Stream的图片。我不想使用该文件。我不知道如何使用其他的。
I've searched and tried some, And here's my code. I don't know why it doesn't show any picture.
我搜索并尝试了一些,这是我的代码。我不知道为什么它没有显示任何图片。
delegate void setImagedelegate(Stream ^ image);
void threadDecodeAndShow()
{
while (1)
{
if (f)
{
//the package that is receiving has some custom headers,
// I first find about the size of the JPEG and
//put a pointer at the beginning of the JPEG part.
BYTE *pImgSur = NULL;
DWORD imageInfoLength = *(DWORD*)m_pImgDataBufPtr[nIndexCurBuf];
DWORD customInfoLenForUser = *(DWORD*)(m_pImgDataBufPtr[nIndexCurBuf] + 4 + imageInfoLength);
DWORD jpegLength = *(DWORD*)(m_pImgDataBufPtr[nIndexCurBuf] + 4 + imageInfoLength + 4 + customInfoLenForUser);
pImgSur = (BYTE *)(m_pImgDataBufPtr[nIndexCurBuf] + 12 + customInfoLenForUser + imageInfoLength);
auto store = gcnew array<Byte>(jpegLength);
System::Runtime::InteropServices::Marshal::Copy(IntPtr(pImgSur), store, 0, jpegLength);
auto stream = gcnew System::IO::MemoryStream(store);
this->setImage(stream);
f = 0;
}
}
}
void setImage(Stream ^ image)
{
if (this->pictureBox1->InvokeRequired)
{
setImagedelegate^ d =
gcnew setImagedelegate(this, &MainPage::setImage);
this->Invoke(d, gcnew array<Object^> { image });
}
else
{
this->pictureBox1->Image = Image::FromStream(image);
this->pictureBox1->Show();
}
}
1 个解决方案
#1
1
You can turn a char* buffer into a stream with a memory stream. Two ways to do it, depends on how long the buffer remains valid. The Image class requires the backing store for the stream to remain readable for the life of the image. So if you are 100% sure that you can rely on the buffer surviving long enough then you can do it like this:
您可以将char *缓冲区转换为具有内存流的流。两种方法,取决于缓冲区保持有效的时间。 Image类要求流的后备存储在图像的生命周期内保持可读。因此,如果您100%确定可以依赖缓冲区存活足够长时间,那么您可以这样做:
using namespace System;
using namespace System::Drawing;
Image^ BytesToImage(char* buffer, size_t len) {
auto stream = gcnew System::IO::UnmanagedMemoryStream((unsigned char*)buffer, len);
return Image::FromStream(stream);
}
If you don't have that guarantee, or you can't be sure, then you have to copy the buffer content:
如果您没有这种保证,或者您无法确定,那么您必须复制缓冲区内容:
Image^ BytesToImageBuffered(char* buffer, size_t len) {
auto store = gcnew array<Byte>(len);
System::Runtime::InteropServices::Marshal::Copy(IntPtr(buffer), store, 0, len);
auto stream = gcnew System::IO::MemoryStream(store);
return Image::FromStream(stream);
}
The garbage collector takes care of destroying the stream and array objects, happens after you dispose the Image object, so no need to help.
垃圾收集器负责销毁流和数组对象,在您处理Image对象后发生,因此无需帮助。
#1
1
You can turn a char* buffer into a stream with a memory stream. Two ways to do it, depends on how long the buffer remains valid. The Image class requires the backing store for the stream to remain readable for the life of the image. So if you are 100% sure that you can rely on the buffer surviving long enough then you can do it like this:
您可以将char *缓冲区转换为具有内存流的流。两种方法,取决于缓冲区保持有效的时间。 Image类要求流的后备存储在图像的生命周期内保持可读。因此,如果您100%确定可以依赖缓冲区存活足够长时间,那么您可以这样做:
using namespace System;
using namespace System::Drawing;
Image^ BytesToImage(char* buffer, size_t len) {
auto stream = gcnew System::IO::UnmanagedMemoryStream((unsigned char*)buffer, len);
return Image::FromStream(stream);
}
If you don't have that guarantee, or you can't be sure, then you have to copy the buffer content:
如果您没有这种保证,或者您无法确定,那么您必须复制缓冲区内容:
Image^ BytesToImageBuffered(char* buffer, size_t len) {
auto store = gcnew array<Byte>(len);
System::Runtime::InteropServices::Marshal::Copy(IntPtr(buffer), store, 0, len);
auto stream = gcnew System::IO::MemoryStream(store);
return Image::FromStream(stream);
}
The garbage collector takes care of destroying the stream and array objects, happens after you dispose the Image object, so no need to help.
垃圾收集器负责销毁流和数组对象,在您处理Image对象后发生,因此无需帮助。