テスト目的で.DLLを受け取りました。この.dllには、後でハードウェアからライブ画像を処理するために使用される機能が含まれています。.DLLからビットマップを取得し、バイト[]に変換して画像に変換する
この単純な.dllでは、イメージを開いてメモリにロードし、幅と高さを取得し、イメージに変換する必要があるピクセルを取得できます。読み込み、幅の取得、高さの取得は問題ありませんが、ピクセルを取得してビットマップまたはイメージに変換することは問題です。私が受け取った
C++サンプルソース:
ApiFunc->OpenImageFile(this->OpenPictureDialog1->FileName.c_str());
ApiFunc->AllocMemory();
w = ApiFunc->GetImageWidth();
h = ApiFunc->GetImageHeight();
Image1->Width = w;
Image1->Height = h;
unsigned char* ptr = ApiFunc->GetImagePixels();
COLORREF pixel;
int r,g,b;
for(int y=0; y<w; y++)
{
for(int x=0; x<h; x++)
{
r = (int)*(ptr+3*x);
g = (int)*(ptr+3*x+1);
b = (int)*(ptr+3*x+2);
Image1->Canvas->Pixels[y][x] = RGB(r,g,b);
}
ptr += 3*h;
}
ApiFuncで、これを見つけることができます。だから今、私が試してみました何
void __fastcall TAPIFunc::LoadDll(HINSTANCE m_hMain)
{
//some others above
GET_IMAGE_PIXELS = (func_GET_IMAGE_PIXELS )GetProcAddress(m_hMain, "GET_IMAGE_PIXELS");
//some others below
}
unsigned char* __fastcall TAPIFunc::GetImagePixels(void)
{
return GET_IMAGE_PIXELS();
}
これまでのところ、私はバイト[を使用して試してみました]を返しますが、MarshalDirectiveExceptionがスローされます。
[DllImport("ImageTest.dll")]
public static extern IntPtr GET_IMAGE_PIXELS();
private void OpenImage(string filename)
{
OPEN_IMAGE_FILE(filename);
ALLOC_MEMORY();
int width = GET_IMAGE_WIDTH(); //=800
int height = GET_IMAGE_HEIGHT(); //=600
IntPtr buffer = GET_IMAGE_PIXELS();
int size = width * height * 3;//not sure what the size must be, I think this is one of the issues, just following logic of one answer below.
//but source: https://stackoverflow.com/a/16300450/2901207
byte[] bitmapImageArray = new byte[size];
Marshal.Copy(buffer, bitmapImageArray, 0, size);
Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format24bppRgb);
BitmapData bmData = bitmap.LockBits(new System.Drawing.Rectangle(0, 0, bitmap.Width, bitmap.Height), ImageLockMode.ReadWrite, bitmap.PixelFormat);
IntPtr pNative = bmData.Scan0;
Marshal.Copy(imageData, 0, pNative,size);
bitmap.UnlockBits(bmData);
bitmap.Save(Environment.CurrentDirectory + @"\result.bmp");
using (var ms = new MemoryStream(bitmapImageArray))
{
//both throw exception: Parameter is not valid
Bitmap bmp = new Bitmap(ms);
Image bitmapImage = Image.FromStream(ms);
}
}
答え源:
answer 1, using bitmap.LockBits method answers 2 and 3, using memoryStream
ただ、私がテストするために有効なイメージを持っていることを確認するために、私はこのオプションを使用して、Photoshopで画像を保存:
醜いテスト画像:
美しい、それはないですか? :)
forループを使用して試してみると、クラッシュするまで実行されます。 count = 1441777まで、別の画像数= 1527793(同じ次元)まで実行されました。
int count = 0;
for (int i = 0; i < width * height * 4; i++)
{
count++;
bitmapImageArray[i] = Marshal.ReadByte(buffer, i);
}
ありがとうございました!私は彼らがしたのと同じループを行う答えを投稿しようとしていましたが、そのようなビットマップを構築するのは少し集中しているようです。 341msから11msに、これを最初に実行してから、残りのソリューションに従ってください – CularBytes