diff --git a/src/filters/transform/vsfilter/Copy.cpp b/src/filters/transform/vsfilter/Copy.cpp index 0eb3c4108..368fc9d3c 100644 --- a/src/filters/transform/vsfilter/Copy.cpp +++ b/src/filters/transform/vsfilter/Copy.cpp @@ -255,7 +255,7 @@ void CDirectVobSubFilter::PrintMessages(BYTE* pOut) //color space tmp.Format( _T("Colorspace: %ls %ls (%ls)\n"), ColorConvTable::GetDefaultRangeType()==ColorConvTable::RANGE_PC ? _T("PC"):_T("TV"), - ColorConvTable::GetDefaultYUVType()==ColorConvTable::BT601 ? _T("BT.601"):_T("BT.709"), + ColorConvTable::GetDefaultYUVType()==ColorConvTable::BT601 ? _T("BT.601"): (ColorConvTable::GetDefaultYUVType()==ColorConvTable::BT709 ? _T("BT.709"):_T("BT.2020")), m_xy_int_opt[INT_COLOR_SPACE]==CDirectVobSub::YuvMatrix_AUTO ? _T("Auto") : m_xy_int_opt[INT_COLOR_SPACE]==CDirectVobSub::GUESS ? _T("Guessed") : _T("Forced") ); msg += tmp; diff --git a/src/filters/transform/vsfilter/DirectVobSub.cpp b/src/filters/transform/vsfilter/DirectVobSub.cpp index 69c7eb999..fcaf573ad 100644 --- a/src/filters/transform/vsfilter/DirectVobSub.cpp +++ b/src/filters/transform/vsfilter/DirectVobSub.cpp @@ -1072,6 +1072,7 @@ CDirectVobSub::CDirectVobSub( const Option *options, CCritSec * pLock ) if( m_xy_int_opt[INT_COLOR_SPACE]!=YuvMatrix_AUTO && m_xy_int_opt[INT_COLOR_SPACE]!=BT_601 && m_xy_int_opt[INT_COLOR_SPACE]!=BT_709 && + m_xy_int_opt[INT_COLOR_SPACE]!=BT_2020 && m_xy_int_opt[INT_COLOR_SPACE]!=GUESS) { m_xy_int_opt[INT_COLOR_SPACE] = YuvMatrix_AUTO; @@ -1258,6 +1259,10 @@ CDirectVobSub::CDirectVobSub( const Option *options, CCritSec * pLock ) { m_xy_str_opt[STRING_PGS_YUV_MATRIX] = _T("BT709"); } + else if (str_pgs_yuv_setting.Right(4).CompareNoCase(_T("2020"))==0) + { + m_xy_str_opt[STRING_PGS_YUV_MATRIX] = _T("BT2020"); + } else { m_xy_str_opt[STRING_PGS_YUV_MATRIX] = _T("GUESS"); @@ -1477,6 +1482,10 @@ CDVS4XySubFilter::CDVS4XySubFilter( const Option *options, CCritSec * pLock ) { m_xy_int_opt[INT_COLOR_SPACE] = DirectVobSubImpl::BT_709; } + else if (str_color_space.Right(4).CompareNoCase(_T("2020"))==0) + { + m_xy_int_opt[INT_COLOR_SPACE] = DirectVobSubImpl::BT_2020; + } else if (str_color_space.Right(5).CompareNoCase(_T("GUESS"))==0) { m_xy_int_opt[INT_COLOR_SPACE] = DirectVobSubImpl::GUESS; @@ -1614,6 +1623,10 @@ CDVS4XySubFilter::CDVS4XySubFilter( const Option *options, CCritSec * pLock ) { m_xy_str_opt[STRING_PGS_YUV_MATRIX] = _T("BT709"); } + else if (str_pgs_yuv_setting.Right(4).CompareNoCase(_T("2020"))==0) + { + m_xy_str_opt[STRING_PGS_YUV_MATRIX] = _T("BT2020"); + } else { m_xy_str_opt[STRING_PGS_YUV_MATRIX] = _T("GUESS"); @@ -1706,6 +1719,9 @@ STDMETHODIMP CDVS4XySubFilter::UpdateRegistry() case DirectVobSubImpl::BT_709: str_color_space += _T(".BT709"); break; + case DirectVobSubImpl::BT_2020: + str_color_space += _T(".BT2020"); + break; case DirectVobSubImpl::GUESS: str_color_space += _T(".GUESS"); break; diff --git a/src/filters/transform/vsfilter/DirectVobSub.h b/src/filters/transform/vsfilter/DirectVobSub.h index 1ca5e898c..e2e3cffea 100644 --- a/src/filters/transform/vsfilter/DirectVobSub.h +++ b/src/filters/transform/vsfilter/DirectVobSub.h @@ -38,6 +38,7 @@ class DirectVobSubImpl : public IDirectVobSub2, public XyOptionsImpl, public IFi YuvMatrix_AUTO = 0 ,BT_601 ,BT_709 + ,BT_2020 ,GUESS }; enum YuvRange diff --git a/src/filters/transform/vsfilter/DirectVobSubFilter.cpp b/src/filters/transform/vsfilter/DirectVobSubFilter.cpp index 4edddd505..da0e59e8e 100644 --- a/src/filters/transform/vsfilter/DirectVobSubFilter.cpp +++ b/src/filters/transform/vsfilter/DirectVobSubFilter.cpp @@ -1713,6 +1713,9 @@ void CDirectVobSubFilter::SetSubtitle(ISubStream* pSubStream, bool fApplyDefStyl case CSimpleTextSubtitle::YCbCrMatrix_BT709: m_video_yuv_matrix_decided_by_sub = ColorConvTable::BT709; break; + case CSimpleTextSubtitle::YCbCrMatrix_BT2020: + m_video_yuv_matrix_decided_by_sub = ColorConvTable::BT2020; + break; default: m_video_yuv_matrix_decided_by_sub = ColorConvTable::NONE; break; @@ -1753,6 +1756,10 @@ void CDirectVobSubFilter::SetSubtitle(ISubStream* pSubStream, bool fApplyDefStyl { color_type = CompositionObject::YUV_Rec709; } + else if ( m_xy_str_opt[STRING_PGS_YUV_MATRIX].CompareNoCase(_T("BT2020"))==0 ) + { + color_type = CompositionObject::YUV_Rec2020; + } m_video_yuv_matrix_decided_by_sub = (m_w > m_bt601Width || m_h > m_bt601Height) ? ColorConvTable::BT709 : ColorConvTable::BT601; @@ -2132,6 +2139,10 @@ void CDirectVobSubFilter::SetYuvMatrix() { yuv_matrix = ColorConvTable::BT709; } + else if (m_xy_str_opt[STRING_CONSUMER_YUV_MATRIX].Right(4).CompareNoCase(L"2020")==0) + { + yuv_matrix = ColorConvTable::BT2020; + } else { XY_LOG_WARN(L"Can NOT get useful YUV range from consumer:"< m_bt601Width || m_h > m_bt601Height) ? ColorConvTable::BT709 : ColorConvTable::BT601; diff --git a/src/filters/transform/vsfilter/DirectVobSubPropPage.cpp b/src/filters/transform/vsfilter/DirectVobSubPropPage.cpp index 22afd7105..996be9105 100644 --- a/src/filters/transform/vsfilter/DirectVobSubPropPage.cpp +++ b/src/filters/transform/vsfilter/DirectVobSubPropPage.cpp @@ -872,6 +872,7 @@ void CDVSMiscPPage::UpdateControlData(bool fSave) if( m_colorSpace != CDirectVobSub::YuvMatrix_AUTO && m_colorSpace != CDirectVobSub::BT_601 && m_colorSpace != CDirectVobSub::BT_709 && + m_colorSpace != CDirectVobSub::BT_2020 && m_colorSpace != CDirectVobSub::GUESS ) { m_colorSpace = CDirectVobSub::YuvMatrix_AUTO; @@ -883,6 +884,8 @@ void CDVSMiscPPage::UpdateControlData(bool fSave) m_colorSpaceDropList.SetItemData( CDirectVobSub::BT_601, CDirectVobSub::BT_601 ); m_colorSpaceDropList.AddString( CString(_T("BT.709")) ); m_colorSpaceDropList.SetItemData( CDirectVobSub::BT_709, CDirectVobSub::BT_709); + m_colorSpaceDropList.AddString( CString(_T("BT.2020")) ); + m_colorSpaceDropList.SetItemData( CDirectVobSub::BT_2020, CDirectVobSub::BT_2020); m_colorSpaceDropList.AddString( CString(_T("Guess")) ); m_colorSpaceDropList.SetItemData( CDirectVobSub::GUESS, CDirectVobSub::GUESS ); m_colorSpaceDropList.SetCurSel( m_colorSpace ); @@ -2243,6 +2246,7 @@ void CXySubFilterMorePPage::UpdateControlData(bool fSave) if( m_yuv_matrix != CDirectVobSub::YuvMatrix_AUTO && m_yuv_matrix != CDirectVobSub::BT_601 && m_yuv_matrix != CDirectVobSub::BT_709 && + m_yuv_matrix != CDirectVobSub::BT_2020 && m_yuv_matrix != CDirectVobSub::GUESS ) { m_yuv_matrix = CDirectVobSub::YuvMatrix_AUTO; @@ -2254,6 +2258,8 @@ void CXySubFilterMorePPage::UpdateControlData(bool fSave) m_combo_yuv_matrix.SetItemData( CDirectVobSub::BT_601, CDirectVobSub::BT_601 ); m_combo_yuv_matrix.AddString( CString(_T("BT.709")) ); m_combo_yuv_matrix.SetItemData( CDirectVobSub::BT_709, CDirectVobSub::BT_709); + m_combo_yuv_matrix.AddString( CString(_T("BT.2020")) ); + m_combo_yuv_matrix.SetItemData( CDirectVobSub::BT_2020, CDirectVobSub::BT_2020); m_combo_yuv_matrix.AddString( CString(_T("Guess")) ); m_combo_yuv_matrix.SetItemData( CDirectVobSub::GUESS, CDirectVobSub::GUESS ); m_combo_yuv_matrix.SetCurSel( m_yuv_matrix ); diff --git a/src/filters/transform/vsfilter/plugins.cpp b/src/filters/transform/vsfilter/plugins.cpp index a26f0db8c..8143bf0d7 100644 --- a/src/filters/transform/vsfilter/plugins.cpp +++ b/src/filters/transform/vsfilter/plugins.cpp @@ -125,6 +125,9 @@ class CFilter : public CUnknown, public CDirectVobSub, public CAMThread, public case CSimpleTextSubtitle::YCbCrMatrix_BT709: yuv_matrix = ColorConvTable::BT709; break; + case CSimpleTextSubtitle::YCbCrMatrix_BT2020: + yuv_matrix = ColorConvTable::BT2020; + break; case CSimpleTextSubtitle::YCbCrMatrix_AUTO: default: yuv_matrix = ColorConvTable::BT601; @@ -141,6 +144,9 @@ class CFilter : public CUnknown, public CDirectVobSub, public CAMThread, public case CDirectVobSub::BT_709: yuv_matrix = ColorConvTable::BT709; break; + case CDirectVobSub::BT_2020: + yuv_matrix = ColorConvTable::BT2020; + break; case CDirectVobSub::GUESS: yuv_matrix = (dst.w > m_bt601Width || dst.h > m_bt601Height) ? ColorConvTable::BT709 : ColorConvTable::BT601; break; diff --git a/src/filters/transform/vsfilter/xy_sub_filter.cpp b/src/filters/transform/vsfilter/xy_sub_filter.cpp index 814b49f2f..e3232e545 100644 --- a/src/filters/transform/vsfilter/xy_sub_filter.cpp +++ b/src/filters/transform/vsfilter/xy_sub_filter.cpp @@ -1315,6 +1315,10 @@ void XySubFilter::SetYuvMatrix() { yuv_matrix = ColorConvTable::BT709; } + else if (m_xy_str_opt[STRING_CONSUMER_YUV_MATRIX].Right(4).CompareNoCase(L"2020")==0) + { + yuv_matrix = ColorConvTable::BT2020; + } else { XY_LOG_WARN(L"Can NOT get useful YUV range from consumer:"< m_bt601Width || m_h > m_bt601Height) ? ColorConvTable::BT709 : ColorConvTable::BT601; @@ -1270,7 +1273,7 @@ void XySubFilterConsumer::PrintMessages(BYTE* pOut) //color space tmp.Format( _T("Colorspace: %ls %ls (%ls)\n"), ColorConvTable::GetDefaultRangeType()==ColorConvTable::RANGE_PC ? _T("PC"):_T("TV"), - ColorConvTable::GetDefaultYUVType()==ColorConvTable::BT601 ? _T("BT.601"):_T("BT.709"), + ColorConvTable::GetDefaultYUVType()==ColorConvTable::BT601 ? _T("BT.601"):(ColorConvTable::GetDefaultYUVType()==ColorConvTable::BT2020 ? _T("BT.2020"):_T("BT.709")), m_xy_int_opt[INT_COLOR_SPACE]==CDirectVobSub::YuvMatrix_AUTO ? _T("Auto") : m_xy_int_opt[INT_COLOR_SPACE]==CDirectVobSub::GUESS ? _T("Guessed") : _T("Forced") ); msg += tmp; diff --git a/src/subpic/color_conv_table.cpp b/src/subpic/color_conv_table.cpp index c8a50239a..5d0a2c980 100644 --- a/src/subpic/color_conv_table.cpp +++ b/src/subpic/color_conv_table.cpp @@ -52,11 +52,13 @@ { 1, 2*(1-Kb) , 0 , 0} \ } -const float MATRIX_BT_601 [3][4] = DEFINE_YUV_MATRIX (0.299f , 0.587f , 0.114f ); -const float MATRIX_BT_601_INV[3][4] = DEFINE_YUV_MATRIX_INV(0.299f , 0.587f , 0.114f ); -const float MATRIX_BT_709 [3][4] = DEFINE_YUV_MATRIX (0.2126f, 0.7152f, 0.0722f); -const float MATRIX_BT_709_INV[3][4] = DEFINE_YUV_MATRIX_INV(0.2126f, 0.7152f, 0.0722f); -const float YUV_PC [3][4] = { +const float MATRIX_BT_601 [3][4] = DEFINE_YUV_MATRIX (0.299f , 0.587f , 0.114f ); +const float MATRIX_BT_601_INV [3][4] = DEFINE_YUV_MATRIX_INV(0.299f , 0.587f , 0.114f ); +const float MATRIX_BT_709 [3][4] = DEFINE_YUV_MATRIX (0.2126f, 0.7152f, 0.0722f); +const float MATRIX_BT_709_INV [3][4] = DEFINE_YUV_MATRIX_INV(0.2126f, 0.7152f, 0.0722f); +const float MATRIX_BT_2020 [3][4] = DEFINE_YUV_MATRIX (0.2627f, 0.678f , 0.0593f); +const float MATRIX_BT_2020_INV[3][4] = DEFINE_YUV_MATRIX_INV(0.2627f, 0.678f , 0.0593f); +const float YUV_PC [3][4] = { {255, 0, 0, 0}, { 0, 255, 0, 128}, { 0, 0, 255, 128} @@ -157,6 +159,7 @@ class ConvMatrix { COLOR_YUV_601, COLOR_YUV_709, + COLOR_YUV_2020, COLOR_RGB, COLOR_COUNT }; @@ -203,40 +206,50 @@ ConvMatrix::~ConvMatrix() bool ConvMatrix::Init() { - MATRIX_DE_QUAN[LEVEL_TV][COLOR_YUV_601] = &YUV_TV_INV[0][0]; - MATRIX_DE_QUAN[LEVEL_TV][COLOR_YUV_709] = &YUV_TV_INV[0][0]; - MATRIX_DE_QUAN[LEVEL_TV][COLOR_RGB ] = &RGB_TV_INV[0][0]; - - MATRIX_DE_QUAN[LEVEL_PC][COLOR_YUV_601] = &YUV_PC_INV[0][0]; - MATRIX_DE_QUAN[LEVEL_PC][COLOR_YUV_709] = &YUV_PC_INV[0][0]; - MATRIX_DE_QUAN[LEVEL_PC][COLOR_RGB ] = &RGB_PC_INV[0][0]; - - MATRIX_INV_TRANS[COLOR_YUV_601] = &MATRIX_BT_601_INV[0][0]; - MATRIX_INV_TRANS[COLOR_YUV_709] = &MATRIX_BT_709_INV[0][0]; - MATRIX_INV_TRANS[COLOR_RGB ] = &IDENTITY[0][0]; - - MATRIX_TRANS[COLOR_YUV_601] = &MATRIX_BT_601[0][0]; - MATRIX_TRANS[COLOR_YUV_709] = &MATRIX_BT_709[0][0]; - MATRIX_TRANS[COLOR_RGB ] = &IDENTITY[0][0]; - - MATRIX_QUAN[LEVEL_TV][COLOR_YUV_601] = &YUV_TV[0][0]; - MATRIX_QUAN[LEVEL_TV][COLOR_YUV_709] = &YUV_TV[0][0]; - MATRIX_QUAN[LEVEL_TV][COLOR_RGB ] = &RGB_TV[0][0]; - - MATRIX_QUAN[LEVEL_PC][COLOR_YUV_601] = &YUV_PC[0][0]; - MATRIX_QUAN[LEVEL_PC][COLOR_YUV_709] = &YUV_PC[0][0]; - MATRIX_QUAN[LEVEL_PC][COLOR_RGB ] = &RGB_PC[0][0]; + MATRIX_DE_QUAN[LEVEL_TV][COLOR_YUV_601 ] = &YUV_TV_INV[0][0]; + MATRIX_DE_QUAN[LEVEL_TV][COLOR_YUV_709 ] = &YUV_TV_INV[0][0]; + MATRIX_DE_QUAN[LEVEL_TV][COLOR_YUV_2020] = &YUV_TV_INV[0][0]; + MATRIX_DE_QUAN[LEVEL_TV][COLOR_RGB ] = &RGB_TV_INV[0][0]; + + MATRIX_DE_QUAN[LEVEL_PC][COLOR_YUV_601 ] = &YUV_PC_INV[0][0]; + MATRIX_DE_QUAN[LEVEL_PC][COLOR_YUV_709 ] = &YUV_PC_INV[0][0]; + MATRIX_DE_QUAN[LEVEL_PC][COLOR_YUV_2020] = &YUV_PC_INV[0][0]; + MATRIX_DE_QUAN[LEVEL_PC][COLOR_RGB ] = &RGB_PC_INV[0][0]; + + MATRIX_INV_TRANS[COLOR_YUV_601 ] = &MATRIX_BT_601_INV[0][0]; + MATRIX_INV_TRANS[COLOR_YUV_709 ] = &MATRIX_BT_709_INV[0][0]; + MATRIX_INV_TRANS[COLOR_YUV_2020] = &MATRIX_BT_2020_INV[0][0]; + MATRIX_INV_TRANS[COLOR_RGB ] = &IDENTITY[0][0]; + + MATRIX_TRANS[COLOR_YUV_601 ] = &MATRIX_BT_601[0][0]; + MATRIX_TRANS[COLOR_YUV_709 ] = &MATRIX_BT_709[0][0]; + MATRIX_TRANS[COLOR_YUV_2020] = &MATRIX_BT_2020[0][0]; + MATRIX_TRANS[COLOR_RGB ] = &IDENTITY[0][0]; + + MATRIX_QUAN[LEVEL_TV][COLOR_YUV_601 ] = &YUV_TV[0][0]; + MATRIX_QUAN[LEVEL_TV][COLOR_YUV_709 ] = &YUV_TV[0][0]; + MATRIX_QUAN[LEVEL_TV][COLOR_YUV_2020] = &YUV_TV[0][0]; + MATRIX_QUAN[LEVEL_TV][COLOR_RGB ] = &RGB_TV[0][0]; + + MATRIX_QUAN[LEVEL_PC][COLOR_YUV_601 ] = &YUV_PC[0][0]; + MATRIX_QUAN[LEVEL_PC][COLOR_YUV_709 ] = &YUV_PC[0][0]; + MATRIX_QUAN[LEVEL_PC][COLOR_YUV_2020] = &YUV_PC[0][0]; + MATRIX_QUAN[LEVEL_PC][COLOR_RGB ] = &RGB_PC[0][0]; InitVSFilterCompactCorretionMatrix(); //InitMatrix(LEVEL_PC, COLOR_RGB, LEVEL_TV, COLOR_YUV_601); //InitMatrix(LEVEL_PC, COLOR_RGB, LEVEL_TV, COLOR_YUV_709); + //InitMatrix(LEVEL_PC, COLOR_RGB, LEVEL_TV, COLOR_YUV_2020); //InitMatrix(LEVEL_TV, COLOR_YUV_601, LEVEL_PC, COLOR_RGB); //InitMatrix(LEVEL_TV, COLOR_YUV_709, LEVEL_PC, COLOR_RGB); + //InitMatrix(LEVEL_TV, COLOR_YUV_2020, LEVEL_PC, COLOR_RGB); //InitMatrix(LEVEL_TV, COLOR_RGB, LEVEL_TV, COLOR_YUV_601); //InitMatrix(LEVEL_TV, COLOR_RGB, LEVEL_TV, COLOR_YUV_709); + //InitMatrix(LEVEL_TV, COLOR_RGB, LEVEL_TV, COLOR_YUV_2020); //InitMatrix(LEVEL_TV, COLOR_YUV_601, LEVEL_TV, COLOR_RGB); //InitMatrix(LEVEL_TV, COLOR_YUV_709, LEVEL_TV, COLOR_RGB); + //InitMatrix(LEVEL_TV, COLOR_YUV_2020, LEVEL_TV, COLOR_RGB); return true; }; @@ -442,55 +455,75 @@ DWORD func(int r8, int g8, int b8) return y; \ } -DWORD RGB_PC_TO_YUV_TV_601(int r8, int g8, int b8); -DWORD RGB_PC_TO_YUV_PC_601(int r8, int g8, int b8); -DWORD RGB_PC_TO_YUV_TV_709(int r8, int g8, int b8); -DWORD RGB_PC_TO_YUV_PC_709(int r8, int g8, int b8); - -DWORD RGB_TV_TO_YUV_TV_601(int r8, int g8, int b8); -DWORD RGB_TV_TO_YUV_PC_601(int r8, int g8, int b8); -DWORD RGB_TV_TO_YUV_TV_709(int r8, int g8, int b8); -DWORD RGB_TV_TO_YUV_PC_709(int r8, int g8, int b8); - -DWORD RGB_PC_TO_UYV_TV_601(int r8, int g8, int b8); -DWORD RGB_PC_TO_UYV_PC_601(int r8, int g8, int b8); -DWORD RGB_PC_TO_UYV_TV_709(int r8, int g8, int b8); -DWORD RGB_PC_TO_UYV_PC_709(int r8, int g8, int b8); - -DWORD RGB_TV_TO_UYV_TV_601(int r8, int g8, int b8); -DWORD RGB_TV_TO_UYV_PC_601(int r8, int g8, int b8); -DWORD RGB_TV_TO_UYV_TV_709(int r8, int g8, int b8); -DWORD RGB_TV_TO_UYV_PC_709(int r8, int g8, int b8); - -DWORD PREMUL_ARGB_PC_TO_AYUV_TV_601(int a8, int r8, int g8, int b8); -DWORD PREMUL_ARGB_PC_TO_AYUV_PC_601(int a8, int r8, int g8, int b8); -DWORD PREMUL_ARGB_PC_TO_AYUV_TV_709(int a8, int r8, int g8, int b8); -DWORD PREMUL_ARGB_PC_TO_AYUV_PC_709(int a8, int r8, int g8, int b8); - -DWORD PREMUL_ARGB_TV_TO_AYUV_TV_601(int a8, int r8, int g8, int b8); -DWORD PREMUL_ARGB_TV_TO_AYUV_PC_601(int a8, int r8, int g8, int b8); -DWORD PREMUL_ARGB_TV_TO_AYUV_TV_709(int a8, int r8, int g8, int b8); -DWORD PREMUL_ARGB_TV_TO_AYUV_PC_709(int a8, int r8, int g8, int b8); - -DWORD RGB_PC_TO_Y_TV_601(int r8, int g8, int b8); -DWORD RGB_PC_TO_Y_PC_601(int r8, int g8, int b8); -DWORD RGB_PC_TO_Y_TV_709(int r8, int g8, int b8); -DWORD RGB_PC_TO_Y_PC_709(int r8, int g8, int b8); - -DWORD RGB_TV_TO_Y_TV_601(int r8, int g8, int b8); -DWORD RGB_TV_TO_Y_PC_601(int r8, int g8, int b8); -DWORD RGB_TV_TO_Y_TV_709(int r8, int g8, int b8); -DWORD RGB_TV_TO_Y_PC_709(int r8, int g8, int b8); - -DWORD YUV_TV_TO_RGB_PC_601(int y, int u, int v); -DWORD YUV_PC_TO_RGB_PC_601(int y, int u, int v); -DWORD YUV_TV_TO_RGB_PC_709(int y, int u, int v); -DWORD YUV_PC_TO_RGB_PC_709(int y, int u, int v); - -DWORD YUV_TV_TO_RGB_TV_601(int y, int u, int v); -DWORD YUV_PC_TO_RGB_TV_601(int y, int u, int v); -DWORD YUV_TV_TO_RGB_TV_709(int y, int u, int v); -DWORD YUV_PC_TO_RGB_TV_709(int y, int u, int v); +DWORD RGB_PC_TO_YUV_TV_601 (int r8, int g8, int b8); +DWORD RGB_PC_TO_YUV_PC_601 (int r8, int g8, int b8); +DWORD RGB_PC_TO_YUV_TV_709 (int r8, int g8, int b8); +DWORD RGB_PC_TO_YUV_PC_709 (int r8, int g8, int b8); +DWORD RGB_PC_TO_YUV_TV_2020(int r8, int g8, int b8); +DWORD RGB_PC_TO_YUV_PC_2020(int r8, int g8, int b8); + +DWORD RGB_TV_TO_YUV_TV_601 (int r8, int g8, int b8); +DWORD RGB_TV_TO_YUV_PC_601 (int r8, int g8, int b8); +DWORD RGB_TV_TO_YUV_TV_709 (int r8, int g8, int b8); +DWORD RGB_TV_TO_YUV_PC_709 (int r8, int g8, int b8); +DWORD RGB_TV_TO_YUV_TV_2020(int r8, int g8, int b8); +DWORD RGB_TV_TO_YUV_PC_2020(int r8, int g8, int b8); + +DWORD RGB_PC_TO_UYV_TV_601 (int r8, int g8, int b8); +DWORD RGB_PC_TO_UYV_PC_601 (int r8, int g8, int b8); +DWORD RGB_PC_TO_UYV_TV_709 (int r8, int g8, int b8); +DWORD RGB_PC_TO_UYV_PC_709 (int r8, int g8, int b8); +DWORD RGB_PC_TO_UYV_TV_2020(int r8, int g8, int b8); +DWORD RGB_PC_TO_UYV_PC_2020(int r8, int g8, int b8); + +DWORD RGB_TV_TO_UYV_TV_601 (int r8, int g8, int b8); +DWORD RGB_TV_TO_UYV_PC_601 (int r8, int g8, int b8); +DWORD RGB_TV_TO_UYV_TV_709 (int r8, int g8, int b8); +DWORD RGB_TV_TO_UYV_PC_709 (int r8, int g8, int b8); +DWORD RGB_TV_TO_UYV_TV_2020(int r8, int g8, int b8); +DWORD RGB_TV_TO_UYV_PC_2020(int r8, int g8, int b8); + +DWORD PREMUL_ARGB_PC_TO_AYUV_TV_601 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_PC_TO_AYUV_PC_601 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_PC_TO_AYUV_TV_709 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_PC_TO_AYUV_PC_709 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_PC_TO_AYUV_TV_2020(int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_PC_TO_AYUV_PC_2020(int a8, int r8, int g8, int b8); + +DWORD PREMUL_ARGB_TV_TO_AYUV_TV_601 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_TV_TO_AYUV_PC_601 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_TV_TO_AYUV_TV_709 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_TV_TO_AYUV_PC_709 (int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_TV_TO_AYUV_TV_2020(int a8, int r8, int g8, int b8); +DWORD PREMUL_ARGB_TV_TO_AYUV_PC_2020(int a8, int r8, int g8, int b8); + +DWORD RGB_PC_TO_Y_TV_601 (int r8, int g8, int b8); +DWORD RGB_PC_TO_Y_PC_601 (int r8, int g8, int b8); +DWORD RGB_PC_TO_Y_TV_709 (int r8, int g8, int b8); +DWORD RGB_PC_TO_Y_PC_709 (int r8, int g8, int b8); +DWORD RGB_PC_TO_Y_TV_2020(int r8, int g8, int b8); +DWORD RGB_PC_TO_Y_PC_2020(int r8, int g8, int b8); + +DWORD RGB_TV_TO_Y_TV_601 (int r8, int g8, int b8); +DWORD RGB_TV_TO_Y_PC_601 (int r8, int g8, int b8); +DWORD RGB_TV_TO_Y_TV_709 (int r8, int g8, int b8); +DWORD RGB_TV_TO_Y_PC_709 (int r8, int g8, int b8); +DWORD RGB_TV_TO_Y_TV_2020(int r8, int g8, int b8); +DWORD RGB_TV_TO_Y_PC_2020(int r8, int g8, int b8); + +DWORD YUV_TV_TO_RGB_PC_601 (int y, int u, int v); +DWORD YUV_PC_TO_RGB_PC_601 (int y, int u, int v); +DWORD YUV_TV_TO_RGB_PC_709 (int y, int u, int v); +DWORD YUV_PC_TO_RGB_PC_709 (int y, int u, int v); +DWORD YUV_TV_TO_RGB_PC_2020(int y, int u, int v); +DWORD YUV_PC_TO_RGB_PC_2020(int y, int u, int v); + +DWORD YUV_TV_TO_RGB_TV_601 (int y, int u, int v); +DWORD YUV_PC_TO_RGB_TV_601 (int y, int u, int v); +DWORD YUV_TV_TO_RGB_TV_709 (int y, int u, int v); +DWORD YUV_PC_TO_RGB_TV_709 (int y, int u, int v); +DWORD YUV_TV_TO_RGB_TV_2020(int y, int u, int v); +DWORD YUV_PC_TO_RGB_TV_2020(int y, int u, int v); typedef ColorConvTable::YuvMatrixType YuvMatrixType; typedef ColorConvTable::YuvRangeType YuvRangeType; @@ -546,6 +579,17 @@ bool ConvFunc::InitConvFunc(YuvMatrixType yuv_type, YuvRangeType range) _yuv_type = yuv_type; _range_type = range; } + else if ( yuv_type==ColorConvTable::BT2020 && range==ColorConvTable::RANGE_TV ) + { + r8g8b8_to_yuv_func = RGB_PC_TO_YUV_TV_2020; + r8g8b8_to_uyv_func = RGB_PC_TO_UYV_TV_2020; + pre_mul_argb_to_ayuv_func = PREMUL_ARGB_PC_TO_AYUV_TV_2020; + r8g8b8_to_y_func = RGB_PC_TO_Y_TV_2020; + y8u8v8_to_rgb_func = YUV_TV_TO_RGB_PC_2020; + + _yuv_type = yuv_type; + _range_type = range; + } else if ( yuv_type==ColorConvTable::BT601 && range==ColorConvTable::RANGE_PC ) { r8g8b8_to_yuv_func = RGB_PC_TO_YUV_PC_601; @@ -568,6 +612,17 @@ bool ConvFunc::InitConvFunc(YuvMatrixType yuv_type, YuvRangeType range) _yuv_type = yuv_type; _range_type = range; } + else if ( yuv_type==ColorConvTable::BT2020 && range==ColorConvTable::RANGE_PC ) + { + r8g8b8_to_yuv_func = RGB_PC_TO_YUV_PC_2020; + r8g8b8_to_uyv_func = RGB_PC_TO_UYV_PC_2020; + pre_mul_argb_to_ayuv_func = PREMUL_ARGB_PC_TO_AYUV_PC_2020; + r8g8b8_to_y_func = RGB_PC_TO_Y_PC_2020; + y8u8v8_to_rgb_func = YUV_PC_TO_RGB_PC_2020; + + _yuv_type = yuv_type; + _range_type = range; + } else { r8g8b8_to_yuv_func = RGB_PC_TO_YUV_TV_601; @@ -586,6 +641,7 @@ bool ConvFunc::InitConvFunc(YuvMatrixType yuv_type, YuvRangeType range) ConvFunc::ConvFunc( YuvMatrixType yuv_type, YuvRangeType range ) { _conv_matrix.Init(); + _conv_matrix.InitMatrix( ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_601, ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_709); @@ -599,6 +655,19 @@ ConvFunc::ConvFunc( YuvMatrixType yuv_type, YuvRangeType range ) ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_601, ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_709); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_601, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_601, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_601, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_601, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_709, ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_601); @@ -611,6 +680,46 @@ ConvFunc::ConvFunc( YuvMatrixType yuv_type, YuvRangeType range ) _conv_matrix.InitMatrix( ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_709, ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_601); + + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_709, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_709, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_709, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_709, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020); + + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_601); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_601); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_601); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_601); + + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_709); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_709); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_TV, ConvMatrix::COLOR_YUV_709); + _conv_matrix.InitMatrix( + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_2020, + ConvMatrix::LEVEL_PC, ConvMatrix::COLOR_YUV_709); + InitConvFunc(yuv_type, range); } @@ -692,6 +801,14 @@ DWORD ColorConvTable::Ayuv2Argb_TV_BT709( DWORD ayuv ) return (ayuv & 0xff000000) | YUV_TV_TO_RGB_PC_709(y, u, v); } +DWORD ColorConvTable::Ayuv2Argb_TV_BT2020( DWORD ayuv ) +{ + int y = (ayuv & 0x00ff0000) >> 16; + int u = (ayuv & 0x0000ff00) >> 8; + int v = (ayuv & 0x000000ff); + return (ayuv & 0xff000000) | YUV_TV_TO_RGB_PC_2020(y, u, v); +} + DWORD ColorConvTable::Ayuv2Argb( DWORD ayuv ) { int y = (ayuv & 0x00ff0000) >> 16; @@ -720,6 +837,16 @@ DWORD ColorConvTable::A8Y8U8V8_To_ARGB_PC_BT709( int a8, int y8, int u8, int v8 return (a8<<24) | YUV_PC_TO_RGB_PC_709(y8, u8, v8); } +DWORD ColorConvTable::A8Y8U8V8_To_ARGB_TV_BT2020( int a8, int y8, int u8, int v8 ) +{ + return (a8<<24) | YUV_TV_TO_RGB_PC_2020(y8, u8, v8); +} + +DWORD ColorConvTable::A8Y8U8V8_To_ARGB_PC_BT2020( int a8, int y8, int u8, int v8 ) +{ + return (a8<<24) | YUV_PC_TO_RGB_PC_2020(y8, u8, v8); +} + DWORD ColorConvTable::A8Y8U8V8_PC_To_TV( int a8, int y8, int u8, int v8 ) { const int FRACTION_SCALE = 1<<16; @@ -765,10 +892,11 @@ DWORD ColorConvTable::A8Y8U8V8_TO_AYUV( int a8, int y8, int u8, int v8, ConvMatrix::LEVEL_TV, ConvMatrix::LEVEL_PC }; - const int type_map[3] = { + const int type_map[4] = { ConvMatrix::COLOR_YUV_601, ConvMatrix::COLOR_YUV_601, - ConvMatrix::COLOR_YUV_709 + ConvMatrix::COLOR_YUV_709, + ConvMatrix::COLOR_YUV_2020 }; //level_map[ColorConvTable::RANGE_NONE] = ConvMatrix::LEVEL_TV; @@ -777,6 +905,7 @@ DWORD ColorConvTable::A8Y8U8V8_TO_AYUV( int a8, int y8, int u8, int v8, //type_map[ColorConvTable::NONE] = ConvMatrix::COLOR_YUV_601; //type_map[ColorConvTable::BT601] = ConvMatrix::COLOR_YUV_601; //type_map[ColorConvTable::BT709] = ConvMatrix::COLOR_YUV_709; + //type_map[ColorConvTable::BT2020] = ConvMatrix::COLOR_YUV_2020; if (in_type==out_type) { if (in_range==RANGE_PC && out_range==RANGE_TV) @@ -805,17 +934,19 @@ DWORD ColorConvTable::A8Y8U8V8_TO_CUR_AYUV( int a8, int y8, int u8, int v8, YuvR DWORD ColorConvTable::A8Y8U8V8_TO_ARGB( int a8, int y8, int u8, int v8, YuvRangeType in_range, YuvMatrixType in_type , bool output_tv_level ) { - const ConvFunc::Y8U8V8ToRGBFunc funcs[2][2][2] = { + const ConvFunc::Y8U8V8ToRGBFunc funcs[2][3][2] = { { - {YUV_TV_TO_RGB_TV_601, YUV_TV_TO_RGB_PC_601}, - {YUV_TV_TO_RGB_TV_709, YUV_TV_TO_RGB_PC_709} + {YUV_TV_TO_RGB_TV_601, YUV_TV_TO_RGB_PC_601}, + {YUV_TV_TO_RGB_TV_709, YUV_TV_TO_RGB_PC_709}, + {YUV_TV_TO_RGB_TV_2020, YUV_TV_TO_RGB_PC_2020} }, { - {YUV_PC_TO_RGB_TV_601, YUV_PC_TO_RGB_PC_601}, - {YUV_PC_TO_RGB_TV_709, YUV_PC_TO_RGB_PC_709} + {YUV_PC_TO_RGB_TV_601, YUV_PC_TO_RGB_PC_601}, + {YUV_PC_TO_RGB_TV_709, YUV_PC_TO_RGB_PC_709}, + {YUV_PC_TO_RGB_TV_2020, YUV_PC_TO_RGB_PC_2020} } }; - return (a8<<24) | funcs[in_range==RANGE_PC?1:0][in_type==BT709?1:0][output_tv_level?0:1](y8,u8,v8); + return (a8<<24) | funcs[in_range==RANGE_PC?1:0][in_type==BT709?1:(in_type==BT2020?2:0)][output_tv_level?0:1](y8,u8,v8); } DWORD ColorConvTable::VSFilterCompactCorretion( DWORD argb, bool output_tv_level ) @@ -838,52 +969,72 @@ const YuvPos POS_YUV = {16, 8, 0}; const YuvPos POS_UYV = {8, 16, 0}; -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) - -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) - -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_UYV) -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_UYV) -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_UYV) -DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_UYV) - -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_UYV) -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_UYV) -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_UYV) -DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_UYV) - -DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_PC_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) -DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) -DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_PC_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) -DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) - -DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) -DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_TV_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) -DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) -DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_TV_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) - -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) - -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) -DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) - -DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) -DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) -DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) -DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) - -DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) -DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) -DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) -DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_TV_2020, RGB_LVL_PC, YUV_LVL_TV, 0.2627, 0.678 , 0.0593, POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_YUV_PC_2020, RGB_LVL_PC, YUV_LVL_PC, 0.2627, 0.678 , 0.0593, POS_YUV) + +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_TV_2020, RGB_LVL_TV, YUV_LVL_TV, 0.2627, 0.678 , 0.0593, POS_YUV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_YUV_PC_2020, RGB_LVL_TV, YUV_LVL_PC, 0.2627, 0.678 , 0.0593, POS_YUV) + +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_TV_2020, RGB_LVL_PC, YUV_LVL_TV, 0.2627, 0.678 , 0.0593, POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_PC_TO_UYV_PC_2020, RGB_LVL_PC, YUV_LVL_PC, 0.2627, 0.678 , 0.0593, POS_UYV) + +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_TV_2020, RGB_LVL_TV, YUV_LVL_TV, 0.2627, 0.678 , 0.0593, POS_UYV) +DEFINE_RGB2YUV_FUNC(RGB_TV_TO_UYV_PC_2020, RGB_LVL_TV, YUV_LVL_PC, 0.2627, 0.678 , 0.0593, POS_UYV) + +DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_PC_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) +DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) +DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_PC_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) +DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) +DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_PC_2020, RGB_LVL_PC, YUV_LVL_TV, 0.2627, 0.678 , 0.0593) +DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_PC_2020, RGB_LVL_PC, YUV_LVL_PC, 0.2627, 0.678 , 0.0593) + +DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) +DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_TV_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) +DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) +DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_TV_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) +DEFINE_YUV2RGB_FUNC(YUV_TV_TO_RGB_TV_2020, RGB_LVL_TV, YUV_LVL_TV, 0.2627, 0.678 , 0.0593) +DEFINE_YUV2RGB_FUNC(YUV_PC_TO_RGB_TV_2020, RGB_LVL_TV, YUV_LVL_PC, 0.2627, 0.678 , 0.0593) + +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_TV_2020, RGB_LVL_PC, YUV_LVL_TV, 0.2627, 0.678 , 0.0593, POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_PC_TO_AYUV_PC_2020, RGB_LVL_PC, YUV_LVL_PC, 0.2627, 0.678 , 0.0593, POS_YUV) + +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 , POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722, POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_TV_2020, RGB_LVL_TV, YUV_LVL_TV, 0.2627, 0.678 , 0.0593, POS_YUV) +DEFINE_PREMUL_ARGB2AYUV_FUNC(PREMUL_ARGB_TV_TO_AYUV_PC_2020, RGB_LVL_TV, YUV_LVL_PC, 0.2627, 0.678 , 0.0593, POS_YUV) + +DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_TV_601, RGB_LVL_PC, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) +DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_PC_601, RGB_LVL_PC, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) +DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_TV_709, RGB_LVL_PC, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) +DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_PC_709, RGB_LVL_PC, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) +DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_TV_2020, RGB_LVL_PC, YUV_LVL_TV, 0.2627, 0.678 , 0.0593) +DEFINE_RGB2Y_FUNC(RGB_PC_TO_Y_PC_2020, RGB_LVL_PC, YUV_LVL_PC, 0.2627, 0.678 , 0.0593) + +DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_TV_601, RGB_LVL_TV, YUV_LVL_TV, 0.299 , 0.587 , 0.114 ) +DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_PC_601, RGB_LVL_TV, YUV_LVL_PC, 0.299 , 0.587 , 0.114 ) +DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_TV_709, RGB_LVL_TV, YUV_LVL_TV, 0.2126, 0.7152, 0.0722) +DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_PC_709, RGB_LVL_TV, YUV_LVL_PC, 0.2126, 0.7152, 0.0722) +DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_TV_2020, RGB_LVL_TV, YUV_LVL_TV, 0.2627, 0.678 , 0.0593) +DEFINE_RGB2Y_FUNC(RGB_TV_TO_Y_PC_2020, RGB_LVL_TV, YUV_LVL_PC, 0.2627, 0.678 , 0.0593) diff --git a/src/subpic/color_conv_table.h b/src/subpic/color_conv_table.h index cc1a92172..83dd1004e 100644 --- a/src/subpic/color_conv_table.h +++ b/src/subpic/color_conv_table.h @@ -2,7 +2,7 @@ /* author: xy */ /* date: 20110914 */ /* description: color table for yuv rgb convertion, */ -/* support both bt.601 and bt.709 */ +/* support bt.601, bt.709 and bt.2020 */ /************************************************************************/ #ifndef __COLOR_CONV_TABLE_H_53D078BB_BBA1_441B_9728_67E29A1CB521__ #define __COLOR_CONV_TABLE_H_53D078BB_BBA1_441B_9728_67E29A1CB521__ @@ -16,6 +16,7 @@ struct ColorConvTable NONE , BT601 , BT709 + , BT2020 }; enum YuvRangeType @@ -44,6 +45,9 @@ struct ColorConvTable static DWORD Ayuv2Argb_TV_BT709(DWORD ayuv); static DWORD A8Y8U8V8_To_ARGB_TV_BT709( int a8, int y8, int u8, int v8 ); static DWORD A8Y8U8V8_To_ARGB_PC_BT709( int a8, int y8, int u8, int v8 ); + static DWORD Ayuv2Argb_TV_BT2020(DWORD ayuv); + static DWORD A8Y8U8V8_To_ARGB_TV_BT2020( int a8, int y8, int u8, int v8 ); + static DWORD A8Y8U8V8_To_ARGB_PC_BT2020( int a8, int y8, int u8, int v8 ); static DWORD A8Y8U8V8_PC_To_TV( int a8, int y8, int u8, int v8 ); static DWORD A8Y8U8V8_TV_To_PC( int a8, int y8, int u8, int v8 ); diff --git a/src/subtitles/CompositionObject.cpp b/src/subtitles/CompositionObject.cpp index a77fe9a9d..96968ca5a 100644 --- a/src/subtitles/CompositionObject.cpp +++ b/src/subtitles/CompositionObject.cpp @@ -73,6 +73,10 @@ void CompositionObject::InitColor(const SubPicDesc& spd) { cur_type = ColorConvTable::BT709; } + else if (m_OriginalColorType==YUV_Rec2020) + { + cur_type = ColorConvTable::BT2020; + } else { XY_LOG_ERROR("Not supported. "< 720 ? CompositionObject::YUV_Rec709 : CompositionObject::YUV_Rec601; + color_type = m_Display.width >= 720 ? CompositionObject::YUV_Rec709 : CompositionObject::YUV_Rec601; } pObject->SetPalette(pCLUT->size, pCLUT->palette, color_type, m_yuvRangeSetting==CompositionObject::RANGE_NONE ? CompositionObject::RANGE_TV : m_yuvRangeSetting); diff --git a/src/subtitles/HdmvSub.cpp b/src/subtitles/HdmvSub.cpp index 86c65a8ae..87dd406af 100644 --- a/src/subtitles/HdmvSub.cpp +++ b/src/subtitles/HdmvSub.cpp @@ -365,7 +365,7 @@ void CHdmvSub::Render(SubPicDesc& spd, REFERENCE_TIME rt, RECT& bbox) CompositionObject::ColorType color_type = m_colorTypeSetting; if (color_type==CompositionObject::NONE) { - color_type = pPresentationSegment->video_descriptor.nVideoWidth > 720 ? + color_type = pPresentationSegment->video_descriptor.nVideoWidth >= 720 ? CompositionObject::YUV_Rec709 : CompositionObject::YUV_Rec601; } pObject->SetPalette(pPresentationSegment->CLUT.size, pPresentationSegment->CLUT.palette, color_type, diff --git a/src/subtitles/STS.cpp b/src/subtitles/STS.cpp index 4eab80666..cb6e84b33 100644 --- a/src/subtitles/STS.cpp +++ b/src/subtitles/STS.cpp @@ -1640,6 +1640,11 @@ if(sver <= 4) style->scrAlignment = (style->scrAlignment&4) ? ((style->scrAlig ret.m_eYCbCrMatrix = CSimpleTextSubtitle::YCbCrMatrix_BT709; ret.m_eYCbCrRange = CSimpleTextSubtitle::YCbCrRange_TV; } + else if (buff.Left(7)==L"tv.2020") + { + ret.m_eYCbCrMatrix = CSimpleTextSubtitle::YCbCrMatrix_BT2020; + ret.m_eYCbCrRange = CSimpleTextSubtitle::YCbCrRange_TV; + } else if (buff.Left(6)==L"pc.601") { ret.m_eYCbCrMatrix = CSimpleTextSubtitle::YCbCrMatrix_BT601; @@ -1650,6 +1655,11 @@ if(sver <= 4) style->scrAlignment = (style->scrAlignment&4) ? ((style->scrAlig ret.m_eYCbCrMatrix = CSimpleTextSubtitle::YCbCrMatrix_BT709; ret.m_eYCbCrRange = CSimpleTextSubtitle::YCbCrRange_PC; } + else if (buff.Left(7)==L"pc.2020") + { + ret.m_eYCbCrMatrix = CSimpleTextSubtitle::YCbCrMatrix_BT2020; + ret.m_eYCbCrRange = CSimpleTextSubtitle::YCbCrRange_PC; + } } } // ret.Sort(); diff --git a/src/subtitles/STS.h b/src/subtitles/STS.h index f8cea6723..b441be460 100644 --- a/src/subtitles/STS.h +++ b/src/subtitles/STS.h @@ -200,6 +200,7 @@ class CSimpleTextSubtitle { YCbCrMatrix_BT601, YCbCrMatrix_BT709, + YCbCrMatrix_BT2020, YCbCrMatrix_AUTO }; enum YCbCrRange diff --git a/src/thirdparty/VirtualDub/Kasumi/h/uberblit_ycbcr_generic.h b/src/thirdparty/VirtualDub/Kasumi/h/uberblit_ycbcr_generic.h index 3b8af02e8..87e9f36d0 100644 --- a/src/thirdparty/VirtualDub/Kasumi/h/uberblit_ycbcr_generic.h +++ b/src/thirdparty/VirtualDub/Kasumi/h/uberblit_ycbcr_generic.h @@ -11,6 +11,7 @@ struct VDPixmapGenYCbCrBasis { extern const VDPixmapGenYCbCrBasis g_VDPixmapGenYCbCrBasis_601; extern const VDPixmapGenYCbCrBasis g_VDPixmapGenYCbCrBasis_709; +extern const VDPixmapGenYCbCrBasis g_VDPixmapGenYCbCrBasis_2020; //////////////////////////////////////////////////////////////////////////// diff --git a/src/thirdparty/VirtualDub/Kasumi/source/uberblit_ycbcr_generic.cpp b/src/thirdparty/VirtualDub/Kasumi/source/uberblit_ycbcr_generic.cpp index 3820c7254..53ed605a6 100644 --- a/src/thirdparty/VirtualDub/Kasumi/source/uberblit_ycbcr_generic.cpp +++ b/src/thirdparty/VirtualDub/Kasumi/source/uberblit_ycbcr_generic.cpp @@ -38,6 +38,15 @@ extern const VDPixmapGenYCbCrBasis g_VDPixmapGenYCbCrBasis_709 = { } }; +extern const VDPixmapGenYCbCrBasis g_VDPixmapGenYCbCrBasis_2020 = { + 0.2627f, + 0.0593f, + { + 0.0f, -0.164553f, 1.8814f, + 1.4746f, -0.571353f, 0.0f, + } +}; + //////////////////////////////////////////////////////////////////////////// VDPixmapGenYCbCrToRGB32Generic::VDPixmapGenYCbCrToRGB32Generic(const VDPixmapGenYCbCrBasis& basis, bool studioRGB) {