summaryrefslogtreecommitdiff
path: root/ARMFCaptureD3D/winmain.cpp
diff options
context:
space:
mode:
authorfcolin2011-11-18 12:14:12 +0000
committerfcolin2011-11-18 12:14:12 +0000
commit6bcf419d2e8f739b432d4790d1ba9d48ab65365b (patch)
tree92815e16f189c8e328dff4fcfa38ebe1d0217fdd /ARMFCaptureD3D/winmain.cpp
parent487e963b081d7ffe2ddf489e11d927982c9101a6 (diff)
downloadamilis-master.zip
amilis-master.tar.gz
amilis-master.tar.bz2
amilis-master.tar.xz
Diffstat (limited to 'ARMFCaptureD3D/winmain.cpp')
-rw-r--r--ARMFCaptureD3D/winmain.cpp1416
1 files changed, 1416 insertions, 0 deletions
diff --git a/ARMFCaptureD3D/winmain.cpp b/ARMFCaptureD3D/winmain.cpp
new file mode 100644
index 0000000..02ad991
--- /dev/null
+++ b/ARMFCaptureD3D/winmain.cpp
@@ -0,0 +1,1416 @@
+//////////////////////////////////////////////////////////////////////////
+//
+// winmain.cpp : Application entry-point
+//
+// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
+// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
+// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
+// PARTICULAR PURPOSE.
+//
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+//////////////////////////////////////////////////////////////////////////
+
+#include "ARMFCaptureD3D.h"
+#include "resource.h"
+#include "ConfigFile\ConfigFile.h"
+#include "debug.h"
+#include "options.h"
+#include "ARAnalyse.h"
+
+// Include the v6 common controls in the manifest
+#pragma comment(linker, \
+ "\"/manifestdependency:type='Win32' "\
+ "name='Microsoft.Windows.Common-Controls' "\
+ "version='6.0.0.0' "\
+ "processorArchitecture='*' "\
+ "publicKeyToken='6595b64144ccf1df' "\
+ "language='*'\"")
+
+
+//
+// ChooseDeviceParam structure
+//
+// Holds an array of IMFActivate pointers that represent video
+// capture devices.
+//
+
+struct ChooseDeviceParam
+{
+ IMFActivate **ppDevices; // Array of IMFActivate pointers.
+ UINT32 count; // Number of elements in the array.
+ UINT32 selection; // Selected device, by array index.
+};
+
+
+//
+// ChooseDeviceParam structure
+//
+// Holds an array of IMFActivate pointers that represent video
+// capture devices.
+//
+
+struct ChooseVideoParam
+{
+ IMFMediaType **ppTypes; // Array of IMFMediaType pointers.
+ UINT32 count; // Number of elements in the array.
+ UINT32 selection; // Selected device, by array index.
+};
+
+BOOL InitializeApplication();
+BOOL InitializeWindow(HWND *pHwnd);
+void CleanUp();
+INT MessageLoop(HWND hwnd);
+
+LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
+INT_PTR CALLBACK DeviceDlgProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
+INT_PTR CALLBACK VideoDlgProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
+void ShowErrorMessage(PCWSTR format, HRESULT hr);
+
+// Window message handlers
+BOOL OnCreate(HWND hwnd, LPCREATESTRUCT lpCreateStruct);
+void OnClose(HWND hwnd);
+void OnCommand(HWND hwnd, int id, HWND hwndCtl, UINT codeNotify);
+void OnSize(HWND hwnd, UINT state, int cx, int cy);
+void OnDeviceChange(HWND hwnd, DEV_BROADCAST_HDR *pHdr);
+void OnPaint(HWND hwnd);
+void OnInitMenu(HWND hwnd, HMENU menu);
+
+// Command handlers
+void OnChooseDevice(HWND hwnd, BOOL bPrompt, const WCHAR *name, int instance);
+void OnChooseFormat(HWND hwnd, BOOL bPrompt, int index);
+int DeviceGetByName(ChooseDeviceParam *pParam , const WCHAR* name, int instance);
+
+
+// Constants
+const WCHAR CLASS_NAME[] = L"MFCapture Window Class";
+const WCHAR WINDOW_NAME[] = L"MFCapture Sample Application";
+
+
+
+// Global variables
+HWND g_hVideo = NULL;
+HWND g_hStatus = NULL;
+HWND g_hTrack = NULL;
+int g_Threshold = 125;
+
+HWND g_hTrackSeuilMin = NULL;
+int g_ThresholdMin = 127;
+
+HWND g_hTrackSeuilMax = NULL;
+int g_ThresholdMax = 127;
+
+CPreview *g_pPreview = NULL;
+HDEVNOTIFY g_hdevnotify = NULL;
+ARAnalyse *g_pAnalyse = NULL;
+ConfigFile *g_config = NULL;
+
+std::wstring g_camera_name;
+int g_camera_instance = 0;
+std::string g_ivy_domain;
+int g_format_video = 0;
+bool g_toggle_video = false;
+bool g_read_calibrationfile = false;
+
+// command line options
+
+std::wstring widen( const string& str )
+{
+ std::wostringstream wstm ;
+ const std::ctype<wchar_t>& ctfacet = std::use_facet< std::ctype<wchar_t> >( wstm.getloc() ) ;
+ for( size_t i=0 ; i<str.size() ; ++i )
+ wstm << ctfacet.widen( str[i] ) ;
+ return wstm.str() ;
+}
+char* narrow( const std::wstring& str )
+{
+ std::ostringstream stm ;
+ const std::ctype<char>& ctfacet = std::use_facet< std::ctype<char> >( stm.getloc() ) ;
+ for( size_t i=0 ; i<str.size() ; ++i )
+ stm << ctfacet.narrow( str[i], 0 ) ;
+ std::string stro = stm.str();
+ char* c = new char [stro.size()+1];
+ strcpy(c, stro.c_str());
+ return c;
+}
+static void parse_args(char *argv)
+{
+ int errors = 0; // Flag: error in options?
+ const char * pa_optarg;
+ int optchar;
+
+ static const char * optv[] = {
+ "h|help",
+ "c:cam <CameName> default: Logitech",
+ "i:instcam <CameNum> default: 0",
+ "b:bus <Ivy domain>",
+ "v|video non affichage video",
+ "f:format <num format video>",
+ "p:projection Read ProjectionFile ",
+ NULL
+ } ;
+
+ Options opts("ARIvy", optv);
+ opts.ctrls( Options::LONG_ONLY );
+ OptStrTokIter iter(argv);
+
+ while( (optchar = opts(iter, pa_optarg)) != 0 ) {
+ switch (optchar) {
+
+ case 'c':
+ g_camera_name = widen( pa_optarg );
+ break;
+ case 'i':
+ g_camera_instance = atoi( pa_optarg );
+ break;
+
+ case 'b':
+ g_ivy_domain = pa_optarg;
+ break;
+ case 'v':
+ g_toggle_video = true;
+ break;
+ case 'f':
+ g_format_video = atoi( pa_optarg );
+ break;
+ case 'p':
+ g_read_calibrationfile = true;
+ break;
+ case 'h': // Help
+ default:
+ ++errors;
+ break;
+ }
+ }
+
+ if (errors) {
+ opts.usage(std::cout,"");
+ getchar();
+ exit(0);
+ }
+
+}
+
+//-------------------------------------------------------------------
+// WinMain
+//
+// Application entry-point.
+//-------------------------------------------------------------------
+
+INT WINAPI wWinMain(HINSTANCE/* hInstance*/, HINSTANCE /*hPrevInstance*/,LPWSTR lpCmdLine, INT /*nCmdShow*/ )
+{
+
+ HWND hwnd = 0;
+ char *cmdLine = narrow(lpCmdLine) ;
+
+ parse_args(cmdLine);
+ free( cmdLine );
+ try
+ {
+ g_config = new ConfigFile("data\\config.inp");
+ HeapSetInformation(NULL, HeapEnableTerminationOnCorruption, NULL, 0);
+
+ // camera param
+ if ( g_camera_name.length() == 0 )
+ g_camera_name = widen(g_config->read<string>("CameraName", "Logitech"));
+
+ // Ivy
+ if ( g_ivy_domain.length() == 0 )
+ g_ivy_domain = g_config->read<string>("IvyBus","");
+
+ if (InitializeApplication() && InitializeWindow(&hwnd))
+ {
+ MessageLoop(hwnd);
+ }
+
+ CleanUp();
+
+ return 0;
+ }
+ catch(ConfigFile::file_not_found ex)
+ {
+ WCHAR msg[MAX_PATH];
+ HRESULT hr = S_OK;
+ hr = StringCbPrintfW(msg, sizeof(msg), L"Fichier de configuration not trouve: %S", ex.filename.c_str());
+
+ if (SUCCEEDED(hr))
+ {
+ MessageBox(NULL, msg, L"Error", MB_ICONERROR);
+ }
+ return -1;
+ }
+ catch( ConfigFile::key_not_found ex)
+ {
+ WCHAR msg[MAX_PATH];
+ HRESULT hr = S_OK;
+ hr = StringCbPrintfW(msg, sizeof(msg), L"cle manquante dans le fichier de configuration: %S", ex.key.c_str());
+
+ if (SUCCEEDED(hr))
+ {
+ MessageBox(NULL, msg, L"Error", MB_ICONERROR);
+ }return -1;
+ }
+
+}
+
+
+//-------------------------------------------------------------------
+// WindowProc
+//
+// Window procedure.
+//-------------------------------------------------------------------
+
+LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
+{
+ switch (uMsg)
+ {
+ HANDLE_MSG(hwnd, WM_CREATE, OnCreate);
+ HANDLE_MSG(hwnd, WM_CLOSE, OnClose);
+ HANDLE_MSG(hwnd, WM_COMMAND, OnCommand);
+ HANDLE_MSG(hwnd, WM_SIZE, OnSize);
+ HANDLE_MSG(hwnd, WM_INITMENU, OnInitMenu);
+
+ case WM_APP_PREVIEW_ERROR:
+ ShowErrorMessage(L"Error", (HRESULT)wParam);
+ break;
+
+ case WM_DEVICECHANGE:
+ OnDeviceChange(hwnd, (PDEV_BROADCAST_HDR)lParam);
+ break;
+ case WM_ERASEBKGND:
+ // Suppress window erasing, to reduce flickering while the video is playing.
+ return 1;
+ //case WM_PAINT:
+ // OnPaint(hwnd);
+ // break;
+ case WM_HSCROLL:
+ {
+ g_Threshold = SendMessage(g_hTrack, TBM_GETPOS, 0, 0);
+ g_ThresholdMin = SendMessage(g_hTrackSeuilMin, TBM_GETPOS, 0, 0);
+ g_ThresholdMax = SendMessage(g_hTrackSeuilMax, TBM_GETPOS, 0, 0);
+
+ if ( g_pAnalyse )
+ g_pAnalyse->setThreshold( g_Threshold );
+ }
+ break;
+
+ }
+ return DefWindowProc(hwnd, uMsg, wParam, lParam);
+}
+
+
+//-------------------------------------------------------------------
+// InitializeApplication
+//
+// Initializes the application.
+//-------------------------------------------------------------------
+
+BOOL InitializeApplication()
+{
+ HRESULT hr = S_OK;
+
+ InitCommonControls();
+
+ hr = CoInitializeEx(NULL, COINIT_APARTMENTTHREADED | COINIT_DISABLE_OLE1DDE);
+
+ if (SUCCEEDED(hr))
+ {
+ hr = MFStartup(MF_VERSION);
+ }
+
+ return (SUCCEEDED(hr));
+}
+
+//-------------------------------------------------------------------
+// CleanUp
+//
+// Releases resources.
+//-------------------------------------------------------------------
+
+void CleanUp()
+{
+ if (g_hdevnotify)
+ {
+ UnregisterDeviceNotification(g_hdevnotify);
+ }
+
+ if (g_pPreview)
+ {
+ g_pPreview->CloseDevice();
+ }
+
+ SafeRelease(&g_pPreview);
+
+ MFShutdown();
+ CoUninitialize();
+}
+
+
+//-------------------------------------------------------------------
+// InitializeWindow
+//
+// Creates the application window.
+//-------------------------------------------------------------------
+
+BOOL InitializeWindow(HWND *pHwnd)
+{
+ WNDCLASS wc = {0};
+
+ wc.lpfnWndProc = WindowProc;
+ wc.hInstance = GetModuleHandle(NULL);
+ wc.hCursor = LoadCursor(NULL, IDC_ARROW);
+ wc.lpszClassName = CLASS_NAME;
+ wc.lpszMenuName = MAKEINTRESOURCE(IDR_MENU1);
+
+ if (!RegisterClass(&wc))
+ {
+ return FALSE;
+ }
+
+ HWND hwnd = CreateWindow(
+ CLASS_NAME,
+ WINDOW_NAME,
+ WS_OVERLAPPEDWINDOW,
+ CW_USEDEFAULT,
+ CW_USEDEFAULT,
+ CW_USEDEFAULT,
+ CW_USEDEFAULT,
+ NULL,
+ NULL,
+ GetModuleHandle(NULL),
+ NULL
+ );
+
+ if (!hwnd)
+ {
+ return FALSE;
+ }
+
+
+ ShowWindow(hwnd, SW_SHOWDEFAULT);
+ UpdateWindow(hwnd);
+
+ *pHwnd = hwnd;
+
+ return TRUE;
+}
+
+
+//-------------------------------------------------------------------
+// MessageLoop
+//
+// Implements the window message loop.
+//-------------------------------------------------------------------
+
+INT MessageLoop(HWND hwnd)
+{
+ MSG msg = {0};
+
+ while (GetMessage(&msg, NULL, 0, 0))
+ {
+ TranslateMessage(&msg);
+ DispatchMessage(&msg);
+ }
+
+ DestroyWindow(hwnd);
+
+ return INT(msg.wParam);
+}
+HWND CreateSlider( HWND parent, int pos, int min, int max, int val)
+{
+HWND hwndTrack = CreateWindowEx(
+ 0, // no extended styles
+ TRACKBAR_CLASS, // class name
+ TEXT("Trackbar Control"), // title (caption)
+ WS_CHILD | WS_VISIBLE |
+ TBS_NOTICKS , // style
+ pos, 0, // position
+ 200, 20, // size
+ parent, // parent window
+ NULL, // control identifier
+ NULL, // instance
+ NULL // no WM_CREATE parameter
+ );
+
+ SendMessage(hwndTrack, TBM_SETRANGE,
+ (WPARAM) TRUE, // redraw flag
+ (LPARAM) MAKELONG(min, max)); // min. & max. positions
+
+ SendMessage(hwndTrack, TBM_SETPAGESIZE,
+ 0, (LPARAM) 1); // new page size
+
+ //SendMessage(hwndTrack, TBM_SETSEL,
+ // (WPARAM) FALSE, // redraw flag
+ // (LPARAM) MAKELONG(0, 255));
+
+ SendMessage(hwndTrack, TBM_SETPOS,
+ (WPARAM) TRUE, // redraw flag
+ (LPARAM) val);
+ return hwndTrack;
+}
+//-------------------------------------------------------------------
+// OnCreate
+//
+// Handles the WM_CREATE message.
+//-------------------------------------------------------------------
+
+BOOL OnCreate(HWND hwnd, LPCREATESTRUCT)
+{
+ HRESULT hr = S_OK;
+
+ // Register this window to get device notification messages.
+
+ DEV_BROADCAST_DEVICEINTERFACE di = { 0 };
+ di.dbcc_size = sizeof(di);
+ di.dbcc_devicetype = DBT_DEVTYP_DEVICEINTERFACE;
+ di.dbcc_classguid = KSCATEGORY_CAPTURE;
+
+ g_hdevnotify = RegisterDeviceNotification(
+ hwnd,
+ &di,
+ DEVICE_NOTIFY_WINDOW_HANDLE
+ );
+
+ if (g_hdevnotify == NULL)
+ {
+ ShowErrorMessage(L"RegisterDeviceNotification failed.", HRESULT_FROM_WIN32(GetLastError()));
+ return FALSE;
+ }
+
+ // Create status bar
+ HWND hStatus = CreateStatusWindow( WS_CHILD | WS_VISIBLE, L"Status text" , hwnd, 100 );
+
+ // Create slider bar
+ HWND hwndTrack = CreateSlider( hwnd, 0, 0, 255, g_Threshold);
+ HWND hwndTrack1 = CreateSlider( hwnd, 210, 0, 255, g_ThresholdMin);
+ HWND hwndTrack2 = CreateSlider( hwnd, 420, 0, 255, g_ThresholdMax);
+
+
+ HWND hVideo = CreateWindow(
+ TEXT("STATIC"),
+ NULL,
+ WS_CHILD | WS_VISIBLE,
+ CW_USEDEFAULT,
+ CW_USEDEFAULT,
+ CW_USEDEFAULT,
+ CW_USEDEFAULT,
+ hwnd,
+ NULL,
+ GetModuleHandle(NULL),
+ NULL
+ );
+
+ if (!hVideo)
+ {
+ ShowErrorMessage(L"Create Child Window failed.", GetLastError());
+ return FALSE;
+ }
+ RECT rcTrackBar;
+ int iTrackHeight;
+
+ RECT rcStatus;
+ int iStatusHeight;
+
+ int iEditHeight;
+ RECT rcClient;
+
+ // Size status bar and get height
+
+ SendMessage(hStatus, WM_SIZE, 0, 0);
+
+ GetWindowRect(hwndTrack, &rcTrackBar);
+ GetWindowRect(hStatus, &rcStatus);
+ iStatusHeight = rcStatus.bottom - rcStatus.top;
+ iTrackHeight = rcTrackBar.bottom - rcTrackBar.top;
+ // Calculate remaining height and size edit
+
+ GetClientRect(hwnd, &rcClient);
+
+ iEditHeight = rcClient.bottom - iStatusHeight - iTrackHeight;
+
+ SetWindowPos(hVideo, NULL, 0, iTrackHeight, rcClient.right, iEditHeight, SWP_NOZORDER);
+
+ g_hVideo = hVideo;
+ g_hStatus = hStatus;
+ g_hTrack = hwndTrack;
+ g_hTrackSeuilMin = hwndTrack1;
+ g_hTrackSeuilMax = hwndTrack2;
+
+ // Create ArToolKit Analyser
+ g_pAnalyse = new ARAnalyse();
+
+ // Create the object that manages video preview.
+ if ( g_hVideo )
+ {
+ hr = CPreview::CreateInstance(g_hVideo, g_hVideo, &g_pPreview);
+
+ if (FAILED(hr))
+ {
+ ShowErrorMessage(L"CPreview::CreateInstance failed.", hr);
+ return FALSE;
+ }
+ // Select the first available device (if any).
+ OnChooseDevice(hwnd, FALSE, g_camera_name.length() ? g_camera_name.c_str() : NULL, g_camera_instance );
+
+ }
+
+
+
+ if ( g_toggle_video )
+ g_pPreview->ToggleVideo();
+ // start Ivy
+ g_pAnalyse->IvyInit(g_ivy_domain.c_str());
+ return TRUE;
+}
+
+
+
+//-------------------------------------------------------------------
+// OnClose
+//
+// Handles WM_CLOSE messages.
+//-------------------------------------------------------------------
+
+void OnClose(HWND /*hwnd*/)
+{
+ PostQuitMessage(0);
+}
+
+
+
+//-------------------------------------------------------------------
+// OnSize
+//
+// Handles WM_SIZE messages.
+//-------------------------------------------------------------------
+
+void OnSize(HWND hwnd, UINT state, int cx, int cy)
+{
+ // Size status bar and get height
+ RECT rcStatus;
+ int iStatusHeight;
+ int iVideoHeight;
+ int iTrackHeight;
+
+
+ // iconified
+ if ( state == SIZE_MINIMIZED ) return;
+
+ GetWindowRect(g_hStatus, &rcStatus);
+ iStatusHeight = rcStatus.bottom - rcStatus.top;
+ GetWindowRect(g_hTrack, &rcStatus);
+ iTrackHeight = rcStatus.bottom - rcStatus.top;
+
+ // Calculate remaining height and size edit
+
+ iVideoHeight = cy - iStatusHeight -iTrackHeight;
+
+ SetWindowPos(g_hVideo, NULL, 0, iTrackHeight, cx, iVideoHeight, SWP_NOZORDER);
+ if (g_pPreview)
+ {
+ g_pPreview->ResizeVideo((WORD)cx, (WORD)iVideoHeight);
+
+ InvalidateRect(hwnd, NULL, FALSE);
+ }
+ // Auto-resize statusbar (Send WM_SIZE message does just that)
+ SendMessage(g_hStatus, WM_SIZE, 0, 0);
+}
+
+
+
+//-------------------------------------------------------------------
+// OnPaint
+//
+// Handles WM_PAINT messages.
+//-------------------------------------------------------------------
+
+//void OnPaint(HWND hwnd)
+//{
+//
+// PAINTSTRUCT ps;
+// HDC hdc = BeginPaint(hwnd, &ps);
+//
+// // The video is not playing, so we must paint the application window.
+// RECT rc;
+// GetClientRect(hwnd, &rc);
+// FillRect(hdc, &rc, (HBRUSH) COLOR_WINDOW);
+// DrawText( hdc, L"ESSAI",5, &rc, 0);
+// EndPaint(hwnd, &ps);
+//
+//
+//}
+//-------------------------------------------------------------------
+// OnInitMenuChange
+//
+// Handles WM_INITMENU messages.
+//-------------------------------------------------------------------
+
+void OnInitMenu(HWND hwnd, HMENU menu)
+{
+
+ EnableMenuItem( menu, ID_ACTION_CALIBRATE, g_pAnalyse->IsCalibrationEnabled() ? MF_ENABLED : MF_DISABLED );
+ EnableMenuItem( menu, ID_ACTION_SAVEPROJECTIONDATA, g_pAnalyse->IsCalibrated() ? MF_ENABLED : MF_DISABLED );
+ CheckMenuItem( menu, ID_ACTION_CALIBRATE, g_pAnalyse->IsCalibrated() ? MF_CHECKED : MF_UNCHECKED );
+ // Blur pass
+ CheckMenuItem( menu, ID_BLURPASSE_0PASS, g_pAnalyse->BlurPass == 0 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_1PASS, g_pAnalyse->BlurPass == 1 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_2PASS, g_pAnalyse->BlurPass == 2 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_3PASS, g_pAnalyse->BlurPass == 3 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_4PASS, g_pAnalyse->BlurPass == 4 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_4PASS, g_pAnalyse->BlurPass == 5 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_4PASS, g_pAnalyse->BlurPass == 6 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_BLURPASSE_4PASS, g_pAnalyse->BlurPass == 10 ? MF_CHECKED : MF_UNCHECKED );
+ // DownSample
+ CheckMenuItem( menu, ID_DOWNSAMPLE_FACTEUR1, g_pAnalyse->DownSample == 1 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_DOWNSAMPLE_FACTEUR2, g_pAnalyse->DownSample == 2 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_DOWNSAMPLE_FACTEUR4, g_pAnalyse->DownSample == 4 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_DOWNSAMPLE_FACTEUR8, g_pAnalyse->DownSample == 8 ? MF_CHECKED : MF_UNCHECKED );
+ // Affichage
+ CheckMenuItem( menu, ID_AFFICHAGE_GRAYSCALE, g_pAnalyse->Display == ARAnalyse::GrayScale ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_AFFICHAGE_BLUR, g_pAnalyse->Display == ARAnalyse::Blur ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_AFFICHAGE_DIFF, g_pAnalyse->Display == ARAnalyse::Diff ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_AFFICHAGE_THRESHOLD, g_pAnalyse->Display == ARAnalyse::Threshold ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_AFFICHAGE_MOYEN, g_pAnalyse->Display == ARAnalyse::Moyen ? MF_CHECKED : MF_UNCHECKED );
+ // Filter
+ CheckMenuItem( menu, ID_FILTER_MOYEN, g_pAnalyse->filter == ARAnalyse::FMoyen ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_FILTER_LAPLACIEN4, g_pAnalyse->filter == ARAnalyse::FLaplacien4 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_FILTER_LAPLACIEN8, g_pAnalyse->filter == ARAnalyse::FLaplacien8 ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_FILTER_LAPLACIEND, g_pAnalyse->filter == ARAnalyse::FLaplaciend ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_FILTER_SOBEL, g_pAnalyse->filter == ARAnalyse::FSobel ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_FILTER_PREWITT, g_pAnalyse->filter == ARAnalyse::FPrewitt ? MF_CHECKED : MF_UNCHECKED );
+ CheckMenuItem( menu, ID_FILTER_GAUSSIAN, g_pAnalyse->filter == ARAnalyse::FGaussian ? MF_CHECKED : MF_UNCHECKED );
+}
+//-------------------------------------------------------------------
+// OnCommand
+//
+// Handles WM_COMMAND messages
+//-------------------------------------------------------------------
+
+void OnCommand(HWND hwnd, int id, HWND /*hwndCtl*/, UINT /*codeNotify*/)
+{
+ switch (id)
+ {
+ case ID_ACTION_CHOOSEDEVICE:
+ OnChooseDevice(hwnd, TRUE, NULL,0);
+ break;
+ case ID_ACTION_CHOOSEFORMAT:
+ OnChooseFormat(hwnd, TRUE, 0);
+ break;
+ case ID_ACTION_DISPLAYVIDEO:
+ if (g_pPreview)
+ {
+ bool video = g_pPreview->ToggleVideo();
+ CheckMenuItem( GetMenu( hwnd ), ID_ACTION_DISPLAYVIDEO, video ? MF_CHECKED : MF_UNCHECKED );
+ }
+
+ break;
+ case ID_ACTION_CALCMOYEN:
+ if (g_pPreview)
+ {
+ bool moy = g_pPreview->ToggleMoyen();
+ CheckMenuItem( GetMenu( hwnd ), ID_ACTION_CALCMOYEN, moy ? MF_CHECKED : MF_UNCHECKED );
+ }
+
+ break;case ID_ACTION_TRANSFORM:
+ if (g_pPreview)
+ {
+ bool trsf = g_pPreview->ToggleTransform();
+ CheckMenuItem( GetMenu( hwnd ), ID_ACTION_TRANSFORM, trsf ? MF_CHECKED : MF_UNCHECKED );
+ }
+ break;
+ case ID_ACTION_AUTOTHRESHOLD:
+ if (g_pAnalyse)
+ {
+ bool auto_threshold = g_pAnalyse->ToggleAutoThreshold();
+ CheckMenuItem( GetMenu( hwnd ), ID_ACTION_AUTOTHRESHOLD, auto_threshold ? MF_CHECKED : MF_UNCHECKED );
+ if ( ! auto_threshold )
+ {
+ SendMessage(g_hTrack, TBM_SETPOS,
+ (WPARAM) TRUE, // redraw flag
+ (LPARAM) g_pAnalyse->getThreshold());
+ }
+ }
+
+ break;
+ case ID_ACTION_CALIBRATE:
+ if (g_pAnalyse)
+ {
+ bool cal = g_pAnalyse->Calibrate();
+ CheckMenuItem( GetMenu( hwnd ), ID_ACTION_CALIBRATE, cal ? MF_CHECKED : MF_UNCHECKED );
+ }
+ break;
+ case ID_ACTION_SAVEPROJECTIONDATA:
+ if ( g_pAnalyse )
+ {
+ g_pAnalyse->SaveCalibration();
+ }
+ break;
+ case ID_BLURPASSE_0PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 0;
+ }
+ break;
+
+ case ID_BLURPASSE_1PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 1;
+ }
+ break;
+
+ case ID_BLURPASSE_2PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 2;
+ }
+ break;
+
+ case ID_BLURPASSE_3PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 3;
+ }
+ break;
+ case ID_BLURPASSE_4PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 4;
+ }
+ break;
+ case ID_BLURPASSE_5PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 5;
+ }
+ break;
+ case ID_BLURPASSE_6PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 6;
+ }
+ break;
+ case ID_BLURPASSE_10PASS:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->BlurPass = 10;
+ }
+ break;
+ case ID_DOWNSAMPLE_FACTEUR1:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->DownSample = 1;
+ }
+ break;
+ case ID_DOWNSAMPLE_FACTEUR2:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->DownSample = 2;
+ }
+ break;
+ case ID_DOWNSAMPLE_FACTEUR4:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->DownSample = 4;
+ }
+ break;
+ case ID_DOWNSAMPLE_FACTEUR8:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->DownSample = 8;
+ }
+ break;
+
+ case ID_AFFICHAGE_GRAYSCALE:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->Display = ARAnalyse::GrayScale;
+ }
+ break;
+ case ID_AFFICHAGE_BLUR:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->Display = ARAnalyse::Blur;
+ }
+ break;
+ case ID_AFFICHAGE_DIFF:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->Display = ARAnalyse::Diff;
+ }
+ break;
+ case ID_AFFICHAGE_THRESHOLD:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->Display = ARAnalyse::Threshold;
+ }
+ break;
+ case ID_AFFICHAGE_MOYEN:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->Display = ARAnalyse::Moyen;
+ }
+ break;
+ case ID_FILTER_MOYEN:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FMoyen;
+ }
+ break;
+ case ID_FILTER_LAPLACIEN4:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FLaplacien4;
+ }
+ break;
+ case ID_FILTER_LAPLACIEN8:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FLaplacien8;
+ }
+ break;
+ case ID_FILTER_LAPLACIEND:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FLaplaciend;
+ }
+ break;
+ case ID_FILTER_SOBEL:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FSobel;
+ }
+ break;
+ case ID_FILTER_PREWITT:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FPrewitt;
+ }
+ break;
+ case ID_FILTER_GAUSSIAN:
+ if (g_pAnalyse)
+ {
+ g_pAnalyse->filter = ARAnalyse::FGaussian;
+ }
+ break;
+ }
+}
+
+//-------------------------------------------------------------------
+// OnChooseDevice
+//
+// Select a video capture device.
+//
+// hwnd: A handle to the application window.
+/// bPrompt: If TRUE, prompt to user to select the device. Otherwise,
+// select the first device in the list.
+//-------------------------------------------------------------------
+
+void OnChooseDevice(HWND hwnd, BOOL bPrompt, const WCHAR* name, int instance)
+{
+ HRESULT hr = S_OK;
+ ChooseDeviceParam param = { 0,0,0 };
+
+ UINT iDevice = 0; // Index into the array of devices
+ BOOL bCancel = FALSE;
+
+ IMFAttributes *pAttributes = NULL;
+
+ // Initialize an attribute store to specify enumeration parameters.
+
+ hr = MFCreateAttributes(&pAttributes, 1);
+
+ if (FAILED(hr)) { goto done; }
+
+ // Ask for source type = video capture devices.
+
+ hr = pAttributes->SetGUID(
+ MF_DEVSOURCE_ATTRIBUTE_SOURCE_TYPE,
+ MF_DEVSOURCE_ATTRIBUTE_SOURCE_TYPE_VIDCAP_GUID
+ );
+
+ if (FAILED(hr)) { goto done; }
+
+ // Enumerate devices.
+ hr = MFEnumDeviceSources(pAttributes, &param.ppDevices, &param.count);
+
+ if (FAILED(hr)) { goto done; }
+
+ // NOTE: param.count might be zero.
+
+ if (bPrompt || name == NULL)
+ {
+ // Ask the user to select a device.
+
+ INT_PTR result = DialogBoxParam(
+ GetModuleHandle(NULL),
+ MAKEINTRESOURCE(IDD_CHOOSE_DEVICE),
+ hwnd,
+ DeviceDlgProc,
+ (LPARAM)&param
+ );
+
+ if (result == IDOK)
+ {
+ iDevice = param.selection;
+ }
+ else
+ {
+ bCancel = TRUE; // User cancelled
+ }
+ }
+ else
+ {
+ iDevice = DeviceGetByName( &param, name, instance );
+ }
+
+ if (!bCancel && (param.count > 0))
+ {
+ // Give this source to the CPlayer object for preview.
+ hr = g_pPreview->SetDevice( param.ppDevices[iDevice], g_format_video );
+ }
+
+done:
+
+ SafeRelease(&pAttributes);
+
+ for (DWORD i = 0; i < param.count; i++)
+ {
+ SafeRelease(&param.ppDevices[i]);
+ }
+ CoTaskMemFree(param.ppDevices);
+
+ if (FAILED(hr))
+ {
+ ShowErrorMessage(L"Cannot create a video capture device", hr);
+ }
+}
+
+
+//-------------------------------------------------------------------
+// OnChooseFormat
+//
+// Select a video format capture.
+//
+// hwnd: A handle to the application window.
+/// bPrompt: If TRUE, prompt to user to select the device. Otherwise,
+// select the first device in the list.
+//-------------------------------------------------------------------
+
+void OnChooseFormat(HWND hwnd, BOOL bPrompt, int index)
+{
+ HRESULT hr = S_OK;
+ ChooseVideoParam param = { 0, 0, 0 };
+
+ UINT iFormat = 0; // Index into the array of devices
+ BOOL bCancel = FALSE;
+
+ hr = g_pPreview->EnumerateCaptureFormats( &param.ppTypes, &param.count);
+
+ // NOTE: param.count might be zero.
+
+ if (bPrompt)
+ {
+ // Ask the user to select a device.
+
+ INT_PTR result = DialogBoxParam(
+ GetModuleHandle(NULL),
+ MAKEINTRESOURCE(IDD_CHOOSE_VIDEO),
+ hwnd,
+ VideoDlgProc,
+ (LPARAM)&param
+ );
+
+ if (result == IDOK)
+ {
+ iFormat = param.selection;
+ }
+ else
+ {
+ bCancel = TRUE; // User cancelled
+ }
+ }
+ else
+ {
+ iFormat = index;
+ }
+ if (!bCancel && (param.count > 0))
+ {
+ // Give this format to the CPlayer object for preview.
+ hr = g_pPreview->SetFormat( param.ppTypes[iFormat] );
+ }
+
+
+
+ for (DWORD i = 0; i < param.count; i++)
+ {
+ SafeRelease(&param.ppTypes[i]);
+ }
+ CoTaskMemFree(param.ppTypes);
+
+ if (FAILED(hr))
+ {
+ ShowErrorMessage(L"Cannot select a video format", hr);
+ }
+}
+
+//-------------------------------------------------------------------
+// OnDeviceChange
+//
+// Handles WM_DEVICECHANGE messages.
+//-------------------------------------------------------------------
+
+void OnDeviceChange(HWND hwnd, DEV_BROADCAST_HDR *pHdr)
+{
+ if (g_pPreview == NULL || pHdr == NULL)
+ {
+ return;
+ }
+
+ HRESULT hr = S_OK;
+ BOOL bDeviceLost = FALSE;
+
+ // Check if the current device was lost.
+
+ hr = g_pPreview->CheckDeviceLost(pHdr, &bDeviceLost);
+
+ if (FAILED(hr) || bDeviceLost)
+ {
+ g_pPreview->CloseDevice();
+
+ MessageBox(hwnd, L"Lost the capture device.", WINDOW_NAME, MB_OK);
+ }
+}
+
+
+/////////////////////////////////////////////////////////////////////
+
+// Dialog functions
+
+int DeviceGetByName(ChooseDeviceParam *pParam , const WCHAR* name, int instance)
+{
+ HRESULT hr = S_OK;
+ DWORD iDevice = 0;
+ int current_inst = 0;
+ bool NameFound = false;
+ for (DWORD i = 0; i < pParam->count; i++)
+ {
+ WCHAR *szFriendlyName = NULL;
+
+ hr = pParam->ppDevices[i]->GetAllocatedString(
+ MF_DEVSOURCE_ATTRIBUTE_FRIENDLY_NAME,
+ &szFriendlyName,
+ NULL
+ );
+ if (FAILED(hr))
+ {
+ break;
+ }
+ NameFound = wcsstr( szFriendlyName, name ) != NULL;
+ CoTaskMemFree(szFriendlyName);
+ // check if devioce containt name
+ if ( NameFound )
+ {
+ iDevice = i;
+ if ( current_inst == instance )
+ break;
+ current_inst++;
+
+ }
+
+ }
+
+ return iDevice;
+}
+
+//-------------------------------------------------------------------
+// OnInitDialog
+//
+// Handles the WM_INITDIALOG message.
+//-------------------------------------------------------------------
+
+void DeviceOnInitDialog(HWND hwnd, ChooseDeviceParam *pParam)
+{
+ HRESULT hr = S_OK;
+
+ // Populate the list with the friendly names of the devices.
+
+ HWND hList = GetDlgItem(hwnd, IDC_DEVICE_LIST);
+
+ for (DWORD i = 0; i < pParam->count; i++)
+ {
+ WCHAR *szFriendlyName = NULL;
+
+ hr = pParam->ppDevices[i]->GetAllocatedString(
+ MF_DEVSOURCE_ATTRIBUTE_FRIENDLY_NAME,
+ &szFriendlyName,
+ NULL
+ );
+
+ if (FAILED(hr))
+ {
+ break;
+ }
+
+
+ int index = ListBox_AddString(hList, szFriendlyName);
+
+ ListBox_SetItemData(hList, index, i);
+
+ CoTaskMemFree(szFriendlyName);
+ }
+
+ // Assume no selection for now.
+ pParam->selection = (UINT32)-1;
+
+ if (pParam->count == 0)
+ {
+ // If there are no devices, disable the "OK" button.
+ EnableWindow(GetDlgItem(hwnd, IDOK), FALSE);
+ }
+}
+
+
+HRESULT DeviceOnOK(HWND hwnd, ChooseDeviceParam *pParam)
+{
+ HWND hList = GetDlgItem(hwnd, IDC_DEVICE_LIST);
+
+ int sel = ListBox_GetCurSel(hList);
+
+ if (sel != LB_ERR)
+ {
+ pParam->selection = (UINT32)ListBox_GetItemData(hList, sel);
+ }
+
+ return S_OK;
+}
+
+
+//-------------------------------------------------------------------
+// DeviceDlgProc
+//
+// Dialog procedure for the "Select Device" dialog.
+//-------------------------------------------------------------------
+
+INT_PTR CALLBACK DeviceDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ static ChooseDeviceParam *pParam = NULL;
+
+ switch (msg)
+ {
+ case WM_INITDIALOG:
+ pParam = (ChooseDeviceParam*)lParam;
+ DeviceOnInitDialog(hwnd, pParam);
+ return TRUE;
+
+ case WM_COMMAND:
+ switch(LOWORD(wParam))
+ {
+ case IDOK:
+ DeviceOnOK(hwnd, pParam);
+ EndDialog(hwnd, LOWORD(wParam));
+ return TRUE;
+
+ case IDCANCEL:
+ EndDialog(hwnd, LOWORD(wParam));
+ return TRUE;
+ }
+ break;
+ }
+
+ return FALSE;
+}
+
+
+
+void ShowErrorMessage(PCWSTR format, HRESULT hrErr)
+{
+ HRESULT hr = S_OK;
+ int dwBufferLength;
+
+ WCHAR msg[MAX_PATH];
+ static LPCVOID s_hModule = 0;
+ const LPCWSTR MESSAGEFILE = L"mferror.dll";
+ DWORD dwFormatFlags =
+ FORMAT_MESSAGE_ALLOCATE_BUFFER |
+ FORMAT_MESSAGE_FROM_SYSTEM |
+ FORMAT_MESSAGE_IGNORE_INSERTS |
+ FORMAT_MESSAGE_MAX_WIDTH_MASK;
+
+ WCHAR *lpMsgBuf = 0;
+ dwBufferLength = FormatMessage(
+ dwFormatFlags,
+ NULL,
+ hrErr,
+ MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), // Default language
+ (LPTSTR)&lpMsgBuf,
+ 0,
+ NULL );
+ //lpMsgBuf[strlen(lpMsgBuf) -2] = '\0'; // remove last \n
+
+ // Not a system message. In theory, you should be able to get both with one call.
+ // In practice (at least on my 64bit box), you need to make 2 calls.
+ if (dwBufferLength == 0)
+ {
+ if (s_hModule == 0)
+ {
+ // Load the Media Foundation error message dll
+ s_hModule = LoadLibraryEx(MESSAGEFILE, NULL, LOAD_LIBRARY_AS_DATAFILE);
+ }
+
+ if (s_hModule != 0)
+ {
+ // If the load succeeds, make sure we look in it
+ dwFormatFlags |= FORMAT_MESSAGE_FROM_HMODULE;
+
+ // Scan both the Windows Media library, and the system library looking for the message
+ dwBufferLength = FormatMessage(
+ dwFormatFlags,
+ s_hModule, // module to get message from (NULL == system)
+ hrErr, // error number to get message for
+ MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), // default language
+ (LPTSTR)&lpMsgBuf,
+ 0,
+ NULL
+ );
+ }
+ }
+ hr = StringCbPrintf(msg, sizeof(msg), L"%s (hr=0x%X) \n%s", format, hrErr, lpMsgBuf);
+ // Free the buffer.
+ LocalFree( lpMsgBuf );
+ if (SUCCEEDED(hr))
+ {
+ MessageBox(NULL, msg, L"Error", MB_ICONERROR);
+ }
+ else
+ {
+ DebugBreak();
+ }
+}
+
+// Dialog functions
+
+//-------------------------------------------------------------------
+// VideoOnInitDialog
+//
+// Handles the WM_INITDIALOG message.
+//-------------------------------------------------------------------
+
+void VideoOnInitDialog(HWND hwnd, ChooseVideoParam *pParam)
+{
+ HRESULT hr = S_OK;
+ PROPVARIANT var;
+ UINT32 rate_num;
+ UINT32 rate_denum;
+ UINT32 width;
+ UINT32 height;
+ WCHAR msg[MAX_PATH];
+
+ // Populate the list with the friendly names of the devices.
+
+ HWND hList = GetDlgItem(hwnd, IDC_VIDEO_LIST);
+
+ for (DWORD i = 0; i < pParam->count; i++)
+ {
+
+ WCHAR *szSubTypeName = NULL;
+
+ hr = pParam->ppTypes[i]->GetItem( MF_MT_SUBTYPE, &var );
+ if (FAILED(hr))
+ {
+ break;
+ }
+
+ hr = GetGUIDName(*var.puuid, &szSubTypeName);
+ if (FAILED(hr))
+ {
+ break;
+ }
+
+ hr = MFGetAttributeSize( pParam->ppTypes[i], MF_MT_FRAME_RATE, &rate_num, &rate_denum );
+ if (FAILED(hr))
+ {
+ break;
+ }
+ hr = MFGetAttributeSize( pParam->ppTypes[i], MF_MT_FRAME_SIZE, &width, &height);
+ if (FAILED(hr))
+ {
+ break;
+ }
+
+
+ if (SUCCEEDED(StringCchPrintf(msg, sizeof(msg), TEXT("%02d %s %dx%d pixel %.01f FPS"), i,szSubTypeName, width,height,((float)rate_num/rate_denum))))
+ {
+ int index = ListBox_AddString(hList, msg);
+
+ ListBox_SetItemData(hList, index, i);
+ }
+
+
+ CoTaskMemFree(szSubTypeName);
+ }
+
+ // Assume no selection for now.
+ pParam->selection = (UINT32)-1;
+
+ if (pParam->count == 0)
+ {
+ // If there are no devices, disable the "OK" button.
+ EnableWindow(GetDlgItem(hwnd, IDOK), FALSE);
+ }
+}
+
+
+HRESULT VideoOnOK(HWND hwnd, ChooseVideoParam *pParam)
+{
+ HWND hList = GetDlgItem(hwnd, IDC_DEVICE_LIST);
+
+ int sel = ListBox_GetCurSel(hList);
+
+ if (sel != LB_ERR)
+ {
+ pParam->selection = (UINT32)ListBox_GetItemData(hList, sel);
+ }
+
+ return S_OK;
+}
+
+
+
+
+//-------------------------------------------------------------------
+// DeviceDlgProc
+//
+// Dialog procedure for the "Select Device" dialog.
+//-------------------------------------------------------------------
+
+INT_PTR CALLBACK VideoDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ static ChooseVideoParam *pParam = NULL;
+
+ switch (msg)
+ {
+ case WM_INITDIALOG:
+ pParam = (ChooseVideoParam*)lParam;
+ VideoOnInitDialog(hwnd, pParam);
+ return TRUE;
+
+ case WM_COMMAND:
+ switch(LOWORD(wParam))
+ {
+ case IDOK:
+ VideoOnOK(hwnd, pParam);
+ EndDialog(hwnd, LOWORD(wParam));
+ return TRUE;
+
+ case IDCANCEL:
+ EndDialog(hwnd, LOWORD(wParam));
+ return TRUE;
+ }
+ break;
+ }
+
+ return FALSE;
+}
+
+