Update to 2.0.0 tree from current Fremantle build
[opencv] / 3rdparty / include / videoInput.h
diff --git a/3rdparty/include/videoInput.h b/3rdparty/include/videoInput.h
new file mode 100644 (file)
index 0000000..4244902
--- /dev/null
@@ -0,0 +1,385 @@
+#ifndef _VIDEOINPUT\r
+#define _VIDEOINPUT\r
+\r
+//THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
+//IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
+//FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\r
+//AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
+//LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\r
+//OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN\r
+//THE SOFTWARE.\r
+\r
+//////////////////////////////////////////////////////////\r
+//Written by Theodore Watson - theo.watson@gmail.com    //\r
+//Do whatever you want with this code but if you find   //\r
+//a bug or make an improvement I would love to know!    //\r
+//                                                                                                             //\r
+//Warning This code is experimental                                    //\r
+//use at your own risk :)                                                              //\r
+//////////////////////////////////////////////////////////\r
+/////////////////////////////////////////////////////////\r
+/*                     Shoutouts \r
+\r
+Thanks to: \r
+                       \r
+                  Dillip Kumar Kara for crossbar code.\r
+                  Zachary Lieberman for getting me into this stuff\r
+                  and for being so generous with time and code.\r
+                  The guys at Potion Design for helping me with VC++\r
+                  Josh Fisher for being a serious C++ nerd :)\r
+                  Golan Levin for helping me debug the strangest \r
+                  and slowest bug in the world!\r
+                  \r
+                  And all the people using this library who send in \r
+                  bugs, suggestions and improvements who keep me working on \r
+                  the next version - yeah thanks a lot ;)\r
+                  \r
+*/\r
+/////////////////////////////////////////////////////////\r
+\r
+\r
+\r
+#include <stdlib.h>\r
+#include <stdio.h>\r
+#include <math.h>\r
+#include <string.h>\r
+#include <wchar.h>\r
+\r
+//this is for TryEnterCriticalSection\r
+#ifndef _WIN32_WINNT\r
+       #   define _WIN32_WINNT 0x400\r
+#endif\r
+#include <windows.h>\r
+\r
+\r
+//Example Usage\r
+/*\r
+       //create a videoInput object\r
+       videoInput VI;\r
+       \r
+       //Prints out a list of available devices and returns num of devices found\r
+       int numDevices = VI.listDevices();      \r
+       \r
+       int device1 = 0;  //this could be any deviceID that shows up in listDevices\r
+       int device2 = 1;  //this could be any deviceID that shows up in listDevices\r
+       \r
+       //if you want to capture at a different frame rate (default is 30) \r
+       //specify it here, you are not guaranteed to get this fps though.\r
+       //VI.setIdealFramerate(dev, 60);        \r
+       \r
+       //setup the first device - there are a number of options:\r
+       \r
+       VI.setupDevice(device1);                                                  //setup the first device with the default settings\r
+       //VI.setupDevice(device1, VI_COMPOSITE);                          //or setup device with specific connection type\r
+       //VI.setupDevice(device1, 320, 240);                              //or setup device with specified video size\r
+       //VI.setupDevice(device1, 320, 240, VI_COMPOSITE);  //or setup device with video size and connection type\r
+\r
+       //VI.setFormat(device1, VI_NTSC_M);                                     //if your card doesn't remember what format it should be\r
+                                                                                                               //call this with the appropriate format listed above\r
+                                                                                                               //NOTE: must be called after setupDevice!\r
+       \r
+       //optionally setup a second (or third, fourth ...) device - same options as above\r
+       VI.setupDevice(device2);                                                  \r
+\r
+       //As requested width and height can not always be accomodated\r
+       //make sure to check the size once the device is setup\r
+\r
+       int width       = VI.getWidth(device1);\r
+       int height      = VI.getHeight(device1);\r
+       int size        = VI.getSize(device1);\r
+       \r
+       unsigned char * yourBuffer1 = new unsigned char[size];\r
+       unsigned char * yourBuffer2 = new unsigned char[size];\r
+       \r
+       //to get the data from the device first check if the data is new\r
+       if(VI.isFrameNew(device1)){\r
+               VI.getPixels(device1, yourBuffer1, false, false);       //fills pixels as a BGR (for openCV) unsigned char array - no flipping\r
+               VI.getPixels(device1, yourBuffer2, true, true);         //fills pixels as a RGB (for openGL) unsigned char array - flipping!\r
+       }\r
+       \r
+       //same applies to device2 etc\r
+       \r
+       //to get a settings dialog for the device\r
+       VI.showSettingsWindow(device1);\r
+       \r
+       \r
+       //Shut down devices properly\r
+       VI.stopDevice(device1);\r
+       VI.stopDevice(device2);\r
+*/\r
+\r
+\r
+//////////////////////////////////////   VARS AND DEFS   //////////////////////////////////\r
+\r
+\r
+//STUFF YOU CAN CHANGE\r
+\r
+//change for verbose debug info\r
+static bool verbose = true;\r
+\r
+//if you need VI to use multi threaded com\r
+//#define VI_COM_MULTI_THREADED\r
+\r
+//STUFF YOU DON'T CHANGE\r
+\r
+//videoInput defines\r
+#define VI_VERSION      0.1995\r
+#define VI_MAX_CAMERAS  20\r
+#define VI_NUM_TYPES    18 //DON'T TOUCH\r
+#define VI_NUM_FORMATS  18 //DON'T TOUCH\r
+\r
+//defines for setPhyCon - tuner is not as well supported as composite and s-video \r
+#define VI_COMPOSITE 0\r
+#define VI_S_VIDEO   1\r
+#define VI_TUNER     2\r
+#define VI_USB       3\r
+#define VI_1394                 4\r
+\r
+//defines for formats\r
+#define VI_NTSC_M      0\r
+#define VI_PAL_B       1\r
+#define VI_PAL_D       2\r
+#define VI_PAL_G       3\r
+#define VI_PAL_H       4\r
+#define VI_PAL_I       5\r
+#define VI_PAL_M       6\r
+#define VI_PAL_N       7\r
+#define VI_PAL_NC      8\r
+#define VI_SECAM_B     9\r
+#define VI_SECAM_D     10\r
+#define VI_SECAM_G     11\r
+#define VI_SECAM_H     12\r
+#define VI_SECAM_K     13\r
+#define VI_SECAM_K1    14\r
+#define VI_SECAM_L     15\r
+#define VI_NTSC_M_J    16\r
+#define VI_NTSC_433    17\r
+\r
+\r
+//allows us to directShow classes here with the includes in the cpp\r
+struct ICaptureGraphBuilder2;\r
+struct IGraphBuilder;\r
+struct IBaseFilter;\r
+struct IAMCrossbar;\r
+struct IMediaControl;\r
+struct ISampleGrabber;\r
+struct IMediaEventEx;\r
+struct IAMStreamConfig;\r
+struct _AMMediaType;\r
+class SampleGrabberCallback;\r
+typedef _AMMediaType AM_MEDIA_TYPE;\r
+\r
+//keeps track of how many instances of VI are being used\r
+//don't touch\r
+static int comInitCount = 0;\r
+\r
+\r
+////////////////////////////////////////   VIDEO DEVICE   ///////////////////////////////////\r
+\r
+class videoDevice{\r
+\r
+       \r
+       public:\r
+                \r
+               videoDevice();\r
+               void setSize(int w, int h);\r
+               void NukeDownstream(IBaseFilter *pBF);\r
+               void destroyGraph();\r
+               ~videoDevice();\r
+               \r
+               int videoSize;\r
+               int width;\r
+               int height;\r
+               int tryWidth;\r
+               int tryHeight;\r
+               \r
+               ICaptureGraphBuilder2 *pCaptureGraph;   // Capture graph builder object\r
+               IGraphBuilder *pGraph;                                  // Graph builder object\r
+           IMediaControl *pControl;                            // Media control object\r
+               IBaseFilter *pVideoInputFilter;                 // Video Capture filter\r
+               IBaseFilter *pGrabberF;\r
+               IBaseFilter * pDestFilter;\r
+               IAMStreamConfig *streamConf;\r
+               ISampleGrabber * pGrabber;                      // Grabs frame\r
+               AM_MEDIA_TYPE * pAmMediaType;\r
+               \r
+               IMediaEventEx * pMediaEvent;\r
+               \r
+               GUID videoType;\r
+               long formatType;\r
+               \r
+               SampleGrabberCallback * sgCallback;                             \r
+               \r
+               bool tryDiffSize;\r
+               bool useCrossbar;\r
+               bool readyToCapture;\r
+               bool sizeSet;\r
+               bool setupStarted;\r
+               bool specificFormat;\r
+               bool autoReconnect;\r
+               int  nFramesForReconnect;\r
+               unsigned long nFramesRunning;\r
+               int  connection;\r
+               int      storeConn;\r
+               int  myID;\r
+               long requestedFrameTime; //ie fps\r
+               \r
+               char    nDeviceName[255];\r
+               WCHAR   wDeviceName[255];\r
+               \r
+               unsigned char * pixels;\r
+               char * pBuffer;\r
+\r
+};\r
+\r
+\r
+\r
+\r
+//////////////////////////////////////   VIDEO INPUT   /////////////////////////////////////\r
+\r
+\r
+\r
+class videoInput{\r
+\r
+       public:\r
+               videoInput();\r
+               ~videoInput();\r
+                               \r
+               //turns off console messages - default is to print messages\r
+               static void setVerbose(bool _verbose);\r
+               \r
+               //Functions in rough order they should be used.\r
+               static int listDevices(bool silent = false);\r
+\r
+               //needs to be called after listDevices - otherwise returns NULL\r
+               static char * getDeviceName(int deviceID);\r
+               \r
+               //choose to use callback based capture - or single threaded\r
+               void setUseCallback(bool useCallback);  \r
+               \r
+               //call before setupDevice\r
+               //directshow will try and get the closest possible framerate to what is requested\r
+               void setIdealFramerate(int deviceID, int idealFramerate);\r
+\r
+               //some devices will stop delivering frames after a while - this method gives you the option to try and reconnect\r
+               //to a device if videoInput detects that a device has stopped delivering frames. \r
+               //you MUST CALL isFrameNew every app loop for this to have any effect\r
+               void setAutoReconnectOnFreeze(int deviceNumber, bool doReconnect, int numMissedFramesBeforeReconnect);\r
+               \r
+               //Choose one of these four to setup your device\r
+               bool setupDevice(int deviceID);\r
+               bool setupDevice(int deviceID, int w, int h);\r
+\r
+               //These two are only for capture cards\r
+               //USB and Firewire cameras souldn't specify connection \r
+               bool setupDevice(int deviceID, int connection); \r
+               bool setupDevice(int deviceID, int w, int h, int connection); \r
+               \r
+               //If you need to you can set your NTSC/PAL/SECAM\r
+               //preference here. if it is available it will be used.\r
+               //see #defines above for available formats - eg VI_NTSC_M or VI_PAL_B\r
+               //should be called after setupDevice\r
+               //can be called multiple times\r
+               bool setFormat(int deviceNumber, int format);   \r
+                               \r
+               //Tells you when a new frame has arrived - you should call this if you have specified setAutoReconnectOnFreeze to true\r
+               bool isFrameNew(int deviceID); \r
+               \r
+               bool isDeviceSetup(int deviceID);\r
+                   \r
+               //Returns the pixels - flipRedAndBlue toggles RGB/BGR flipping - and you can flip the image too\r
+               unsigned char * getPixels(int deviceID, bool flipRedAndBlue = true, bool flipImage = false);\r
+               \r
+               //Or pass in a buffer for getPixels to fill returns true if successful.\r
+               bool getPixels(int id, unsigned char * pixels, bool flipRedAndBlue = true, bool flipImage = false);\r
+               \r
+               //Launches a pop up settings window\r
+               //For some reason in GLUT you have to call it twice each time. \r
+               void showSettingsWindow(int deviceID);\r
+               \r
+               //Manual control over settings thanks..... \r
+               //These are experimental for now.\r
+               bool setVideoSettingFilter(int deviceID, long Property, long lValue, long Flags = NULL, bool useDefaultValue = false);\r
+               bool setVideoSettingFilterPct(int deviceID, long Property, float pctValue, long Flags = NULL);\r
+               bool getVideoSettingFilter(int deviceID, long Property, long &min, long &max, long &SteppingDelta, long &currentValue, long &flags, long &defaultValue);\r
+\r
+               bool setVideoSettingCamera(int deviceID, long Property, long lValue, long Flags = NULL, bool useDefaultValue = false);\r
+               bool setVideoSettingCameraPct(int deviceID, long Property, float pctValue, long Flags = NULL);\r
+               bool getVideoSettingCamera(int deviceID, long Property, long &min, long &max, long &SteppingDelta, long &currentValue, long &flags, long &defaultValue);\r
+\r
+               //bool setVideoSettingCam(int deviceID, long Property, long lValue, long Flags = NULL, bool useDefaultValue = false);\r
+\r
+               //get width, height and number of pixels\r
+               int  getWidth(int deviceID);\r
+               int  getHeight(int deviceID);\r
+               int  getSize(int deviceID);\r
+               \r
+               //completely stops and frees a device\r
+               void stopDevice(int deviceID);\r
+               \r
+               //as above but then sets it up with same settings\r
+               bool restartDevice(int deviceID);\r
+               \r
+               //number of devices available\r
+               int  devicesFound;\r
+               \r
+               long propBrightness;\r
+               long propContrast;\r
+               long propHue;\r
+               long propSaturation;\r
+               long propSharpness;\r
+               long propGamma;\r
+               long propColorEnable;\r
+               long propWhiteBalance;\r
+               long propBacklightCompensation;\r
+               long propGain;\r
+\r
+               long propPan;\r
+               long propTilt;\r
+               long propRoll;\r
+               long propZoom;\r
+               long propExposure;\r
+               long propIris;\r
+               long propFocus;\r
+                               \r
+               \r
+       private:                \r
+               void setPhyCon(int deviceID, int conn);                   \r
+               void setAttemptCaptureSize(int deviceID, int w, int h);   \r
+               bool setup(int deviceID);\r
+               void processPixels(unsigned char * src, unsigned char * dst, int width, int height, bool bRGB, bool bFlip);\r
+               int  start(int deviceID, videoDevice * VD);                   \r
+               int  getDeviceCount();\r
+               void getMediaSubtypeAsString(GUID type, char * typeAsString);\r
+               \r
+               HRESULT getDevice(IBaseFilter **pSrcFilter, int deviceID, WCHAR * wDeviceName, char * nDeviceName);\r
+               static HRESULT ShowFilterPropertyPages(IBaseFilter *pFilter);\r
+               HRESULT SaveGraphFile(IGraphBuilder *pGraph, WCHAR *wszPath);\r
+               HRESULT routeCrossbar(ICaptureGraphBuilder2 **ppBuild, IBaseFilter **pVidInFilter, int conType, GUID captureMode);\r
+                       \r
+               //don't touch\r
+               static bool comInit();\r
+               static bool comUnInit();\r
+\r
+               int  connection;\r
+               int  callbackSetCount;\r
+               bool bCallback;\r
+               \r
+               GUID CAPTURE_MODE;\r
+               \r
+               //Extra video subtypes\r
+               GUID MEDIASUBTYPE_Y800;\r
+               GUID MEDIASUBTYPE_Y8;\r
+               GUID MEDIASUBTYPE_GREY;\r
+\r
+               videoDevice * VDList[VI_MAX_CAMERAS];\r
+               GUID mediaSubtypes[VI_NUM_TYPES];\r
+               long formatTypes[VI_NUM_FORMATS];\r
+\r
+               static void __cdecl basicThread(void * objPtr);\r
+\r
+               static char deviceNames[VI_MAX_CAMERAS][255];\r
+\r
+}; \r
+  \r
+ #endif\r