0

このコードを使用して、カメラの写真を取得しようとしています:

            IGraphBuilder _graph = null;
            ISampleGrabber _grabber = null;
            IBaseFilter _sourceObject = null;
            IBaseFilter _grabberObject = null;
            IMediaControl _control = null;

            // Create the main graph
            _graph = Activator.CreateInstance(Type.GetTypeFromCLSID(FilterGraph)) as IGraphBuilder;

            // Create the webcam source
            _sourceObject = FilterInfo.CreateFilter(_monikerString);

            // Create the grabber
            _grabber = Activator.CreateInstance(Type.GetTypeFromCLSID(SampleGrabber)) as ISampleGrabber;
            _grabberObject = _grabber as IBaseFilter;

            // Add the source and grabber to the main graph
            _graph.AddFilter(_sourceObject, "source");
            _graph.AddFilter(_grabberObject, "grabber");

            IPin pin = _sourceObject.GetPin(PinDirection.Output, 0);

            IAMStreamConfig streamConfig = pin as IAMStreamConfig;
            int count = 0, size = 0;
            streamConfig.GetNumberOfCapabilities(out count, out size);

            int width = 0, height = 0;
            AMMediaType mediaType = null;
            AMMediaType mediaTypeCandidate = null;
            for(int index = 0; index < count; index++) {
                VideoStreamConfigCaps scc = new VideoStreamConfigCaps();
                int test = streamConfig.GetStreamCaps(index, out mediaTypeCandidate, scc);
                if(mediaTypeCandidate.MajorType == MediaTypes.Video && mediaTypeCandidate.SubType == MediaSubTypes.YUY2) {
                    VideoInfoHeader header = (VideoInfoHeader)Marshal.PtrToStructure(mediaTypeCandidate.FormatPtr, typeof(VideoInfoHeader));

                    if(header.BmiHeader.Width == 1280 && header.BmiHeader.Height == 720) {
                        width = header.BmiHeader.Width;
                        height = header.BmiHeader.Height;
                        if(mediaType != null)
                            mediaType.Dispose();
                        mediaType = mediaTypeCandidate;
                    } else
                        mediaTypeCandidate.Dispose();
                } else
                    mediaTypeCandidate.Dispose();
            }

            streamConfig.SetFormat(mediaType);

そしてそれは動作しますが、このコードによって生成された画像が表示されません:

uint pcount = (uint)(_capGrabber.Width * _capGrabber.Height * PixelFormats.Bgr32.BitsPerPixel / 8);

                    // Create a file mapping
                    _section = CreateFileMapping(new IntPtr(-1), IntPtr.Zero, 0x04, 0, pcount, null);
                    _map = MapViewOfFile(_section, 0xF001F, 0, 0, pcount);

                    // Get the bitmap
                    BitmapSource = Imaging.CreateBitmapSourceFromMemorySection(_section, _capGrabber.Width,
                        _capGrabber.Height, PixelFormats.Bgr32, _capGrabber.Width * PixelFormats.Bgr32.BitsPerPixel / 8, 0) as InteropBitmap;
                    _capGrabber.Map = _map;

                    // Invoke event
                    if (NewBitmapReady != null)
                    {
                        NewBitmapReady(this, null);
                    }

SubMediaTyp が YUY2 であるためです。このコードにコンバーターを追加するにはどうすればよいですか? IGraphBuilder に追加できる ColorConvert について読んだことがあります。それはどのように機能しますか?

4

1 に答える 1

0

RGB のフレーバーCreateBitmapSourceFromMemorySection以外のものを受け入れることは期待できません。メディア タイプを受け入れる可能性はさらに低いため、ビデオ ストリームをマネージ ビットマップ/イメージング オブジェクトとしてエクスポートする前に、DirectShow パイプラインでビデオ ストリームを RGB に変換する必要があります。YUY2

これを実現するには、通常、24 ビット RGB サブタイプに初期化されたサンプル グラバー フィルターを追加し、DirectShow に必要なコンバーターを自動的に提供させます。

ここで詳細な説明とコード スニペットを参照してください: DirectShow: SampleGrabber を使用してフレームを取得する例...

media.majorType    = MediaType.Video;
media.subType    = MediaSubType.RGB24;
media.formatPtr = IntPtr.Zero;
hr = sampGrabber.SetMediaType(media);
于 2012-07-26T18:22:17.957 に答える