1036 lines
24 KiB
C++
1036 lines
24 KiB
C++
|
/*****************************************************************************
|
||
|
*
|
||
|
* (C) COPYRIGHT MICROSOFT CORPORATION, 2000
|
||
|
*
|
||
|
* TITLE: WiaProc.cpp
|
||
|
*
|
||
|
* VERSION: 1.0
|
||
|
*
|
||
|
* DATE: 2000/11/14
|
||
|
*
|
||
|
* DESCRIPTION: Manages Wia side of things
|
||
|
*
|
||
|
*****************************************************************************/
|
||
|
#include <stdafx.h>
|
||
|
#include <mmsystem.h>
|
||
|
|
||
|
#include "wiavideotest.h"
|
||
|
|
||
|
static struct
|
||
|
{
|
||
|
DWORD dwWiaDevMgrCookie;
|
||
|
DWORD dwSelectedDeviceCookie;
|
||
|
IUnknown *pCreateCallback;
|
||
|
IUnknown *pDeleteCallback;
|
||
|
IUnknown *pDisconnectedCallback;
|
||
|
IUnknown *pConnectedCallback;
|
||
|
IGlobalInterfaceTable *pGIT;
|
||
|
CRITICAL_SECTION CritSec;
|
||
|
} LOCAL_GVAR =
|
||
|
{
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
0,
|
||
|
FALSE,
|
||
|
NULL
|
||
|
};
|
||
|
|
||
|
|
||
|
/****************************Local Function Prototypes********************/
|
||
|
HRESULT ClearDeviceList();
|
||
|
HRESULT AddItemToList(IWiaPropertyStorage *pItem,
|
||
|
TCHAR *pszFriendlyName,
|
||
|
TCHAR *pszDeviceID);
|
||
|
|
||
|
WPARAM GetNumDevicesInList();
|
||
|
|
||
|
IWiaPropertyStorage* GetWiaStorage(WPARAM uiIndex);
|
||
|
|
||
|
HRESULT CreateWiaDevMgr(IWiaDevMgr **ppDevMgr);
|
||
|
|
||
|
HRESULT GetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
LONG *pnValue);
|
||
|
|
||
|
HRESULT GetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
TCHAR *pszBuffer,
|
||
|
UINT cbBuffer);
|
||
|
|
||
|
HRESULT SetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
const PROPVARIANT *ppv,
|
||
|
PROPID nNameFirst);
|
||
|
|
||
|
|
||
|
HRESULT AppUtil_ConvertToWideString(const TCHAR *pszStringToConvert,
|
||
|
WCHAR *pwszString,
|
||
|
UINT cchString);
|
||
|
|
||
|
HRESULT AppUtil_ConvertToTCHAR(const WCHAR *pwszStringToConvert,
|
||
|
TCHAR *pszString,
|
||
|
UINT cchString);
|
||
|
|
||
|
HRESULT CreateRootItem(IWiaDevMgr *pDevMgr,
|
||
|
const TCHAR *pszWiaDeviceID,
|
||
|
IWiaItem **ppRootItem);
|
||
|
|
||
|
HRESULT RegisterForEvents(IWiaDevMgr *pDevMgr);
|
||
|
|
||
|
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_Init
|
||
|
//
|
||
|
HRESULT WiaProc_Init()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
IWiaDevMgr *pWiaDevMgr = NULL;
|
||
|
|
||
|
if (LOCAL_GVAR.dwWiaDevMgrCookie != 0)
|
||
|
{
|
||
|
return S_OK;
|
||
|
}
|
||
|
|
||
|
__try
|
||
|
{
|
||
|
if (!InitializeCriticalSectionAndSpinCount(&LOCAL_GVAR.CritSec, MINLONG))
|
||
|
{
|
||
|
hr = HRESULT_FROM_WIN32(::GetLastError());
|
||
|
}
|
||
|
}
|
||
|
__except(EXCEPTION_EXECUTE_HANDLER)
|
||
|
{
|
||
|
hr = E_OUTOFMEMORY;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = CreateWiaDevMgr(&pWiaDevMgr);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = CoCreateInstance(CLSID_StdGlobalInterfaceTable,
|
||
|
NULL,
|
||
|
CLSCTX_INPROC_SERVER,
|
||
|
IID_IGlobalInterfaceTable,
|
||
|
(void **)&LOCAL_GVAR.pGIT);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
LOCAL_GVAR.pGIT->RegisterInterfaceInGlobal(pWiaDevMgr,
|
||
|
IID_IWiaDevMgr,
|
||
|
&LOCAL_GVAR.dwWiaDevMgrCookie);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = RegisterForEvents(pWiaDevMgr);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
WiaProc_PopulateDeviceList();
|
||
|
}
|
||
|
|
||
|
if (pWiaDevMgr)
|
||
|
{
|
||
|
pWiaDevMgr->Release();
|
||
|
pWiaDevMgr = NULL;
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_Term
|
||
|
//
|
||
|
HRESULT WiaProc_Term()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
ClearDeviceList();
|
||
|
|
||
|
if (LOCAL_GVAR.dwSelectedDeviceCookie != 0)
|
||
|
{
|
||
|
LOCAL_GVAR.pGIT->RevokeInterfaceFromGlobal(LOCAL_GVAR.dwSelectedDeviceCookie);
|
||
|
LOCAL_GVAR.dwSelectedDeviceCookie = 0;
|
||
|
}
|
||
|
|
||
|
if (LOCAL_GVAR.dwWiaDevMgrCookie != 0)
|
||
|
{
|
||
|
LOCAL_GVAR.pGIT->RevokeInterfaceFromGlobal(LOCAL_GVAR.dwWiaDevMgrCookie);
|
||
|
LOCAL_GVAR.dwWiaDevMgrCookie = 0;
|
||
|
|
||
|
DeleteCriticalSection(&LOCAL_GVAR.CritSec);
|
||
|
}
|
||
|
|
||
|
if (LOCAL_GVAR.pCreateCallback)
|
||
|
{
|
||
|
LOCAL_GVAR.pCreateCallback->Release();
|
||
|
LOCAL_GVAR.pCreateCallback = NULL;
|
||
|
}
|
||
|
|
||
|
if (LOCAL_GVAR.pDeleteCallback)
|
||
|
{
|
||
|
LOCAL_GVAR.pDeleteCallback->Release();
|
||
|
LOCAL_GVAR.pDeleteCallback = NULL;
|
||
|
}
|
||
|
|
||
|
if (LOCAL_GVAR.pConnectedCallback)
|
||
|
{
|
||
|
LOCAL_GVAR.pConnectedCallback->Release();
|
||
|
LOCAL_GVAR.pConnectedCallback = NULL;
|
||
|
}
|
||
|
|
||
|
if (LOCAL_GVAR.pDisconnectedCallback)
|
||
|
{
|
||
|
LOCAL_GVAR.pDisconnectedCallback->Release();
|
||
|
LOCAL_GVAR.pDisconnectedCallback = NULL;
|
||
|
}
|
||
|
|
||
|
if (LOCAL_GVAR.pGIT)
|
||
|
{
|
||
|
LOCAL_GVAR.pGIT->Release();
|
||
|
LOCAL_GVAR.pGIT = NULL;
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_CreateSelectedDevice
|
||
|
//
|
||
|
HRESULT WiaProc_CreateSelectedDevice(TCHAR *pszDeviceID,
|
||
|
UINT cchDeviceID)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
WPARAM Index = 0;
|
||
|
TCHAR szDeviceID[MAX_PATH] = {0};
|
||
|
IWiaDevMgr *pWiaDevMgr = NULL;
|
||
|
|
||
|
if ((LOCAL_GVAR.dwWiaDevMgrCookie == 0) ||
|
||
|
(LOCAL_GVAR.pGIT == NULL))
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
hr = LOCAL_GVAR.pGIT->GetInterfaceFromGlobal(LOCAL_GVAR.dwWiaDevMgrCookie,
|
||
|
IID_IWiaDevMgr,
|
||
|
(void**)&pWiaDevMgr);
|
||
|
|
||
|
if (pWiaDevMgr == NULL)
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
LRESULT lResult = 0;
|
||
|
lResult = SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_GETCURSEL,
|
||
|
0,
|
||
|
0);
|
||
|
|
||
|
Index = (WPARAM) lResult;
|
||
|
|
||
|
if (Index == LB_ERR)
|
||
|
{
|
||
|
hr = E_FAIL;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
IWiaItem *pSelectedDevice = NULL;
|
||
|
LPARAM lParam = 0;
|
||
|
|
||
|
lParam = SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_GETITEMDATA,
|
||
|
Index,
|
||
|
0);
|
||
|
|
||
|
IWiaPropertyStorage *pItem = (IWiaPropertyStorage*)lParam;
|
||
|
|
||
|
if (pItem)
|
||
|
{
|
||
|
|
||
|
hr = GetProperty(pItem, WIA_DIP_DEV_ID, szDeviceID,
|
||
|
sizeof(szDeviceID)/sizeof(TCHAR));
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = CreateRootItem(pWiaDevMgr,
|
||
|
szDeviceID,
|
||
|
&pSelectedDevice);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = LOCAL_GVAR.pGIT->RegisterInterfaceInGlobal(pSelectedDevice,
|
||
|
IID_IWiaItem,
|
||
|
&LOCAL_GVAR.dwSelectedDeviceCookie);
|
||
|
}
|
||
|
|
||
|
if (pszDeviceID)
|
||
|
{
|
||
|
_tcsncpy(pszDeviceID, szDeviceID, cchDeviceID);
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice)
|
||
|
{
|
||
|
pSelectedDevice->Release();
|
||
|
pSelectedDevice = NULL;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (pWiaDevMgr)
|
||
|
{
|
||
|
pWiaDevMgr->Release();
|
||
|
pWiaDevMgr = NULL;
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_GetImageDirectory
|
||
|
//
|
||
|
HRESULT WiaProc_GetImageDirectory(TCHAR *pszImageDirectory,
|
||
|
UINT cchImageDirectory)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
IWiaPropertyStorage *pStorage = NULL;
|
||
|
IWiaItem *pSelectedDevice = NULL;
|
||
|
|
||
|
if ((LOCAL_GVAR.dwSelectedDeviceCookie == 0) ||
|
||
|
(LOCAL_GVAR.pGIT == NULL) ||
|
||
|
(pszImageDirectory == NULL))
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = LOCAL_GVAR.pGIT->GetInterfaceFromGlobal(LOCAL_GVAR.dwSelectedDeviceCookie,
|
||
|
IID_IWiaItem,
|
||
|
(void**)&pSelectedDevice);
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice == NULL)
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = pSelectedDevice->QueryInterface(IID_IWiaPropertyStorage,
|
||
|
(void**) &pStorage);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = GetProperty(pStorage, WIA_DPV_IMAGES_DIRECTORY, pszImageDirectory,
|
||
|
cchImageDirectory);
|
||
|
}
|
||
|
|
||
|
if (pStorage)
|
||
|
{
|
||
|
pStorage->Release();
|
||
|
pStorage = NULL;
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice)
|
||
|
{
|
||
|
pSelectedDevice->Release();
|
||
|
pSelectedDevice = NULL;
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_DeviceTakePicture
|
||
|
//
|
||
|
HRESULT WiaProc_DeviceTakePicture()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
IWiaItem *pSelectedDevice = NULL;
|
||
|
|
||
|
if ((LOCAL_GVAR.dwSelectedDeviceCookie == 0) ||
|
||
|
(LOCAL_GVAR.pGIT == NULL))
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = LOCAL_GVAR.pGIT->GetInterfaceFromGlobal(LOCAL_GVAR.dwSelectedDeviceCookie,
|
||
|
IID_IWiaItem,
|
||
|
(void**)&pSelectedDevice);
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice == NULL)
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
IWiaItem *pUnused = NULL;
|
||
|
hr = pSelectedDevice->DeviceCommand(0,
|
||
|
&WIA_CMD_TAKE_PICTURE,
|
||
|
&pUnused);
|
||
|
|
||
|
if (pUnused)
|
||
|
{
|
||
|
pUnused->Release();
|
||
|
pUnused = NULL;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice)
|
||
|
{
|
||
|
pSelectedDevice->Release();
|
||
|
pSelectedDevice = NULL;
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
|
||
|
///////////////////////////////
|
||
|
// ClearDeviceList
|
||
|
//
|
||
|
HRESULT ClearDeviceList()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
WPARAM NumDevices = 0;
|
||
|
|
||
|
NumDevices = GetNumDevicesInList();
|
||
|
|
||
|
//
|
||
|
// Free all the IWiaItem pointers we saved in our
|
||
|
// list box.
|
||
|
//
|
||
|
if (NumDevices != LB_ERR)
|
||
|
{
|
||
|
for (WPARAM i = 0; i < NumDevices; i++)
|
||
|
{
|
||
|
IWiaPropertyStorage *pItem = NULL;
|
||
|
|
||
|
pItem = GetWiaStorage(i);
|
||
|
|
||
|
if (pItem)
|
||
|
{
|
||
|
pItem->Release();
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// Empty the list
|
||
|
//
|
||
|
SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_RESETCONTENT,
|
||
|
0,
|
||
|
0);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_PopulateDeviceList
|
||
|
//
|
||
|
HRESULT WiaProc_PopulateDeviceList()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
IEnumWIA_DEV_INFO *pEnum = NULL;
|
||
|
IWiaDevMgr *pWiaDevMgr = NULL;
|
||
|
|
||
|
hr = LOCAL_GVAR.pGIT->GetInterfaceFromGlobal(LOCAL_GVAR.dwWiaDevMgrCookie,
|
||
|
IID_IWiaDevMgr,
|
||
|
(void**)&pWiaDevMgr);
|
||
|
|
||
|
if (pWiaDevMgr == NULL)
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// Clear out the device list if it has any items in it.
|
||
|
//
|
||
|
ClearDeviceList();
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = pWiaDevMgr->EnumDeviceInfo(0, &pEnum);
|
||
|
}
|
||
|
|
||
|
while (hr == S_OK)
|
||
|
{
|
||
|
IWiaItem *pRootItem = NULL;
|
||
|
IWiaPropertyStorage *pPropStorage = NULL;
|
||
|
TCHAR szFriendlyName[MAX_PATH + 1] = {0};
|
||
|
TCHAR szWiaDeviceID[MAX_PATH + 1] = {0};
|
||
|
|
||
|
//
|
||
|
// Get the next device in the enumeration.
|
||
|
//
|
||
|
hr = pEnum->Next(1, &pPropStorage, NULL);
|
||
|
|
||
|
//
|
||
|
// Get the device's Wia Device ID
|
||
|
//
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = GetProperty(pPropStorage, WIA_DIP_DEV_ID, szWiaDeviceID,
|
||
|
sizeof(szWiaDeviceID)/sizeof(TCHAR));
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// Get the device's Wia Device Name
|
||
|
//
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = GetProperty(pPropStorage, WIA_DIP_DEV_NAME, szFriendlyName,
|
||
|
sizeof(szFriendlyName)/sizeof(TCHAR));
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// We do not relesae the propstorage item because we store the pointer
|
||
|
// in our list until we shutdown the app.
|
||
|
//
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
AddItemToList(pPropStorage, szFriendlyName, szWiaDeviceID);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_SETCURSEL,
|
||
|
0,
|
||
|
0);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// RegisterForEvents
|
||
|
//
|
||
|
HRESULT RegisterForEvents(IWiaDevMgr *pWiaDevMgr)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
CWiaEvent *pWiaEvent = NULL;
|
||
|
IWiaEventCallback *pIWiaEvent = NULL;
|
||
|
|
||
|
if (pWiaDevMgr == NULL)
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// Register our callback events
|
||
|
//
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
// create the WiaEvent
|
||
|
pWiaEvent = new CWiaEvent();
|
||
|
|
||
|
if (pWiaEvent == NULL)
|
||
|
{
|
||
|
hr = E_OUTOFMEMORY;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = pWiaEvent->QueryInterface(IID_IWiaEventCallback,
|
||
|
(void**)&pIWiaEvent);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = pWiaDevMgr->RegisterEventCallbackInterface(WIA_REGISTER_EVENT_CALLBACK,
|
||
|
NULL,
|
||
|
&WIA_EVENT_DEVICE_CONNECTED,
|
||
|
pIWiaEvent,
|
||
|
&LOCAL_GVAR.pConnectedCallback);
|
||
|
|
||
|
hr = pWiaDevMgr->RegisterEventCallbackInterface(WIA_REGISTER_EVENT_CALLBACK,
|
||
|
NULL,
|
||
|
&WIA_EVENT_DEVICE_DISCONNECTED,
|
||
|
pIWiaEvent,
|
||
|
&LOCAL_GVAR.pDisconnectedCallback);
|
||
|
|
||
|
hr = pWiaDevMgr->RegisterEventCallbackInterface(WIA_REGISTER_EVENT_CALLBACK,
|
||
|
NULL,
|
||
|
&WIA_EVENT_ITEM_CREATED,
|
||
|
pIWiaEvent,
|
||
|
&LOCAL_GVAR.pCreateCallback);
|
||
|
|
||
|
hr = pWiaDevMgr->RegisterEventCallbackInterface(WIA_REGISTER_EVENT_CALLBACK,
|
||
|
NULL,
|
||
|
&WIA_EVENT_ITEM_DELETED,
|
||
|
pIWiaEvent,
|
||
|
&LOCAL_GVAR.pDeleteCallback);
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// We don't need to delete pWiaEvent since we are releasing it.
|
||
|
//
|
||
|
if (pIWiaEvent)
|
||
|
{
|
||
|
pIWiaEvent->Release();
|
||
|
pIWiaEvent = NULL;
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
|
||
|
///////////////////////////////
|
||
|
// AddItemToList
|
||
|
//
|
||
|
HRESULT AddItemToList(IWiaPropertyStorage *pItem,
|
||
|
TCHAR *pszFriendlyName,
|
||
|
TCHAR *pszDeviceID)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
WPARAM Index = 0;
|
||
|
|
||
|
if ((pItem == NULL) ||
|
||
|
(pszFriendlyName == NULL) ||
|
||
|
(pszDeviceID == NULL))
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
TCHAR szNewItem[MAX_PATH * 2] = {0};
|
||
|
|
||
|
_sntprintf(szNewItem, sizeof(szNewItem)/sizeof(TCHAR),
|
||
|
TEXT("%s (%s)"), pszFriendlyName, pszDeviceID);
|
||
|
|
||
|
LRESULT lResult = 0;
|
||
|
|
||
|
lResult = SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_ADDSTRING,
|
||
|
0,
|
||
|
(LPARAM) szNewItem);
|
||
|
|
||
|
Index = (WPARAM) lResult;
|
||
|
|
||
|
//
|
||
|
// pItem already has an AddRef on it.
|
||
|
//
|
||
|
SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_SETITEMDATA,
|
||
|
Index,
|
||
|
(LPARAM) pItem);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
|
||
|
///////////////////////////////
|
||
|
// GetNumDevicesInList
|
||
|
//
|
||
|
WPARAM GetNumDevicesInList()
|
||
|
{
|
||
|
LRESULT lResult = 0;
|
||
|
WPARAM NumItems = 0;
|
||
|
|
||
|
lResult = SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_GETCOUNT,
|
||
|
0,
|
||
|
0);
|
||
|
|
||
|
NumItems = (WPARAM) lResult;
|
||
|
|
||
|
return NumItems;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// GetWiaStorage
|
||
|
//
|
||
|
IWiaPropertyStorage* GetWiaStorage(WPARAM Index)
|
||
|
{
|
||
|
LPARAM lParam = 0;
|
||
|
IWiaPropertyStorage *pItem = NULL;
|
||
|
|
||
|
lParam = SendDlgItemMessage(APP_GVAR.hwndMainDlg,
|
||
|
IDC_LIST_WIA_DEVICES,
|
||
|
LB_GETITEMDATA,
|
||
|
Index,
|
||
|
0);
|
||
|
|
||
|
pItem = (IWiaPropertyStorage*)lParam;
|
||
|
|
||
|
return pItem;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// CreateWiaDevMgr
|
||
|
//
|
||
|
HRESULT CreateWiaDevMgr(IWiaDevMgr **ppDevMgr)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if (ppDevMgr == NULL)
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
hr = CoCreateInstance(CLSID_WiaDevMgr,
|
||
|
NULL,
|
||
|
CLSCTX_LOCAL_SERVER,
|
||
|
IID_IWiaDevMgr,
|
||
|
(void**) ppDevMgr);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_GetProperty
|
||
|
//
|
||
|
// Generic
|
||
|
//
|
||
|
HRESULT WiaProc_GetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
PROPVARIANT *pPropVar)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if ((pPropStorage == NULL) ||
|
||
|
(pPropVar == NULL))
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
PropVariantInit(pPropVar);
|
||
|
|
||
|
PROPSPEC ps = {0};
|
||
|
|
||
|
ps.ulKind = PRSPEC_PROPID;
|
||
|
ps.propid = nPropID;
|
||
|
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
hr = pPropStorage->ReadMultiple(1, &ps, pPropVar);
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// GetProperty
|
||
|
//
|
||
|
// For 'long' properties
|
||
|
//
|
||
|
HRESULT GetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
LONG *pnValue)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if ((pPropStorage == NULL) ||
|
||
|
(pnValue == NULL))
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
PROPVARIANT pvPropValue;
|
||
|
|
||
|
*pnValue = 0;
|
||
|
|
||
|
PropVariantInit(&pvPropValue);
|
||
|
|
||
|
hr = WiaProc_GetProperty(pPropStorage, nPropID, &pvPropValue);
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
if ((pvPropValue.vt == VT_I4) ||
|
||
|
(pvPropValue.vt == VT_UI4))
|
||
|
{
|
||
|
*pnValue = pvPropValue.lVal;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
PropVariantClear(&pvPropValue);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// GetProperty
|
||
|
//
|
||
|
// For 'string' properties
|
||
|
//
|
||
|
HRESULT GetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
TCHAR *pszBuffer,
|
||
|
UINT cbBuffer)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if ((pPropStorage == NULL) ||
|
||
|
(pszBuffer == NULL))
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
PROPVARIANT pvPropValue;
|
||
|
|
||
|
PropVariantInit(&pvPropValue);
|
||
|
|
||
|
hr = WiaProc_GetProperty(pPropStorage, nPropID, &pvPropValue);
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
if ((pvPropValue.vt == VT_LPWSTR) ||
|
||
|
(pvPropValue.vt == VT_BSTR))
|
||
|
{
|
||
|
AppUtil_ConvertToTCHAR(pvPropValue.pwszVal, pszBuffer, cbBuffer);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// This frees the BSTR
|
||
|
//
|
||
|
PropVariantClear(&pvPropValue);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
|
||
|
|
||
|
///////////////////////////////
|
||
|
// CreateRootItem
|
||
|
//
|
||
|
HRESULT CreateRootItem(IWiaDevMgr *pDevMgr,
|
||
|
const TCHAR *pszWiaDeviceID,
|
||
|
IWiaItem **ppRootItem)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if ((pDevMgr == NULL) ||
|
||
|
(pszWiaDeviceID == NULL) ||
|
||
|
(ppRootItem == NULL))
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
BOOL bRetry = TRUE;
|
||
|
|
||
|
BSTR bstrDeviceID = NULL;
|
||
|
WCHAR wszWiaDeviceID[MAX_PATH] = {0};
|
||
|
|
||
|
AppUtil_ConvertToWideString(pszWiaDeviceID, wszWiaDeviceID,
|
||
|
sizeof(wszWiaDeviceID) / sizeof(WCHAR));
|
||
|
|
||
|
bstrDeviceID = SysAllocString(wszWiaDeviceID);
|
||
|
|
||
|
for (UINT uiRetryCount = 0;
|
||
|
(uiRetryCount < 5) && (bRetry);
|
||
|
++uiRetryCount)
|
||
|
{
|
||
|
|
||
|
hr = pDevMgr->CreateDevice(bstrDeviceID,
|
||
|
ppRootItem);
|
||
|
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
//
|
||
|
// Break out of loop
|
||
|
//
|
||
|
bRetry = FALSE;
|
||
|
}
|
||
|
else if (hr == WIA_ERROR_BUSY)
|
||
|
{
|
||
|
//
|
||
|
// Wait a little while before retrying
|
||
|
//
|
||
|
Sleep(200);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
//
|
||
|
// All other errors are considered fatal
|
||
|
//
|
||
|
bRetry = FALSE;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (bstrDeviceID)
|
||
|
{
|
||
|
SysFreeString(bstrDeviceID);
|
||
|
bstrDeviceID = NULL;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// SetProperty
|
||
|
//
|
||
|
// Generic
|
||
|
//
|
||
|
HRESULT SetProperty(IWiaPropertyStorage *pPropStorage,
|
||
|
PROPID nPropID,
|
||
|
const PROPVARIANT *ppv,
|
||
|
PROPID nNameFirst)
|
||
|
{
|
||
|
HRESULT hr = 0;
|
||
|
PROPSPEC ps = {0};
|
||
|
|
||
|
if ((pPropStorage == NULL) ||
|
||
|
(ppv == NULL))
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
ps.ulKind = PRSPEC_PROPID;
|
||
|
ps.propid = nPropID;
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = pPropStorage->WriteMultiple(1, &ps, ppv, nNameFirst);
|
||
|
}
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_SetLastSavedImage
|
||
|
//
|
||
|
// For 'string' properties
|
||
|
//
|
||
|
HRESULT WiaProc_SetLastSavedImage(BSTR bstrLastSavedImage)
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
IWiaItem *pSelectedDevice = NULL;
|
||
|
IWiaPropertyStorage *pStorage = NULL;
|
||
|
PROPVARIANT pv = {0};
|
||
|
|
||
|
if ((LOCAL_GVAR.dwSelectedDeviceCookie == 0) ||
|
||
|
(LOCAL_GVAR.pGIT == NULL))
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
EnterCriticalSection(&LOCAL_GVAR.CritSec);
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = LOCAL_GVAR.pGIT->GetInterfaceFromGlobal(LOCAL_GVAR.dwSelectedDeviceCookie,
|
||
|
IID_IWiaItem,
|
||
|
(void**)&pSelectedDevice);
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice == NULL)
|
||
|
{
|
||
|
hr = E_POINTER;
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
hr = pSelectedDevice->QueryInterface(IID_IWiaPropertyStorage,
|
||
|
(void**)&pStorage);
|
||
|
}
|
||
|
|
||
|
if (hr == S_OK)
|
||
|
{
|
||
|
PropVariantInit(&pv);
|
||
|
|
||
|
pv.vt = VT_BSTR;
|
||
|
pv.bstrVal = bstrLastSavedImage;
|
||
|
|
||
|
hr = SetProperty(pStorage, WIA_DPV_LAST_PICTURE_TAKEN, &pv, 2);
|
||
|
}
|
||
|
|
||
|
if (pStorage)
|
||
|
{
|
||
|
pStorage->Release();
|
||
|
pStorage = NULL;
|
||
|
}
|
||
|
|
||
|
if (pSelectedDevice)
|
||
|
{
|
||
|
pSelectedDevice->Release();
|
||
|
pSelectedDevice = NULL;
|
||
|
}
|
||
|
|
||
|
LeaveCriticalSection(&LOCAL_GVAR.CritSec);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_PopulateItemList
|
||
|
//
|
||
|
HRESULT WiaProc_PopulateItemList()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if (LOCAL_GVAR.dwSelectedDeviceCookie == 0)
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
hr = ImageLst_PopulateWiaItemList(LOCAL_GVAR.pGIT,
|
||
|
LOCAL_GVAR.dwSelectedDeviceCookie);
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
///////////////////////////////
|
||
|
// WiaProc_DestroySelectedDevice
|
||
|
//
|
||
|
HRESULT WiaProc_DestroySelectedDevice()
|
||
|
{
|
||
|
HRESULT hr = S_OK;
|
||
|
|
||
|
if (LOCAL_GVAR.dwSelectedDeviceCookie == 0)
|
||
|
{
|
||
|
return E_POINTER;
|
||
|
}
|
||
|
|
||
|
ImageLst_CancelLoadAndWait(5000);
|
||
|
|
||
|
if ((LOCAL_GVAR.dwSelectedDeviceCookie != 0) &&
|
||
|
(LOCAL_GVAR.pGIT != NULL))
|
||
|
{
|
||
|
LOCAL_GVAR.pGIT->RevokeInterfaceFromGlobal(LOCAL_GVAR.dwSelectedDeviceCookie);
|
||
|
LOCAL_GVAR.dwSelectedDeviceCookie = 0;
|
||
|
}
|
||
|
|
||
|
ImageLst_Clear();
|
||
|
|
||
|
return hr;
|
||
|
}
|
||
|
|
||
|
|