diff --git a/cfg/per-class/classA_randomaccess.cfg b/cfg/per-class/classA_randomaccess.cfg
new file mode 100644
index 0000000000000000000000000000000000000000..891dfa12e61ce1615e4b2d0140dae24f95040ec3
--- /dev/null
+++ b/cfg/per-class/classA_randomaccess.cfg
@@ -0,0 +1,13 @@
+CTUSize: 256
+MaxMTTHierarchyDepth: 4
+MaxMTTHierarchyDepthI: 4
+MaxMTTHierarchyDepthISliceL: 4
+MaxMTTHierarchyDepthISliceC: 4
+MaxBTLumaISlice: 128
+MaxBTChromaISlice: 128
+MaxBTNonISlice: 128
+MaxTTLumaISlice: 128
+MaxTTChromaISlice: 128
+MaxTTNonISlice: 128
+MaxMTTHierarchyDepthByTid: 333322
+QpOutValCb: 17 23 35 40
\ No newline at end of file
diff --git a/cfg/per-class/classB_randomaccess.cfg b/cfg/per-class/classB_randomaccess.cfg
new file mode 100644
index 0000000000000000000000000000000000000000..372093cbb68f8e6109fd2c6f46f5a1d896774248
--- /dev/null
+++ b/cfg/per-class/classB_randomaccess.cfg
@@ -0,0 +1,13 @@
+CTUSize: 128
+MaxMTTHierarchyDepth: 4
+MaxMTTHierarchyDepthI: 4
+MaxMTTHierarchyDepthISliceL: 4
+MaxMTTHierarchyDepthISliceC: 4
+MaxBTLumaISlice: 128
+MaxBTChromaISlice: 128
+MaxBTNonISlice: 128
+MaxTTLumaISlice: 128
+MaxTTChromaISlice: 128
+MaxTTNonISlice: 128
+MaxMTTHierarchyDepthByTid: 333322
+QpOutValCb: 17 23 35 40
\ No newline at end of file
diff --git a/cfg/per-class/classC_randomaccess.cfg b/cfg/per-class/classC_randomaccess.cfg
new file mode 100644
index 0000000000000000000000000000000000000000..180fc3a3eecfd004de7bf0e2afb3e697f609cb2b
--- /dev/null
+++ b/cfg/per-class/classC_randomaccess.cfg
@@ -0,0 +1,12 @@
+MaxMTTHierarchyDepth: 3
+MaxMTTHierarchyDepthI: 4
+MaxMTTHierarchyDepthISliceL: 4
+MaxMTTHierarchyDepthISliceC: 4
+MaxBTLumaISlice:  64
+MaxBTChromaISlice: 64
+MaxBTNonISlice: 128
+MaxTTLumaISlice: 32
+MaxTTChromaISlice: 32
+MaxTTNonISlice: 64
+MaxMTTHierarchyDepthByTid: 333333
+QpOutValCb: 17 23 35 40
\ No newline at end of file
diff --git a/cfg/per-class/classD_randomaccess.cfg b/cfg/per-class/classD_randomaccess.cfg
new file mode 100644
index 0000000000000000000000000000000000000000..180fc3a3eecfd004de7bf0e2afb3e697f609cb2b
--- /dev/null
+++ b/cfg/per-class/classD_randomaccess.cfg
@@ -0,0 +1,12 @@
+MaxMTTHierarchyDepth: 3
+MaxMTTHierarchyDepthI: 4
+MaxMTTHierarchyDepthISliceL: 4
+MaxMTTHierarchyDepthISliceC: 4
+MaxBTLumaISlice:  64
+MaxBTChromaISlice: 64
+MaxBTNonISlice: 128
+MaxTTLumaISlice: 32
+MaxTTChromaISlice: 32
+MaxTTNonISlice: 64
+MaxMTTHierarchyDepthByTid: 333333
+QpOutValCb: 17 23 35 40
\ No newline at end of file
diff --git a/source/App/EncoderApp/EncApp.cpp b/source/App/EncoderApp/EncApp.cpp
index b678584b3ec2c3c2f9196b080459aa1b8a0c8019..b5aa741db6e2323835709869b5aebab8d94ee766 100644
--- a/source/App/EncoderApp/EncApp.cpp
+++ b/source/App/EncoderApp/EncApp.cpp
@@ -1212,6 +1212,10 @@ void EncApp::xInitLibCfg()
   m_cEncLib.setNumRefLayers                                       ( m_numRefLayers );
 
   m_cEncLib.setVPSParameters(m_cfgVPSParameters);
+
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  m_cEncLib.setMaxMTTHierarchyDepthByTid                          ( m_maxMTTHierarchyDepthByTid );
+#endif
 }
 
 void EncApp::xCreateLib( std::list<PelUnitBuf*>& recBufList, const int layerId )
diff --git a/source/App/EncoderApp/EncAppCfg.cpp b/source/App/EncoderApp/EncAppCfg.cpp
index 8112500c0320be6e81df91bd1ed267acf66b83c9..bbc0ef67c1d6f17294ac0712e9e74b16878e3046 100644
--- a/source/App/EncoderApp/EncAppCfg.cpp
+++ b/source/App/EncoderApp/EncAppCfg.cpp
@@ -957,6 +957,9 @@ bool EncAppCfg::parseCfg( int argc, char* argv[] )
   ("MinQTChromaISliceInChromaSamples",                m_uiMinQT[2],                                        4u, "MinQTChromaISliceInChromaSamples")
   ("MinQTNonISlice",                                  m_uiMinQT[1],                                        8u, "MinQTNonISlice")
   ("MaxMTTHierarchyDepth",                            m_uiMaxMTTHierarchyDepth,                            3u, "MaxMTTHierarchyDepth")
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  ("MaxMTTHierarchyDepthByTid",                       m_sMaxMTTHierarchyDepthByTid,          string("333333"), "MaxMTTHierarchyDepthByTid")
+#endif
   ("MaxMTTHierarchyDepthI",                           m_uiMaxMTTHierarchyDepthI,                           3u, "MaxMTTHierarchyDepthI")
   ("MaxMTTHierarchyDepthISliceL",                     m_uiMaxMTTHierarchyDepthI,                           3u, "MaxMTTHierarchyDepthISliceL")
   ("MaxMTTHierarchyDepthISliceC",                     m_uiMaxMTTHierarchyDepthIChroma,                     3u, "MaxMTTHierarchyDepthISliceC")
@@ -2688,6 +2691,16 @@ bool EncAppCfg::parseCfg( int argc, char* argv[] )
   }
 #endif
 
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  CHECK( m_sMaxMTTHierarchyDepthByTid.size() > MAX_TLAYER, "MaxMTTHierarchyDepthByTid is greater than MAX_TLAYER" );
+
+  for( int i = 0; i < m_sMaxMTTHierarchyDepthByTid.size(); i++ )
+  {
+    CHECK( i >= MAX_TLAYER, "Index exceeds MAX_TLAYER" );
+    m_maxMTTHierarchyDepthByTid[i] = std::stoul( m_sMaxMTTHierarchyDepthByTid.substr( i, 1 ) );
+  }
+#endif
+
   // check validity of input parameters
   if( xCheckParameter() )
   {
@@ -3204,6 +3217,19 @@ bool EncAppCfg::xCheckParameter()
   xConfirmPara( m_confWinTop    % SPS::getWinUnitY(m_chromaFormatIDC) != 0, "Top conformance window offset must be an integer multiple of the specified chroma subsampling");
   xConfirmPara( m_confWinBottom % SPS::getWinUnitY(m_chromaFormatIDC) != 0, "Bottom conformance window offset must be an integer multiple of the specified chroma subsampling");
 
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  int sumMaxMTTHierarchyDepthByTid = 0;
+  for( auto &p : m_maxMTTHierarchyDepthByTid )
+  {
+    sumMaxMTTHierarchyDepthByTid += p;
+  }
+
+  if( sumMaxMTTHierarchyDepthByTid == 0 )
+  {
+    xConfirmPara( m_uiMaxBT[1] != m_uiMinQT[1], "MaxBTNonISlice shall be equal to MinQTNonISlice when MaxMTTHierarchyDepth is 0." );
+    xConfirmPara( m_uiMaxTT[1] != m_uiMinQT[1], "MaxTTNonISlice shall be equal to MinQTNonISlice when MaxMTTHierarchyDepth is 0." );
+  }
+#endif
 
   // max CU width and height should be power of 2
   uint32_t ui = m_uiMaxCUWidth;
@@ -4095,6 +4121,10 @@ void EncAppCfg::xPrintParameter()
   }
   msg(DETAILS, "CTU size / min CU size                 : %d / %d \n", m_uiMaxCUWidth, 1 << m_log2MinCuSize);
 
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  msg( DETAILS, "Max MTT Hierarchy Depth in B-slices by temporal ID: %s\n", m_sMaxMTTHierarchyDepthByTid.c_str() );
+#endif
+
   msg(DETAILS, "subpicture info present flag           : %s\n", m_subPicInfoPresentFlag ? "Enabled" : "Disabled");
   if (m_subPicInfoPresentFlag)
   {
diff --git a/source/App/EncoderApp/EncAppCfg.h b/source/App/EncoderApp/EncAppCfg.h
index 45bd7a81cf9d066312e63877fb351902c30dc34c..5349b4a341fef38faf48757a7d6b9814ddfd3581 100644
--- a/source/App/EncoderApp/EncAppCfg.h
+++ b/source/App/EncoderApp/EncAppCfg.h
@@ -341,6 +341,10 @@ protected:
   unsigned m_subPicIdLen;
   std::vector<uint16_t> m_subPicId;
   bool      m_SplitConsOverrideEnabledFlag;
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  std::string m_sMaxMTTHierarchyDepthByTid;
+  unsigned m_maxMTTHierarchyDepthByTid[MAX_TLAYER];
+#endif
   unsigned  m_uiMinQT[3]; // 0: I slice luma; 1: P/B slice; 2: I slice chroma
   unsigned  m_uiMaxMTTHierarchyDepth;
   unsigned  m_uiMaxMTTHierarchyDepthI;
diff --git a/source/Lib/CommonLib/TypeDef.h b/source/Lib/CommonLib/TypeDef.h
index b906ca705056f801606b49aa84f9f71e9c9e6397..753a12354e8e4ab8f7395f165a10fb6cc6f4ec06 100644
--- a/source/Lib/CommonLib/TypeDef.h
+++ b/source/Lib/CommonLib/TypeDef.h
@@ -56,6 +56,7 @@
 
 
 #if BASE_ENCODER
+#define JVET_X0144_MAX_MTT_DEPTH_TID                      1 // JVET-X0144: max MTT hierarchy depth set by temporal ID
 // Lossy encoder speedups
 #define AFFINE_ENC_OPT                                    1 // Affine encoder optimization
 #define AMVR_ENC_OPT                                      1 // Encoder optimization for AMVR
diff --git a/source/Lib/DecoderLib/VLCReader.cpp b/source/Lib/DecoderLib/VLCReader.cpp
index a369af00e3dce06a2366d315caf0ec444941507d..2bdd5771e908af2cc1ae6f9fdea16f2b167fd9ef 100644
--- a/source/Lib/DecoderLib/VLCReader.cpp
+++ b/source/Lib/DecoderLib/VLCReader.cpp
@@ -1935,8 +1935,13 @@ void HLSyntaxReader::parseSPS(SPS* pcSPS)
     {
       READ_UVLC(uiCode, "sps_log2_diff_max_bt_min_qt_intra_slice_chroma");       maxBTSize[2] <<= uiCode;
       READ_UVLC(uiCode, "sps_log2_diff_max_tt_min_qt_intra_slice_chroma");       maxTTSize[2] <<= uiCode;
+#if TU_256
+      CHECK( maxTTSize[2] > MAX_CU_SIZE, "The value of sps_log2_diff_max_tt_min_qt_intra_slice_chroma shall be in the range of 0 to min(6,CtbLog2SizeY) - MinQtLog2SizeIntraChroma" );
+      CHECK( maxBTSize[2] > MAX_CU_SIZE, "The value of sps_log2_diff_max_bt_min_qt_intra_slice_chroma shall be in the range of 0 to min(6,CtbLog2SizeY) - MinQtLog2SizeIntraChroma" );
+#else
       CHECK(maxTTSize[2] > 64, "The value of sps_log2_diff_max_tt_min_qt_intra_slice_chroma shall be in the range of 0 to min(6,CtbLog2SizeY) - MinQtLog2SizeIntraChroma");
       CHECK(maxBTSize[2] > 64, "The value of sps_log2_diff_max_bt_min_qt_intra_slice_chroma shall be in the range of 0 to min(6,CtbLog2SizeY) - MinQtLog2SizeIntraChroma");
+#endif
     }
   }
 #endif
@@ -3498,7 +3503,11 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag
       READ_UVLC(uiCode, "ph_log2_diff_min_qt_min_cb_inter_slice");
       unsigned minQtLog2SizeInterY = uiCode + sps->getLog2MinCodingBlockSize();
       minQT[1] = 1 << minQtLog2SizeInterY;
+#if TU_256
+      CHECK( minQT[1] > MAX_CU_SIZE, "The value of ph_log2_diff_min_qt_min_cb_inter_slice shall be in the range of 0 to min(8, CtbLog2SizeY) - MinCbLog2SizeY." );
+#else
       CHECK(minQT[1] > 64, "The value of ph_log2_diff_min_qt_min_cb_inter_slice shall be in the range of 0 to min(6, CtbLog2SizeY) - MinCbLog2SizeY.");
+#endif
       CHECK(minQT[1] > (1<<ctbLog2SizeY), "The value of ph_log2_diff_min_qt_min_cb_inter_slice shall be in the range of 0 to min(6, CtbLog2SizeY) - MinCbLog2SizeY");
       READ_UVLC(uiCode, "ph_max_mtt_hierarchy_depth_inter_slice");              maxBTD[1] = uiCode;
 
@@ -3509,7 +3518,11 @@ void HLSyntaxReader::parsePictureHeader( PicHeader* picHeader, ParameterSetManag
         CHECK(uiCode > ctbLog2SizeY - minQtLog2SizeInterY, "The value of ph_log2_diff_max_bt_min_qt_inter_slice shall be in the range of 0 to CtbLog2SizeY - MinQtLog2SizeInterY");
         READ_UVLC(uiCode, "ph_log2_diff_max_tt_min_qt_inter_slice");            maxTTSize[1] <<= uiCode;
         CHECK(uiCode > ctbLog2SizeY - minQtLog2SizeInterY, "The value of ph_log2_diff_max_tt_min_qt_inter_slice shall be in the range of 0 to CtbLog2SizeY - MinQtLog2SizeInterY");
+#if TU_256
+        CHECK( maxTTSize[1] > MAX_CU_SIZE, "The value of ph_log2_diff_max_tt_min_qt_inter_slice shall be in the range of 0 to min(8,CtbLog2SizeY) - MinQtLog2SizeInterY." );
+#else
         CHECK(maxTTSize[1] > 64, "The value of ph_log2_diff_max_tt_min_qt_inter_slice shall be in the range of 0 to min(6,CtbLog2SizeY) - MinQtLog2SizeInterY.");
+#endif
       }
     }
     // delta quantization and chrom and chroma offset
diff --git a/source/Lib/EncoderLib/EncCfg.h b/source/Lib/EncoderLib/EncCfg.h
index d4d6ea185e2fb794c522d585d42529dfee112e2e..3d4231fec42f169aed224c5dfcb6ed27c317a6df 100644
--- a/source/Lib/EncoderLib/EncCfg.h
+++ b/source/Lib/EncoderLib/EncCfg.h
@@ -347,6 +347,9 @@ protected:
   unsigned  m_uiMaxMTTHierarchyDepth;
   unsigned  m_uiMaxMTTHierarchyDepthI;
   unsigned  m_uiMaxMTTHierarchyDepthIChroma;
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  unsigned  m_maxMTTHierarchyDepthByTid[MAX_TLAYER];
+#endif
   bool      m_dualITree;
   unsigned  m_maxCUWidth;
   unsigned  m_maxCUHeight;
@@ -1132,6 +1135,11 @@ public:
   void      setMaxTTSizes                   ( unsigned* maxTT)   { m_uiMaxTT[0] = maxTT[0]; m_uiMaxTT[1] = maxTT[1]; m_uiMaxTT[2] = maxTT[2]; }
   void      setMaxMTTHierarchyDepth         ( unsigned uiMaxMTTHierarchyDepth, unsigned uiMaxMTTHierarchyDepthI, unsigned uiMaxMTTHierarchyDepthIChroma )
                                                              { m_uiMaxMTTHierarchyDepth = uiMaxMTTHierarchyDepth; m_uiMaxMTTHierarchyDepthI = uiMaxMTTHierarchyDepthI; m_uiMaxMTTHierarchyDepthIChroma = uiMaxMTTHierarchyDepthIChroma; }
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+  void      setMaxMTTHierarchyDepthByTid    ( unsigned* maxMTTHierarchyDepthByTid )   { std::memcpy( m_maxMTTHierarchyDepthByTid, maxMTTHierarchyDepthByTid, sizeof( m_maxMTTHierarchyDepthByTid) );}
+  unsigned  getMaxMTTHierarchyDepthByTid    ( int i ) const                           { CHECK( (i < 0 || i >= MAX_TLAYER), "EncCgf::getMaxMTTHierarchyDepthByTid: abnormal index value" ); return m_maxMTTHierarchyDepthByTid[i]; }
+  unsigned* getMaxMTTHierarchyDepthsByTid   ()                                        { return &m_maxMTTHierarchyDepthByTid[0]; }
+#endif
   unsigned  getMaxMTTHierarchyDepth         ()         const { return m_uiMaxMTTHierarchyDepth; }
   unsigned  getMaxMTTHierarchyDepthI        ()         const { return m_uiMaxMTTHierarchyDepthI; }
   unsigned  getMaxMTTHierarchyDepthIChroma  ()         const { return m_uiMaxMTTHierarchyDepthIChroma; }
diff --git a/source/Lib/EncoderLib/EncGOP.cpp b/source/Lib/EncoderLib/EncGOP.cpp
index c3494b17662062e06f56b55494ff4acc9561e8af..20ece5ed98f529960afb14f8a3d9bef6ea40b53a 100644
--- a/source/Lib/EncoderLib/EncGOP.cpp
+++ b/source/Lib/EncoderLib/EncGOP.cpp
@@ -2401,6 +2401,14 @@ void EncGOP::compressGOP( int iPOCLast, int iNumPicRcvd, PicList& rcListPic,
         int refLayer = pcSlice->getDepth();
         if( refLayer > 9 ) refLayer = 9; // Max layer is 10
 
+#if JVET_X0144_MAX_MTT_DEPTH_TID
+        if( m_pcCfg->getMaxMTTHierarchyDepthByTid( refLayer ) != m_pcCfg->getMaxMTTHierarchyDepth() )
+        {
+          picHeader->setSplitConsOverrideFlag( true );
+          picHeader->setMaxMTTHierarchyDepth( P_SLICE, m_pcCfg->getMaxMTTHierarchyDepthByTid( refLayer ) );
+        }
+#endif
+
         if( m_bInitAMaxBT && pcSlice->getPOC() > m_uiPrevISlicePOC )
         {
           ::memset( m_uiBlkSize, 0, sizeof( m_uiBlkSize ) );