0

I'm working on winapi gui application, that displays liveview images from Canon DSLR with EDSDK API. During testing I successfully display test image with this code:

Rect destRect(15, 15, 620, 413);
HDC hdc = GetDC(hwndDlg);
Graphics graphics(hdc);
Bitmap* myBitmap = new Bitmap(L"test.jpg");
graphics.DrawImage(myBitmap, destRect);
ReleaseDC(hwndDlg, hdc);

But I can't imagine how to replace "test.jpg" with values from this function:

EdsError downloadEvfData(EdsCameraRef camera)
{
    EdsError err = EDS_ERR_OK;
    //    Create memory stream.
    err = EdsCreateMemoryStream(0, &stream);
    //    Create EvfImageRef.
    if(err == EDS_ERR_OK)
    {
        err = EdsCreateEvfImageRef(stream, &evfImage);
    }
    // Download live view image data.
    if(err == EDS_ERR_OK)
    {
        err = EdsDownloadEvfImage(camera, evfImage);
    }

    err = EdsGetPointer(stream, (EdsVoid**) &data);
    if (err != EDS_ERR_OK)
    {
        cout << "Download Live View Image Error in Function EdsGetPointer: " << err << "\n";
        return false;
    }
    err = EdsGetLength(stream, &length);
    if (err != EDS_ERR_OK)
    {
        cout << "Download Live View Image Error in Function EdsGetLength: " << err << "\n";
        return false;
    }

Any help will be highly appreciated!

  • What's `stream`? – IInspectable Mar 18 '21 at 16:57
  • That's memory stream. This part of code is from Canon EDSDK sample. More info here: https://stackoverflow.com/a/5396349/7661382 – Anton Vakulenko Mar 18 '21 at 17:14
  • Apparently you can get the address of the memory it represents, as well as its length. That's all you need to create an `IStream` ([SHCreateMemStream](https://learn.microsoft.com/en-us/windows/win32/api/shlwapi/nf-shlwapi-shcreatememstream)) and call [Bitmap::FromStream](https://learn.microsoft.com/en-us/windows/win32/api/gdiplusheaders/nf-gdiplusheaders-bitmap-fromstream). – IInspectable Mar 18 '21 at 17:26
  • Unfortunately, code ```Bitmap* myBitmap = new Bitmap(stream, FALSE);``` get this error: "invalid conversion from 'EdsStreamRef' {aka '__EdsObject*'} to 'INT' {aka 'int'} [-fpermissive]|" – Anton Vakulenko Mar 18 '21 at 17:32
  • Right. That's not what I suggested either. If you need an `IStream` you cannot just pass any type that happens to contain the word `Stream`. It needs to be an `IStream`. – IInspectable Mar 18 '21 at 17:45

1 Answers1

0

Many thanks to IInspectable. Here the code that displays liveview images on the app's window (plain winapi):

EdsError downloadEvfData(EdsCameraRef camera)
{
    EdsError err = EDS_ERR_OK;
    //    Create memory stream.
    err = EdsCreateMemoryStream(0, &stream);
    //    Create EvfImageRef.
    if(err == EDS_ERR_OK)
    {
        err = EdsCreateEvfImageRef(stream, &evfImage);
    }
    // Download live view image data.
    if(err == EDS_ERR_OK)
    {
        err = EdsDownloadEvfImage(camera, evfImage);
    }
    // get pointer to stream ("image")
    if (err == EDS_ERR_OK)
    {
        err = EdsGetPointer(stream, (EdsVoid**) &data);
    }
    // get length of stream ("image size")
    if (err == EDS_ERR_OK)
    {
        err = EdsGetLength(stream, &length);
    }

    // Display image
    Rect destRect(15, 15, 620, 413);
    HDC hdc = GetDC(GetActiveWindow());
    Graphics graphics(hdc);
    Bitmap* myBitmap = new Bitmap(SHCreateMemStream(data,length), FALSE);
    graphics.DrawImage(myBitmap, destRect);
    ReleaseDC(GetActiveWindow(), hdc);

    // Release stream
    if(stream != NULL)
    {
        EdsRelease(stream);
        stream = NULL;
    }
    // Release evfImage
    if(evfImage != NULL)
    {
        EdsRelease(evfImage);
        evfImage = NULL;
    }
    // delete "image"
    data = NULL;
}