]> git.sesse.net Git - nageru/commitdiff
Fix an issue with changing video bitrate when x264 speed control was in effect.
authorSteinar H. Gunderson <sgunderson@bigfoot.com>
Mon, 1 Aug 2016 17:53:23 +0000 (19:53 +0200)
committerSteinar H. Gunderson <sgunderson@bigfoot.com>
Mon, 1 Aug 2016 17:53:34 +0000 (19:53 +0200)
x264_encoder.cpp
x264_speed_control.cpp
x264_speed_control.h

index f77549d98c7d749a0a29ae89a213a3f3e903a285..9874519362aadf8a3059eb77f2e797243d230459 100644 (file)
@@ -249,12 +249,18 @@ void X264Encoder::encode_frame(X264Encoder::QueuedFrame qf)
        // See if we have a new bitrate to change to.
        unsigned new_rate = new_bitrate_kbit.exchange(0);  // Read and clear.
        if (new_rate != 0) {
-               x264_param_t param;
-               x264_encoder_parameters(x264, &param);
-               param.rc.i_bitrate = new_rate;
-               update_vbv_settings(&param);
-               x264_encoder_reconfig(x264, &param);
-               printf("changing rate to %u\n", new_rate);
+               if (speed_control) {
+                       speed_control->set_config_override_function([new_rate](x264_param_t *param) {
+                               param->rc.i_bitrate = new_rate;
+                               update_vbv_settings(param);
+                       });
+               } else {
+                       x264_param_t param;
+                       x264_encoder_parameters(x264, &param);
+                       param.rc.i_bitrate = new_rate;
+                       update_vbv_settings(&param);
+                       x264_encoder_reconfig(x264, &param);
+               }
        }
 
        if (speed_control) {
index c6add3e9403f2e8334f28a19bcb80e57387071fc..7eca74d1550e72ed9dcb7a9d5a73a78f881149e4 100644 (file)
@@ -305,6 +305,9 @@ void X264SpeedControl::apply_preset(int new_preset)
        p.analyse.b_mixed_references = s->mix;
        p.analyse.i_direct_mv_pred = s->direct;
        p.analyse.i_me_range = s->merange;
+       if (override_func) {
+               override_func(&p);
+       }
        x264_encoder_reconfig(x264, &p);
        preset = new_preset;
 }
index 84eb090380850f8264ed224a3f26a987a0f80ebf..7add8fdd4c2c2a3c9386d74a0854aa2389bc9e41 100644 (file)
@@ -47,6 +47,7 @@
 #include <stdint.h>
 #include <string.h>
 #include <math.h>
+#include <functional>
 
 extern "C" {
 #include "x264.h"
@@ -80,6 +81,17 @@ public:
        void before_frame(float new_buffer_fill, int new_buffer_size, float f_uspf);
        void after_frame();
 
+       // x264 seemingly has an issue where x264_encoder_reconfig() is not reflected
+       // immediately in x264_encoder_parameters(). Since speed control keeps calling
+       // those two all the time, any changes you make outside X264SpeedControl
+       // could be overridden. Thus, to make changes to encoder parameters, you should
+       // instead set a function here, which will be called every time parameters
+       // are modified.
+       void set_config_override_function(std::function<void(x264_param_t *)> override_func)
+       {
+               this->override_func = override_func;
+       }
+
 private:
        void set_buffer_size(int new_buffer_size);
        int dither_preset(float f);
@@ -112,4 +124,6 @@ private:
                double avg_preset;
                int den;
        } stat;
+
+       std::function<void(x264_param_t *)> override_func = nullptr;
 };