shithub: openh264

Download patch

ref: 00ecb3ae0b2f955b38f6e6524eec86f1acd18d79
parent: a5b14c2998c67e0a81ae5365b43c1aa9491908ac
author: Ed Wei <[email protected]>
date: Mon May 1 07:47:23 EDT 2017

Clean up usage of the content quantization parameter (QP).

This builds on the work in cisco/openh264#2746 to allow the user to
configure the screen content min and max QR values, which default to
the range [26, 35].

Setting the QP range is useful for exploring the parameter space for
screen content to make the appropriate tradeoffs between quality and
bitrate usage for a large variety of network environments.
See: cisco/openh264#2732

--- a/codec/console/enc/src/welsenc.cpp
+++ b/codec/console/enc/src/welsenc.cpp
@@ -412,8 +412,8 @@
   printf ("  -rc          rate control mode: 0-quality mode; 1-bitrate mode; 2-bitrate limited mode; -1-rc off \n");
   printf ("  -tarb        Overall target bitrate\n");
   printf ("  -maxbrTotal  Overall max bitrate\n");
-  printf ("  -maxqp       Maximum Qp\n");
-  printf ("  -minqp       Minimum Qp\n");
+  printf ("  -maxqp       Maximum Qp (default: %d, or for screen content usage: %d)\n", QP_MAX_VALUE, MAX_SCREEN_QP);
+  printf ("  -minqp       Minimum Qp (default: %d, or for screen content usage: %d)\n", QP_MIN_VALUE, MIN_SCREEN_QP);
   printf ("  -numl        Number Of Layers: Must exist with layer_cfg file and the number of input layer_cfg file must equal to the value set by this command\n");
   printf ("  The options below are layer-based: (need to be set with layer id)\n");
   printf ("  -lconfig     (Layer) (spatial layer configure file)\n");
--- a/codec/encoder/core/inc/param_svc.h
+++ b/codec/encoder/core/inc/param_svc.h
@@ -173,8 +173,8 @@
     param.iSpatialLayerNum              = 1;            // number of dependency(Spatial/CGS) layers used to be encoded
     param.iTemporalLayerNum             = 1;            // number of temporal layer specified
 
-    param.iMaxQp = 51;
-    param.iMinQp = 0;
+    param.iMaxQp = QP_MAX_VALUE;
+    param.iMinQp = QP_MIN_VALUE;
     param.iUsageType = CAMERA_VIDEO_REAL_TIME;
     param.uiMaxNalSize = 0;
     param.bIsLosslessLink = false;
--- a/codec/encoder/core/inc/rc.h
+++ b/codec/encoder/core/inc/rc.h
@@ -76,6 +76,8 @@
   MAX_SCREEN_QP         = 35,
   DELTA_QP              = 2,
   DELTA_QP_BGD_THD      = 3,
+  QP_MIN_VALUE          = 0,
+  QP_MAX_VALUE          = 51,
 
 //frame skip constants
   SKIP_QP_90P           = 24,
--- a/codec/encoder/core/src/encoder_ext.cpp
+++ b/codec/encoder/core/src/encoder_ext.cpp
@@ -384,8 +384,8 @@
       }
 
     }
-    pCfg->iMinQp = WELS_CLIP3 (pCfg->iMinQp, GOM_MIN_QP_MODE, 51);
-    pCfg->iMaxQp = WELS_CLIP3 (pCfg->iMaxQp, pCfg->iMinQp, 51);
+    pCfg->iMinQp = WELS_CLIP3 (pCfg->iMinQp, GOM_MIN_QP_MODE, QP_MAX_VALUE);
+    pCfg->iMaxQp = WELS_CLIP3 (pCfg->iMaxQp, pCfg->iMinQp, QP_MAX_VALUE);
   }
   // ref-frames validation
   if (((pCfg->iUsageType == CAMERA_VIDEO_REAL_TIME) || (pCfg->iUsageType == SCREEN_CONTENT_REAL_TIME))
--- a/codec/encoder/core/src/ratectl.cpp
+++ b/codec/encoder/core/src/ratectl.cpp
@@ -1284,13 +1284,11 @@
   SVAAFrameInfo* pVaa = static_cast<SVAAFrameInfo*> (pEncCtx->pVaa);
   SWelsSvcRc* pWelsSvcRc =  &pEncCtx->pWelsSvcRc[pEncCtx->uiDependencyId];
 
-  int32_t iMinQp = MIN_SCREEN_QP;
+  int32_t iMinQp = pEncCtx->pSvcParam->iMinQp;
   if (pVaa->eSceneChangeIdc == LARGE_CHANGED_SCENE)
-    iMinQp = MIN_SCREEN_QP + 2;
+    iMinQp += 2;
   else if (pVaa->eSceneChangeIdc == MEDIUM_CHANGED_SCENE)
-    iMinQp = MIN_SCREEN_QP + 1;
-  else
-    iMinQp = MIN_SCREEN_QP;
+    iMinQp += 1;
   if (pEncCtx->bDeliveryFlag)
     pEncCtx->iGlobalQp -= 1;
   else