prevent popup deactivation while button_down
[goodguy/history.git] / cinelerra-5.0 / cinelerra / keyframepopup.C
1
2 /*
3  * CINELERRA
4  * Copyright (C) 2008 Adam Williams <broadcast at earthling dot net>
5  * 
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.
10  * 
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.
15  * 
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
19  * 
20  */
21
22 #include "apatchgui.h"
23 #include "autoconf.h"
24 #include "automation.h"
25 #include "autos.h"
26 #include "bcwindowbase.h"
27 #include "cpanel.h"
28 #include "cwindowgui.h" 
29 #include "cwindow.h"
30 #include "edl.h"
31 #include "edlsession.h"
32 #include "filexml.h"
33 #include "gwindow.h"
34 #include "gwindowgui.h"
35 #include "keyframe.h"
36 #include "keyframegui.h"
37 #include "keyframepopup.h"
38 #include "language.h"
39 #include "localsession.h"
40 #include "maincursor.h"
41 #include "mainmenu.h"
42 #include "mainundo.h"
43 #include "mwindowgui.h"
44 #include "mwindow.h"
45 #include "patchbay.h"
46 #include "patchgui.h" 
47 #include "track.h"
48 #include "vpatchgui.h"
49
50 KeyframePopup::KeyframePopup(MWindow *mwindow, MWindowGUI *gui)
51  : BC_PopupMenu(0, 
52                 0, 
53                 0, 
54                 "", 
55                 0)
56 {
57         this->mwindow = mwindow;
58         this->gui = gui;
59         key_hide = 0;
60         key_delete = 0;
61         key_copy = 0;
62         key_linear = 0;
63         key_bezier = 0;
64         edit = 0;
65 }
66
67 KeyframePopup::~KeyframePopup()
68 {
69 }
70
71 void KeyframePopup::create_objects()
72 {
73         add_item(key_hide = new KeyframePopupHide(mwindow, this));
74 }
75
76 int KeyframePopup::update(Plugin *plugin, KeyFrame *keyframe)
77 {
78         this->keyframe_plugin = plugin;
79         this->keyframe_auto = keyframe;
80         this->keyframe_autos = keyframe->autos;
81         this->keyframe_automation = 0;
82
83 // Suspect this routine is only used for plugins so this is never reached
84         if(keyframe->autos->type == Autos::AUTOMATION_TYPE_FLOAT)
85         {
86                 if(!key_linear) add_item(key_linear = new KeyframePopupLinear(mwindow, this));
87                 if(!key_bezier) add_item(key_bezier = new KeyframePopupBezier(mwindow, this));
88         }
89         else
90         {
91                 if(key_linear) delete key_linear;
92                 if(key_bezier) delete key_bezier;
93                 key_linear = 0;
94                 key_bezier = 0;
95         }
96
97         if(plugin)
98         {
99                 if(!edit) add_item(edit = new KeyframePopupEdit(mwindow, this));
100         }
101         else
102         {
103                 delete edit;
104                 edit = 0;
105         }
106         return 0;
107 }
108
109 int KeyframePopup::update(Automation *automation, 
110         Autos *autos, 
111         Auto *auto_keyframe)
112 {
113         this->keyframe_plugin = 0;
114         this->keyframe_automation = automation;
115         this->keyframe_autos = autos;
116         this->keyframe_auto = auto_keyframe;
117
118         if(auto_keyframe && autos->type == Autos::AUTOMATION_TYPE_FLOAT)
119         {
120                 if(!key_linear) add_item(key_linear = new KeyframePopupLinear(mwindow, this));
121                 if(!key_bezier) add_item(key_bezier = new KeyframePopupBezier(mwindow, this));
122         }
123         else
124         {
125                 if(key_linear) delete key_linear;
126                 if(key_bezier) delete key_bezier;
127                 key_linear = 0;
128                 key_bezier = 0;
129         }
130
131         if(auto_keyframe)
132         {
133                 if(!key_delete) add_item(key_delete = new KeyframePopupDelete(mwindow, this));
134                 if(!key_copy) add_item(key_copy = new KeyframePopupCopy(mwindow, this));
135         }
136         else
137         {
138                 if(key_delete) delete key_delete;
139                 if(key_copy) delete key_copy;
140                 key_delete = 0;
141                 key_copy = 0;
142         }
143         
144         if(edit)
145         {
146                 delete edit;
147                 edit = 0;
148         }
149
150 /* snap to cursor */
151         if(keyframe_auto)
152         {
153                 double current_position = mwindow->edl->local_session->get_selectionstart(1);
154                 double new_position = keyframe_automation->track->from_units(keyframe_auto->position);
155                 mwindow->edl->local_session->set_selectionstart(new_position);
156                 mwindow->edl->local_session->set_selectionend(new_position);
157
158                 if (current_position != new_position)
159                 {
160                         mwindow->edl->local_session->set_selectionstart(new_position);
161                         mwindow->edl->local_session->set_selectionend(new_position);
162                         mwindow->gui->lock_window();
163                         mwindow->gui->update(1, 1, 1, 1, 1, 1, 0);      
164                         mwindow->gui->unlock_window();
165                 }
166         }
167         
168         return 0;
169 }
170
171
172
173
174
175 KeyframePopupDelete::KeyframePopupDelete(MWindow *mwindow, KeyframePopup *popup)
176  : BC_MenuItem(_("Delete keyframe"))
177 {
178         this->mwindow = mwindow;
179         this->popup = popup;
180 }
181
182 KeyframePopupDelete::~KeyframePopupDelete()
183 {
184 }
185
186 int KeyframePopupDelete::handle_event()
187 {
188         mwindow->undo->update_undo_before(_("delete keyframe"), 0);
189         delete popup->keyframe_auto;
190         popup->keyframe_auto = 0;
191         mwindow->save_backup();
192         mwindow->undo->update_undo_after(_("delete keyframe"), LOAD_ALL);
193
194         mwindow->gui->update(0,
195                 1,      // 1 for incremental drawing.  2 for full refresh
196                 0,
197                 0,
198                 0,
199             0,   
200             0);
201         mwindow->update_plugin_guis();
202         mwindow->restart_brender();
203         mwindow->sync_parameters(CHANGE_EDL);
204
205         return 1;
206 }
207
208
209
210
211
212 KeyframePopupLinear::KeyframePopupLinear(MWindow *mwindow, KeyframePopup *popup)
213  : BC_MenuItem(_("Make linear"))
214 {
215         this->mwindow = mwindow;
216         this->popup = popup;
217 }
218
219 KeyframePopupLinear::~KeyframePopupLinear()
220 {
221 }
222
223 int KeyframePopupLinear::handle_event()
224 {
225         mwindow->undo->update_undo_before();
226         popup->keyframe_auto->mode = Auto::LINEAR;
227         mwindow->save_backup();
228         mwindow->undo->update_undo_after(_("make linear curve"), LOAD_ALL);
229
230         mwindow->gui->update(0,
231                 1,      // 1 for incremental drawing.  2 for full refresh
232                 0,
233                 0,
234                 0,
235             0,   
236             0);
237         mwindow->update_plugin_guis();
238         mwindow->restart_brender();
239         mwindow->sync_parameters(CHANGE_EDL);
240
241         return 1;
242 }
243
244
245
246
247
248 KeyframePopupBezier::KeyframePopupBezier(MWindow *mwindow, KeyframePopup *popup)
249  : BC_MenuItem(_("Make bezier"))
250 {
251         this->mwindow = mwindow;
252         this->popup = popup;
253 }
254
255 KeyframePopupBezier::~KeyframePopupBezier()
256 {
257 }
258
259 int KeyframePopupBezier::handle_event()
260 {
261         mwindow->undo->update_undo_before();
262         popup->keyframe_auto->mode = Auto::BEZIER;
263         mwindow->save_backup();
264         mwindow->undo->update_undo_after(_("make bezier curve"), LOAD_ALL);
265
266         mwindow->gui->update(0,
267                 1,      // 1 for incremental drawing.  2 for full refresh
268                 0,
269                 0,
270                 0,
271             0,   
272             0);
273         mwindow->update_plugin_guis();
274         mwindow->restart_brender();
275         mwindow->sync_parameters(CHANGE_EDL);
276
277         return 1;
278 }
279
280
281
282
283
284 KeyframePopupHide::KeyframePopupHide(MWindow *mwindow, KeyframePopup *popup)
285  : BC_MenuItem(_("Hide keyframe type"))
286 {
287         this->mwindow = mwindow;
288         this->popup = popup;
289 }
290
291 int KeyframePopupHide::handle_event()
292 {
293 // Get the array index of the curve
294         int update_gui = 0;
295         if(popup->keyframe_autos)
296         {
297                 if(popup->keyframe_autos->type == Autos::AUTOMATION_TYPE_PLUGIN)
298                 {
299                         mwindow->edl->session->auto_conf->plugins = 0;
300                         update_gui = 1;
301                 }
302                 else
303                 {
304                         Track *track = popup->keyframe_autos->track;
305                         if(track)
306                         {
307                                 Automation *automation = track->automation;
308                                 if(automation)
309                                 {
310                                         for(int i = 0; i < AUTOMATION_TOTAL; i++)
311                                         {
312                                                 if(automation->autos[i] == popup->keyframe_autos)
313                                                 {
314                                                         mwindow->edl->session->auto_conf->autos[i] = 0;
315                                                         update_gui = 1;
316                                                         break;
317                                                 }
318                                         }
319                                 }
320                         }
321                 }
322         }
323
324         if(update_gui)
325         {
326                 mwindow->gui->update(0,
327                         1,      // 1 for incremental drawing.  2 for full refresh
328                         0,
329                         0,
330                         0,
331                 0,   
332                 0);
333                 mwindow->gui->mainmenu->update_toggles(1);
334                 mwindow->gui->unlock_window();
335                 mwindow->gwindow->gui->update_toggles(1);
336                 mwindow->gui->lock_window("KeyframePopupHide::handle_event");
337         }
338
339         return 1;
340 }
341
342
343
344 KeyframePopupCopy::KeyframePopupCopy(MWindow *mwindow, KeyframePopup *popup)
345  : BC_MenuItem(_("Copy"))
346 {
347         this->mwindow = mwindow;
348         this->popup = popup;
349 }
350
351 int KeyframePopupCopy::handle_event()
352 {
353 /*
354         FIXME:
355         we want to copy just keyframe under cursor, NOT all keyframes at this frame
356         - very hard to do, so this is good approximation for now...
357 */
358         
359 //      if (popup->keyframe_automation)
360 //      {
361 //              FileXML file;
362 //              EDL *edl = mwindow->edl;
363 //              Track *track = popup->keyframe_automation->track;
364 //              int64_t position = popup->keyframe_auto->position;
365 //              AutoConf autoconf;
366 // // first find out type of our auto
367 //              autoconf.set_all(0);
368 //              if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->projector_autos)
369 //                      autoconf.projector = 1;
370 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->pzoom_autos)
371 //                      autoconf.pzoom = 1;
372 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->camera_autos)
373 //                      autoconf.camera = 1;
374 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->czoom_autos)
375 //                      autoconf.czoom = 1;             
376 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->mode_autos)
377 //                      autoconf.mode = 1;
378 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->mask_autos)
379 //                      autoconf.mask = 1;
380 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->pan_autos)
381 //                      autoconf.pan = 1;                  
382 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->fade_autos)
383 //                      autoconf.fade = 1;
384 //              else if (popup->keyframe_autos == (Autos *)popup->keyframe_automation->mute_autos)
385 //                      autoconf.mute = 1;              
386 // 
387 // 
388 // // now create a clipboard
389 //              file.tag.set_title("AUTO_CLIPBOARD");
390 //              file.tag.set_property("LENGTH", 0);
391 //              file.tag.set_property("FRAMERATE", edl->session->frame_rate);
392 //              file.tag.set_property("SAMPLERATE", edl->session->sample_rate);
393 //              file.append_tag();
394 //              file.append_newline();
395 //              file.append_newline();
396 // 
397 // /*           track->copy_automation(position, 
398 //                      position, 
399 //                      &file,
400 //                      0,
401 //                      0);
402 //                      */
403 //              file.tag.set_title("TRACK");
404 // // Video or audio
405 //              track->save_header(&file);
406 //              file.append_tag();
407 //              file.append_newline();
408 // 
409 //              track->automation->copy(position, 
410 //                      position, 
411 //                      &file,
412 //                      0,
413 //                      0,
414 //                      &autoconf);
415 //              
416 //              
417 //              
418 //              file.tag.set_title("/TRACK");
419 //              file.append_tag();
420 //              file.append_newline();
421 //              file.append_newline();
422 //              file.append_newline();
423 //              file.append_newline();
424 // 
425 // 
426 // 
427 //              file.tag.set_title("/AUTO_CLIPBOARD");
428 //              file.append_tag();
429 //              file.append_newline();
430 //              file.terminate_string();
431 // 
432 //              mwindow->gui->lock_window();
433 //              mwindow->gui->get_clipboard()->to_clipboard(file.string, 
434 //                      strlen(file.string), 
435 //                      SECONDARY_SELECTION);
436 //              mwindow->gui->unlock_window();
437 // 
438 //      } else
439
440         mwindow->copy_automation();
441         return 1;
442 }
443
444
445 KeyframePopupEdit::KeyframePopupEdit(MWindow *mwindow, KeyframePopup *popup)
446  : BC_MenuItem(_("Presets..."))
447 {
448         this->mwindow = mwindow;
449         this->popup = popup;
450 }
451
452 int KeyframePopupEdit::handle_event()
453 {
454         mwindow->show_keyframe_gui(popup->keyframe_plugin);
455         return 1;
456 }
457
458
459