user1059993
user1059993

Reputation: 3

How to pass array of bitmaps from managed C++ to unmanaged C++

I currently have an array of System::Drawing::Bitmaps in a dll in managed C++ code. I would like to be able to call into the method in the managed C++ from unmanaged(native) C++. The question is how to do I pass the array back to unmanaged C++?

I can call GetHbitmap() on the managed C++ bitmap which returns an IntPtr. Should I pass an array of IntPtrs? Not quite sure the best way to do this. So to be clear I have this:

Managed C++ Method:

void GetBitmaps(<????>* bitmaps)
{
    //Calling into C# to get the bitmaps

    array<System::Drawing::Bitmap^>^ bmp=ct->DataGetBitmaps(gcnew String(SessionID));
    for(int i=0;i<bmp.Length;i++)
    {
        System::Drawing::Bitmap^ bm=(System::Drawing::Bitmap^)bmp.GetValue(i);
        IntPtr hBmp=bm->GetHbitmap();
    }

    //So now how to I convert the hBmp to an array value that I can then pass back to unmanaged C++(hence the <????> question for the type)
}

Is an array of HBITMAPS? And if so how can you convert the IntPtr hBmp to that array?

The managed C++ code works all well and good and correctly gets the array of bitmaps. but now I need to get those bitmaps back to the unmanaged C++ when the unmanaged C++ calls into the GetBitmaps method. I don't know what type of variable I should be passing in and then once I pass it in, what do I do to convert it to a type that unmanaged C++ can use?

Upvotes: 0

Views: 1023

Answers (1)

Hans Passant
Hans Passant

Reputation: 942207

You'll surely need to create an unmanaged array to call your native code. You will also have to take care of proper cleanup afterwards. So basic code ought to look like this:

#include "stdafx.h"
#include <windows.h>
#pragma comment(lib, "gdi32.lib")
#pragma managed(push, off)
#include <yourunmanagedcode.h>
#pragma managed(pop)

using namespace System;
using namespace System::Drawing;
using namespace YourManagedCode;

    void SetBitmaps(const wchar_t* SessionID, CSharpSomething^ ct)
    {
        array<Bitmap^>^ bitmaps = ct->DataGetBitmaps(gcnew String(SessionID));
        HBITMAP* array = new HBITMAP[bitmaps->Length];
        try {
            for (int i = 0; i < bitmaps->Length; i++) {
                array[i] = (HBITMAP)bitmaps[i]->GetHbitmap().ToPointer();
            }
            // Call native method
            NativeDoSomething(array, bitmaps->Length);
        }
        finally {
            // Clean up the array after the call
            for (int i = 0; i < bitmaps->Length; i++) DeleteObject(array[i]);
            delete[] array;
        }
    }

There was not nearly enough information in your question to make this accurate, I had to use place-holder names for things like the C# class name and namespace and the native code .h file and function name and signature. You'll of course have to substitute them.

Upvotes: 1

Related Questions