2015-11-24 15:17:25 -05:00
/*
2015-11-30 12:51:18 -05:00
Copyright ( C ) 2015 Paul Davis
2015-11-24 15:17:25 -05:00
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 ; if not , write to the Free Software
Foundation , Inc . , 675 Mass Ave , Cambridge , MA 0213 9 , USA .
*/
2015-11-29 11:32:28 -05:00
# include <gtkmm/alignment.h>
# include <gtkmm/label.h>
2015-11-30 12:51:18 -05:00
# include <gtkmm/liststore.h>
2015-11-29 11:32:28 -05:00
# include "pbd/unwind.h"
# include "pbd/strsplit.h"
2015-12-01 09:03:16 -05:00
# include "pbd/file_utils.h"
2015-11-29 11:32:28 -05:00
2018-12-10 08:32:56 -05:00
# include "gtkmm2ext/actions.h"
2016-01-11 21:36:44 -05:00
# include "gtkmm2ext/bindings.h"
2015-11-24 15:17:25 -05:00
# include "gtkmm2ext/gtk_ui.h"
2015-11-29 11:32:28 -05:00
# include "gtkmm2ext/gui_thread.h"
2015-11-24 15:17:25 -05:00
# include "gtkmm2ext/utils.h"
2015-11-29 11:32:28 -05:00
# include "ardour/audioengine.h"
2015-12-01 09:03:16 -05:00
# include "ardour/filesystem_paths.h"
2015-11-29 11:32:28 -05:00
2015-11-24 18:00:11 -05:00
# include "faderport.h"
2015-11-30 12:51:18 -05:00
# include "gui.h"
2015-11-24 15:17:25 -05:00
2016-07-14 14:44:52 -04:00
# include "pbd/i18n.h"
2015-11-24 15:17:25 -05:00
using namespace PBD ;
using namespace ARDOUR ;
2015-11-24 20:12:01 -05:00
using namespace ArdourSurface ;
2015-11-24 15:17:25 -05:00
using namespace std ;
using namespace Gtk ;
using namespace Gtkmm2ext ;
void *
2015-11-24 18:00:11 -05:00
FaderPort : : get_gui ( ) const
2015-11-24 15:17:25 -05:00
{
if ( ! gui ) {
2015-11-24 18:00:11 -05:00
const_cast < FaderPort * > ( this ) - > build_gui ( ) ;
2015-11-24 15:17:25 -05:00
}
static_cast < Gtk : : VBox * > ( gui ) - > show_all ( ) ;
return gui ;
}
void
2015-11-24 18:00:11 -05:00
FaderPort : : tear_down_gui ( )
2015-11-24 15:17:25 -05:00
{
if ( gui ) {
Gtk : : Widget * w = static_cast < Gtk : : VBox * > ( gui ) - > get_parent ( ) ;
if ( w ) {
w - > hide ( ) ;
delete w ;
}
}
2015-11-30 12:51:18 -05:00
delete static_cast < FPGUI * > ( gui ) ;
2015-11-24 15:17:25 -05:00
gui = 0 ;
}
void
2015-11-24 18:00:11 -05:00
FaderPort : : build_gui ( )
2015-11-24 15:17:25 -05:00
{
2015-11-29 11:32:28 -05:00
gui = ( void * ) new FPGUI ( * this ) ;
2015-11-24 15:17:25 -05:00
}
/*--------------------*/
2015-11-29 11:32:28 -05:00
FPGUI : : FPGUI ( FaderPort & p )
: fp ( p )
, table ( 2 , 5 )
2016-01-25 14:48:21 -05:00
, action_table ( 5 , 4 )
2015-11-29 11:32:28 -05:00
, ignore_active_change ( false )
{
set_border_width ( 12 ) ;
table . set_row_spacings ( 4 ) ;
table . set_col_spacings ( 6 ) ;
table . set_border_width ( 12 ) ;
table . set_homogeneous ( false ) ;
2015-12-01 09:03:16 -05:00
std : : string data_file_path ;
string name = " faderport-small.png " ;
Searchpath spath ( ARDOUR : : ardour_data_search_path ( ) ) ;
spath . add_subdirectory_to_paths ( " icons " ) ;
find_file ( spath , name , data_file_path ) ;
if ( ! data_file_path . empty ( ) ) {
image . set ( data_file_path ) ;
hpacker . pack_start ( image , false , false ) ;
}
2015-11-29 11:32:28 -05:00
Gtk : : Label * l ;
Gtk : : Alignment * align ;
int row = 0 ;
input_combo . pack_start ( midi_port_columns . short_name ) ;
output_combo . pack_start ( midi_port_columns . short_name ) ;
input_combo . signal_changed ( ) . connect ( sigc : : bind ( sigc : : mem_fun ( * this , & FPGUI : : active_port_changed ) , & input_combo , true ) ) ;
output_combo . signal_changed ( ) . connect ( sigc : : bind ( sigc : : mem_fun ( * this , & FPGUI : : active_port_changed ) , & output_combo , false ) ) ;
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Incoming MIDI on: " ) ) ) ;
2015-11-29 11:32:28 -05:00
l - > set_alignment ( 1.0 , 0.5 ) ;
table . attach ( * l , 0 , 1 , row , row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
table . attach ( input_combo , 1 , 2 , row , row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) , 0 , 0 ) ;
row + + ;
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Outgoing MIDI on: " ) ) ) ;
2015-11-29 11:32:28 -05:00
l - > set_alignment ( 1.0 , 0.5 ) ;
table . attach ( * l , 0 , 1 , row , row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
table . attach ( output_combo , 1 , 2 , row , row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) , 0 , 0 ) ;
row + + ;
2015-11-30 12:51:18 -05:00
build_mix_action_combo ( mix_combo [ 0 ] , FaderPort : : ButtonState ( 0 ) ) ;
build_mix_action_combo ( mix_combo [ 1 ] , FaderPort : : ShiftDown ) ;
2015-12-01 09:23:02 -05:00
build_mix_action_combo ( mix_combo [ 2 ] , FaderPort : : LongPress ) ;
2015-11-30 12:51:18 -05:00
build_proj_action_combo ( proj_combo [ 0 ] , FaderPort : : ButtonState ( 0 ) ) ;
build_proj_action_combo ( proj_combo [ 1 ] , FaderPort : : ShiftDown ) ;
2015-12-01 09:23:02 -05:00
build_proj_action_combo ( proj_combo [ 2 ] , FaderPort : : LongPress ) ;
2015-11-30 12:51:18 -05:00
build_trns_action_combo ( trns_combo [ 0 ] , FaderPort : : ButtonState ( 0 ) ) ;
build_trns_action_combo ( trns_combo [ 1 ] , FaderPort : : ShiftDown ) ;
2015-12-01 09:23:02 -05:00
build_trns_action_combo ( trns_combo [ 2 ] , FaderPort : : LongPress ) ;
2015-11-29 11:32:28 -05:00
2015-12-01 11:20:09 -05:00
build_available_action_menu ( ) ;
2016-01-25 14:48:21 -05:00
build_foot_action_combo ( foot_combo [ 0 ] , FaderPort : : ButtonState ( 0 ) ) ;
build_foot_action_combo ( foot_combo [ 1 ] , FaderPort : : ShiftDown ) ;
build_foot_action_combo ( foot_combo [ 2 ] , FaderPort : : LongPress ) ;
2015-12-01 16:19:16 -05:00
/* No shift-press combo for User because that is labelled as "next"
* ( marker )
*/
2015-12-01 11:20:09 -05:00
build_user_action_combo ( user_combo [ 0 ] , FaderPort : : ButtonState ( 0 ) ) ;
2015-12-01 16:19:16 -05:00
build_user_action_combo ( user_combo [ 1 ] , FaderPort : : LongPress ) ;
2015-12-01 11:20:09 -05:00
2015-11-30 12:51:18 -05:00
action_table . set_row_spacings ( 4 ) ;
action_table . set_col_spacings ( 6 ) ;
action_table . set_border_width ( 12 ) ;
action_table . set_homogeneous ( false ) ;
int action_row = 0 ;
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Press Action " ) ) ) ;
2015-12-01 09:23:02 -05:00
l - > set_alignment ( 0.5 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
action_table . attach ( * l , 1 , 2 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Shift-Press Action " ) ) ) ;
2015-12-01 09:23:02 -05:00
l - > set_alignment ( 0.5 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
action_table . attach ( * l , 2 , 3 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Long Press Action " ) ) ) ;
2015-12-01 09:23:02 -05:00
l - > set_alignment ( 0.5 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
action_table . attach ( * l , 3 , 4 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
action_row + + ;
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Mix " ) ) ) ;
2015-11-30 12:51:18 -05:00
l - > set_alignment ( 1.0 , 0.5 ) ;
action_table . attach ( * l , 0 , 1 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-11-29 11:32:28 -05:00
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
align - > add ( mix_combo [ 0 ] ) ;
action_table . attach ( * align , 1 , 2 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( mix_combo [ 1 ] ) ;
action_table . attach ( * align , 2 , 3 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( mix_combo [ 2 ] ) ;
action_table . attach ( * align , 3 , 4 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
action_row + + ;
2015-11-29 11:32:28 -05:00
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Proj " ) ) ) ;
2015-11-29 11:32:28 -05:00
l - > set_alignment ( 1.0 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
action_table . attach ( * l , 0 , 1 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-11-29 11:32:28 -05:00
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
align - > add ( proj_combo [ 0 ] ) ;
action_table . attach ( * align , 1 , 2 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( proj_combo [ 1 ] ) ;
action_table . attach ( * align , 2 , 3 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( proj_combo [ 2 ] ) ;
action_table . attach ( * align , 3 , 4 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
action_row + + ;
2015-11-29 11:32:28 -05:00
2015-12-01 10:31:29 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Trns " ) ) ) ;
2015-11-29 11:32:28 -05:00
l - > set_alignment ( 1.0 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
action_table . attach ( * l , 0 , 1 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-11-29 11:32:28 -05:00
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
2015-11-30 12:51:18 -05:00
align - > add ( trns_combo [ 0 ] ) ;
action_table . attach ( * align , 1 , 2 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( trns_combo [ 1 ] ) ;
action_table . attach ( * align , 2 , 3 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( trns_combo [ 2 ] ) ;
action_table . attach ( * align , 3 , 4 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
action_row + + ;
2015-12-01 11:20:09 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " User " ) ) ) ;
l - > set_alignment ( 1.0 , 0.5 ) ;
action_table . attach ( * l , 0 , 1 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( user_combo [ 0 ] ) ;
action_table . attach ( * align , 1 , 2 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-12-01 16:19:16 -05:00
/* skip shift press combo */
2015-12-01 11:20:09 -05:00
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( user_combo [ 1 ] ) ;
action_table . attach ( * align , 3 , 4 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
action_row + + ;
2016-01-25 14:48:21 -05:00
l = manage ( new Gtk : : Label ) ;
l - > set_markup ( string_compose ( " <span weight= \" bold \" >%1</span> " , _ ( " Footswitch " ) ) ) ;
l - > set_alignment ( 1.0 , 0.5 ) ;
action_table . attach ( * l , 0 , 1 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( foot_combo [ 0 ] ) ;
action_table . attach ( * align , 1 , 2 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( foot_combo [ 1 ] ) ;
action_table . attach ( * align , 2 , 3 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
align = manage ( new Alignment ) ;
align - > set ( 0.0 , 0.5 ) ;
align - > add ( foot_combo [ 2 ] ) ;
action_table . attach ( * align , 3 , 4 , action_row , action_row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
action_row + + ;
2015-11-30 12:51:18 -05:00
table . attach ( action_table , 0 , 5 , row , row + 1 , AttachOptions ( FILL | EXPAND ) , AttachOptions ( 0 ) ) ;
2015-11-29 11:32:28 -05:00
row + + ;
2015-12-01 09:03:16 -05:00
hpacker . pack_start ( table , true , true ) ;
pack_start ( hpacker , false , false ) ;
2015-11-29 11:32:28 -05:00
2015-11-30 12:51:18 -05:00
/* update the port connection combos */
update_port_combos ( ) ;
/* catch future changes to connection state */
2015-11-29 11:32:28 -05:00
fp . ConnectionChange . connect ( connection_change_connection , invalidator ( * this ) , boost : : bind ( & FPGUI : : connection_handler , this ) , gui_context ( ) ) ;
}
FPGUI : : ~ FPGUI ( )
2015-11-24 15:17:25 -05:00
{
}
2015-11-29 11:32:28 -05:00
void
FPGUI : : connection_handler ( )
2015-11-24 15:17:25 -05:00
{
2015-11-29 11:32:28 -05:00
/* ignore all changes to combobox active strings here, because we're
updating them to match a new ( " external " ) reality - we were called
because port connections have changed .
*/
PBD : : Unwinder < bool > ici ( ignore_active_change , true ) ;
2015-11-30 12:51:18 -05:00
update_port_combos ( ) ;
}
void
FPGUI : : update_port_combos ( )
{
2015-11-29 11:32:28 -05:00
vector < string > midi_inputs ;
vector < string > midi_outputs ;
ARDOUR : : AudioEngine : : instance ( ) - > get_ports ( " " , ARDOUR : : DataType : : MIDI , ARDOUR : : PortFlags ( ARDOUR : : IsOutput | ARDOUR : : IsTerminal ) , midi_inputs ) ;
ARDOUR : : AudioEngine : : instance ( ) - > get_ports ( " " , ARDOUR : : DataType : : MIDI , ARDOUR : : PortFlags ( ARDOUR : : IsInput | ARDOUR : : IsTerminal ) , midi_outputs ) ;
Glib : : RefPtr < Gtk : : ListStore > input = build_midi_port_list ( midi_inputs , true ) ;
Glib : : RefPtr < Gtk : : ListStore > output = build_midi_port_list ( midi_outputs , false ) ;
bool input_found = false ;
bool output_found = false ;
int n ;
input_combo . set_model ( input ) ;
output_combo . set_model ( output ) ;
Gtk : : TreeModel : : Children children = input - > children ( ) ;
Gtk : : TreeModel : : Children : : iterator i ;
i = children . begin ( ) ;
+ + i ; /* skip "Disconnected" */
for ( n = 1 ; i ! = children . end ( ) ; + + i , + + n ) {
string port_name = ( * i ) [ midi_port_columns . full_name ] ;
if ( fp . input_port ( ) - > connected_to ( port_name ) ) {
input_combo . set_active ( n ) ;
input_found = true ;
break ;
}
}
if ( ! input_found ) {
input_combo . set_active ( 0 ) ; /* disconnected */
}
children = output - > children ( ) ;
i = children . begin ( ) ;
+ + i ; /* skip "Disconnected" */
for ( n = 1 ; i ! = children . end ( ) ; + + i , + + n ) {
string port_name = ( * i ) [ midi_port_columns . full_name ] ;
if ( fp . output_port ( ) - > connected_to ( port_name ) ) {
output_combo . set_active ( n ) ;
output_found = true ;
break ;
}
}
if ( ! output_found ) {
output_combo . set_active ( 0 ) ; /* disconnected */
}
2015-11-24 15:17:25 -05:00
}
2015-11-29 11:32:28 -05:00
void
FPGUI : : build_available_action_menu ( )
{
/* build a model of all available actions (needs to be tree structured
* more )
*/
available_action_model = TreeStore : : create ( action_columns ) ;
vector < string > paths ;
vector < string > labels ;
vector < string > tooltips ;
vector < string > keys ;
2016-01-11 21:36:44 -05:00
vector < Glib : : RefPtr < Gtk : : Action > > actions ;
2018-12-10 08:32:56 -05:00
ActionManager : : get_all_actions ( paths , labels , tooltips , keys , actions ) ;
2016-01-11 21:36:44 -05:00
2015-11-29 11:32:28 -05:00
typedef std : : map < string , TreeIter > NodeMap ;
NodeMap nodes ;
NodeMap : : iterator r ;
vector < string > : : iterator k ;
vector < string > : : iterator p ;
vector < string > : : iterator t ;
vector < string > : : iterator l ;
available_action_model - > clear ( ) ;
TreeIter rowp ;
TreeModel : : Row parent ;
2015-12-03 21:45:41 -05:00
/* Disabled item (row 0) */
2015-11-29 11:32:28 -05:00
rowp = available_action_model - > append ( ) ;
parent = * ( rowp ) ;
2015-12-03 21:45:41 -05:00
parent [ action_columns . name ] = _ ( " Disabled " ) ;
2015-11-29 11:32:28 -05:00
/* Key aliasing */
rowp = available_action_model - > append ( ) ;
parent = * ( rowp ) ;
parent [ action_columns . name ] = _ ( " Shift " ) ;
rowp = available_action_model - > append ( ) ;
parent = * ( rowp ) ;
parent [ action_columns . name ] = _ ( " Control " ) ;
rowp = available_action_model - > append ( ) ;
parent = * ( rowp ) ;
parent [ action_columns . name ] = _ ( " Option " ) ;
rowp = available_action_model - > append ( ) ;
parent = * ( rowp ) ;
parent [ action_columns . name ] = _ ( " CmdAlt " ) ;
for ( l = labels . begin ( ) , k = keys . begin ( ) , p = paths . begin ( ) , t = tooltips . begin ( ) ; l ! = labels . end ( ) ; + + k , + + p , + + t , + + l ) {
TreeModel : : Row row ;
vector < string > parts ;
parts . clear ( ) ;
split ( * p , parts , ' / ' ) ;
if ( parts . empty ( ) ) {
continue ;
}
//kinda kludgy way to avoid displaying menu items as mappable
2019-02-16 15:05:41 -05:00
if ( parts [ 1 ] = = _ ( " Main Menu " ) )
2015-11-29 11:32:28 -05:00
continue ;
if ( parts [ 1 ] = = _ ( " JACK " ) )
continue ;
if ( parts [ 1 ] = = _ ( " redirectmenu " ) )
continue ;
if ( parts [ 1 ] = = _ ( " RegionList " ) )
continue ;
if ( parts [ 1 ] = = _ ( " ProcessorMenu " ) )
continue ;
if ( ( r = nodes . find ( parts [ 1 ] ) ) = = nodes . end ( ) ) {
/* top level is missing */
TreeIter rowp ;
TreeModel : : Row parent ;
rowp = available_action_model - > append ( ) ;
nodes [ parts [ 1 ] ] = rowp ;
parent = * ( rowp ) ;
parent [ action_columns . name ] = parts [ 1 ] ;
row = * ( available_action_model - > append ( parent . children ( ) ) ) ;
} else {
row = * ( available_action_model - > append ( ( * r - > second ) - > children ( ) ) ) ;
}
/* add this action */
if ( l - > empty ( ) ) {
row [ action_columns . name ] = * t ;
action_map [ * t ] = * p ;
} else {
row [ action_columns . name ] = * l ;
action_map [ * l ] = * p ;
}
2015-12-01 11:20:09 -05:00
string path = ( * p ) ;
/* ControlProtocol::access_action() is not interested in the
legacy " <Actions>/ " prefix part of a path .
*/
path = path . substr ( strlen ( " <Actions>/ " ) ) ;
row [ action_columns . path ] = path ;
2015-11-29 11:32:28 -05:00
}
}
void
2015-11-30 15:05:30 -05:00
FPGUI : : action_changed ( Gtk : : ComboBox * cb , FaderPort : : ButtonID id , FaderPort : : ButtonState bs )
2015-11-30 12:51:18 -05:00
{
TreeModel : : const_iterator row = cb - > get_active ( ) ;
string action_path = ( * row ) [ action_columns . path ] ;
2015-11-30 15:05:30 -05:00
/* release binding */
fp . set_action ( id , action_path , false , bs ) ;
2015-11-30 12:51:18 -05:00
}
void
FPGUI : : build_action_combo ( Gtk : : ComboBox & cb , vector < pair < string , string > > const & actions , FaderPort : : ButtonID id , FaderPort : : ButtonState bs )
2015-11-29 11:32:28 -05:00
{
Glib : : RefPtr < Gtk : : ListStore > model ( Gtk : : ListStore : : create ( action_columns ) ) ;
TreeIter rowp ;
TreeModel : : Row row ;
2015-12-01 10:31:29 -05:00
string current_action = fp . get_action ( id , false , bs ) ; /* lookup release action */
2015-11-30 13:50:33 -05:00
int active_row = - 1 ;
int n ;
vector < pair < string , string > > : : const_iterator i ;
2015-11-29 11:32:28 -05:00
rowp = model - > append ( ) ;
row = * ( rowp ) ;
2015-11-30 12:51:18 -05:00
row [ action_columns . name ] = _ ( " Disabled " ) ;
row [ action_columns . path ] = string ( ) ;
2015-11-30 13:50:33 -05:00
if ( current_action . empty ( ) ) {
active_row = 0 ;
}
for ( i = actions . begin ( ) , n = 0 ; i ! = actions . end ( ) ; + + i , + + n ) {
2015-11-30 12:51:18 -05:00
rowp = model - > append ( ) ;
row = * ( rowp ) ;
row [ action_columns . name ] = i - > first ;
row [ action_columns . path ] = i - > second ;
2015-11-30 13:50:33 -05:00
if ( current_action = = i - > second ) {
active_row = n + 1 ;
}
2015-11-30 12:51:18 -05:00
}
2015-11-29 11:32:28 -05:00
cb . set_model ( model ) ;
cb . pack_start ( action_columns . name ) ;
2015-11-30 13:50:33 -05:00
if ( active_row > = 0 ) {
cb . set_active ( active_row ) ;
}
2015-11-30 15:05:30 -05:00
cb . signal_changed ( ) . connect ( sigc : : bind ( sigc : : mem_fun ( * this , & FPGUI : : action_changed ) , & cb , id , bs ) ) ;
2015-11-29 11:32:28 -05:00
}
void
2015-11-30 12:51:18 -05:00
FPGUI : : build_mix_action_combo ( Gtk : : ComboBox & cb , FaderPort : : ButtonState bs )
2015-11-29 11:32:28 -05:00
{
2015-11-30 12:51:18 -05:00
vector < pair < string , string > > actions ;
2018-12-10 18:40:16 -05:00
actions . push_back ( make_pair ( string ( _ ( " Show Mixer Window " ) ) , string ( X_ ( " Common/show-mixer " ) ) ) ) ;
2015-12-10 18:25:29 -05:00
actions . push_back ( make_pair ( string ( _ ( " Show/Hide Mixer list " ) ) , string ( X_ ( " Common/ToggleMixerList " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Toggle Meterbridge " ) , string ( X_ ( " Common/toggle-meterbridge " ) ) ) ) ;
2015-11-30 12:51:18 -05:00
actions . push_back ( make_pair ( string ( _ ( " Show/Hide Editor mixer strip " ) ) , string ( X_ ( " Editor/show-editor-mixer " ) ) ) ) ;
build_action_combo ( cb , actions , FaderPort : : Mix , bs ) ;
2015-11-29 11:32:28 -05:00
}
2015-11-30 12:51:18 -05:00
void
FPGUI : : build_proj_action_combo ( Gtk : : ComboBox & cb , FaderPort : : ButtonState bs )
{
vector < pair < string , string > > actions ;
2017-03-14 10:27:59 -04:00
actions . push_back ( make_pair ( string ( _ ( " Show Editor Window " ) ) , string ( X_ ( " Mixer/show-editor " ) ) ) ) ;
2015-11-30 15:05:30 -05:00
actions . push_back ( make_pair ( string ( " Toggle Editor Lists " ) , string ( X_ ( " Editor/show-editor-list " ) ) ) ) ;
2015-12-10 18:25:29 -05:00
actions . push_back ( make_pair ( string ( " Toggle Summary " ) , string ( X_ ( " Editor/ToggleSummary " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Toggle Meterbridge " ) , string ( X_ ( " Common/toggle-meterbridge " ) ) ) ) ;
2015-11-30 15:05:30 -05:00
actions . push_back ( make_pair ( string ( _ ( " Zoom to Session " ) ) , string ( X_ ( " Editor/zoom-to-session " ) ) ) ) ;
2015-12-10 18:25:29 -05:00
// actions.push_back (make_pair (string (_("Zoom In")), string (X_("Editor/temporal-zoom-in"))));
// actions.push_back (make_pair (string (_("Zoom Out")), string (X_("Editor/temporal-zoom-out"))));
2015-11-30 12:51:18 -05:00
build_action_combo ( cb , actions , FaderPort : : Proj , bs ) ;
}
2015-11-29 11:32:28 -05:00
void
2015-11-30 12:51:18 -05:00
FPGUI : : build_trns_action_combo ( Gtk : : ComboBox & cb , FaderPort : : ButtonState bs )
2015-11-29 11:32:28 -05:00
{
2015-11-30 12:51:18 -05:00
vector < pair < string , string > > actions ;
2015-12-10 18:25:29 -05:00
actions . push_back ( make_pair ( string ( " Toggle Big Clock " ) , string ( X_ ( " Window/toggle-big-clock " ) ) ) ) ; //note: this would really make sense if the Big Clock had transport buttons on it
actions . push_back ( make_pair ( string ( " Toggle Locations window " ) , string ( X_ ( " Window/toggle-locations " ) ) ) ) ;
2015-11-30 15:05:30 -05:00
actions . push_back ( make_pair ( string ( " Toggle Metronome " ) , string ( X_ ( " Transport/ToggleClick " ) ) ) ) ;
2015-12-10 18:25:29 -05:00
actions . push_back ( make_pair ( string ( " Toggle External Sync " ) , string ( X_ ( " Transport/ToggleExternalSync " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Toggle Follow Playhead " ) , string ( X_ ( " Editor/toggle-follow-playhead " ) ) ) ) ;
// actions.push_back (make_pair (string("Set Playhead @pointer"), string(X_("Editor/set-playhead"))));
2015-11-30 12:51:18 -05:00
build_action_combo ( cb , actions , FaderPort : : Trns , bs ) ;
2015-11-29 11:32:28 -05:00
}
2016-01-25 14:48:21 -05:00
void
FPGUI : : build_foot_action_combo ( Gtk : : ComboBox & cb , FaderPort : : ButtonState bs )
{
vector < pair < string , string > > actions ;
actions . push_back ( make_pair ( string ( " Toggle Roll " ) , string ( X_ ( " Transport/ToggleRoll " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Toggle Rec-Enable " ) , string ( X_ ( " Transport/Record " ) ) ) ) ;
2016-01-25 15:00:39 -05:00
actions . push_back ( make_pair ( string ( " Toggle Roll+Rec " ) , string ( X_ ( " Transport/record-roll " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Toggle Loop " ) , string ( X_ ( " Transport/Loop " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Toggle Click " ) , string ( X_ ( " Transport/ToggleClick " ) ) ) ) ;
2018-10-07 11:09:38 -04:00
actions . push_back ( make_pair ( string ( " Record with Pre-Roll " ) , string ( X_ ( " Transport/RecordPreroll " ) ) ) ) ;
actions . push_back ( make_pair ( string ( " Record with Count-In " ) , string ( X_ ( " Transport/RecordCountIn " ) ) ) ) ;
2016-01-25 14:48:21 -05:00
2016-02-02 09:21:13 -05:00
build_action_combo ( cb , actions , FaderPort : : Footswitch , bs ) ;
2016-01-25 14:48:21 -05:00
}
2015-12-03 21:45:41 -05:00
bool
FPGUI : : find_action_in_model ( const TreeModel : : iterator & iter , std : : string const & action_path , TreeModel : : iterator * found )
{
TreeModel : : Row row = * iter ;
string path = row [ action_columns . path ] ;
if ( path = = action_path ) {
* found = iter ;
return true ;
}
return false ;
}
2015-12-01 11:20:09 -05:00
void
FPGUI : : build_user_action_combo ( Gtk : : ComboBox & cb , FaderPort : : ButtonState bs )
{
cb . set_model ( available_action_model ) ;
cb . pack_start ( action_columns . name ) ;
cb . signal_changed ( ) . connect ( sigc : : bind ( sigc : : mem_fun ( * this , & FPGUI : : action_changed ) , & cb , FaderPort : : User , bs ) ) ;
2015-12-03 21:45:41 -05:00
/* set the active "row" to the right value for the current button binding */
string current_action = fp . get_action ( FaderPort : : User , false , bs ) ; /* lookup release action */
if ( current_action . empty ( ) ) {
cb . set_active ( 0 ) ; /* "disabled" */
return ;
}
TreeModel : : iterator iter = available_action_model - > children ( ) . end ( ) ;
available_action_model - > foreach_iter ( sigc : : bind ( sigc : : mem_fun ( * this , & FPGUI : : find_action_in_model ) , current_action , & iter ) ) ;
if ( iter ! = available_action_model - > children ( ) . end ( ) ) {
cb . set_active ( iter ) ;
} else {
cb . set_active ( 0 ) ;
}
2015-12-01 11:20:09 -05:00
}
2015-11-29 11:32:28 -05:00
Glib : : RefPtr < Gtk : : ListStore >
FPGUI : : build_midi_port_list ( vector < string > const & ports , bool for_input )
{
Glib : : RefPtr < Gtk : : ListStore > store = ListStore : : create ( midi_port_columns ) ;
TreeModel : : Row row ;
row = * store - > append ( ) ;
row [ midi_port_columns . full_name ] = string ( ) ;
row [ midi_port_columns . short_name ] = _ ( " Disconnected " ) ;
for ( vector < string > : : const_iterator p = ports . begin ( ) ; p ! = ports . end ( ) ; + + p ) {
row = * store - > append ( ) ;
row [ midi_port_columns . full_name ] = * p ;
std : : string pn = ARDOUR : : AudioEngine : : instance ( ) - > get_pretty_name_by_name ( * p ) ;
if ( pn . empty ( ) ) {
pn = ( * p ) . substr ( ( * p ) . find ( ' : ' ) + 1 ) ;
}
row [ midi_port_columns . short_name ] = pn ;
}
return store ;
}
void
FPGUI : : active_port_changed ( Gtk : : ComboBox * combo , bool for_input )
{
if ( ignore_active_change ) {
return ;
}
TreeModel : : iterator active = combo - > get_active ( ) ;
string new_port = ( * active ) [ midi_port_columns . full_name ] ;
if ( new_port . empty ( ) ) {
if ( for_input ) {
fp . input_port ( ) - > disconnect_all ( ) ;
} else {
fp . output_port ( ) - > disconnect_all ( ) ;
}
return ;
}
if ( for_input ) {
if ( ! fp . input_port ( ) - > connected_to ( new_port ) ) {
fp . input_port ( ) - > disconnect_all ( ) ;
fp . input_port ( ) - > connect ( new_port ) ;
}
} else {
if ( ! fp . output_port ( ) - > connected_to ( new_port ) ) {
fp . output_port ( ) - > disconnect_all ( ) ;
fp . output_port ( ) - > connect ( new_port ) ;
}
}
}