implemented core subtitle support
This commit is contained in:
@@ -56,7 +56,7 @@ bool ExportTask::Run()
|
||||
}
|
||||
|
||||
if (!encoder_->Open()) {
|
||||
SetError(tr("Failed to open file"));
|
||||
SetError(tr("Failed to open file: %1").arg(encoder_->GetError()));
|
||||
encoder_->deleteLater();
|
||||
return false;
|
||||
}
|
||||
@@ -102,6 +102,7 @@ bool ExportTask::Run()
|
||||
|
||||
// Start render process
|
||||
TimeRangeList video_range, audio_range;
|
||||
TimeRange subtitle_range;
|
||||
|
||||
if (params_.video_enabled()) {
|
||||
video_range = {range};
|
||||
@@ -111,7 +112,11 @@ bool ExportTask::Run()
|
||||
audio_range = {range};
|
||||
}
|
||||
|
||||
Render(color_manager_, video_range, audio_range, RenderMode::kOnline, nullptr,
|
||||
if (params_.subtitles_enabled()) {
|
||||
subtitle_range = range;
|
||||
}
|
||||
|
||||
Render(color_manager_, video_range, audio_range, subtitle_range, RenderMode::kOnline, nullptr,
|
||||
video_force_size, video_force_matrix, encoder_->GetDesiredPixelFormat(),
|
||||
color_processor_);
|
||||
|
||||
@@ -191,6 +196,11 @@ void ExportTask::AudioDownloaded(const TimeRange &range, SampleBufferPtr samples
|
||||
}
|
||||
}
|
||||
|
||||
void ExportTask::EncodeSubtitle(const SubtitleBlock *sub)
|
||||
{
|
||||
encoder_->WriteSubtitle(sub);
|
||||
}
|
||||
|
||||
void ExportTask::WriteAudioLoop(const TimeRange& time, SampleBufferPtr samples)
|
||||
{
|
||||
encoder_->WriteAudio(samples);
|
||||
|
||||
@@ -42,6 +42,8 @@ protected:
|
||||
|
||||
virtual void AudioDownloaded(const TimeRange& range, SampleBufferPtr samples, qint64 job_time) override;
|
||||
|
||||
virtual void EncodeSubtitle(const SubtitleBlock *sub) override;
|
||||
|
||||
virtual bool TwoStepFrameRendering() const override
|
||||
{
|
||||
return false;
|
||||
|
||||
@@ -67,6 +67,7 @@ bool PreCacheTask::Run()
|
||||
Render(project_->color_manager(),
|
||||
video_range,
|
||||
TimeRangeList(),
|
||||
TimeRange(),
|
||||
RenderMode::kOnline,
|
||||
viewer()->video_frame_cache());
|
||||
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
#include "render.h"
|
||||
|
||||
#include "common/timecodefunctions.h"
|
||||
#include "node/project/sequence/sequence.h"
|
||||
#include "render/rendermanager.h"
|
||||
|
||||
namespace olive {
|
||||
@@ -40,7 +41,7 @@ RenderTask::~RenderTask()
|
||||
|
||||
bool RenderTask::Render(ColorManager* manager,
|
||||
const TimeRangeList& video_range,
|
||||
const TimeRangeList &audio_range,
|
||||
const TimeRangeList &audio_range, const TimeRange &subtitle_range,
|
||||
RenderMode::Mode mode,
|
||||
FrameHashCache* cache, const QSize &force_size,
|
||||
const QMatrix4x4 &force_matrix, VideoParams::Format force_format,
|
||||
@@ -129,6 +130,50 @@ bool RenderTask::Render(ColorManager* manager,
|
||||
mode, cache, force_size, force_matrix, force_format, force_color_output);
|
||||
}
|
||||
|
||||
// Subtitle loop, loops over all blocks in sequence on all tracks
|
||||
if (!subtitle_range.length().isNull()) {
|
||||
Sequence *sequence = dynamic_cast<Sequence*>(viewer_);
|
||||
if (sequence) {
|
||||
TrackList *list = sequence->track_list(Track::kSubtitle);
|
||||
QVector<int> block_indexes(list->GetTrackCount(), 0);
|
||||
|
||||
QVector<int> tracks_to_push;
|
||||
do {
|
||||
tracks_to_push.clear();
|
||||
|
||||
for (int i=0; i<block_indexes.size(); i++) {
|
||||
Track *this_track = list->GetTrackAt(i);
|
||||
int &this_block_index = block_indexes[i];
|
||||
if (this_block_index >= this_track->Blocks().size()) {
|
||||
continue;
|
||||
}
|
||||
Block *this_block = this_track->Blocks().at(this_block_index);
|
||||
|
||||
Track *compare_track = tracks_to_push.isEmpty() ? nullptr : list->GetTrackAt(tracks_to_push.first());
|
||||
const int &compare_block_index = tracks_to_push.isEmpty() ? -1 : block_indexes.at(tracks_to_push.first());
|
||||
Block *compare_block = compare_track ? compare_track->Blocks().at(compare_block_index) : nullptr;
|
||||
if (!compare_track || compare_block->in() >= this_block->in()) {
|
||||
if (compare_track && compare_block->in() != this_block->in()) {
|
||||
tracks_to_push.clear();
|
||||
}
|
||||
tracks_to_push.append(i);
|
||||
}
|
||||
}
|
||||
|
||||
for (int i=0; i<tracks_to_push.size(); i++) {
|
||||
Track *this_track = list->GetTrackAt(tracks_to_push.at(i));
|
||||
Block *this_block = this_track->Blocks().at(block_indexes.at(tracks_to_push.at(i)));
|
||||
|
||||
if (const SubtitleBlock *sub = dynamic_cast<const SubtitleBlock*>(this_block)) {
|
||||
EncodeSubtitle(sub);
|
||||
}
|
||||
|
||||
block_indexes[tracks_to_push.at(i)]++;
|
||||
}
|
||||
} while (!tracks_to_push.isEmpty());
|
||||
}
|
||||
}
|
||||
|
||||
finished_watcher_mutex_.lock();
|
||||
|
||||
while (!IsCancelled()) {
|
||||
@@ -238,6 +283,11 @@ void RenderTask::DownloadFrame(QThread *thread, FramePtr frame, const QByteArray
|
||||
hash));
|
||||
}
|
||||
|
||||
void RenderTask::EncodeSubtitle(const SubtitleBlock *subtitle)
|
||||
{
|
||||
Q_UNUSED(subtitle)
|
||||
}
|
||||
|
||||
void RenderTask::PrepareWatcher(RenderTicketWatcher *watcher, QThread *thread)
|
||||
{
|
||||
watcher->moveToThread(thread);
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
|
||||
#include <QtConcurrent/QtConcurrent>
|
||||
|
||||
#include "node/block/subtitle/subtitle.h"
|
||||
#include "node/color/colormanager/colormanager.h"
|
||||
#include "node/output/viewer/viewer.h"
|
||||
#include "task/task.h"
|
||||
@@ -41,7 +42,8 @@ public:
|
||||
|
||||
protected:
|
||||
bool Render(ColorManager *manager, const TimeRangeList &video_range,
|
||||
const TimeRangeList &audio_range, RenderMode::Mode mode,
|
||||
const TimeRangeList &audio_range, const TimeRange &subtitle_range,
|
||||
RenderMode::Mode mode,
|
||||
FrameHashCache *cache, const QSize& force_size = QSize(0, 0),
|
||||
const QMatrix4x4& force_matrix = QMatrix4x4(),
|
||||
VideoParams::Format force_format = VideoParams::kFormatInvalid,
|
||||
@@ -53,6 +55,8 @@ protected:
|
||||
|
||||
virtual void AudioDownloaded(const TimeRange& range, SampleBufferPtr samples, qint64 job_time) = 0;
|
||||
|
||||
virtual void EncodeSubtitle(const SubtitleBlock *subtitle);
|
||||
|
||||
ViewerOutput* viewer() const
|
||||
{
|
||||
return viewer_;
|
||||
|
||||
Reference in New Issue
Block a user