diff --git a/FL/menu_popup.C b/FL/menu_popup.C new file mode 100644 index 0000000..1a501ad --- /dev/null +++ b/FL/menu_popup.C @@ -0,0 +1,34 @@ + +/*******************************************************************************/ +/* Copyright (C) 2008 Jonathan Moore Liles */ +/* */ +/* This program is free software; you can redistribute it and/or modify it */ +/* under the terms of the GNU General Public License as published by the */ +/* Free Software Foundation; either version 2 of the License, or (at your */ +/* option) any later version. */ +/* */ +/* This program is distributed in the hope that it will be useful, but WITHOUT */ +/* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or */ +/* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for */ +/* more details. */ +/* */ +/* You should have received a copy of the GNU General Public License along */ +/* with This program; see the file COPYING. If not,write to the Free Software */ +/* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ +/*******************************************************************************/ + +#include +#include + +/* popup menu and execute callback */ +bool +menu_popup ( Fl_Menu_ *m ) +{ + const Fl_Menu_Item *r = m->menu()->popup( Fl::event_x(), Fl::event_y(), m->label() ); + + if ( r ) + { + m->value( r ); + r->do_callback( static_cast(m) ); + } +} diff --git a/FL/menu_popup.H b/FL/menu_popup.H new file mode 100644 index 0000000..5f0f6ab --- /dev/null +++ b/FL/menu_popup.H @@ -0,0 +1,21 @@ + +/*******************************************************************************/ +/* Copyright (C) 2008 Jonathan Moore Liles */ +/* */ +/* This program is free software; you can redistribute it and/or modify it */ +/* under the terms of the GNU General Public License as published by the */ +/* Free Software Foundation; either version 2 of the License, or (at your */ +/* option) any later version. */ +/* */ +/* This program is distributed in the hope that it will be useful, but WITHOUT */ +/* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or */ +/* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for */ +/* more details. */ +/* */ +/* You should have received a copy of the GNU General Public License along */ +/* with This program; see the file COPYING. If not,write to the Free Software */ +/* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ +/*******************************************************************************/ + +class Fl_Menu_; +bool menu_popup ( Fl_Menu_ *m ); diff --git a/Timeline/Audio_Region.C b/Timeline/Audio_Region.C index 907dc6d..d17bce3 100644 --- a/Timeline/Audio_Region.C +++ b/Timeline/Audio_Region.C @@ -286,6 +286,8 @@ Audio_Region::update_menu ( void ) _menu->copy( items ); } +#include "FL/menu_popup.H" + int Audio_Region::handle ( int m ) { @@ -359,13 +361,7 @@ Audio_Region::handle ( int m ) update_menu(); - const Fl_Menu_Item *r = _menu->menu()->popup( X, Y, _menu->label() ); - - if ( r ) - { - _menu->value( r ); - r->do_callback( static_cast(_menu) ); - } + menu_popup( _menu ); return 1; } diff --git a/Timeline/Timeline.C b/Timeline/Timeline.C index cade52f..cce482c 100644 --- a/Timeline/Timeline.C +++ b/Timeline/Timeline.C @@ -152,8 +152,6 @@ Timeline::cb_scroll ( Fl_Widget *w ) } } -#include - void Timeline::menu_cb ( Fl_Widget *w, void *v ) { diff --git a/Timeline/Track.C b/Timeline/Track.C index 21f23d8..9fa3662 100644 --- a/Timeline/Track.C +++ b/Timeline/Track.C @@ -478,8 +478,115 @@ Track::draw ( void ) Fl_Group::draw(); } +#include + +void +Track::menu_cb ( Fl_Widget *w, void *v ) +{ + ((Track*)v)->menu_cb( (Fl_Menu_*) w ); +} + +void +Track::menu_cb ( const Fl_Menu_ *m ) +{ + char picked[256]; + + m->item_pathname( picked, sizeof( picked ) ); + + Logger log( this ); + + if ( ! strcmp( picked, "Type/Mono" ) ) + { + configure_inputs( 1 ); + configure_outputs( 1 ); + } + else if ( ! strcmp( picked, "Type/Stereo" ) ) + { + configure_inputs( 2 ); + configure_outputs( 2 ); + } + else if ( ! strcmp( picked, "Type/Quad" ) ) + { + configure_inputs( 4 ); + configure_outputs( 4 ); + } + else if ( ! strcmp( picked, "Type/..." ) ) + { + const char *s = fl_input( "How many channels?", "3" ); + int c = atoi( s ); + + if ( c <= 0 || c > 10 ) + fl_alert( "Invalid number of channels." ); + else + { + configure_inputs( c ); + configure_outputs( c ); + } + } + else if ( ! strcmp( picked, "/Add Control" ) ) + { + new Control_Sequence( this ); + } + else if ( ! strcmp( picked, "/Add Annotation" ) ) + { + add( new Annotation_Sequence( this ) ); + } + else if ( ! strcmp( picked, "/Color" ) ) + { + unsigned char r, g, b; + + Fl::get_color( color(), r, g, b ); + + if ( fl_color_chooser( "Track Color", r, g, b ) ) + { + color( fl_rgb_color( r, g, b ) ); + } + + redraw(); + } + else if ( ! strcmp( picked, "/Remove" ) ) + { + int r = fl_choice( "Are you certain you want to remove track \"%s\"?", "Cancel", NULL, "Remove", name() ); + + if ( r == 2 ) + { + timeline->remove_track( this ); + Fl::delete_widget( this ); + } + } +} + +/** build the context menu */ +Fl_Menu_Button & +Track::menu ( void ) const +{ + static Fl_Menu_Button m( 0, 0, 0, 0, "Track" ); + + int c = output.size(); + + Fl_Menu_Item menu[] = + { + { "Type", 0, &Track::menu_cb, 0, FL_SUBMENU }, + { "Mono", 0, &Track::menu_cb, 0, FL_MENU_RADIO | ( c == 1 ? FL_MENU_VALUE : 0 ) }, + { "Stereo", 0, &Track::menu_cb, 0, FL_MENU_RADIO | ( c == 2 ? FL_MENU_VALUE : 0 ) }, + { "Quad", 0, &Track::menu_cb, 0, FL_MENU_RADIO | ( c == 4 ? FL_MENU_VALUE : 0 ) }, + { "...", 0, &Track::menu_cb, 0, FL_MENU_RADIO | ( c == 3 || c > 4 ? FL_MENU_VALUE : 0 ) }, + { 0 }, + { "Add Control" }, + { "Add Annotation" }, + { "Color" }, + { "Remove", 0, &Track::menu_cb, 0 }, // transport->rolling ? FL_MENU_INACTIVE : 0 }, + { 0 }, + }; + + m.copy( menu, (void*)this ); + + return m; +} + #include "FL/event_name.H" #include "FL/test_press.H" +#include "FL/menu_popup.H" int Track::handle ( int m ) @@ -490,6 +597,8 @@ Track::handle ( int m ) switch ( m ) { + case FL_KEYBOARD: + return menu().test_shortcut() || Fl_Group::handle( m ); case FL_MOUSEWHEEL: { Logger log( this ); @@ -516,90 +625,10 @@ Track::handle ( int m ) if ( Fl_Group::handle( m ) ) return 1; + if ( test_press( FL_BUTTON3 ) && X < Track::width() ) { - int c = output.size(); - - /* context menu */ - Fl_Menu_Item menu[] = - { - { "Type", 0, 0, 0, FL_SUBMENU }, - { "Mono", 0, 0, 0, FL_MENU_RADIO | ( c == 1 ? FL_MENU_VALUE : 0 ) }, - { "Stereo", 0, 0, 0, FL_MENU_RADIO | ( c == 2 ? FL_MENU_VALUE : 0 ) }, - { "Quad", 0, 0, 0, FL_MENU_RADIO | ( c == 4 ? FL_MENU_VALUE : 0 ) }, - { "...", 0, 0, 0, FL_MENU_RADIO | ( c == 3 || c > 4 ? FL_MENU_VALUE : 0 ) }, - { 0 }, - { "Add Control" }, - { "Add Annotation" }, - { "Color" }, - { "Remove", 0, 0, 0 }, // transport->rolling ? FL_MENU_INACTIVE : 0 }, - { 0 }, - }; - - const Fl_Menu_Item *r = menu->popup( X, Y, "Track" ); - - if ( r && r > &menu[ 0 ] ) - { - if ( r < &menu[ 4 ] ) - { - int c = r - &menu[1]; - int ca[] = { 1, 2, 4 }; - - configure_inputs( ca[ c ] ); - configure_outputs( ca[ c ] ); - } - else - { - if ( r == &menu[ 4 ] ) - { - const char *s = fl_input( "How many channels?", "3" ); - - int c = atoi( s ); - - if ( c <= 0 || c > 10 ) - fl_alert( "Invalid number of channels." ); - else - { - configure_inputs( c ); - configure_outputs( c ); - } - } - else if ( r == &menu[ 6 ] ) - { - new Control_Sequence( this ); - } - else if ( r == &menu[ 7 ] ) - { - add( new Annotation_Sequence( this ) ); - } - else if ( r == &menu[ 8 ] ) - { - unsigned char r, g, b; - - Fl::get_color( color(), r, g, b ); - - if ( fl_color_chooser( "Track Color", r, g, b ) ) - { - color( fl_rgb_color( r, g, b ) ); - } - -// color( fl_show_colormap( color() ) ); - redraw(); - } - else if ( r == &menu[ 9 ] ) - { - int r = fl_choice( "Are you certain you want to remove track \"%s\"?", "Cancel", NULL, "Remove", name() ); - - if ( r == 2 ) - { - timeline->remove_track( this ); - Fl::delete_widget( this ); - } - } - } - return 1; - } - + menu_popup( &menu() ); return 1; } diff --git a/Timeline/Track.H b/Timeline/Track.H index 8bb66b6..33165cc 100644 --- a/Timeline/Track.H +++ b/Timeline/Track.H @@ -261,6 +261,12 @@ public: void sequence ( Audio_Sequence * t ); Audio_Sequence * sequence ( void ) const { return _sequence; } + + Fl_Menu_Button & menu ( void ) const; + + static void menu_cb ( Fl_Widget *w, void *v ); + void menu_cb ( const Fl_Menu_ *m ); + void draw ( void ); int handle ( int m );