convert.cpp 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. #include "convert.h"
  2. using namespace std;
  3. #if !defined(SAFE_RELEASE)
  4. #define SAFE_RELEASE(X) \
  5. if (X) { \
  6. X->Release(); \
  7. X = nullptr; \
  8. }
  9. #endif
  10. #if !defined(PRINTERR1)
  11. #define PRINTERR1(x) printf(__FUNCTION__ ": Error 0x%08x at line %d in file %s\n", x, __LINE__, __FILE__);
  12. #endif
  13. #if !defined(PRINTERR)
  14. #define PRINTERR(x, y) printf(__FUNCTION__ ": Error 0x%08x in %s at line %d in file %s\n", x, y, __LINE__, __FILE__);
  15. #endif
  16. /// Initialize Video Context
  17. HRESULT D3dConverter::Open(ID3D11Device* pDev, ID3D11DeviceContext* pCtx,
  18. const D3D11_VIDEO_PROCESSOR_COLOR_SPACE& inColorSpace, D3D11_VIDEO_PROCESSOR_COLOR_SPACE& outColorSpace)
  19. {
  20. m_pDev = pDev;
  21. m_pCtx = pCtx;
  22. m_pDev->AddRef();
  23. m_pCtx->AddRef();
  24. /// Obtain Video device and Video device context
  25. HRESULT hr = m_pDev->QueryInterface(__uuidof(ID3D11VideoDevice), (void**)&m_pVid);
  26. if (FAILED(hr)) {
  27. PRINTERR(hr, "QAI for ID3D11VideoDevice");
  28. }
  29. hr = m_pCtx->QueryInterface(__uuidof(ID3D11VideoContext), (void**)&m_pVidCtx);
  30. if (FAILED(hr)) {
  31. PRINTERR(hr, "QAI for ID3D11VideoContext");
  32. }
  33. _inColorSpace = inColorSpace;
  34. _outColorSpace = outColorSpace;
  35. return hr;
  36. }
  37. /// Release all Resources
  38. void D3dConverter::Close()
  39. {
  40. for (auto& it : viewMap) {
  41. ID3D11VideoProcessorOutputView* pVPOV = it.second;
  42. pVPOV->Release();
  43. }
  44. SAFE_RELEASE(m_pVP);
  45. SAFE_RELEASE(m_pVPEnum);
  46. SAFE_RELEASE(m_pVidCtx);
  47. SAFE_RELEASE(m_pVid);
  48. SAFE_RELEASE(m_pCtx);
  49. SAFE_RELEASE(m_pDev);
  50. }
  51. /// Perform Colorspace conversion
  52. HRESULT D3dConverter::Convert(ID3D11Texture2D* pIn, ID3D11Texture2D* pOut)
  53. {
  54. HRESULT hr = S_OK;
  55. D3D11_TEXTURE2D_DESC inDesc = {0};
  56. D3D11_TEXTURE2D_DESC outDesc = {0};
  57. pIn->GetDesc(&inDesc);
  58. pOut->GetDesc(&outDesc);
  59. /// Check if VideoProcessor needs to be reconfigured
  60. /// Reconfiguration is required if input/output dimensions have changed
  61. if (m_pVP) {
  62. if (m_inDesc.Width != inDesc.Width || m_inDesc.Height != inDesc.Height || m_outDesc.Width != outDesc.Width || m_outDesc.Height != outDesc.Height) {
  63. SAFE_RELEASE(m_pVPEnum);
  64. SAFE_RELEASE(m_pVP);
  65. }
  66. }
  67. if (!m_pVP) {
  68. /// Initialize Video Processor
  69. m_inDesc = inDesc;
  70. m_outDesc = outDesc;
  71. D3D11_VIDEO_PROCESSOR_CONTENT_DESC contentDesc = {
  72. D3D11_VIDEO_FRAME_FORMAT_PROGRESSIVE,
  73. {0, 0}, inDesc.Width, inDesc.Height,
  74. {0, 0}, outDesc.Width, outDesc.Height,
  75. D3D11_VIDEO_USAGE_PLAYBACK_NORMAL};
  76. hr = m_pVid->CreateVideoProcessorEnumerator(&contentDesc, &m_pVPEnum);
  77. if (FAILED(hr)) {
  78. PRINTERR(hr, "CreateVideoProcessorEnumerator");
  79. }
  80. hr = m_pVid->CreateVideoProcessor(m_pVPEnum, 0, &m_pVP);
  81. if (FAILED(hr)) {
  82. PRINTERR(hr, "CreateVideoProcessor");
  83. }
  84. m_pVidCtx->VideoProcessorSetStreamColorSpace(m_pVP, 0, &_inColorSpace);
  85. m_pVidCtx->VideoProcessorSetOutputColorSpace(m_pVP, &_outColorSpace);
  86. }
  87. /// Obtain Video Processor Input view from input texture
  88. ID3D11VideoProcessorInputView* pVPIn = nullptr;
  89. D3D11_VIDEO_PROCESSOR_INPUT_VIEW_DESC inputVD = {0, D3D11_VPIV_DIMENSION_TEXTURE2D, {0, 0}};
  90. hr = m_pVid->CreateVideoProcessorInputView(pIn, m_pVPEnum, &inputVD, &pVPIn);
  91. if (FAILED(hr)) {
  92. PRINTERR(hr, "CreateVideoProcessInputView");
  93. return hr;
  94. }
  95. /// Obtain Video Processor Output view from output texture
  96. ID3D11VideoProcessorOutputView* pVPOV = nullptr;
  97. D3D11_VIDEO_PROCESSOR_OUTPUT_VIEW_DESC ovD = {D3D11_VPOV_DIMENSION_TEXTURE2D};
  98. hr = m_pVid->CreateVideoProcessorOutputView(pOut, m_pVPEnum, &ovD, &pVPOV);
  99. if (FAILED(hr)) {
  100. SAFE_RELEASE(pVPIn);
  101. PRINTERR(hr, "CreateVideoProcessorOutputView");
  102. return hr;
  103. }
  104. /// Create a Video Processor Stream to run the operation
  105. D3D11_VIDEO_PROCESSOR_STREAM stream = {TRUE, 0, 0, 0, 0, nullptr, pVPIn, nullptr};
  106. /// Perform the Colorspace conversion
  107. hr = m_pVidCtx->VideoProcessorBlt(m_pVP, pVPOV, 0, 1, &stream);
  108. if (FAILED(hr)) {
  109. SAFE_RELEASE(pVPIn);
  110. PRINTERR(hr, "VideoProcessorBlt");
  111. return hr;
  112. }
  113. SAFE_RELEASE(pVPIn);
  114. SAFE_RELEASE(pVPOV);
  115. return hr;
  116. }