MFC / ActiveX :Bitmap aus Resourcen als Variant* übergeben
-
Hallo!
Ich habe eine ActiveX-Componente entworfen in der dann aus einer Anwendung, welche die ActiveX-Componente eingefügt hat, eine Methode
"GetImage(VARIANT* image)" aufgerufen werden kann.
Wenn Also diese Methode aufgerufen wird, soll eine Bitmap-Resource in ein VARIANT SafeArray gepackt werden und übergeben werden.
Kann mir da jemand weiterhelfen?
Als ertstes müsste mir wahrscheinlich das Bitamap als Byte-Array vorliegen um es dann in ein SafeArray zu packen. Aber daran scheitert es bei schon, obwohl das Bitmap im Speicher als Resource doch eigentlich schon als Byte-Array vorliegt, oder nicht?Danke im Vorraus! Für jeden Ansatz bin ich dankbar!
-
Muss es direkt binär sein.
Andere Methode:
Erzeuge ein IPicture Objekt. Packe den IUnknown Zeiger in den Variant und gut ist.
-
BOOL CGetImageCtrl::getImage(VARIANT* image) { AFX_MANAGE_STATE(AfxGetStaticModuleState()); CBitmap bmp ; bmp.LoadBitmap(IDB_BITMAP1); PICTDESC desc; HRESULT hres; // how make a picture object // setup pictdesc structure desc.cbSizeofstruct = sizeof(PICTDESC) ; desc.picType = PICTYPE_BITMAP; desc.bmp.hbitmap = (HBITMAP)bmp.GetSafeHandle(); LPPICTURE pPicture = 0; // create the StdPicture object hres = ::OleCreatePictureIndirect(&desc, IID_IPicture, FALSE, /*don't destroy it*/ (LPVOID*)&pPicture); return TRUE; }Also dies habe ich gefunden. Ich habe doch nun ein Picture Object oder? Welchen Zeiger kann ich jetzt in meinen Variant packen?
-
Auf pPicture kannst Du nun ein QueryInterface für IUnknown durchführen. Den IUnkown Zeiger speicherst Du dann im Variant. NIcht vergessen den IPicture Zeiger wieder freizugeben.
-
Hier nun meine getImage (VARIANT *image) Methode:
VARIANT_BOOL CGetImageCtrl::getImage(VARIANT* image) { AFX_MANAGE_STATE(AfxGetStaticModuleState()); // TODO: Fügen Sie hier Ihren Dispatchhandlercode ein. CBitmap bmp ; VARIANT p1; PICTDESC desc; HRESULT hres; bmp.LoadBitmap(IDB_BITMAP1); VariantInit(&p1); // setup pictdesc structure desc.cbSizeofstruct = sizeof(PICTDESC) ; desc.picType = PICTYPE_BITMAP; desc.bmp.hbitmap = (HBITMAP)bmp.GetSafeHandle(); IPicture *pd; // create the StdPicture object hres = ::OleCreatePictureIndirect(&desc, IID_IPicture, FALSE,(LPVOID*)&pd); if(SUCCEEDED(hres)) { p1.vt = VT_UNKNOWN; p1.punkVal = pd; *image = p1; } return VARIANT_TRUE; }Dies ist der Teil aus meiner Anwendung, wo ich die Methode aufrufe und das Bitmap anzeigen lassen möchte:
void CGetImageTestDlg::OnBnClickedButton1() { // TODO: Fügen Sie hier Ihren Kontrollbehandlungscode für die Benachrichtigung ein. VARIANT image; IUnknown* pUnk; IPicture *pPicture= 0; long lWidth, lHeight; int iWidth, iHeight; CClientDC pDC(this); CDC memdc; memdc.CreateCompatibleDC(&pDC); VariantInit(&image); // Aufruf der Methode: m_myGetImage.getImage(&image); pUnk = image.punkVal; HRESULT hr = pUnk->QueryInterface(&pPicture); if(SUCCEEDED(hr)) { //breite u. höhe vom bild holen pPicture->get_Width(&lWidth); pPicture->get_Height(&lHeight); //in Pixel konvertieren iWidth = (lWidth * GetDeviceCaps(pDC, LOGPIXELSX)) / 2540; iHeight = (lHeight * GetDeviceCaps(pDC, LOGPIXELSY)) / 2540; RECT rc; GetClientRect( &rc); //Bild anzeigen mittels Render pPicture->Render(pDC, 0, 0, iWidth, iHeight, 0, lHeight, lWidth, -lHeight, 0); ////// VERSUCH DER Ausgabe über die CBitmap Klasse////////////////////////// //HBITMAP hBmp ; //pPicture->get_Handle((OLE_HANDLE FAR *) &hBmp); //// create a temporary bitmap //CBitmap * TempBmp = CBitmap::FromHandle(hBmp); //memdc.SelectObject(TempBmp);//select original bitmap //pDC.BitBlt(200, 300, iWidth, iHeight, &memdc, 0, 0, SRCCOPY); ///////////////////////////////////////////////////////////////////////////////// } }In den Integer-Werten "iWidth, iHeight" stehen schon die richtige Höhe bzw. Breite des BMP, aber angezeigt bekomm ich nichts.
Hast Du vielleicht noch ne Idee, oder siehst du wo der Fehler liegt.
Danke!