From e23393f4ff9f772ac8f47926cf490dc87a630ed4 Mon Sep 17 00:00:00 2001 From: Good Guy Date: Wed, 19 Dec 2018 18:40:17 -0700 Subject: [PATCH] add grouping, default proxy vcodec h264.mp4, default titlebar alpha=1, green bar bug --- cinelerra-5.1/cinelerra/edit.C | 16 +- cinelerra-5.1/cinelerra/edit.h | 3 + cinelerra-5.1/cinelerra/editpopup.C | 9 +- cinelerra-5.1/cinelerra/edl.C | 24 +++ cinelerra-5.1/cinelerra/edl.h | 2 + cinelerra-5.1/cinelerra/mainsession.C | 9 +- cinelerra-5.1/cinelerra/mainsession.h | 10 ++ cinelerra-5.1/cinelerra/mainsession.inc | 1 + cinelerra-5.1/cinelerra/mwindow.C | 37 ++++- cinelerra-5.1/cinelerra/mwindow.h | 6 +- cinelerra-5.1/cinelerra/mwindowedit.C | 28 +++- cinelerra-5.1/cinelerra/mwindowgui.C | 3 +- cinelerra-5.1/cinelerra/proxy.C | 2 + cinelerra-5.1/cinelerra/resourcepixmap.C | 4 +- cinelerra-5.1/cinelerra/trackcanvas.C | 178 +++++++++++++++++------ cinelerra-5.1/cinelerra/trackcanvas.h | 2 + cinelerra-5.1/cinelerra/tracks.C | 42 +++++- cinelerra-5.1/cinelerra/tracks.h | 22 ++- cinelerra-5.1/cinelerra/tracksedit.C | 30 ++++ 19 files changed, 349 insertions(+), 79 deletions(-) diff --git a/cinelerra-5.1/cinelerra/edit.C b/cinelerra-5.1/cinelerra/edit.C index 79e95f36..e40b8c18 100644 --- a/cinelerra-5.1/cinelerra/edit.C +++ b/cinelerra-5.1/cinelerra/edit.C @@ -87,6 +87,7 @@ void Edit::reset() hard_left = 0; hard_right = 0; color = 0; + group_id = 0; } Indexable* Edit::get_source() @@ -143,6 +144,7 @@ int Edit::copy(int64_t start, file->tag.set_property("HARD_LEFT", hard_left); file->tag.set_property("HARD_RIGHT", hard_right); file->tag.set_property("COLOR", color); + file->tag.set_property("GROUP_ID", group_id); if(user_title[0]) file->tag.set_property("USER_TITLE", user_title); //printf("Edit::copy 5\n"); @@ -240,7 +242,15 @@ int Edit::silence() asset || nested_edl : *((SEdit *)this)->get_text()) ? 0 : 1; } - +void Edit::mute() +{ + if( track->data_type != TRACK_SUBTITLE ) { + asset = 0; + nested_edl = 0; + } + else + *((SEdit *)this)->get_text() = 0; +} void Edit::copy_from(Edit *edit) { @@ -252,6 +262,7 @@ void Edit::copy_from(Edit *edit) this->hard_left = edit->hard_left; this->hard_right = edit->hard_right; this->color = edit->color; + this->group_id = edit->group_id; strcpy (this->user_title, edit->user_title); if(edit->transition) @@ -378,7 +389,7 @@ int Edit::dump(FILE *fp) asset, asset ? asset->path : ""); fflush(fp); - fprintf(fp," channel %d, color %08x\n", channel, color); + fprintf(fp," channel %d, color %08x, group_id %d\n", channel, color, group_id); if(transition) { fprintf(fp," TRANSITION %p\n", transition); @@ -396,6 +407,7 @@ int Edit::load_properties(FileXML *file, int64_t &startproject) hard_left = file->tag.get_property("HARD_LEFT", (int64_t)0); hard_right = file->tag.get_property("HARD_RIGHT", (int64_t)0); color = file->tag.get_property("COLOR", (int64_t)-1); + group_id = file->tag.get_property("GROUP_ID", group_id); user_title[0] = 0; file->tag.get_property("USER_TITLE", user_title); this->startproject = startproject; diff --git a/cinelerra-5.1/cinelerra/edit.h b/cinelerra-5.1/cinelerra/edit.h index 67b09159..e00e7da1 100644 --- a/cinelerra-5.1/cinelerra/edit.h +++ b/cinelerra-5.1/cinelerra/edit.h @@ -114,6 +114,7 @@ public: void detach_transition(); // Determine if silence depending on existance of asset or plugin title virtual int silence(); + void mute(); // Media edit information // Units are native units for the track. @@ -129,6 +130,8 @@ public: int channel; // ID for resource pixmaps int id; +// ID for selection groups + int group_id; // User defined title for timeline char user_title[BCTEXTLEN]; int is_plugin, is_selected; diff --git a/cinelerra-5.1/cinelerra/editpopup.C b/cinelerra-5.1/cinelerra/editpopup.C index cbc57606..f48f0564 100644 --- a/cinelerra-5.1/cinelerra/editpopup.C +++ b/cinelerra-5.1/cinelerra/editpopup.C @@ -116,7 +116,7 @@ EditPopupCopy::EditPopupCopy(MWindow *mwindow, EditPopup *popup) int EditPopupCopy::handle_event() { - mwindow->selected_to_clipboard(0); + mwindow->selected_edits_to_clipboard(0); return 1; } @@ -131,7 +131,7 @@ EditPopupCopyPack::EditPopupCopyPack(MWindow *mwindow, EditPopup *popup) int EditPopupCopyPack::handle_event() { - mwindow->selected_to_clipboard(1); + mwindow->selected_edits_to_clipboard(1); return 1; } @@ -441,8 +441,9 @@ EditTitleColorDefault::EditTitleColorDefault( int EditTitleColorDefault::handle_event() { - color_picker->color = 0; - color_picker->update_gui(0, 0); + const int color = 0, alpha = 0; + color_picker->color = color | (~alpha << 24); + color_picker->update_gui(color, alpha); return 1; } diff --git a/cinelerra-5.1/cinelerra/edl.C b/cinelerra-5.1/cinelerra/edl.C index 4cea20f5..79662761 100644 --- a/cinelerra-5.1/cinelerra/edl.C +++ b/cinelerra-5.1/cinelerra/edl.C @@ -1676,3 +1676,27 @@ int EDL::in_use(Indexable *indexable) return 0; } +int EDL::regroup(int next_id) +{ + ArrayList new_groups; + for( Track *track=tracks->first; track; track=track->next ) { + for( Edit *edit=track->edits->first; edit; edit=edit->next ) { + if( !edit->group_id ) continue; + int k = new_groups.size(); + while( --k >= 0 && new_groups[k] != edit->group_id ); + if( k >= 0 ) continue; + new_groups.append(edit->group_id); + } + } + for( Track *track=tracks->first; track; track=track->next ) { + for( Edit *edit=track->edits->first; edit; edit=edit->next ) { + if( !edit->group_id ) continue; + int k = new_groups.size(); + while( --k >= 0 && new_groups[k] != edit->group_id ); + if( k < 0 ) continue; + edit->group_id = k + next_id; + } + } + return new_groups.size(); +} + diff --git a/cinelerra-5.1/cinelerra/edl.h b/cinelerra-5.1/cinelerra/edl.h index 5e184d22..ad7e8cf9 100644 --- a/cinelerra-5.1/cinelerra/edl.h +++ b/cinelerra-5.1/cinelerra/edl.h @@ -223,6 +223,8 @@ public: int insert_clips(ArrayList *new_edls, int load_mode, Track *first_track = 0); // Add a copy of EDL* to the clip array. Returns the copy. EDL* add_clip(EDL *edl); +// resequence group ids starting at next_id + int regroup(int next_id); void get_shared_plugins(Track *source, ArrayList *plugin_locations, int omit_recordable, int data_type); diff --git a/cinelerra-5.1/cinelerra/mainsession.C b/cinelerra-5.1/cinelerra/mainsession.C index ef81185a..acc5e4d1 100644 --- a/cinelerra-5.1/cinelerra/mainsession.C +++ b/cinelerra-5.1/cinelerra/mainsession.C @@ -56,6 +56,11 @@ MainSession::MainSession(MWindow *mwindow) drag_clips = new ArrayList; drag_edits = new ArrayList; drag_edit = 0; + drag_group = 0; + drag_group_edit = 0; + drag_group_position = 0; + drag_group_first_track = 0; + group_number = 1; clip_number = 1; brender_end = 0; cwindow_controls = 1; @@ -125,6 +130,8 @@ MainSession::~MainSession() delete drag_auto_gang; delete drag_clips; delete drag_edits; + if( drag_group ) + drag_group->remove_user(); } void MainSession::boundaries() @@ -451,7 +458,7 @@ int MainSession::load_defaults(BC_Hash *defaults) current_tip = defaults->get("CURRENT_TIP", current_tip); actual_frame_rate = defaults->get("ACTUAL_FRAME_RATE", (float)-1); - title_bar_alpha = defaults->get("TITLE_BAR_ALPHA", (float)0); + title_bar_alpha = defaults->get("TITLE_BAR_ALPHA", (float)1); boundaries(); return 0; diff --git a/cinelerra-5.1/cinelerra/mainsession.h b/cinelerra-5.1/cinelerra/mainsession.h index 8cbc35c3..a3ad511c 100644 --- a/cinelerra-5.1/cinelerra/mainsession.h +++ b/cinelerra-5.1/cinelerra/mainsession.h @@ -82,6 +82,14 @@ public: // Edit whose handle is being dragged Edit *drag_edit; +// Selected edits clip of grouped drag + EDL *drag_group; +// drag edit of selected edits + Edit *drag_group_edit; +// cursor position in selected edits at start of drag + double drag_group_position; +// top track of selected edits + Track *drag_group_first_track; // Edits who are being dragged ArrayList *drag_edits; // Button pressed during drag @@ -107,6 +115,8 @@ public: // Clip number for automatic title generation int clip_number; +// Next group id index + int group_number; // Audio session int changes_made; diff --git a/cinelerra-5.1/cinelerra/mainsession.inc b/cinelerra-5.1/cinelerra/mainsession.inc index 32c4748c..d9506c58 100644 --- a/cinelerra-5.1/cinelerra/mainsession.inc +++ b/cinelerra-5.1/cinelerra/mainsession.inc @@ -62,6 +62,7 @@ enum DRAG_PLUGINHANDLE1, // Waiting to move out of drag threshold DRAG_PLUGINHANDLE2, // Dragging outside drag threshold DRAG_SPEED, + DRAG_GROUP, DROP_TARGETING, }; diff --git a/cinelerra-5.1/cinelerra/mwindow.C b/cinelerra-5.1/cinelerra/mwindow.C index 263bbd98..6e8547d6 100644 --- a/cinelerra-5.1/cinelerra/mwindow.C +++ b/cinelerra-5.1/cinelerra/mwindow.C @@ -2021,6 +2021,8 @@ if(debug) printf("MWindow::load_filenames %d\n", __LINE__); EDL *nested_edl = new EDL; nested_edl->create_objects(); nested_edl->load_xml(&xml_file, LOAD_ALL); + int groups = nested_edl->regroup(session->group_number); + session->group_number += groups; //printf("MWindow::load_filenames %p %s\n", nested_edl, nested_edl->project_path); new_edl->create_nested(nested_edl); new_edl->set_path(filenames->get(i)); @@ -2029,6 +2031,8 @@ if(debug) printf("MWindow::load_filenames %d\n", __LINE__); else { // Load EDL for pasting new_edl->load_xml(&xml_file, LOAD_ALL); + int groups = new_edl->regroup(session->group_number); + session->group_number += groups; if(debug) printf("MWindow::load_filenames %d\n", __LINE__); test_plugins(new_edl, filenames->get(i)); if(debug) printf("MWindow::load_filenames %d\n", __LINE__); @@ -3307,6 +3311,11 @@ int MWindow::get_hash_color(Edit *edit) uint8_t *bp = (uint8_t*)cp; int v = 0; while( *bp ) v += *bp++; + return get_hash_color(v); +} + +int MWindow::get_hash_color(int v) +{ int hash = 0x303030; if( v & 0x01 ) hash ^= 0x000040; if( v & 0x02 ) hash ^= 0x004000; @@ -3319,15 +3328,33 @@ int MWindow::get_hash_color(Edit *edit) return hash; } +int MWindow::get_group_color(int v) +{ + int color = 0x606060; + if( v & 0x01 ) color ^= 0x000080; + if( v & 0x02 ) color ^= 0x008000; + if( v & 0x04 ) color ^= 0x800000; + if( v & 0x08 ) color ^= 0x100000; + if( v & 0x10 ) color ^= 0x001000; + if( v & 0x20 ) color ^= 0x000010; + if( v & 0x40 ) color ^= 0x080808; + if( v & 0x80 ) color ^= 0x909090; + return color; +} + int MWindow::get_title_color(Edit *edit) { - unsigned color = edit->color; + unsigned color = edit->color & 0xffffff; + unsigned alpha = (~edit->color>>24) & 0xff; if( !color ) { - if( !preferences->autocolor_assets ) return 0; - color = get_hash_color(edit); + if( edit->group_id ) + color = get_group_color(edit->group_id); + else if( preferences->autocolor_assets ) + color = get_hash_color(edit); + else + return 0; } - unsigned alpha = (~edit->color>>24) & 0xff; - if( alpha == 0xff ) + if( !alpha ) alpha = session->title_bar_alpha*255; return color | (~alpha<<24); } diff --git a/cinelerra-5.1/cinelerra/mwindow.h b/cinelerra-5.1/cinelerra/mwindow.h index 4371099e..a69a9dca 100644 --- a/cinelerra-5.1/cinelerra/mwindow.h +++ b/cinelerra-5.1/cinelerra/mwindow.h @@ -182,7 +182,8 @@ public: void update_vwindow(); // Fit selected time to horizontal display range void fit_selection(); - void selected_to_clipboard(int packed); + EDL *selected_edits_to_clip(int packed, double *start_position=0, Track **start_track=0); + void selected_edits_to_clipboard(int packed); // Fit selected autos to the vertical display range void fit_autos(int doall); void change_currentautorange(int autogrouptype, int increment, int changemax); @@ -311,6 +312,8 @@ public: void hide_keyframe_gui(Plugin *plugin); void update_keyframe_guis(); int get_hash_color(Edit *edit); + int get_hash_color(int v); + int get_group_color(int v); int get_title_color(Edit *edit); // ============================= editing commands ======================== @@ -400,6 +403,7 @@ public: void move_edits(ArrayList *edits, Track *track, double position, // 0 - old style (cut and insert elswhere), 1- new style - (clear and overwrite elsewere) int behaviour); + void move_group(EDL *group, Track *first_track, double position); // Move effect to position void move_effect(Plugin *plugin, Track *track, int64_t position); void move_effect(Plugin *plugin, PluginSet *plugin_set, int64_t position); diff --git a/cinelerra-5.1/cinelerra/mwindowedit.C b/cinelerra-5.1/cinelerra/mwindowedit.C index 6e2df1c9..d458a78b 100644 --- a/cinelerra-5.1/cinelerra/mwindowedit.C +++ b/cinelerra-5.1/cinelerra/mwindowedit.C @@ -903,7 +903,7 @@ void MWindow::match_output_size(Track *track) } -void MWindow::selected_to_clipboard(int packed) +EDL *MWindow::selected_edits_to_clip(int packed, double *start_position, Track **start_track) { double start = DBL_MAX, end = DBL_MIN; Track *first_track=0, *last_track = 0; @@ -921,7 +921,9 @@ void MWindow::selected_to_clipboard(int packed) if( !first_track ) first_track = track; last_track = track; } - if( !first_track ) return; + if( start_position ) *start_position = start; + if( start_track ) *start_track = first_track; + if( !first_track ) return 0; EDL *new_edl = new EDL(); new_edl->create_objects(); new_edl->copy_session(edl); @@ -969,6 +971,13 @@ void MWindow::selected_to_clipboard(int packed) } if( last_track == track ) break; } + return new_edl; +} + +void MWindow::selected_edits_to_clipboard(int packed) +{ + EDL *new_edl = MWindow::selected_edits_to_clip(packed); + if( !new_edl ) return; double length = new_edl->tracks->total_length(); FileXML file; new_edl->copy(0, length, 1, &file, "", 1); @@ -1022,7 +1031,7 @@ void MWindow::delete_edits(int collapse) // packed - omit unselected from selection, unpacked - replace unselected with silence void MWindow::cut_selected_edits(int collapse, int packed) { - selected_to_clipboard(packed); + selected_edits_to_clipboard(packed); ArrayList edits; edl->tracks->get_selected_edits(&edits); delete_edits(&edits, _("cut edit"), collapse); @@ -1054,6 +1063,19 @@ void MWindow::move_edits(ArrayList *edits, gui->update(1, NORMAL_DRAW, 1, 0, 0, 0, 0); } +void MWindow::move_group(EDL *group, Track *first_track, double position) +{ + undo->update_undo_before(); + edl->tracks->move_group(group, first_track, position); + save_backup(); + undo->update_undo_after(_("move group"), LOAD_ALL); + restart_brender(); + cwindow->refresh_frame(CHANGE_EDL); + + update_plugin_guis(); + gui->update(1, NORMAL_DRAW, 1, 0, 0, 0, 0); +} + void MWindow::move_effect(Plugin *plugin, Track *track, int64_t position) { undo->update_undo_before(); diff --git a/cinelerra-5.1/cinelerra/mwindowgui.C b/cinelerra-5.1/cinelerra/mwindowgui.C index 0f2ef123..743c721c 100644 --- a/cinelerra-5.1/cinelerra/mwindowgui.C +++ b/cinelerra-5.1/cinelerra/mwindowgui.C @@ -1007,6 +1007,7 @@ int MWindowGUI::drag_motion() if( mwindow->session->current_operation == DRAG_ASSET || mwindow->session->current_operation == DRAG_EDIT || + mwindow->session->current_operation == DRAG_GROUP || mwindow->session->current_operation == DRAG_AEFFECT_COPY || mwindow->session->current_operation == DRAG_VEFFECT_COPY ) { @@ -1198,7 +1199,7 @@ int MWindowGUI::keypress_event() packed = 1; case 'c': if( !ctrl_down() || alt_down() ) break; - mwindow->selected_to_clipboard(packed); + mwindow->selected_edits_to_clipboard(packed); result = 1; break; case 'b': diff --git a/cinelerra-5.1/cinelerra/proxy.C b/cinelerra-5.1/cinelerra/proxy.C index 4394120d..e368c17c 100644 --- a/cinelerra-5.1/cinelerra/proxy.C +++ b/cinelerra-5.1/cinelerra/proxy.C @@ -50,6 +50,7 @@ #define WIDTH 400 #define HEIGHT 330 #define MAX_SCALE 16 +#define PROXY_DEFAULT_VCODEC "h265.mp4" ProxyMenuItem::ProxyMenuItem(MWindow *mwindow) : BC_MenuItem(_("Proxy settings..."), _("Alt-r"), 'r') @@ -82,6 +83,7 @@ ProxyDialog::ProxyDialog(MWindow *mwindow) this->mwindow = mwindow; gui = 0; asset = new Asset; + strcpy(asset->vcodec, PROXY_DEFAULT_VCODEC); bzero(size_text, sizeof(char*) * MAX_SIZES); bzero(size_factors, sizeof(int) * MAX_SIZES); size_text[0] = cstrdup(_("Original size")); diff --git a/cinelerra-5.1/cinelerra/resourcepixmap.C b/cinelerra-5.1/cinelerra/resourcepixmap.C index 0da77299..cd93e654 100644 --- a/cinelerra-5.1/cinelerra/resourcepixmap.C +++ b/cinelerra-5.1/cinelerra/resourcepixmap.C @@ -270,13 +270,15 @@ VFrame *ResourcePixmap::change_picon_alpha(VFrame *picon_frame, int alpha) { uint8_t **picon_rows = picon_frame->get_rows(); int w = picon_frame->get_w(), h = picon_frame->get_h(); + int color_model = picon_frame->get_color_model(); + int bpp = BC_CModels::calculate_pixelsize(color_model); VFrame *frame = new VFrame(w, h, BC_RGBA8888); uint8_t **rows = frame->get_rows(); for( int y=0; ysession->current_operation = NO_OPERATION; + EDL *drag_group = mwindow->session->drag_group; + if( drag_group ) { + Track *drop_track = mwindow->session->track_highlighted; + Track *drag_track = mwindow->session->drag_group_first_track; + Edit *drag_edit = mwindow->session->drag_group_edit; + Track *edit_track = drag_edit ? drag_edit->track : 0; + while( drop_track && edit_track ) { + if( edit_track == drag_track ) break; + edit_track = edit_track->previous; + drop_track = drop_track->previous; + } + if( drop_track && test_track_group(drag_group, drop_track) ) { + double position = mwindow->edl->get_cursor_position(cursor_x, pane->number); + position = mwindow->edl->align_to_frame(position, 0); + position -= mwindow->session->drag_group_position; + mwindow->move_group(drag_group, drop_track, position); + } + drag_group->remove_user(); + mwindow->session->drag_group = 0; + } + result = 1; + break; } } @@ -1537,7 +1561,24 @@ void TrackCanvas::draw_highlighting() // } } break; - + case DRAG_GROUP: + if( mwindow->session->track_highlighted && mwindow->session->drag_group && + mwindow->session->drag_group_edit && mwindow->session->drag_group_first_track ) { + Track *track = mwindow->session->track_highlighted; + EDL *drag_group = mwindow->session->drag_group; + Track *edit_track = mwindow->session->drag_group_edit->track; + Track *drag_track = mwindow->session->drag_group_first_track; + while( track && edit_track && edit_track != drag_track ) { + edit_track = edit_track->previous; + track = track->previous; + } + int color = track && test_track_group(drag_group, track) ? GREEN : RED; + track_dimensions(mwindow->session->track_highlighted, x, y, w, h); + int dx = get_cursor_x() - mwindow->session->drag_origin_x; + int dy = y - mwindow->session->drag_origin_y; + draw_selected_edits(mwindow->edl, dx, dy, color, -1); + } + break; // Dragging an effect from the timeline case DRAG_AEFFECT_COPY: case DRAG_VEFFECT_COPY: @@ -1601,18 +1642,27 @@ void TrackCanvas::draw_highlighting() if( draw_box ) draw_highlight_rectangle(x, y, w, h); - for( Track *track=mwindow->edl->tracks->first; track; track=track->next ) { + draw_selected_edits(mwindow->edl, 0, 0, GREEN+BLUE, RED); +} + +void TrackCanvas::draw_selected_edits(EDL *edl, int dx, int dy, int color0, int color1) +{ + for( Track *track=edl->tracks->first; track; track=track->next ) { for( Edit *edit=track->edits->first; edit; edit=edit->next ) { if( !edit->is_selected ) continue; + int64_t x, y, w, h; edit_dimensions(edit, x, y, w, h); + x += dx; y += dy; if( !MWindowGUI::visible(x, x + w, 0, get_w()) ) continue; if( !MWindowGUI::visible(y, y + h, 0, get_h()) ) continue; - set_color(GREEN | BLUE); - set_inverse(); + set_opaque(); + int inner = color1 < 0 ? color0 : !edit->group_id ? color0 : + mwindow->get_group_color(edit->group_id); + set_color(inner); draw_rectangle(x, y, w, h); - set_color(RED); + int outer = color1 < 0 ? color0 : !edit->group_id ? color1 : inner; + set_color(outer); draw_rectangle(x-1, y-1, w+2, h+2); - set_opaque(); } } } @@ -4202,21 +4252,16 @@ int TrackCanvas::cursor_update(int in_motion) case DROP_TARGETING: new_cursor = GRABBED_CURSOR; + result = 1; break; default: if(is_event_win() && cursor_inside()) { // Update clocks cursor_x = get_cursor_x(); - position = (double)cursor_x * - (double)mwindow->edl->local_session->zoom_sample / - (double)mwindow->edl->session->sample_rate + - (double)mwindow->edl->local_session->view_start[pane->number] * - (double)mwindow->edl->local_session->zoom_sample / - (double)mwindow->edl->session->sample_rate; + position = mwindow->edl->get_cursor_position(cursor_x, pane->number); position = mwindow->edl->align_to_frame(position, 0); update_clock = 1; - // set all timebars for(int i = 0; i < TOTAL_PANES; i++) if(gui->pane[i]) gui->pane[i]->canvas->timebar_position = position; @@ -4463,6 +4508,7 @@ int TrackCanvas::button_release_event() break; case DRAG_EDIT: + case DRAG_GROUP: case DRAG_AEFFECT_COPY: case DRAG_VEFFECT_COPY: // Trap in drag stop @@ -4742,22 +4788,36 @@ int TrackCanvas::do_edits(int cursor_x, int cursor_y, int button_press, int drag cursor_y >= edit_y && cursor_y < edit_y + edit_h) { // Select duration of edit if(button_press) { - if( !drag_start && get_double_click() ) { - mwindow->edl->local_session->set_selectionstart(edit->track->from_units(edit->startproject)); - mwindow->edl->local_session->set_selectionend(edit->track->from_units(edit->startproject) + - edit->track->from_units(edit->length)); - if(mwindow->edl->session->cursor_on_frames) - { - mwindow->edl->local_session->set_selectionstart( - mwindow->edl->align_to_frame(mwindow->edl->local_session->get_selectionstart(1), 0)); - mwindow->edl->local_session->set_selectionend( - mwindow->edl->align_to_frame(mwindow->edl->local_session->get_selectionend(1), 1)); + if( get_double_click() ) { + if( shift_down() ) { + if( edit->group_id > 0 ) { + mwindow->edl->tracks->clear_selected_edits(); + mwindow->edl->tracks->del_group(edit->group_id); + } + else { + int id = mwindow->session->group_number++; + mwindow->edl->tracks->new_group(id); + } + mwindow->session->current_operation = NO_OPERATION; + result = 1; + } + else if( !drag_start ) { + double start = edit->track->from_units(edit->startproject); + start = mwindow->edl->align_to_frame(start, 0); + mwindow->edl->local_session->set_selectionstart(start); + double end = edit->track->from_units(edit->startproject+edit->length); + end = mwindow->edl->align_to_frame(end, 0); + mwindow->edl->local_session->set_selectionend(end); + result = 1; } - result = 1; } - if( ctrl_down() && get_buttonpress() == 1 && + else if( ctrl_down() && get_buttonpress() == 1 && mwindow->edl->session->editing_mode == EDITING_ARROW ) { - edit->is_selected = !edit->is_selected ? 1 : 0; + int v = !edit->is_selected ? 1 : 0; + if( !edit->group_id ) + edit->is_selected = v; + else + mwindow->edl->tracks->set_group_selected(edit->group_id, v); result = 1; } if( result ) { @@ -4769,32 +4829,44 @@ int TrackCanvas::do_edits(int cursor_x, int cursor_y, int button_press, int drag else if( drag_start && track->record ) { if( mwindow->edl->session->editing_mode == EDITING_ARROW ) { // Need to create drag window - mwindow->session->current_operation = DRAG_EDIT; mwindow->session->drag_edit = edit; -// Construct list of all affected edits - mwindow->edl->tracks->clear_selected_edits(); - if( ctrl_down() ) - edit->is_selected = 1; - else - mwindow->edl->tracks->select_affected_edits( - edit->track->from_units(edit->startproject), - edit->track); - mwindow->edl->tracks->get_selected_edits(mwindow->session->drag_edits); mwindow->session->drag_origin_x = cursor_x; mwindow->session->drag_origin_y = cursor_y; // Where the drag started, so we know relative position inside the edit later - mwindow->session->drag_position = (double)cursor_x * - mwindow->edl->local_session->zoom_sample / - mwindow->edl->session->sample_rate + - (double)mwindow->edl->local_session->view_start[pane->number] * - mwindow->edl->local_session->zoom_sample / - mwindow->edl->session->sample_rate; - - int cx, cy; - get_abs_cursor(cx, cy); - gui->drag_popup = new BC_DragWindow(gui, - mwindow->theme->get_image("clip_icon"), cx, cy); + mwindow->session->drag_position = + mwindow->edl->get_cursor_position(cursor_x, pane->number); +// Construct list of all affected edits + if( !shift_down() ) { + mwindow->session->current_operation = DRAG_EDIT; + mwindow->edl->tracks->clear_selected_edits(); + if( !ctrl_down() ) { + mwindow->edl->tracks->select_affected_edits( + edit->track->from_units(edit->startproject), + edit->track); + } + else + edit->is_selected = 1; + mwindow->edl->tracks->get_selected_edits(mwindow->session->drag_edits); + int cx, cy; get_abs_cursor(cx, cy); + gui->drag_popup = new BC_DragWindow(gui, + mwindow->theme->get_image("clip_icon"), cx, cy); + } + else if( edit->is_selected ) { + if( mwindow->session->drag_group ) + mwindow->session->drag_group->remove_user(); + double start_position = 0; + mwindow->session->drag_group = + mwindow->selected_edits_to_clip(0, &start_position, + &mwindow->session->drag_group_first_track); + if( mwindow->session->drag_group ) { + mwindow->session->current_operation = DRAG_GROUP; + mwindow->session->drag_group_position = + mwindow->session->drag_position - start_position; + mwindow->session->drag_group_edit = edit; + mwindow->session->drag_origin_y = edit_y; + } + } result = 1; } } @@ -4805,6 +4877,17 @@ int TrackCanvas::do_edits(int cursor_x, int cursor_y, int button_press, int drag } +int TrackCanvas::test_track_group(EDL *group, Track *first_track) +{ + Track *src = group->tracks->first; + for( Track *track=first_track; track && src; track=track->next ) { + if( !track->record ) continue; + if( src->data_type != track->data_type ) return 0; + src = src->next; + } + return !src ? 1 : 0; +} + int TrackCanvas::test_resources(int cursor_x, int cursor_y) { return 0; @@ -5102,6 +5185,7 @@ int TrackCanvas::button_press_event() if( update_cursor < 0 ) { // double_click edit gui->swindow->update_selection(); + gui->draw_canvas(0, 0); } if( update_cursor ) { gui->update_timebar(0); diff --git a/cinelerra-5.1/cinelerra/trackcanvas.h b/cinelerra-5.1/cinelerra/trackcanvas.h index a0c12a2d..88d76416 100644 --- a/cinelerra-5.1/cinelerra/trackcanvas.h +++ b/cinelerra-5.1/cinelerra/trackcanvas.h @@ -260,6 +260,7 @@ public: void draw_loop_points(); void draw_transitions(); void draw_drag_handle(); + void draw_selected_edits(EDL *edl, int dx, int dy, int color0, int color1); void draw_plugins(); void refresh_plugintoggles(); void update_edit_handles(Edit *edit, int64_t edit_x, int64_t edit_y, int64_t edit_w, int64_t edit_h); @@ -304,6 +305,7 @@ public: int do_tracks(int cursor_x, int cursor_y, int button_press); + int test_track_group(EDL *group, Track *first_track); int test_resources(int cursor_x, int cursor_y); int do_plugins(int cursor_x, int cursor_y, diff --git a/cinelerra-5.1/cinelerra/tracks.C b/cinelerra-5.1/cinelerra/tracks.C index bab0b6b4..0f53df74 100644 --- a/cinelerra-5.1/cinelerra/tracks.C +++ b/cinelerra-5.1/cinelerra/tracks.C @@ -131,6 +131,7 @@ void Tracks::get_selected_edits(ArrayList *drag_edits) { drag_edits->remove_all(); for( Track *track=first; track; track=track->next ) { + if( !track->record ) continue; for( Edit *edit=track->edits->first; edit; edit=edit->next ) { if( !edit->is_selected ) continue; drag_edits->append(edit); @@ -651,6 +652,46 @@ int Tracks::track_exists(Track *track) return 0; } +int Tracks::new_group(int id) +{ + int count = 0; + for( Track *track=first; track; track=track->next ) { + if( !track->record ) continue; + for( Edit *edit=track->edits->first; edit; edit=edit->next ) { + if( !edit->is_selected ) continue; + edit->group_id = id; + ++count; + } + } + return count; +} + +int Tracks::set_group_selected(int id, int v) +{ + int count = 0; + for( Track *track=first; track; track=track->next ) { + for( Edit *edit=track->edits->first; edit; edit=edit->next ) { + if( edit->group_id != id ) continue; + edit->is_selected = v; + ++count; + } + } + return count; +} + +int Tracks::del_group(int id) +{ + int count = 0; + for( Track *track=first; track; track=track->next ) { + for( Edit *edit=track->edits->first; edit; edit=edit->next ) { + if( edit->group_id != id ) continue; + edit->is_selected = 1; + edit->group_id = 0; + ++count; + } + } + return count; +} Track *Tracks::get(int idx, int data_type) { @@ -662,4 +703,3 @@ Track *Tracks::get(int idx, int data_type) return 0; } - diff --git a/cinelerra-5.1/cinelerra/tracks.h b/cinelerra-5.1/cinelerra/tracks.h index 22baa7b0..4d3bef90 100644 --- a/cinelerra-5.1/cinelerra/tracks.h +++ b/cinelerra-5.1/cinelerra/tracks.h @@ -49,24 +49,20 @@ public: int load(FileXML *xml, int &track_offset, uint32_t load_flags); - void move_edits(ArrayList *edits, - Track *track, - double position, - int edit_labels, - int edit_plugins, - int edit_autos, - int behaviour); - void move_effect(Plugin *plugin, - Track *track, - int64_t position); - void move_effect(Plugin *plugin, - PluginSet *plugin_set, - int64_t position); + void move_edits(ArrayList *edits, Track *track, double position, + int edit_labels, int edit_plugins, int edit_autos, int behaviour); + void move_group(EDL *group, Track *first_track, double position); + void move_effect(Plugin *plugin, Track *track, int64_t position); + void move_effect(Plugin *plugin, PluginSet *plugin_set, int64_t position); // Construct a list of all the recordable edits which start on position void clear_selected_edits(); void select_affected_edits(double position, Track *start_track); void get_selected_edits(ArrayList *drag_edits); + int next_group_id(); + int new_group(int id); + int set_group_selected(int id, int v); + int del_group(int id); void get_automation_extents(float *min, float *max, diff --git a/cinelerra-5.1/cinelerra/tracksedit.C b/cinelerra-5.1/cinelerra/tracksedit.C index 6655eb8e..b80a8887 100644 --- a/cinelerra-5.1/cinelerra/tracksedit.C +++ b/cinelerra-5.1/cinelerra/tracksedit.C @@ -740,6 +740,36 @@ void Tracks::move_edits(ArrayList *edits, } } +void Tracks::move_group(EDL *group, Track *first_track, double position) +{ + for( Track *track=first; track; track=track->next ) { + if( !track->record ) continue; + for( Edit *edit=track->edits->first; edit; edit=edit->next ) { + if( !edit->is_selected ) continue; + edit->mute(); edit->is_selected = 0; + } + } + Track *src = group->tracks->first; + for( Track *track=first_track; track && src; track=track->next ) { + if( !track->record ) continue; + int64_t pos = track->to_units(position, 0); + for( Edit *edit=src->edits->first; edit; edit=edit->next ) { + if( edit->silence() ) continue; + int64_t start = pos + edit->startproject; + int64_t end = start + edit->length; + track->edits->clear(start, end); + Edit *dst = track->edits->insert_new_edit(start); + dst->copy_from(edit); + dst->startproject = start; + dst->is_selected = 1; + while( (dst=dst->next) != 0 ) + dst->startproject += edit->length; + } + track->optimize(); + src = src->next; + } +} + void Tracks::move_effect(Plugin *plugin, Track *track, int64_t position) { Track *source_track = plugin->track; -- 2.26.2