lv2 rework, sams ffmpeg icons, elision patch
[goodguy/history.git] / cinelerra-5.1 / cinelerra / mwindowedit.C
index ca3475edb94716c44e4d2d658f671378b41e2fff..065c1f9f08d475fe994aec06fb3a1f39de87cd04 100644 (file)
@@ -325,55 +325,66 @@ void MWindow::clear(int clear_handle)
        }
 }
 
+void MWindow::update_gui(int changed_edl)
+{
+       restart_brender();
+       update_plugin_guis();
+       if( changed_edl ) {
+               gui->update(1, 2, 1, 1, 1, 1, 0);
+               cwindow->update(1, 0, 0, 0, 1);
+               cwindow->refresh_frame(CHANGE_EDL);
+       }
+       else {
+               gui->draw_overlays(1);
+               sync_parameters(CHANGE_PARAMS);
+               gui->update_patchbay();
+               cwindow->update(1, 0, 0);
+       }
+}
+
 void MWindow::set_automation_mode(int mode)
 {
        undo->update_undo_before();
+       speed_before();
        edl->tracks->set_automation_mode(
                edl->local_session->get_selectionstart(),
                edl->local_session->get_selectionend(),
                mode);
+       int changed_edl = speed_after(1);
        save_backup();
        char string[BCSTRLEN];
        sprintf(string,"set %s", FloatAuto::curve_name(mode));
-       undo->update_undo_after(string, LOAD_AUTOMATION);
-
-       restart_brender();
-       update_plugin_guis();
-       gui->draw_overlays(1);
-       sync_parameters(CHANGE_PARAMS);
-       gui->update_patchbay();
-       cwindow->update(1, 0, 0);
+       undo->update_undo_after(string,
+               !changed_edl ? LOAD_AUTOMATION :
+                       LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
+       update_gui(changed_edl);
 }
 
 void MWindow::clear_automation()
 {
        undo->update_undo_before();
+       speed_before();
        edl->tracks->clear_automation(edl->local_session->get_selectionstart(),
                edl->local_session->get_selectionend());
+       int changed_edl = speed_after(1);
        save_backup();
-       undo->update_undo_after(_("clear keyframes"), LOAD_AUTOMATION);
-
-       restart_brender();
-       update_plugin_guis();
-       gui->draw_overlays(1);
-       sync_parameters(CHANGE_PARAMS);
-       gui->update_patchbay();
-       cwindow->update(1, 0, 0);
+       undo->update_undo_after(_("clear keyframes"),
+               !changed_edl ? LOAD_AUTOMATION :
+                       LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
+       update_gui(changed_edl);
 }
 
 int MWindow::clear_default_keyframe()
 {
        undo->update_undo_before();
+       speed_before();
        edl->tracks->clear_default_keyframe();
+       int changed_edl = speed_after(1);
        save_backup();
-       undo->update_undo_after(_("clear default keyframe"), LOAD_AUTOMATION);
-
-       restart_brender();
-       gui->draw_overlays(1);
-       sync_parameters(CHANGE_PARAMS);
-       gui->update_patchbay();
-       cwindow->update(1, 0, 0);
-
+       undo->update_undo_after(_("clear default keyframe"),
+               !changed_edl ? LOAD_AUTOMATION :
+                       LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
+       update_gui(changed_edl);
        return 0;
 }
 
@@ -593,21 +604,16 @@ void MWindow::cut_right_label()
 int MWindow::cut_automation()
 {
        undo->update_undo_before();
-
+       speed_before();
        copy_automation();
-
        edl->tracks->clear_automation(edl->local_session->get_selectionstart(),
                edl->local_session->get_selectionend());
+       int changed_edl = speed_after(1);
        save_backup();
-       undo->update_undo_after(_("cut keyframes"), LOAD_AUTOMATION);
-
-
-       restart_brender();
-       update_plugin_guis();
-       gui->draw_overlays(1);
-       sync_parameters(CHANGE_PARAMS);
-       gui->update_patchbay();
-       cwindow->update(1, 0, 0);
+       undo->update_undo_after(_("cut keyframes"),
+               !changed_edl ? LOAD_AUTOMATION :
+                       LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
+       update_gui(changed_edl);
        return 0;
 }
 
@@ -615,18 +621,15 @@ int MWindow::cut_default_keyframe()
 {
 
        undo->update_undo_before();
+       speed_before();
        copy_default_keyframe();
        edl->tracks->clear_default_keyframe();
-       undo->update_undo_after(_("cut default keyframe"), LOAD_AUTOMATION);
-
-       restart_brender();
-       gui->draw_overlays(1);
-       sync_parameters(CHANGE_PARAMS);
-       gui->update_patchbay();
-       cwindow->update(1, 0, 0);
+       int changed_edl = speed_after(1);
        save_backup();
-
-
+       undo->update_undo_after(_("cut default keyframe"),
+               !changed_edl ? LOAD_AUTOMATION :
+                       LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
+       update_gui(changed_edl);
        return 0;
 }
 
@@ -1243,26 +1246,23 @@ int MWindow::paste_automation()
 
        if( len ) {
                undo->update_undo_before();
+               speed_before();
                char *string = new char[len];
                gui->from_clipboard(string, len, BC_PRIMARY_SELECTION);
                FileXML file;
                file.read_from_string(string);
-
+               delete [] string;
                double start = edl->local_session->get_selectionstart();
                double end = edl->local_session->get_selectionend();
                edl->tracks->clear_automation(start, end);
                edl->tracks->paste_automation(start, &file, 0, 1,
                        edl->session->typeless_keyframes);
+               int changed_edl = speed_after(1);
                save_backup();
-               undo->update_undo_after(_("paste keyframes"), LOAD_AUTOMATION);
-               delete [] string;
-
-               restart_brender();
-               update_plugin_guis();
-               gui->draw_overlays(1);
-               sync_parameters(CHANGE_PARAMS);
-               gui->update_patchbay();
-               cwindow->update(1, 0, 0);
+               undo->update_undo_after(_("paste keyframes"),
+                       !changed_edl ? LOAD_AUTOMATION :
+                               LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
+               update_gui(changed_edl);
        }
 
        return 0;
@@ -1274,24 +1274,22 @@ int MWindow::paste_default_keyframe()
 
        if( len ) {
                undo->update_undo_before();
+               speed_before();
                char *string = new char[len];
                gui->from_clipboard(string, len, BC_PRIMARY_SELECTION);
                FileXML file;
                file.read_from_string(string);
+               delete [] string;
                double start = edl->local_session->get_selectionstart();
                edl->tracks->paste_automation(start, &file, 1, 0,
                        edl->session->typeless_keyframes);
 //             edl->tracks->paste_default_keyframe(&file);
-               undo->update_undo_after(_("paste default keyframe"), LOAD_AUTOMATION);
-
-               restart_brender();
-               update_plugin_guis();
-               gui->draw_overlays(1);
-               sync_parameters(CHANGE_PARAMS);
-               gui->update_patchbay();
-               cwindow->update(1, 0, 0);
-               delete [] string;
+               int changed_edl = speed_after(1);
+               undo->update_undo_after(_("paste default keyframe"),
+                       !changed_edl ? LOAD_AUTOMATION :
+                               LOAD_AUTOMATION + LOAD_EDITS + LOAD_TIMEBAR);
                save_backup();
+               update_gui(changed_edl);
        }
 
        return 0;
@@ -1600,6 +1598,10 @@ void MWindow::paste_silence()
 {
        double start = edl->local_session->get_selectionstart();
        double end = edl->local_session->get_selectionend();
+       if( EQUIV(start, end) ) {
+               if( edl->session->frame_rate > 0 )
+                       end += 1./edl->session->frame_rate;
+       }
        undo->update_undo_before();
        edl->paste_silence(start, end,
                edl->session->labels_follow_edits,
@@ -1796,7 +1798,7 @@ void MWindow::align_edits()
 
 void MWindow::set_edit_length(double length)
 {
-       gui->lock_window("MWindow::detach_transitions 1");
+       gui->lock_window("MWindow::set_edit_length 1");
 
        undo->update_undo_before();
        double start = edl->local_session->get_selectionstart();
@@ -1816,7 +1818,7 @@ void MWindow::set_edit_length(double length)
 
 void MWindow::set_transition_length(Transition *transition, double length)
 {
-       gui->lock_window("MWindow::detach_transitions 1");
+       gui->lock_window("MWindow::set_transition_length 1");
 
        undo->update_undo_before();
        //double start = edl->local_session->get_selectionstart();
@@ -1835,7 +1837,7 @@ void MWindow::set_transition_length(Transition *transition, double length)
 
 void MWindow::set_transition_length(double length)
 {
-       gui->lock_window("MWindow::detach_transitions 1");
+       gui->lock_window("MWindow::set_transition_length 2");
 
        undo->update_undo_before();
        double start = edl->local_session->get_selectionstart();
@@ -2053,9 +2055,9 @@ void MWindow::save_clip(EDL *new_edl, const char *txt)
                n = snprintf(cp, sz, "%s", txt);
                cp += n;  sz -= n;
        }
-       n = snprintf(cp, sz, 
+       n = snprintf(cp, sz,
                "%02d/%02d/%02d %02d:%02d:%02d,  +%s\n",
-               dtm.tm_year+1900, dtm.tm_mon+1, dtm.tm_mday, 
+               dtm.tm_year+1900, dtm.tm_mon+1, dtm.tm_mday,
                dtm.tm_hour, dtm.tm_min, dtm.tm_sec, duration);
        cp += n;  sz -= n;
        if( path && *path ) {
@@ -2438,4 +2440,58 @@ void MWindow::cut_commercials()
        cwindow->refresh_frame(CHANGE_EDL);
 }
 
+int MWindow::normalize_speed(EDL *old_edl, EDL *new_edl)
+{
+       int result = 0;
+       Track *old_track = old_edl->tracks->first;
+       Track *new_track = new_edl->tracks->first;
+       for( ; old_track && new_track; old_track=old_track->next, new_track=new_track->next ) {
+               if( old_track->data_type != new_track->data_type ) continue;
+               FloatAutos *old_speeds = (FloatAutos *)old_track->automation->autos[AUTOMATION_SPEED];
+               FloatAutos *new_speeds = (FloatAutos *)new_track->automation->autos[AUTOMATION_SPEED];
+               if( !old_speeds || !new_speeds ) continue;
+               FloatAuto *old_speed = (FloatAuto *)old_speeds->first;
+               FloatAuto *new_speed = (FloatAuto *)new_speeds->first;
+               while( old_speed && new_speed && old_speed->equals(new_speed) ) {
+                       old_speed = (FloatAuto *)old_speed->next;
+                       new_speed = (FloatAuto *)new_speed->next;
+               }
+               Edit *old_edit = old_track->edits->first;
+               Edit *new_edit = new_track->edits->first;
+               for( ; old_edit && new_edit; old_edit=old_edit->next, new_edit=new_edit->next ) {
+                       int64_t edit_start = old_edit->startproject, edit_end = edit_start + old_edit->length;
+                       if( old_speed || new_speed ) {
+                               double orig_start = old_speeds->automation_integral(0, edit_start, PLAY_FORWARD);
+                               double orig_end   = old_speeds->automation_integral(0, edit_end, PLAY_FORWARD);
+                               edit_start = new_speeds->speed_position(orig_start);
+                               edit_end = new_speeds->speed_position(orig_end);
+                               result = 1;
+                       }
+                       new_edit->startproject = edit_start;
+                       new_edit->length = edit_end - edit_start;
+               }
+       }
+       return result;
+}
+
+void MWindow::speed_before()
+{
+       if( !speed_edl ) {
+               speed_edl = new EDL;
+               speed_edl->create_objects();
+       }
+       speed_edl->copy_all(edl);
+}
+
+int MWindow::speed_after(int done)
+{
+       int result = 0;
+       if( speed_edl && done >= 0 )
+               result = normalize_speed(speed_edl, edl);
+       if( done ) {
+               speed_edl->remove_user();
+               speed_edl = 0;
+       }
+       return result;
+}