Нет обратного вызова из обработчика событий Canon SDK 2.12

Я написал простую консольную программу для съемки на Canon EOS 600D. Пока работает нормально, но хотелось бы

  • получить событие, когда снимок сделан
  • если бы это было новое изображение, вызывающее событие, я хотел бы получить его как объект файла для доступа
    это свойства, такие как имя файла

Мой обработчик событий инициализируется, но я не получаю событие / обратный вызов, когда делается снимок.

Я читал в других ветках, что это может быть проблемой, если я работаю на 64-битной Windows, но почти все системы сегодня 64-битные. Это действительно проблема?

Вот код, который у меня есть:

#include "stdafx.h"#include <EDSDK.h>
#include <EDSDKErrors.h>
#include <EDSDKTypes.h>
#include <string>
#include <iostream>

using namespace std;

EdsError getFirstCamera(EdsCameraRef *camera);
EdsError EDSCALLBACK handleObjectEvent(EdsObjectEvent event, EdsBaseRef object,     EdsVoid * context);

string nmea = "$GPRMC,122030.232,A,4317.2345,N,14025.3423,W,12.2,245.1,230711,002.5,E*6F";

int _tmain(int argc, _TCHAR* argv[])
{
EdsError err=EDS_ERR_OK;
EdsCameraRef camera=NULL;
bool isSDKloaded=false;

// Initialize SDK
err=EdsInitializeSDK();
if(err==EDS_ERR_OK)
{
isSDKloaded=true;
}

// Get first camera
if(err==EDS_ERR_OK)
{
err=getFirstCamera(&camera);
}

// Open session with camera
if(err==EDS_ERR_OK)
{
err=EdsOpenSession(camera);

if(err==EDS_ERR_OK)
{
cout << "session started successfully" << endl;
}
else
{
cout << "session failed" << endl;
}
}

EdsInt32 saveTarget = kEdsSaveTo_Camera;

// Set camera properties
if(err==EDS_ERR_OK)
{
err = EdsSetPropertyData( camera, kEdsPropID_SaveTo, 0, 4, &saveTarget );

if(err==EDS_ERR_OK)
{
cout << "camera properties set!" << endl;
}
else
{
cout << "not able to set camera properties" << endl;
}
}

// Set object event handler
if(err==EDS_ERR_OK)
{
err = EdsSetObjectEventHandler(camera, kEdsObjectEvent_All,
handleObjectEvent,
NULL);
if(err==EDS_ERR_OK)
{
cout << "Event handler initialized!" << endl;
}
else
{
cout << "Not able to initialize event handler" << endl;
}
}

// Take picture
if(err==EDS_ERR_OK)
{

err = EdsSendCommand(camera, kEdsCameraCommand_TakePicture, 0);
if(err==EDS_ERR_OK)
{
cout << "Picture successfully taken!" << endl;
}
else
{
cout << "not able to set camera properties" << endl;
}
}

// End session and release SDK
EdsCloseSession(camera);
EdsTerminateSDK();

if(nmea != "")
{
cout << nmea <<endl;
}
else
{
cout << "das kann eigentlich nicht sein!" << endl;
}

system("Pause");

return 0;
}EdsError getFirstCamera(EdsCameraRef *camera)
{
EdsError err=EDS_ERR_OK;
EdsCameraListRef cameraList=NULL;
EdsUInt32 count=0;

// Get camera list
err = EdsGetCameraList(&cameraList);

// Get number of cameras
if(err == EDS_ERR_OK)
{
err = EdsGetChildCount(cameraList, &count);
if(count == 0)
{
err = EDS_ERR_DEVICE_NOT_FOUND;
}
}

// Get first camera retrieved
if(err == EDS_ERR_OK)
{
err = EdsGetChildAtIndex(cameraList , 0 , camera);
}

// Release camera list
if(cameraList != NULL)
{
EdsRelease(cameraList);
cameraList = NULL;
}

return err;
}

EdsError EDSCALLBACK handleObjectEvent(EdsObjectEvent event, EdsBaseRef object, EdsVoid * context)
{
EdsDirectoryItemInfo objectInfo;
EdsError err=EDS_ERR_OK;
cout << "Event ausgelöst!" << endl;

switch(event)
{
case kEdsObjectEvent_DirItemCreated:
err = EdsGetDirectoryItemInfo(object, &objectInfo);

if(objectInfo.isFolder == 1)
{
cout << "Der Ordner " << objectInfo.szFileName << " wurde erzeugt" << endl;
}

if(objectInfo.isFolder == 0)
{
cout << "Die Datei " << objectInfo.szFileName << " wurde erzeugt" << endl;
}

break;
default:
cout << "Prüfe den EventHandler!" << endl;
break;
}

//Release object
if(object)
{
EdsRelease(object);
}

return err;
}

Спасибо за помощь!

С наилучшими пожеланиями,
Ричард

2

Решение

Как указано в ответе Сета, для работы Canon SDK необходим цикл сообщений Windows. Обратные вызовы не будут вызываться, если вы не обрабатываете сообщения Windows.

Основываясь на вашем коде, вы, вероятно, захотите сделать что-то вроде этого псевдокода:

bool bPhotoTaken = false;
main()
{
// Initialize EDSDK, start session with camera, change SaveTo property
// register ObjectEventHandler
// send kEdsCameraCommand_TakePicture

while((bRet = GetMessage(&msg, NULL, 0, 0)) != 0)
{
if(bRet == -1 || bPhotoTaken)
{
break;
}
else
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}

// Cleanup EDSDK
}

и ваш обратный вызов ObjectEventHandler после получения DirItemRequestTransfer загрузит изображение, а затем установит bPhotoTaken=true;, который прервет цикл обработки сообщений и выйдет из вашего приложения.

2

Другие решения

Во-первых, EDSDK на самом деле не работает в 64-битном режиме, поэтому используйте 32-битный. 64-битный экспериментальный в лучшем случае.

Во-вторых, EDSDK использует унаследованную модель потоков COM STA, которая требует, чтобы в главном потоке работал цикл сообщений Windows. Если у вас нет цикла обработки сообщений, вы не получите никаких обратных вызовов.

0

По вопросам рекламы [email protected]