summaryrefslogtreecommitdiff
path: root/src/lib
diff options
context:
space:
mode:
authorCarl Hetherington <cth@carlh.net>2025-10-22 15:32:30 +0200
committerCarl Hetherington <cth@carlh.net>2025-10-23 22:39:24 +0200
commitaf517d2d2a0a02ea167ffac4c617845727984720 (patch)
tree496a91e93a8a790e8d3dace58e8961e70b2c9b55 /src/lib
parentbda1a2c382229a5f1a893c015d23524807e022df (diff)
Add DCP-o-matic Processor tool.
Diffstat (limited to 'src/lib')
-rw-r--r--src/lib/fix_audio_levels_job.cc99
-rw-r--r--src/lib/fix_audio_levels_job.h46
-rw-r--r--src/lib/variant.cc7
-rw-r--r--src/lib/variant.h1
-rw-r--r--src/lib/wscript1
5 files changed, 154 insertions, 0 deletions
diff --git a/src/lib/fix_audio_levels_job.cc b/src/lib/fix_audio_levels_job.cc
new file mode 100644
index 000000000..b5d9e39d9
--- /dev/null
+++ b/src/lib/fix_audio_levels_job.cc
@@ -0,0 +1,99 @@
+/*
+ Copyright (C) 2025 Carl Hetherington <cth@carlh.net>
+
+ This file is part of DCP-o-matic.
+
+ DCP-o-matic is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ DCP-o-matic is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with DCP-o-matic. If not, see <http://www.gnu.org/licenses/>.
+
+*/
+
+
+#include "analyse_audio_job.h"
+#include "audio_content.h"
+#include "copy_dcp_details_to_film.h"
+#include "dcp_content.h"
+#include "dcp_film_encoder.h"
+#include "dcp_transcode_job.h"
+#include "film.h"
+#include "fix_audio_levels_job.h"
+#include "playlist.h"
+#include <fmt/format.h>
+#include <boost/filesystem.hpp>
+#include <string>
+
+#include "i18n.h"
+
+
+using std::make_shared;
+using std::shared_ptr;
+using std::string;
+using boost::optional;
+
+
+FixAudioLevelsJob::FixAudioLevelsJob(boost::filesystem::path input_dcp_path, boost::filesystem::path output_dcp_path, float leqm_target, bool make_quieter_dcps_louder)
+ : Job(shared_ptr<const Film>())
+ , _input_dcp_path(input_dcp_path)
+ , _output_dcp_path(output_dcp_path)
+ , _leqm_target(leqm_target)
+ , _make_quieter_dcps_louder(make_quieter_dcps_louder)
+{
+
+}
+
+
+string
+FixAudioLevelsJob::name() const
+{
+ return fmt::format(_("Correcting audio levels of {} to {}"), _input_dcp_path.string(), _leqm_target);
+}
+
+
+string
+FixAudioLevelsJob::json_name() const
+{
+ return N_("fix_audio_levels");
+}
+
+
+void
+FixAudioLevelsJob::run()
+{
+ auto input_dcp = make_shared<DCPContent>(_input_dcp_path);
+ auto film = std::make_shared<Film>(_output_dcp_path);
+ input_dcp->examine(film, shared_from_this(), true);
+ film->add_content({input_dcp});
+ copy_dcp_settings_to_film(input_dcp, film);
+
+ auto playlist = make_shared<Playlist>();
+ playlist->add(film, input_dcp);
+
+ AnalyseAudioJob analyse(film, playlist, false, boost::none);
+ analyse.run();
+
+ auto const level = analyse.analysis().leqm();
+ DCPOMATIC_ASSERT(level);
+
+ if ((!_make_quieter_dcps_louder && *level < _leqm_target) || !input_dcp->audio) {
+ set_progress(1);
+ set_state(FINISHED_OK);
+ }
+
+ input_dcp->audio->set_gain(_leqm_target - *level);
+ auto transcode = make_shared<DCPTranscodeJob>(film, TranscodeJob::ChangedBehaviour::IGNORE);
+ transcode->set_encoder(make_shared<DCPFilmEncoder>(film, transcode, true));
+ transcode->run();
+
+ set_progress(1);
+ set_state(FINISHED_OK);
+}
diff --git a/src/lib/fix_audio_levels_job.h b/src/lib/fix_audio_levels_job.h
new file mode 100644
index 000000000..eb504bb98
--- /dev/null
+++ b/src/lib/fix_audio_levels_job.h
@@ -0,0 +1,46 @@
+/*
+ Copyright (C) 2025 Carl Hetherington <cth@carlh.net>
+
+ This file is part of DCP-o-matic.
+
+ DCP-o-matic is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ DCP-o-matic is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with DCP-o-matic. If not, see <http://www.gnu.org/licenses/>.
+
+*/
+
+
+#include "job.h"
+
+
+class FixAudioLevelsJob : public Job
+{
+public:
+ /** @param input_dcp_path Directory containing the DCP to process.
+ * @param output_dcp_path Directory in which to write the fixed DCP (if required). The DCP will be created as a directory
+ * within output_dcp_path.
+ * @param leqm_target LEQ(m) target.
+ * @param make_quieter_dcps_louder true to increase the gain of DCPs that are less than leqm_target, false to only correct those which are louder.
+ */
+ FixAudioLevelsJob(boost::filesystem::path input_dcp_path, boost::filesystem::path output_dcp_path, float leqm_target, bool make_quieter_dcps_louder);
+
+ std::string name() const override;
+ std::string json_name() const override;
+ void run() override;
+
+private:
+ boost::filesystem::path _input_dcp_path;
+ boost::filesystem::path _output_dcp_path;
+ float _leqm_target;
+ bool _make_quieter_dcps_louder;
+};
+
diff --git a/src/lib/variant.cc b/src/lib/variant.cc
index 81931dcf7..5ca7a9982 100644
--- a/src/lib/variant.cc
+++ b/src/lib/variant.cc
@@ -36,6 +36,7 @@ static char const* _dcpomatic_batch_converter_app = "DCP-o-matic 2 Batch Convert
static char const* _dcpomatic_playlist_editor = "DCP-o-matic Playlist Editor";
static char const* _dcpomatic_combiner = "DCP-o-matic Combiner";
static char const* _dcpomatic_batch_converter = "DCP-o-matic Batch Converter";
+static char const* _dcpomatic_processor = "DCP-o-matic Processor";
static char const* _report_problem_email = "carl@dcpomatic.com";
@@ -107,6 +108,12 @@ variant::dcpomatic_verifier()
}
std::string
+variant::dcpomatic_processor()
+{
+ return _dcpomatic_processor;
+}
+
+std::string
variant::insert_dcpomatic(std::string const& s)
{
return fmt::format(s, _dcpomatic);
diff --git a/src/lib/variant.h b/src/lib/variant.h
index c7e26c1d6..d1fc7ad7e 100644
--- a/src/lib/variant.h
+++ b/src/lib/variant.h
@@ -35,6 +35,7 @@ std::string dcpomatic_kdm_creator();
std::string dcpomatic_player();
std::string dcpomatic_playlist_editor();
std::string dcpomatic_verifier();
+std::string dcpomatic_processor();
std::string insert_dcpomatic(std::string const& s);
std::string insert_dcpomatic_encode_server(std::string const& s);
diff --git a/src/lib/wscript b/src/lib/wscript
index 2e7b0339c..abded0152 100644
--- a/src/lib/wscript
+++ b/src/lib/wscript
@@ -104,6 +104,7 @@ sources = """
fcpxml.cc
fcpxml_content.cc
fcpxml_decoder.cc
+ fix_audio_levels_job.cc
frame_info.cc
file_group.cc
file_log.cc