global_mainwindow = this;
ui->setupUi(this);
- global_disk_space_estimator = new DiskSpaceEstimator(bind(&MainWindow::report_disk_space, this, _1, _2));
+ global_disk_space_estimator = new DiskSpaceEstimator(bind(&MainWindow::report_disk_space, this, _1, _2, _3));
disk_free_label = new QLabel(this);
disk_free_label->setStyleSheet("QLabel {padding-right: 5px;}");
ui->menuBar->setCornerWidget(disk_free_label);
}
}
-void MainWindow::report_disk_space(off_t free_bytes, double estimated_seconds_left)
+void MainWindow::report_disk_space(off_t free_bytes, double estimated_seconds_left, double file_length_seconds)
{
char time_str[256];
if (estimated_seconds_left < 60.0) {
char buf[256];
snprintf(buf, sizeof(buf), "Disk free: %'.0f MB (approx. %s)", free_bytes / 1048576.0, time_str);
- std::string label = buf;
+ // NOTE: The default formatter does not use file_length_seconds for anything,
+ // but the theme might want to do so.
+ std::string label = global_mixer->format_status_line(buf, file_length_seconds);
post_to_main_thread([this, label]{
disk_free_label->setText(QString::fromStdString(label));
void next_page();
// Called from DiskSpaceEstimator.
- void report_disk_space(off_t free_bytes, double estimated_seconds_left);
+ void report_disk_space(off_t free_bytes, double estimated_seconds_left, double file_length_seconds);
// Called from the mixer.
void audio_level_callback(float level_lufs, float peak_db, std::vector<AudioMixer::BusLevel> bus_levels, float global_level_lufs, float range_low_lufs, float range_high_lufs, float final_makeup_gain_db, float correlation);
theme->set_wb(channel, r, g, b);
}
+ std::string format_status_line(const std::string &disk_space_left_text, double file_length_seconds)
+ {
+ return theme->format_status_line(disk_space_left_text, file_length_seconds);
+ }
+
// Note: You can also get this through the global variable global_audio_mixer.
AudioMixer *get_audio_mixer() { return audio_mixer.get(); }
const AudioMixer *get_audio_mixer() const { return audio_mixer.get(); }
abort();
}
}
+
+string Theme::format_status_line(const string &disk_space_left_text, double file_length_seconds)
+{
+ lock_guard<mutex> lock(m);
+ lua_getglobal(L, "format_status_line");
+ if (lua_isnil(L, -1)) {
+ lua_pop(L, 1);
+ return disk_space_left_text;
+ }
+
+ lua_pushstring(L, disk_space_left_text.c_str());
+ lua_pushnumber(L, file_length_seconds);
+ if (lua_pcall(L, 2, 1, 0) != 0) {
+ fprintf(stderr, "error running function format_status_line(): %s\n", lua_tostring(L, -1));
+ abort();
+ }
+ string text = checkstdstring(L, 1);
+ lua_pop(L, 1);
+ assert(lua_gettop(L) == 0);
+ return text;
+}
theme_menu_callback = callback;
}
+ std::string format_status_line(const std::string &disk_space_left_text, double file_length_seconds);
+
private:
void register_globals();
void register_class(const char *class_name, const luaL_Reg *funcs, EffectType effect_type = NO_EFFECT_TYPE);
void DiskSpaceEstimator::report_write_internal(const string &filename, off_t file_size, uint64_t pts)
{
+ if (measure_points.empty()) {
+ first_pts_this_file = pts;
+ }
+
// Reject points that are out-of-order (happens with B-frames).
if (!measure_points.empty() && pts <= measure_points.back().pts) {
return;
// Only report every second, since updating the UI can be expensive.
if (last_pts_reported == 0 || pts - last_pts_reported >= TIMEBASE) {
- callback(free_bytes, seconds_left);
+ callback(free_bytes, seconds_left, double(pts - first_pts_this_file) / TIMEBASE);
last_pts_reported = pts;
}
}
class DiskSpaceEstimator {
public:
- typedef std::function<void(off_t free_bytes, double estimated_seconds_left)> callback_t;
+ typedef std::function<void(off_t free_bytes, double estimated_seconds_left, double file_length_seconds)> callback_t;
DiskSpaceEstimator(callback_t callback);
// Report that a video frame with the given pts and size has just been
};
std::deque<MeasurePoint> measure_points;
uint64_t last_pts_reported = 0;
+ uint64_t first_pts_this_file = 0;
off_t total_size = 0; // For report_write().
std::string last_filename; // For report_append().