يتميز D3D11 بآبار واجهة برمجة تطبيقات الفيديو التي هي أساسا DXVA2 مع واجهة تم تغييرها قليلا أعلاه. تحتاج إلى فهم جيد من H.264 bitstreams للمتابعة (حقا!). أي تأكد من أن لديك محلل H.264 في متناول اليد لاستخراج حقول من هياكل SPS و PPS وجميع شرائح الإطار المشفر.
1) احصل على مثيل ID3D11VideDodevice من ID3D11Device ، و ID3D11VideOconText من سياق جهاز D3D11 الفوري ملاحظة: على Win7 ، يجب عليك إنشاء جهازك بمستوى الميزة 9_3 للحصول على دعم الفيديو! (في WIN8 يعمل فقط)
2) إنشاء مثيل ID3D11VideOdeCoder لـ H.264 استخدم ID3D11VideDoDevice :: getVideOdeCoderProfileCount ، getVideOdeCoderProfile ، checkVideOdeCoderFormat ... للتكرار من خلال جميع ملفات التعريف المدعومة ، والعثور على GuidD11_decoder_profile_h264_vld_nof for for H264. كما outputFormat أفضل رهان هو dxgi_format_nv12.
3) فك تشفير الإطارات الفردية انظر دعم Direct3D 11 فك تشفير الفيديو في مؤسسة الوسائط:
- id3d11videocontext :: decoderbeginframe (decoder ، outputview -> mucded frame methure)
- ملء المخازن المؤقتة:
- d3d11_video_decoder_buffer_picture_parameters
- d3d11_video_decoder_buffer_inverse_quantization_matrix
- d3d11_video_decoder_buffer_bitstream
- d3d11_video_decoder_buffer_slice_control
تمتلئ المخازن المؤقتة مع هياكل DXVA2 المقابلة (انظر DXVA2.H) المواصفات الكاملة DXVA2 ، ستحتاج إليها لتعيين حقول SPS/PPS H.264 وفقًا لذلك.
نرى:
ثم:
- id3d11videocontext :: submitbuffers لارتكاب جميع المخازن المؤقتة المملوءة
- id3d11videocontext :: decoderendframe لإنهاء الإطار الحالي
3) D3D11_VIDEO_DECODER_BUFFER_PICTURE_PARAMETERS يحتوي أيضًا على معلومات حول جميع إطارات المراجع/السطح - تحتاج إلى إدارتها بنفسك ، أي تأكد من أن الأسطح/القوام متاحة ل GPU!
إنه معقد للغاية ، تحقق من FFMPEG و Media Player Classic ، وكلاهما لديه DXVA2 (وإن لم يكن عبر DX11) دعم.
4) التحويل من NV12 إلى RGB (A) ، يسمح بعض وحدات معالجة الرسومات (D3D11) باستخدام NV12 كمدخلات تظليل ، بعضها لا. في حال لم يكن من الممكن استخدام NV12 مباشرة ، يمكنك إلقاء نظرة على واجهات D3D11VideOprocessor التي تتميز بتحويل NV12/YUV420-> RGB لجميع وحدات معالجة الرسومات مع دعم D3D11.
يمكن إجراء التحويل في كود مثل هذا:
// Setup ID3D11Video*
ID3D11VideoProcessor * d3dVideoProc = ...;
ID3D11VideoDevice * d3dVideoDevice = ...;
ID3D11VideoProcessorEnumerator * d3dVideoProcEnum = ...;
ID3D11Texture2D * srcTextureNV12Fmt = ...;
ID3D11Texture2D * dstTextureRGBFmt = ...;
// Use Video Processor
// Create views for VideoProc In/Output
ID3D11VideoProcessorInputView * videoProcInputView;
ID3D11VideoProcessorOutputView * videoProcOutputView;
{
D3D11_VIDEO_PROCESSOR_INPUT_VIEW_DESC inputViewDesc = { 0 };
inputViewDesc.ViewDimension = D3D11_VPIV_DIMENSION_TEXTURE2D;
inputViewDesc.Texture2D.ArraySlice = arraySliceIdx;
inputViewDesc.Texture2D.MipSlice = 0;
hr = d3dVideoDevice->CreateVideoProcessorInputView(srcTextureNV12Fmt, d3dVideoProcEnum, &inputViewDesc, &videoProcInputView);
}
{
D3D11_VIDEO_PROCESSOR_OUTPUT_VIEW_DESC outputViewDesc = { D3D11_VPOV_DIMENSION_TEXTURE2D };
outputViewDesc.Texture2D.MipSlice = 0;
hr = d3dVideoDevice->CreateVideoProcessorOutputView(dstTextureRGBFmt, d3dVideoProcEnum, &outputViewDesc, &videoProcOutputView);
}
// Setup streams
D3D11_VIDEO_PROCESSOR_STREAM streams = { 0 };
streams.Enable = TRUE;
streams.pInputSurface = videoProcInputView.get();
RECT srcRect = { /* source rectangle in pixels*/ };
RECT dstRect = { /* destination rectangle in pixels*/ };
// Perform VideoProc Blit Operation (with color conversion)
hr = videoCtx_->VideoProcessorBlt(d3dVideoProc, videoProcOutputView.get(), 0, 1, &streams);