4 * Copyright (C) 2008 Adam Williams <broadcast at earthling dot net>
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 #include "automation.h"
23 #include "bcsignals.h"
24 #include "cplayback.h"
27 #include "edlsession.h"
31 #include "localsession.h"
32 #include "mainsession.h"
35 #include "mwindowgui.h"
38 #include "playbackengine.h"
41 #include "trackcanvas.h"
43 #include "transportque.h"
48 PatchGUI::PatchGUI(MWindow *mwindow,
54 this->mwindow = mwindow;
55 this->patchbay = patchbay;
70 track_id = track ? track->get_id() : -1;
88 void PatchGUI::create_objects()
93 int PatchGUI::reposition(int x, int y)
99 if( x != this->x || y != this->y ) {
100 this->x = x; this->y = y;
103 title->reposition_window(title->get_x(), y1 + y, 0);
105 expand->reposition_window(expand->get_x(), y1 + y);
106 y1 += mwindow->theme->title_h;
109 play->reposition_window(play->get_x(), y1 + y);
111 record->reposition_window(record->get_x(), y1 + y);
112 x1 += record->get_w();
113 // automate->reposition_window(x1, y1 + y);
114 // x1 += automate->get_w();
115 gang->reposition_window(gang->get_x(), y1 + y);
117 draw->reposition_window(draw->get_x(), y1 + y);
119 mute->reposition_window(mute->get_x(), y1 + y);
122 y1 += mwindow->theme->play_h;
126 y1 += mwindow->theme->title_h;
128 y1 += mwindow->theme->play_h;
134 int PatchGUI::update(int x, int y)
136 //TRACE("PatchGUI::update 1");
138 //TRACE("PatchGUI::update 10");
140 int h = track->vertical_span(mwindow->theme);
143 //printf("PatchGUI::update 10\n");
145 int y2 = y1 + mwindow->theme->title_h;
148 delete title; title = 0;
149 delete expand; expand = 0;
152 title->update(track->title);
153 expand->update(track->expand_view);
157 VFrame **expandpatch_data = mwindow->theme->get_image_set("expandpatch_data");
158 int x2 = patchbay->get_w() - expandpatch_data[0]->get_w() - 5;
159 patchbay->add_subwindow(title = new TitlePatch(mwindow, this, x1 + x, y1 + y, x2-x1-5));
160 patchbay->add_subwindow(expand = new ExpandPatch(mwindow, this, x2, y1 + y));
166 y2 = y1 + mwindow->theme->play_h;
169 delete play; play = 0;
170 delete record; record = 0;
171 delete gang; gang = 0;
172 delete draw; draw = 0;
173 delete mute; mute = 0;
176 play->update(track->play);
177 record->update(track->record);
178 gang->update(track->gang);
179 draw->update(track->draw);
180 mute->update(mwindow->get_int_auto(this, AUTOMATION_MUTE)->value);
184 patchbay->add_subwindow(play = new PlayPatch(mwindow, this, x1 + x, y1 + y));
185 //printf("PatchGUI::update %d %d\n", __LINE__, play->get_h());
187 patchbay->add_subwindow(record = new RecordPatch(mwindow, this, x1 + x, y1 + y));
188 x1 += record->get_w();
189 patchbay->add_subwindow(gang = new GangPatch(mwindow, this, x1 + x, y1 + y));
191 patchbay->add_subwindow(draw = new DrawPatch(mwindow, this, x1 + x, y1 + y));
193 patchbay->add_subwindow(mute = new MutePatch(mwindow, this, x1 + x, y1 + y));
204 void PatchGUI::toggle_behavior(int type,
209 if(toggle->shift_down()) {
210 int sense = type != Tracks::MUTE ? 1 : 0;
211 // all selected if nothing previously selected or
212 // if this patch was previously the only one selected
213 int total_type = mwindow->edl->tracks->total_of(type);
214 int total_selected = sense ? total_type :
215 mwindow->edl->tracks->total() - total_type;
216 int selected = !total_selected || (total_selected == 1 &&
217 *output == sense ) ? sense : 1-sense;
218 mwindow->edl->tracks->select_all(type, selected);
219 if( selected != sense ) *output = sense;
221 patchbay->drag_operation = type;
222 patchbay->new_status = 1;
227 // Select + drag behavior
228 patchbay->drag_operation = type;
229 patchbay->new_status = value;
235 mwindow->gui->unlock_window();
236 mwindow->restart_brender();
237 mwindow->sync_parameters(CHANGE_EDL);
238 mwindow->gui->lock_window("PatchGUI::toggle_behavior 1");
242 mwindow->gui->unlock_window();
243 mwindow->restart_brender();
244 mwindow->sync_parameters(CHANGE_PARAMS);
245 mwindow->gui->lock_window("PatchGUI::toggle_behavior 2");
248 // Update affected tracks in cwindow
250 mwindow->cwindow->update(0, 1, 1);
257 mwindow->gui->update(0, 1, 0, 0, 0, 0, 0);
265 mwindow->gui->update_patchbay();
269 char* PatchGUI::calculate_nudge_text(int *changed)
271 if(changed) *changed = 0;
272 if(track->edl->session->nudge_format)
274 sprintf(string_return, "%.4f", track->from_units(track->nudge));
275 if(changed && nudge && atof(nudge->get_text()) - atof(string_return) != 0)
280 sprintf(string_return, "%jd", track->nudge);
281 if(changed && nudge && atoi(nudge->get_text()) - atoi(string_return) != 0)
284 return string_return;
288 int64_t PatchGUI::calculate_nudge(const char *string)
290 if(mwindow->edl->session->nudge_format)
293 sscanf(string, "%f", &result);
294 return track->to_units(result, 0);
299 sscanf(string, "%jd", &temp);
315 PlayPatch::PlayPatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
318 mwindow->theme->get_image_set("playpatch_data"),
325 this->mwindow = mwindow;
327 set_tooltip(_("Play track"));
331 int PlayPatch::button_press_event()
333 if(is_event_win() && get_buttonpress() == 1)
335 mwindow->undo->update_undo_before();
336 set_status(BC_Toggle::TOGGLE_DOWN);
337 update(!get_value());
338 patch->toggle_behavior(Tracks::PLAY,
341 &patch->track->play);
347 int PlayPatch::button_release_event()
349 int result = BC_Toggle::button_release_event();
350 if(patch->patchbay->drag_operation == Tracks::PLAY)
352 mwindow->undo->update_undo_after(_("play patch"), LOAD_PATCHES);
353 patch->patchbay->drag_operation = Tracks::NONE;
368 RecordPatch::RecordPatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
371 mwindow->theme->get_image_set("recordpatch_data"),
372 patch->track->record,
378 this->mwindow = mwindow;
380 set_tooltip(_("Arm track"));
384 int RecordPatch::button_press_event()
386 if(is_event_win() && get_buttonpress() == 1)
388 mwindow->undo->update_undo_before();
389 set_status(BC_Toggle::TOGGLE_DOWN);
390 update(!get_value());
391 patch->toggle_behavior(Tracks::RECORD,
394 &patch->track->record);
395 patch->title->set_back_color(patch->track->record ?
396 get_resources()->text_background :
397 get_resources()->text_background_disarmed);
398 patch->title->set_text_row(0);
404 int RecordPatch::button_release_event()
406 int result = BC_Toggle::button_release_event();
407 if(patch->patchbay->drag_operation == Tracks::RECORD)
409 mwindow->undo->update_undo_after(_("record patch"), LOAD_PATCHES);
410 patch->patchbay->drag_operation = Tracks::NONE;
425 GangPatch::GangPatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
427 mwindow->theme->get_image_set("gangpatch_data"),
434 this->mwindow = mwindow;
436 set_tooltip(_("Gang faders"));
440 int GangPatch::button_press_event()
442 if(is_event_win() && get_buttonpress() == 1)
444 mwindow->undo->update_undo_before();
445 set_status(BC_Toggle::TOGGLE_DOWN);
446 update(!get_value());
447 patch->toggle_behavior(Tracks::GANG,
450 &patch->track->gang);
456 int GangPatch::button_release_event()
458 int result = BC_Toggle::button_release_event();
459 if(patch->patchbay->drag_operation == Tracks::GANG)
461 mwindow->undo->update_undo_after(_("gang patch"), LOAD_PATCHES);
462 patch->patchbay->drag_operation = Tracks::NONE;
477 DrawPatch::DrawPatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
479 mwindow->theme->get_image_set("drawpatch_data"),
486 this->mwindow = mwindow;
488 set_tooltip(_("Draw media"));
492 int DrawPatch::button_press_event()
494 if(is_event_win() && get_buttonpress() == 1)
496 mwindow->undo->update_undo_before();
497 set_status(BC_Toggle::TOGGLE_DOWN);
498 update(!get_value());
499 patch->toggle_behavior(Tracks::DRAW,
502 &patch->track->draw);
508 int DrawPatch::button_release_event()
510 int result = BC_Toggle::button_release_event();
511 if(patch->patchbay->drag_operation == Tracks::DRAW)
513 mwindow->undo->update_undo_after(_("draw patch"), LOAD_PATCHES);
514 patch->patchbay->drag_operation = Tracks::NONE;
528 MutePatch::MutePatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
530 mwindow->theme->get_image_set("mutepatch_data"),
531 mwindow->get_int_auto(patch, AUTOMATION_MUTE)->value,
537 this->mwindow = mwindow;
539 set_tooltip(_("Don't send to output"));
543 int MutePatch::button_press_event()
545 if(is_event_win() && get_buttonpress() == 1)
547 mwindow->undo->update_undo_before();
548 set_status(BC_Toggle::TOGGLE_DOWN);
549 update(!get_value());
551 double position = mwindow->edl->local_session->get_selectionstart(1);
552 Autos *mute_autos = patch->track->automation->autos[AUTOMATION_MUTE];
555 current = (IntAuto*)mute_autos->get_auto_for_editing(position);
556 current->value = get_value();
558 patch->toggle_behavior(Tracks::MUTE,
565 if(mwindow->edl->session->auto_conf->autos[AUTOMATION_MUTE])
567 mwindow->gui->draw_overlays(1);
574 int MutePatch::button_release_event()
576 int result = BC_Toggle::button_release_event();
577 if(patch->patchbay->drag_operation == Tracks::MUTE)
579 mwindow->undo->update_undo_after(_("mute patch"), LOAD_PATCHES);
580 patch->patchbay->drag_operation = Tracks::NONE;
587 ExpandPatch::ExpandPatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
590 mwindow->theme->get_image_set("expandpatch_data"),
591 patch->track->expand_view,
597 this->mwindow = mwindow;
602 int ExpandPatch::button_press_event()
604 if(is_event_win() && get_buttonpress() == 1)
606 mwindow->undo->update_undo_before();
607 set_status(BC_Toggle::TOGGLE_DOWN);
608 update(!get_value());
609 patch->toggle_behavior(Tracks::EXPAND,
612 &patch->track->expand_view);
613 mwindow->edl->tracks->update_y_pixels(mwindow->theme);
614 mwindow->gui->draw_trackmovement();
620 int ExpandPatch::button_release_event()
622 int result = BC_Toggle::button_release_event();
623 if(patch->patchbay->drag_operation == Tracks::EXPAND)
625 mwindow->undo->update_undo_after(_("expand patch"), LOAD_PATCHES);
626 patch->patchbay->drag_operation = Tracks::NONE;
632 TitlePatch::TitlePatch(MWindow *mwindow, PatchGUI *patch, int x, int y, int w)
633 : BC_TextBox(x, y, w, 1, patch->track->title, 1, MEDIUMFONT, 1)
635 this->mwindow = mwindow;
637 set_back_color(patch->track->record ?
638 get_resources()->text_background :
639 get_resources()->text_background_disarmed);
642 void TitlePatch::update(const char *text)
644 set_back_color(patch->track->record ?
645 get_resources()->text_background :
646 get_resources()->text_background_disarmed);
647 BC_TextBox::update(text);
650 int TitlePatch::handle_event()
652 mwindow->undo->update_undo_before(_("track title"), this);
653 strcpy(patch->track->title, get_text());
654 mwindow->update_plugin_titles();
655 mwindow->gui->draw_overlays(1);
656 mwindow->undo->update_undo_after(_("track title"), LOAD_PATCHES);
661 NudgePatch::NudgePatch(MWindow *mwindow,
670 patch->calculate_nudge_text(0))
672 this->mwindow = mwindow;
674 set_tooltip(_("Nudge"));
677 int NudgePatch::handle_event()
679 set_value(patch->calculate_nudge(get_text()));
683 void NudgePatch::set_value(int64_t value)
685 mwindow->undo->update_undo_before(_("nudge."), this);
686 patch->track->nudge = value;
688 if(patch->track->gang && patch->track->record)
689 patch->patchbay->synchronize_nudge(patch->track->nudge, patch->track);
691 mwindow->undo->update_undo_after(_("nudge."), LOAD_PATCHES);
693 mwindow->gui->unlock_window();
694 if(patch->track->data_type == TRACK_VIDEO)
695 mwindow->restart_brender();
696 mwindow->sync_parameters(CHANGE_PARAMS);
697 mwindow->gui->lock_window("NudgePatch::handle_event 2");
699 mwindow->session->changes_made = 1;
703 int NudgePatch::button_press_event()
707 if(is_event_win() && cursor_inside())
709 if(get_buttonpress() == 4)
711 int value = patch->calculate_nudge(get_text());
712 value += calculate_increment();
718 if(get_buttonpress() == 5)
720 int value = patch->calculate_nudge(get_text());
721 value -= calculate_increment();
727 if(get_buttonpress() == 3)
729 patch->patchbay->nudge_popup->activate_menu(patch);
735 return BC_TextBox::button_press_event();
740 int64_t NudgePatch::calculate_increment()
742 if(patch->track->data_type == TRACK_AUDIO)
744 return (int64_t)ceil(patch->track->edl->session->sample_rate / 10.0);
748 return (int64_t)ceil(1.0 / patch->track->edl->session->frame_rate);
752 void NudgePatch::update()
755 char *string = patch->calculate_nudge_text(&changed);
757 BC_TextBox::update(string);
761 MixPatch::MixPatch(MWindow *mwindow, PatchGUI *patch, int x, int y)
762 : BC_Toggle(x, y, mwindow->theme->get_image_set("mixpatch_data"),
763 patch->mixer, "", 0, 0, 0)
765 this->mwindow = mwindow;
769 MixPatch::~MixPatch()
773 int MixPatch::handle_event()
775 int v = patch->track ? get_value() : 0;
776 if( patch->mixer != v ) {
778 mwindow->gui->update_mixers(patch->track, v);
781 mwindow->update_mixer_tracks();
786 void MixPatch::update(int v)
789 BC_Toggle::update(v);