fixed a bunch of multithreaded loading issues and #174

This commit is contained in:
itsmattkc
2018-12-20 23:20:00 +11:00
parent 4de524e7fa
commit 9797a3bf4b
16 changed files with 82 additions and 51 deletions
+7 -2
View File
@@ -39,6 +39,7 @@ LoadDialog::LoadDialog(QWidget *parent, bool autorecovery) : QDialog(parent) {
lt = new LoadThread(this, autorecovery);
QObject::connect(lt, SIGNAL(success()), this, SLOT(thread_done()));
QObject::connect(lt, SIGNAL(error()), this, SLOT(die()));
QObject::connect(lt, SIGNAL(report_progress(int)), bar, SLOT(setValue(int)));
lt->start();
}
@@ -46,8 +47,12 @@ LoadDialog::LoadDialog(QWidget *parent, bool autorecovery) : QDialog(parent) {
void LoadDialog::cancel() {
lt->cancel();
lt->wait();
mainWindow->new_project();
reject();
die();
}
void LoadDialog::die() {
mainWindow->new_project();
reject();
}
void LoadDialog::thread_done() {
+1
View File
@@ -17,6 +17,7 @@ public:
LoadDialog(QWidget* parent, bool autorecovery);
private slots:
void cancel();
void die();
void thread_done();
private:
QProgressBar* bar;
+1
View File
@@ -1,6 +1,7 @@
#include "clipboard.h"
#include "project/clip.h"
#include "project/effect.h"
int clipboard_type = CLIPBOARD_TYPE_CLIP;
QVector<void*> clipboard;
+36 -24
View File
@@ -31,6 +31,7 @@ struct TransitionData {
LoadThread::LoadThread(LoadDialog* l, bool a) : ld(l), autorecovery(a), cancelled(false) {
connect(this, SIGNAL(finished()), this, SLOT(deleteLater()));
connect(this, SIGNAL(success()), this, SLOT(success_func()));
connect(this, SIGNAL(error()), this, SLOT(error_func()));
connect(this, SIGNAL(start_create_effect_ui(QXmlStreamReader*, Clip*, int, const EffectMeta*, long, bool)), this, SLOT(create_effect_ui(QXmlStreamReader*, Clip*, int, const EffectMeta*, long, bool)));
}
@@ -572,23 +573,7 @@ void LoadThread::run() {
cont = load_worker(file, stream, LOAD_TYPE_VERSION);
// find project's internal URL
cont = load_worker(file, stream, LOAD_TYPE_URL);
if (autorecovery) {
QString orig_filename = internal_proj_url;
int insert_index = internal_proj_url.lastIndexOf(".ove", -1, Qt::CaseInsensitive);
if (insert_index == -1) insert_index = internal_proj_url.length();
int counter = 1;
while (QFileInfo::exists(orig_filename)) {
orig_filename = internal_proj_url;
QString recover_text = "recovered";
if (counter > 1) {
recover_text += " " + QString::number(counter);
}
orig_filename.insert(insert_index, " (" + recover_text + ")");
counter++;
}
mainWindow->updateTitle(orig_filename);
}
cont = load_worker(file, stream, LOAD_TYPE_URL);
// load folders first
if (cont) {
@@ -614,11 +599,14 @@ void LoadThread::run() {
if (!cancelled) {
if (!cont) {
if (show_err) QMessageBox::critical(mainWindow, "Project Load Error", "Error loading project: " + error_str, QMessageBox::Ok);
xml_error = false;
if (show_err) emit error();
} else if (stream.hasError()) {
dout << "[ERROR] Error parsing XML." << stream.errorString();
QMessageBox::critical(mainWindow, "XML Parsing Error", "Couldn't load '" + project_url + "'. " + stream.errorString(), QMessageBox::Ok);
error_str = stream.errorString();
xml_error = true;
emit error();
cont = false;
} else {
// attach nested sequence clips to their sequences
for (int i=0;i<loaded_clips.size();i++) {
@@ -641,9 +629,7 @@ void LoadThread::run() {
for (int i=0;i<loaded_media_items.size();i++) {
panel_project->start_preview_generator(loaded_media_items.at(i), true);
}
} else {
mainWindow->new_project();
}
}
file.close();
@@ -652,10 +638,36 @@ void LoadThread::run() {
void LoadThread::cancel() {
waitCond.wakeAll();
cancelled = true;
cancelled = true;
}
void LoadThread::error_func() {
if (xml_error) {
dout << "[ERROR] Error parsing XML." << error_str;
QMessageBox::critical(mainWindow, "XML Parsing Error", "Couldn't load '" + project_url + "'. " + error_str, QMessageBox::Ok);
} else {
QMessageBox::critical(mainWindow, "Project Load Error", "Error loading project: " + error_str, QMessageBox::Ok);
}
}
void LoadThread::success_func() {
if (autorecovery) {
QString orig_filename = internal_proj_url;
int insert_index = internal_proj_url.lastIndexOf(".ove", -1, Qt::CaseInsensitive);
if (insert_index == -1) insert_index = internal_proj_url.length();
int counter = 1;
while (QFileInfo::exists(orig_filename)) {
orig_filename = internal_proj_url;
QString recover_text = "recovered";
if (counter > 1) {
recover_text += " " + QString::number(counter);
}
orig_filename.insert(insert_index, " (" + recover_text + ")");
counter++;
}
mainWindow->updateTitle(orig_filename);
}
mainWindow->setWindowModified(autorecovery);
if (open_seq != NULL) set_sequence(open_seq);
update_ui(false);
+4 -1
View File
@@ -12,7 +12,7 @@ struct Footage;
struct Clip;
struct Sequence;
class LoadDialog;
class EffectMeta;
struct EffectMeta;
class LoadThread : public QThread
{
@@ -23,9 +23,11 @@ public:
void cancel();
signals:
void success();
void error();
void start_create_effect_ui(QXmlStreamReader* stream, Clip* c, int type, const EffectMeta* meta, long effect_length, bool effect_enabled);
void report_progress(int p);
private slots:
void error_func();
void success_func();
void create_effect_ui(QXmlStreamReader* stream, Clip* c, int type, const EffectMeta* meta, long effect_length, bool effect_enabled);
private:
@@ -61,6 +63,7 @@ private:
QWaitCondition waitCond;
bool cancelled;
bool xml_error;
};
#endif // LOADTHREAD_H
+4 -2
View File
@@ -227,6 +227,9 @@ MainWindow::MainWindow(QWidget *parent) :
}
MainWindow::~MainWindow() {
panel_sequence_viewer->viewer_widget->delete_function();
panel_footage_viewer->viewer_widget->delete_function();
set_sequence(NULL);
QString data_dir = get_data_path();
@@ -439,8 +442,7 @@ void MainWindow::new_project() {
}
}
void MainWindow::on_actionSplit_at_Playhead_triggered()
{
void MainWindow::on_actionSplit_at_Playhead_triggered() {
if (panel_timeline->focused()) {
panel_timeline->split_at_playhead();
}
+2
View File
@@ -201,6 +201,8 @@ void EffectControls::show_effect_menu(int type, int subtype) {
void EffectControls::clear_effects(bool clear_cache) {
// clear existing clips
deselect_all_effects(NULL);
QVBoxLayout* video_layout = static_cast<QVBoxLayout*>(ui->video_effect_area->layout());
QVBoxLayout* audio_layout = static_cast<QVBoxLayout*>(ui->audio_effect_area->layout());
QLayoutItem* item;
+1 -1
View File
@@ -125,7 +125,7 @@ QDockWidget *get_focused_panel() {
if (w == NULL) {
if (panel_project->is_focused()) {
w = panel_project;
} else if (panel_effect_controls->keyframe_focus()) {
} else if (panel_effect_controls->keyframe_focus() || panel_effect_controls->is_focused()) {
w = panel_effect_controls;
} else if (panel_sequence_viewer->is_focused()) {
w = panel_sequence_viewer;
+12 -10
View File
@@ -859,16 +859,18 @@ void Project::save_folder(QXmlStreamWriter& stream, int type, bool set_ids_only,
stream.writeAttribute("maintainpitch", QString::number(c->maintain_audio_pitch));
stream.writeAttribute("reverse", QString::number(c->reverse));
stream.writeAttribute("type", QString::number(c->media->get_type()));
switch (c->media->get_type()) {
case MEDIA_TYPE_FOOTAGE:
stream.writeAttribute("media", QString::number(c->media->to_footage()->save_id));
stream.writeAttribute("stream", QString::number(c->media_stream));
break;
case MEDIA_TYPE_SEQUENCE:
stream.writeAttribute("sequence", QString::number(c->media->to_sequence()->save_id));
break;
}
if (c->media != NULL) {
stream.writeAttribute("type", QString::number(c->media->get_type()));
switch (c->media->get_type()) {
case MEDIA_TYPE_FOOTAGE:
stream.writeAttribute("media", QString::number(c->media->to_footage()->save_id));
stream.writeAttribute("stream", QString::number(c->media_stream));
break;
case MEDIA_TYPE_SEQUENCE:
stream.writeAttribute("sequence", QString::number(c->media->to_sequence()->save_id));
break;
}
}
stream.writeStartElement("linked"); // linked
for (int k=0;k<c->linked.size();k++) {
+3 -2
View File
@@ -87,7 +87,8 @@ void close_clip(Clip* clip) {
} else {
if (clip->media != NULL && clip->media->get_type() == MEDIA_TYPE_SEQUENCE)
closeActiveClips(clip->media->to_sequence(), false);
clip->open = false;
clip->open = false;
}
}
@@ -342,7 +343,7 @@ void closeActiveClips(Sequence *s, bool wait) {
if (c != NULL) {
if (c->media != NULL && c->media->get_type() == MEDIA_TYPE_SEQUENCE) {
closeActiveClips(c->media->to_sequence(), wait);
close_clip(c);
if (c->open) close_clip(c);
} else if (clip_uses_cacher(c) && c->open) {
close_clip(c);
if (c->multithreaded && wait) c->cacher->wait();
+1
View File
@@ -210,6 +210,7 @@ double Clip::getMediaFrameRate() {
if (!qIsNaN(rate)) return rate;
}
if (sequence != NULL) return sequence->frame_rate;
return qSNaN();
}
void Clip::recalculateMaxLength() {
+2 -3
View File
@@ -432,7 +432,7 @@ Effect::~Effect() {
close();
}
delete container;
delete container;
for (int i=0;i<rows.size();i++) {
delete rows.at(i);
@@ -750,11 +750,11 @@ void Effect::close() {
if (!isOpen) {
dout << "[WARNING] Tried to close an effect that was already closed";
}
delete_texture();
if (glslProgram != NULL) {
delete glslProgram;
glslProgram = NULL;
}
delete_texture();
isOpen = false;
}
@@ -991,7 +991,6 @@ bool Effect::valueHasChanged(double timecode) {
void Effect::delete_texture() {
if (texture != NULL) {
texture->destroy();
delete texture;
texture = NULL;
}
+2 -2
View File
@@ -183,8 +183,8 @@ const QString &Media::get_name() {
switch (type) {
case MEDIA_TYPE_FOOTAGE: return to_footage()->name;
case MEDIA_TYPE_SEQUENCE: return to_sequence()->name;
case MEDIA_TYPE_FOLDER: return folder_name;
}
default: return folder_name;
}
}
void Media::set_name(const QString &n) {
+3 -1
View File
@@ -12,6 +12,8 @@
#include <QWidget>
#include <QPainter>
#include "debug.h"
CollapsibleWidget::CollapsibleWidget(QWidget* parent) : QWidget(parent) {
selected = false;
@@ -48,7 +50,7 @@ void CollapsibleWidget::header_click(bool s, bool deselect) {
selected = s;
title_bar->selected = s;
if (s) {
QPalette p = palette();
QPalette p = title_bar->palette();
p.setColor(QPalette::Background, QColor(255, 255, 255, 64));
title_bar->setPalette(p);
} else {
+2 -2
View File
@@ -1237,7 +1237,7 @@ void TimelineWidget::update_ghosts(const QPoint& mouse_pos, bool lock_frame) {
if (g.clip != -1) c = sequence->clips.at(g.clip);
FootageStream* ms = NULL;
if (g.clip != -1 && c->media->get_type() == MEDIA_TYPE_FOOTAGE) {
if (g.clip != -1 && c->media != NULL && c->media->get_type() == MEDIA_TYPE_FOOTAGE) {
ms = c->media->to_footage()->get_stream_from_file_index(c->track < 0, c->media_stream);
}
@@ -1277,7 +1277,7 @@ void TimelineWidget::update_ghosts(const QPoint& mouse_pos, bool lock_frame) {
if (validator < 1) frame_diff += (1 - validator);
// prevent clip length exceeding media length
if (c->media->get_type() == MEDIA_TYPE_SEQUENCE
if ((c->media != NULL && c->media->get_type() == MEDIA_TYPE_SEQUENCE)
|| (ms != NULL && !ms->infinite_length)) {
validator = g.old_clip_in + g.ghost_length + frame_diff;
if (validator > g.media_length) frame_diff -= validator - g.media_length;
+1 -1
View File
@@ -67,7 +67,7 @@ ViewerWidget::ViewerWidget(QWidget *parent) :
void ViewerWidget::delete_function() {
// destroy all textures as well
if (viewer->seq != NULL) {
if (viewer->seq != NULL) {
makeCurrent();
closeActiveClips(viewer->seq, true);
doneCurrent();