fixed #94
This commit is contained in:
+25
-12
@@ -265,6 +265,7 @@ void Project::load_project() {
|
||||
int temp_media_id;
|
||||
Sequence* temp_seq;
|
||||
Clip* temp_clip;
|
||||
int temp_clip_id;
|
||||
|
||||
int state = LOAD_STATE_IDLE;
|
||||
while (!stream.atEnd()) {
|
||||
@@ -305,13 +306,24 @@ void Project::load_project() {
|
||||
break;
|
||||
case LOAD_STATE_SEQUENCE:
|
||||
if (stream.isEndElement() && stream.name() == "sequence") {
|
||||
// convert link ids to pointers
|
||||
// correct IDs
|
||||
for (int i=0;i<temp_seq->clip_count();i++) {
|
||||
Clip* c = temp_seq->get_clip(i);
|
||||
for (int j=0;j<c->link_ids.size();j++) {
|
||||
c->linked.append(temp_seq->get_clip(c->link_ids.at(j)));
|
||||
Clip* clip = temp_seq->get_clip(i);
|
||||
|
||||
// correct IDs in linked clips
|
||||
for (int j=0;j<clip->linked.size();j++) {
|
||||
for (int k=0;k<temp_seq->clip_count();k++) {
|
||||
if (temp_seq->get_clip(k)->id == clip->linked.at(j)) {
|
||||
clip->linked[j] = k;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
for (int i=0;i<temp_seq->clip_count();i++) {
|
||||
// correct actual IDs
|
||||
temp_seq->get_clip(i)->id = i;
|
||||
}
|
||||
|
||||
new_sequence(temp_seq);
|
||||
state = LOAD_STATE_IDLE;
|
||||
@@ -344,11 +356,15 @@ void Project::load_project() {
|
||||
case LOAD_STATE_CLIP:
|
||||
if (stream.isEndElement() && stream.name() == "clip") {
|
||||
temp_seq->add_clip(temp_clip);
|
||||
temp_clip->id = temp_clip_id; // uses loaded ID (corrects later)
|
||||
state = LOAD_STATE_SEQUENCE;
|
||||
} else if (stream.isStartElement()) {
|
||||
if (stream.name() == "name") {
|
||||
stream.readNext();
|
||||
temp_clip->name = stream.text().toString();
|
||||
} else if (stream.name() == "id") {
|
||||
stream.readNext();
|
||||
temp_clip_id = stream.text().toInt();
|
||||
} else if (stream.name() == "clipin") {
|
||||
stream.readNext();
|
||||
temp_clip->clip_in = stream.text().toInt();
|
||||
@@ -411,7 +427,7 @@ void Project::load_project() {
|
||||
state = LOAD_STATE_CLIP;
|
||||
} else if (stream.isStartElement() && stream.name() == "link") {
|
||||
stream.readNext();
|
||||
temp_clip->link_ids.append(stream.text().toInt());
|
||||
temp_clip->linked.append(stream.text().toInt());
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -469,15 +485,11 @@ void Project::save_project() {
|
||||
stream.writeTextElement("alayout", QString::number(s->audio_layout));
|
||||
stream.writeStartElement("clips");
|
||||
|
||||
// give clips IDs for links
|
||||
for (int i=0;i<s->clip_count();i++) {
|
||||
s->get_clip(i)->save_id = i;
|
||||
}
|
||||
|
||||
for (int i=0;i<s->clip_count();i++) {
|
||||
Clip* c = s->get_clip(i);
|
||||
|
||||
if (c != NULL) {
|
||||
stream.writeStartElement("clip");
|
||||
stream.writeTextElement("id", QString::number(c->id));
|
||||
stream.writeTextElement("name", c->name);
|
||||
stream.writeTextElement("clipin", QString::number(c->clip_in));
|
||||
stream.writeTextElement("in", QString::number(c->timeline_in));
|
||||
@@ -492,7 +504,7 @@ void Project::save_project() {
|
||||
stream.writeTextElement("stream", QString::number(c->media_stream->file_index));
|
||||
stream.writeStartElement("linked");
|
||||
for (int j=0;j<c->linked.size();j++) {
|
||||
stream.writeTextElement("link", QString::number(c->linked.at(j)->save_id));
|
||||
stream.writeTextElement("link", QString::number(c->linked.at(j)));
|
||||
}
|
||||
stream.writeEndElement();
|
||||
stream.writeStartElement("effects");
|
||||
@@ -506,6 +518,7 @@ void Project::save_project() {
|
||||
stream.writeEndElement();
|
||||
stream.writeEndElement();
|
||||
}
|
||||
}
|
||||
stream.writeEndElement();
|
||||
}
|
||||
}
|
||||
|
||||
+52
-13
@@ -86,6 +86,7 @@ void Timeline::next_cut() {
|
||||
long n_cut = LONG_MAX;
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c != NULL) {
|
||||
if (c->timeline_in < n_cut && c->timeline_in > playhead) {
|
||||
n_cut = c->timeline_in;
|
||||
seek_enabled = true;
|
||||
@@ -94,6 +95,7 @@ void Timeline::next_cut() {
|
||||
seek_enabled = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (seek_enabled) seek(n_cut);
|
||||
}
|
||||
|
||||
@@ -101,10 +103,12 @@ void Timeline::reset_all_audio() {
|
||||
// reset all clip audio
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c != NULL) {
|
||||
c->reset_audio = true;
|
||||
c->frame_sample_index = 0;
|
||||
c->audio_buffer_write = 0;
|
||||
}
|
||||
}
|
||||
clear_audio_ibuffer();
|
||||
}
|
||||
|
||||
@@ -267,7 +271,7 @@ void Timeline::select_all() {
|
||||
selections.clear();
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
selections.append({c->timeline_in, c->timeline_out, c->track});
|
||||
if (c != NULL) selections.append({c->timeline_in, c->timeline_out, c->track});
|
||||
}
|
||||
repaint_timeline();
|
||||
}
|
||||
@@ -295,10 +299,10 @@ void Timeline::delete_selection(bool ripple_delete) {
|
||||
// check every clip after and see if it'll collide
|
||||
// NOTE, we could probably re-use the validation code for the ripple tool here for optimization (since it's technically better code I think)
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c->timeline_in >= ripple_point) {
|
||||
if (c != NULL && c->timeline_in >= ripple_point) {
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* cc = sequence->get_clip(j);
|
||||
if (cc->timeline_in < ripple_point) {
|
||||
if (cc != NULL && cc->timeline_in < ripple_point) {
|
||||
validator = c->timeline_in - ripple_length - cc->timeline_out;
|
||||
if (validator < 0) ripple_length += validator;
|
||||
|
||||
@@ -340,7 +344,7 @@ void Timeline::set_zoom(bool in) {
|
||||
void Timeline::ripple(long ripple_point, long ripple_length) {
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c->timeline_in >= ripple_point) {
|
||||
if (c != NULL && c->timeline_in >= ripple_point) {
|
||||
c->timeline_in += ripple_length;
|
||||
c->timeline_out += ripple_length;
|
||||
}
|
||||
@@ -451,7 +455,7 @@ void Timeline::split_clip_and_relink(Clip* pre_clip, long frame, bool relink) {
|
||||
|
||||
// find linked clips of old clip
|
||||
for (int i=0;i<pre_clip->linked.size();i++) {
|
||||
Clip* link = pre_clip->linked.at(i);
|
||||
Clip* link = sequence->get_clip(pre_clip->linked.at(i));
|
||||
if (!panel_timeline->is_clip_selected(link)) {
|
||||
Clip* s = sequence->split_clip(link, frame);
|
||||
if (s != NULL) splits.append(s);
|
||||
@@ -464,7 +468,7 @@ void Timeline::split_clip_and_relink(Clip* pre_clip, long frame, bool relink) {
|
||||
for (int j=0;j<splits.size();j++) {
|
||||
Clip* cc = splits.at(j);
|
||||
if (c != cc) {
|
||||
c->linked.append(cc);
|
||||
c->linked.append(cc->id);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -479,7 +483,7 @@ void Timeline::delete_areas_and_relink(QVector<Selection>& areas) {
|
||||
const Selection& s = areas.at(i);
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* c = sequence->get_clip(j);
|
||||
if (c->track == s.track && !c->undeletable) {
|
||||
if (c != NULL && c->track == s.track && !c->undeletable) {
|
||||
if (c->timeline_in >= s.in && c->timeline_out <= s.out) {
|
||||
// clips falls entirely within deletion area
|
||||
sequence->delete_clip(j);
|
||||
@@ -513,8 +517,8 @@ void Timeline::delete_areas_and_relink(QVector<Selection>& areas) {
|
||||
Clip* c = pre_clips.at(i);
|
||||
for (int j=0;j<pre_clips.size();j++) {
|
||||
for (int k=0;k<c->linked.size();k++) {
|
||||
if (c->linked.at(k) == pre_clips.at(j)) {
|
||||
post_clips.at(i)->linked.append(post_clips.at(j));
|
||||
if (c->linked.at(k) == pre_clips.at(j)->id) {
|
||||
post_clips.at(i)->linked.append(post_clips.at(j)->id);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -529,6 +533,7 @@ void Timeline::copy(bool del) {
|
||||
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c != NULL) {
|
||||
for (int j=0;j<selections.size();j++) {
|
||||
const Selection& s = selections.at(j);
|
||||
if (s.track == c->track && !((c->timeline_in < s.in && c->timeline_out < s.in) || (c->timeline_in > s.out && c->timeline_out > s.out))) {
|
||||
@@ -539,6 +544,9 @@ void Timeline::copy(bool del) {
|
||||
|
||||
Clip* copied_clip = c->copy();
|
||||
|
||||
// copy linked IDs (we correct these later in paste())
|
||||
copied_clip->linked = c->linked;
|
||||
|
||||
if (copied_clip->timeline_in < s.in) {
|
||||
copied_clip->clip_in += (s.in - copied_clip->timeline_in);
|
||||
copied_clip->timeline_in = s.in;
|
||||
@@ -559,6 +567,7 @@ void Timeline::copy(bool del) {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int i=0;i<clip_clipboard.size();i++) {
|
||||
// initialize all timeline_ins to 0 or offsets of
|
||||
@@ -571,6 +580,23 @@ void Timeline::copy(bool del) {
|
||||
}
|
||||
}
|
||||
|
||||
void Timeline::relink_clips_using_ids(QVector<Clip*>& old_clips, QVector<Clip*>& new_clips) {
|
||||
// relink pasted clips
|
||||
for (int i=0;i<old_clips.size();i++) {
|
||||
// these indices should correspond
|
||||
Clip* oc = old_clips.at(i);
|
||||
Clip* nc = new_clips.at(i);
|
||||
|
||||
for (int j=0;j<oc->linked.size();j++) {
|
||||
for (int k=0;k<old_clips.size();k++) { // find clip with that ID
|
||||
if (old_clips.at(k)->id == oc->linked.at(j)) {
|
||||
nc->linked.append(new_clips.at(k)->id);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Timeline::paste() {
|
||||
if (clip_clipboard.size() > 0) {
|
||||
QVector<Selection> delete_areas;
|
||||
@@ -579,14 +605,20 @@ void Timeline::paste() {
|
||||
delete_areas.append({c->timeline_in + playhead, c->timeline_out + playhead, c->track});
|
||||
}
|
||||
delete_areas_and_relink(delete_areas);
|
||||
|
||||
QVector<Clip*> added_clips;
|
||||
for (int i=0;i<clip_clipboard.size();i++) {
|
||||
Clip* c = clip_clipboard.at(i);
|
||||
Clip* cc = c->copy();
|
||||
cc->timeline_in += playhead;
|
||||
cc->timeline_out += playhead;
|
||||
cc->sequence = sequence;
|
||||
added_clips.append(cc);
|
||||
sequence->add_clip(cc);
|
||||
}
|
||||
|
||||
relink_clips_using_ids(clip_clipboard, added_clips);
|
||||
|
||||
redraw_all_clips(true);
|
||||
}
|
||||
}
|
||||
@@ -600,9 +632,10 @@ bool Timeline::split_selection() {
|
||||
|
||||
// find clips within selection and split
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* clip = sequence->get_clip(j);
|
||||
if (clip != NULL) {
|
||||
for (int i=0;i<selections.size();i++) {
|
||||
const Selection& s = selections.at(i);
|
||||
Clip* clip = sequence->get_clip(j);
|
||||
if (s.track == clip->track) {
|
||||
Clip* post_a = sequence->split_clip(clip, s.in);
|
||||
Clip* post_b = sequence->split_clip(clip, s.out);
|
||||
@@ -620,6 +653,7 @@ bool Timeline::split_selection() {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// relink after splitting
|
||||
for (int i=0;i<pre_splits.size();i++) {
|
||||
@@ -627,8 +661,8 @@ bool Timeline::split_selection() {
|
||||
Clip* pre = pre_splits.at(i);
|
||||
for (int j=0;j<pre_splits.size();j++) {
|
||||
for (int k=0;k<pre->linked.size();k++) {
|
||||
if (pre->linked.at(k) == pre_splits.at(j)) {
|
||||
post_splits.at(i)->linked.append(post_splits.at(j));
|
||||
if (pre->linked.at(k) == pre_splits.at(j)->id) {
|
||||
post_splits.at(i)->linked.append(post_splits.at(j)->id);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -644,7 +678,7 @@ void Timeline::split_at_playhead() {
|
||||
// see if whole clips are selected
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* clip = sequence->get_clip(j);
|
||||
if (is_clip_selected(clip)) {
|
||||
if (clip != NULL && is_clip_selected(clip)) {
|
||||
// should this relink?
|
||||
sequence->split_clip(clip, playhead);
|
||||
split_selected = true;
|
||||
@@ -660,11 +694,14 @@ void Timeline::split_at_playhead() {
|
||||
// if nothing was selected or no selections fell within playhead, simply split at playhead
|
||||
if (!split_selected) {
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* c = sequence->get_clip(j);
|
||||
if (c != NULL) {
|
||||
// always relinks
|
||||
split_clip_and_relink(sequence->get_clip(j), playhead, true);
|
||||
split_selected = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (split_selected) redraw_all_clips(true);
|
||||
}
|
||||
@@ -686,6 +723,7 @@ void Timeline::snap_to_clip(long* l, bool playhead_inclusive) {
|
||||
if (!playhead_inclusive || !snap_to_point(playhead, l)) {
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c != NULL) {
|
||||
if (snap_to_point(c->timeline_in, l)) {
|
||||
break;
|
||||
} else if (snap_to_point(c->timeline_out, l)) {
|
||||
@@ -694,6 +732,7 @@ void Timeline::snap_to_clip(long* l, bool playhead_inclusive) {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Timeline::increase_track_height() {
|
||||
|
||||
@@ -69,6 +69,7 @@ public:
|
||||
void split_at_playhead();
|
||||
void split_clip_and_relink(Clip* clip, long frame, bool relink);
|
||||
void delete_areas_and_relink(QVector<Selection>& areas);
|
||||
void relink_clips_using_ids(QVector<Clip*>& old_clips, QVector<Clip*>& new_clips);
|
||||
void update_sequence();
|
||||
void increase_track_height();
|
||||
void decrease_track_height();
|
||||
|
||||
@@ -32,6 +32,7 @@ void handle_media(Sequence* sequence, long playhead, bool multithreaded) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
|
||||
// if clip starts within one second and/or hasn't finished yet
|
||||
if (c != NULL) {
|
||||
if (is_clip_active(c, playhead)) {
|
||||
// if thread is already working, we don't want to touch this,
|
||||
// but we also don't want to hang the UI thread
|
||||
@@ -59,6 +60,7 @@ void handle_media(Sequence* sequence, long playhead, bool multithreaded) {
|
||||
close_clip(c);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void open_clip(Clip* clip, bool multithreaded) {
|
||||
@@ -295,7 +297,7 @@ void set_sequence(Sequence* s) {
|
||||
// clean up - close all open clips
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c->open) {
|
||||
if (c != NULL && c->open) {
|
||||
close_clip(c);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ Clip* Clip::copy() {
|
||||
Clip* copy = new Clip();
|
||||
|
||||
copy->enabled = enabled;
|
||||
copy->id = id;
|
||||
copy->name = QString(name);
|
||||
copy->clip_in = clip_in;
|
||||
copy->timeline_in = timeline_in;
|
||||
|
||||
+2
-5
@@ -40,6 +40,7 @@ struct Clip
|
||||
|
||||
// timeline variables
|
||||
bool enabled;
|
||||
int id;
|
||||
QString name;
|
||||
long clip_in;
|
||||
long timeline_in;
|
||||
@@ -57,7 +58,7 @@ struct Clip
|
||||
|
||||
// other variables (should be "duplicated" in copy())
|
||||
QList<Effect*> effects;
|
||||
QVector<Clip*> linked;
|
||||
QVector<int> linked;
|
||||
|
||||
// media handling
|
||||
AVFormatContext* formatCtx;
|
||||
@@ -94,10 +95,6 @@ struct Clip
|
||||
bool reset_audio;
|
||||
bool audio_just_reset;
|
||||
long audio_target_frame;
|
||||
|
||||
// only used for saving/loading
|
||||
int save_id;
|
||||
QVector<int> link_ids;
|
||||
};
|
||||
|
||||
#endif // CLIP_H
|
||||
|
||||
+43
-40
@@ -16,6 +16,7 @@ Sequence::~Sequence() {
|
||||
}
|
||||
|
||||
void Sequence::add_clip(Clip* c) {
|
||||
c->id = clip_count();
|
||||
clips.append(c);
|
||||
}
|
||||
|
||||
@@ -32,7 +33,8 @@ void Sequence::delete_clip(int i) {
|
||||
for (int j=0;j<clip_count();j++) {
|
||||
Clip* c = get_clip(j);
|
||||
for (int k=0;k<c->linked.size();k++) {
|
||||
if (c->linked[k] == clips[i]) {
|
||||
if (c->linked[k] == clips[i]->id) {
|
||||
// c->linked[k] = NULL;
|
||||
c->linked.removeAt(k);
|
||||
break;
|
||||
}
|
||||
@@ -41,15 +43,14 @@ void Sequence::delete_clip(int i) {
|
||||
|
||||
// finally remove from vector
|
||||
delete clips.at(i);
|
||||
// clips[i] = NULL;
|
||||
clips.removeAt(i);
|
||||
clips[i] = NULL;
|
||||
}
|
||||
|
||||
long Sequence::getEndFrame() {
|
||||
long end = 0;
|
||||
for (int j=0;j<clip_count();j++) {
|
||||
Clip* c = get_clip(j);
|
||||
if (c->timeline_out > end) {
|
||||
if (c != NULL && c->timeline_out > end) {
|
||||
end = c->timeline_out;
|
||||
}
|
||||
}
|
||||
@@ -61,12 +62,14 @@ void Sequence::get_track_limits(int* video_tracks, int* audio_tracks) {
|
||||
int at = 0;
|
||||
for (int j=0;j<clip_count();j++) {
|
||||
Clip* c = get_clip(j);
|
||||
if (c != NULL) {
|
||||
if (c->track < 0 && c->track < vt) { // video clip
|
||||
vt = c->track;
|
||||
} else if (c->track > at) {
|
||||
at = c->track;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (video_tracks != NULL) *video_tracks = vt;
|
||||
if (audio_tracks != NULL) *audio_tracks = at;
|
||||
}
|
||||
@@ -91,52 +94,52 @@ Clip* Sequence::split_clip(Clip* pre, long frame) {
|
||||
}
|
||||
|
||||
void Sequence::undo_add_current() {
|
||||
if (undo_stack.size() == UNDO_LIMIT) {
|
||||
delete undo_stack.at(0);
|
||||
undo_stack.removeFirst();
|
||||
} else {
|
||||
undo_pointer++;
|
||||
while (undo_stack.size() > undo_pointer+1) {
|
||||
delete undo_stack.last();
|
||||
undo_stack.removeLast();
|
||||
}
|
||||
}
|
||||
// if (undo_stack.size() == UNDO_LIMIT) {
|
||||
// delete undo_stack.at(0);
|
||||
// undo_stack.removeFirst();
|
||||
// } else {
|
||||
// undo_pointer++;
|
||||
// while (undo_stack.size() > undo_pointer+1) {
|
||||
// delete undo_stack.last();
|
||||
// undo_stack.removeLast();
|
||||
// }
|
||||
// }
|
||||
|
||||
// copy clips
|
||||
QVector<Clip*>* copied_clips = new QVector<Clip*>();
|
||||
for (int i=0;i<clip_count();i++) {
|
||||
copied_clips->append(get_clip(i)->copy());
|
||||
}
|
||||
undo_stack.append(copied_clips);
|
||||
// // copy clips
|
||||
// QVector<Clip*>* copied_clips = new QVector<Clip*>();
|
||||
// for (int i=0;i<clip_count();i++) {
|
||||
// copied_clips->append(get_clip(i)->copy());
|
||||
// }
|
||||
// undo_stack.append(copied_clips);
|
||||
}
|
||||
|
||||
void Sequence::set_undo(int i) {
|
||||
for (int i=0;i<clip_count();i++) {
|
||||
delete clips.at(i);
|
||||
}
|
||||
clips.clear();
|
||||
// for (int i=0;i<clip_count();i++) {
|
||||
// delete clips.at(i);
|
||||
// }
|
||||
// clips.clear();
|
||||
|
||||
QVector<Clip*>* copy_from_list = undo_stack.at(undo_pointer);
|
||||
for (int i=0;i<copy_from_list->size();i++) {
|
||||
add_clip(copy_from_list->at(i)->copy());
|
||||
}
|
||||
// QVector<Clip*>* copy_from_list = undo_stack.at(undo_pointer);
|
||||
// for (int i=0;i<copy_from_list->size();i++) {
|
||||
// add_clip(copy_from_list->at(i)->copy());
|
||||
// }
|
||||
}
|
||||
|
||||
void Sequence::undo() {
|
||||
if (undo_pointer > 0) {
|
||||
undo_pointer--;
|
||||
set_undo(undo_pointer);
|
||||
} else {
|
||||
qDebug() << "[INFO] No more undos";
|
||||
}
|
||||
// if (undo_pointer > 0) {
|
||||
// undo_pointer--;
|
||||
// set_undo(undo_pointer);
|
||||
// } else {
|
||||
// qDebug() << "[INFO] No more undos";
|
||||
// }
|
||||
}
|
||||
void Sequence::redo() {
|
||||
if (undo_pointer == undo_stack.size() - 1) {
|
||||
qDebug() << "[INFO] No more redos";
|
||||
} else {
|
||||
undo_pointer++;
|
||||
set_undo(undo_pointer);
|
||||
}
|
||||
// if (undo_pointer == undo_stack.size() - 1) {
|
||||
// qDebug() << "[INFO] No more redos";
|
||||
// } else {
|
||||
// undo_pointer++;
|
||||
// set_undo(undo_pointer);
|
||||
// }
|
||||
}
|
||||
|
||||
// static variable for the currently active sequence
|
||||
|
||||
@@ -16,7 +16,6 @@ public:
|
||||
int clip_count();
|
||||
Clip* get_clip(int i);
|
||||
void delete_clip(int i);
|
||||
// void delete_area(long in, long out, int track);
|
||||
Clip* split_clip(Clip* pre, long frame);
|
||||
void get_track_limits(int* video_tracks, int* audio_tracks);
|
||||
long getEndFrame();
|
||||
|
||||
+25
-12
@@ -148,7 +148,7 @@ void TimelineWidget::dropEvent(QDropEvent* event) {
|
||||
for (int j=0;j<added_clips.size();j++) {
|
||||
Clip* cc = added_clips.at(j);
|
||||
if (c != cc && c->media == cc->media) {
|
||||
c->linked.append(cc);
|
||||
c->linked.append(cc->id);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -198,7 +198,8 @@ void TimelineWidget::mousePressEvent(QMouseEvent *event) {
|
||||
track_resize_mouse_cache = event->pos().y();
|
||||
panel_timeline->moving_init = true;
|
||||
} else if (clip_index >= 0) {
|
||||
if (panel_timeline->is_clip_selected(sequence->get_clip(clip_index))) {
|
||||
Clip* c = sequence->get_clip(clip_index);
|
||||
if (c != NULL && panel_timeline->is_clip_selected(c)) {
|
||||
// TODO if shift is down, deselect it
|
||||
} else {
|
||||
// if "shift" is not down
|
||||
@@ -207,18 +208,20 @@ void TimelineWidget::mousePressEvent(QMouseEvent *event) {
|
||||
}
|
||||
|
||||
Clip* clip = sequence->get_clip(clip_index);
|
||||
if (clip != NULL) {
|
||||
panel_timeline->selections.append({clip->timeline_in, clip->timeline_out, clip->track});
|
||||
|
||||
// if alt is not down, select links
|
||||
if (!(event->modifiers() & Qt::AltModifier)) {
|
||||
for (int i=0;i<clip->linked.size();i++) {
|
||||
Clip* link = clip->linked.at(i);
|
||||
Clip* link = sequence->get_clip(c->linked.at(i));
|
||||
if (!panel_timeline->is_clip_selected(link)) {
|
||||
panel_timeline->selections.append({link->timeline_in, link->timeline_out, link->track});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
panel_timeline->moving_init = true;
|
||||
} else {
|
||||
panel_timeline->selections.clear();
|
||||
@@ -233,7 +236,8 @@ void TimelineWidget::mousePressEvent(QMouseEvent *event) {
|
||||
case TIMELINE_TOOL_RAZOR:
|
||||
{
|
||||
if (clip_index >= 0) {
|
||||
panel_timeline->split_clip_and_relink(sequence->get_clip(clip_index), panel_timeline->drag_frame_start, !(event->modifiers() & Qt::AltModifier));
|
||||
Clip* clip = sequence->get_clip(clip_index);
|
||||
if (clip != NULL) panel_timeline->split_clip_and_relink(clip, panel_timeline->drag_frame_start, !(event->modifiers() & Qt::AltModifier));
|
||||
}
|
||||
panel_timeline->splitting = true;
|
||||
panel_timeline->redraw_all_clips(true);
|
||||
@@ -248,6 +252,7 @@ void TimelineWidget::mouseReleaseEvent(QMouseEvent *event) {
|
||||
if (panel_timeline->moving_proc) {
|
||||
if (event->modifiers() & Qt::AltModifier) { // if holding alt, duplicate rather than move
|
||||
// duplicate clips
|
||||
QVector<Clip*> old_clips;
|
||||
QVector<Clip*> copy_clips;
|
||||
QVector<Selection> delete_areas;
|
||||
for (int i=0;i<panel_timeline->ghosts.size();i++) {
|
||||
@@ -261,6 +266,7 @@ void TimelineWidget::mouseReleaseEvent(QMouseEvent *event) {
|
||||
|
||||
delete_areas.append({g.in, g.out, g.track});
|
||||
|
||||
old_clips.append(g.clip);
|
||||
copy_clips.append(c);
|
||||
}
|
||||
}
|
||||
@@ -270,6 +276,8 @@ void TimelineWidget::mouseReleaseEvent(QMouseEvent *event) {
|
||||
// step 2 - delete anything that exists in area that clip is moving to
|
||||
sequence->add_clip(copy_clips.at(i));
|
||||
}
|
||||
// relink duplicated clips
|
||||
panel_timeline->relink_clips_using_ids(old_clips, copy_clips);
|
||||
}
|
||||
} else {
|
||||
// move clips
|
||||
@@ -355,7 +363,7 @@ void TimelineWidget::mouseReleaseEvent(QMouseEvent *event) {
|
||||
Clip* aclip = NULL;
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* clip = sequence->get_clip(i);
|
||||
if (panel_timeline->is_clip_selected(clip)) {
|
||||
if (clip != NULL && panel_timeline->is_clip_selected(clip)) {
|
||||
if (clip->track < 0) {
|
||||
if (got_vclip) {
|
||||
vclip = NULL;
|
||||
@@ -380,7 +388,7 @@ void TimelineWidget::mouseReleaseEvent(QMouseEvent *event) {
|
||||
if (vclip != NULL && aclip != NULL) {
|
||||
bool found = false;
|
||||
for (int i=0;i<vclip->linked.size();i++) {
|
||||
if (vclip->linked.at(i) == aclip) {
|
||||
if (vclip->linked.at(i) == aclip->id) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
@@ -441,6 +449,7 @@ void validate_snapping(Ghost& g, long* frame_diff) {
|
||||
if (!subvalidate_snapping(g, frame_diff, panel_timeline->playhead)) {
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* c = sequence->get_clip(j);
|
||||
if (c != NULL) {
|
||||
if (!subvalidate_snapping(g, frame_diff, c->timeline_in)) {
|
||||
subvalidate_snapping(g, frame_diff, c->timeline_out);
|
||||
}
|
||||
@@ -448,6 +457,7 @@ void validate_snapping(Ghost& g, long* frame_diff) {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void TimelineWidget::update_ghosts(QPoint& mouse_pos) {
|
||||
@@ -682,7 +692,7 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
|
||||
// create ghosts
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (panel_timeline->is_clip_selected(c)) {
|
||||
if (c != NULL && panel_timeline->is_clip_selected(c)) {
|
||||
panel_timeline->ghosts.append({c, c->timeline_in, c->timeline_out, c->track, c->clip_in});
|
||||
}
|
||||
}
|
||||
@@ -692,9 +702,11 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
|
||||
for (int i=0;i<panel_timeline->ghosts.size();i++) {
|
||||
// get clips before and after ripple point
|
||||
for (int j=0;j<sequence->clip_count();j++) {
|
||||
Clip* cc = sequence->get_clip(j);
|
||||
|
||||
if (cc != NULL) {
|
||||
// don't cache any currently selected clips
|
||||
Clip* c = panel_timeline->ghosts.at(i).clip;
|
||||
Clip* cc = sequence->get_clip(j);
|
||||
bool is_selected = false;
|
||||
for (int k=0;k<panel_timeline->ghosts.size();k++) {
|
||||
if (panel_timeline->ghosts.at(k).clip == cc) {
|
||||
@@ -742,6 +754,7 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
init_ghosts();
|
||||
@@ -754,7 +767,7 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
|
||||
bool repaint = false;
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* clip = sequence->get_clip(i);
|
||||
if (clip->track == track) {
|
||||
if (clip != NULL && clip->track == track) {
|
||||
panel_timeline->split_clip_and_relink(clip, panel_timeline->drag_frame_start, !(event->modifiers() & Qt::AltModifier));
|
||||
repaint = true;
|
||||
}
|
||||
@@ -775,7 +788,7 @@ void TimelineWidget::mouseMoveEvent(QMouseEvent *event) {
|
||||
int closeness = INT_MAX;
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c->track == mouse_track) {
|
||||
if (c != NULL && c->track == mouse_track) {
|
||||
if (c->timeline_in > mouse_frame_lower && c->timeline_in < mouse_frame_upper) {
|
||||
int nc = abs(c->timeline_in + 1 - panel_timeline->cursor_frame);
|
||||
if (nc < closeness) {
|
||||
@@ -855,7 +868,7 @@ void TimelineWidget::redraw_clips() {
|
||||
int audio_track_limit = 0;
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* clip = sequence->get_clip(i);
|
||||
if (is_track_visible(clip->track)) {
|
||||
if (clip != NULL && is_track_visible(clip->track)) {
|
||||
if (clip->track < 0 && clip->track < video_track_limit) { // video clip
|
||||
video_track_limit = clip->track;
|
||||
} else if (clip->track > audio_track_limit) {
|
||||
@@ -1068,7 +1081,7 @@ int TimelineWidget::getScreenPointFromTrack(int track) {
|
||||
int TimelineWidget::getClipIndexFromCoords(long frame, int track) {
|
||||
for (int i=0;i<sequence->clip_count();i++) {
|
||||
Clip* c = sequence->get_clip(i);
|
||||
if (c->track == track) {
|
||||
if (c != NULL && c->track == track) {
|
||||
if (frame >= c->timeline_in && frame < c->timeline_out) {
|
||||
return i;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user