13
0

(1) awful grungy code to make tab/shift-tab correctly end route editing in track+bus tab (2) traversify the track+bus tab so that s/m/r keys solo/mute/rec-enable the appropriate things (more work to do here to follow modifier conventions established elsewhere)

git-svn-id: svn://localhost/ardour2/branches/3.0@7855 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
Paul Davis 2010-09-29 01:22:11 +00:00
parent fef6643165
commit 9f3f3738e7
2 changed files with 182 additions and 15 deletions

View File

@ -58,12 +58,15 @@ using namespace Glib;
using Gtkmm2ext::Keyboard;
EditorRoutes::EditorRoutes (Editor* e)
: EditorComponent (e),
_ignore_reorder (false),
_no_redisplay (false),
_redisplay_does_not_sync_order_keys (false),
_redisplay_does_not_reset_order_keys (false),
_menu (0)
: EditorComponent (e)
, _ignore_reorder (false)
, _no_redisplay (false)
, _redisplay_does_not_sync_order_keys (false)
, _redisplay_does_not_reset_order_keys (false)
,_menu (0)
, old_focus (0)
, selection_countdown (0)
, name_editable (0)
{
_scroller.add (_display);
_scroller.set_policy (POLICY_NEVER, POLICY_AUTOMATIC);
@ -156,7 +159,9 @@ EditorRoutes::EditorRoutes (Editor* e)
_display.append_column (*solo_isolate_state_column);
_display.append_column (*solo_safe_state_column);
_display.append_column (_("Name"), _columns.text);
int colnum = _display.append_column (_("Name"), _columns.text);
TreeViewColumn* c = _display.get_column (colnum-1);
c->set_data ("i_am_the_tab_column", (void*) 0xfeedface);
_display.append_column (_("V"), _columns.visible);
_display.set_headers_visible (true);
@ -171,6 +176,7 @@ EditorRoutes::EditorRoutes (Editor* e)
CellRendererText* name_cell = dynamic_cast<CellRendererText*> (_display.get_column_cell_renderer (5));
assert (name_cell);
name_cell->signal_editing_started().connect (sigc::mem_fun (*this, &EditorRoutes::name_edit_started));
TreeViewColumn* name_column = _display.get_column (5);
@ -201,11 +207,71 @@ EditorRoutes::EditorRoutes (Editor* e)
_model->signal_rows_reordered().connect (sigc::mem_fun (*this, &EditorRoutes::reordered));
_display.signal_button_press_event().connect (sigc::mem_fun (*this, &EditorRoutes::button_press), false);
_display.signal_key_press_event().connect (sigc::mem_fun(*this, &EditorRoutes::key_press), false);
_scroller.signal_key_press_event().connect (sigc::mem_fun(*this, &EditorRoutes::key_press), false);
_scroller.signal_focus_in_event().connect (sigc::mem_fun (*this, &EditorRoutes::focus_in), false);
_scroller.signal_focus_out_event().connect (sigc::mem_fun (*this, &EditorRoutes::focus_out));
_display.signal_enter_notify_event().connect (sigc::mem_fun (*this, &EditorRoutes::enter_notify), false);
_display.signal_leave_notify_event().connect (sigc::mem_fun (*this, &EditorRoutes::leave_notify), false);
_display.set_enable_search (false);
Route::SyncOrderKeys.connect (*this, MISSING_INVALIDATOR, ui_bind (&EditorRoutes::sync_order_keys, this, _1), gui_context());
}
bool
EditorRoutes::focus_in (GdkEventFocus*)
{
Window* win = dynamic_cast<Window*> (_scroller.get_toplevel ());
if (win) {
old_focus = win->get_focus ();
} else {
old_focus = 0;
}
/* try to do nothing on focus in (doesn't work, hence selection_count nonsense) */
return true;
}
bool
EditorRoutes::focus_out (GdkEventFocus*)
{
if (old_focus) {
old_focus->grab_focus ();
old_focus = 0;
}
return false;
}
bool
EditorRoutes::enter_notify (GdkEventCrossing* ev)
{
/* arm counter so that ::selection_filter() will deny selecting anything for the
next two attempts to change selection status.
*/
selection_countdown = 2;
_scroller.grab_focus ();
Keyboard::magic_widget_grab_focus ();
return false;
}
bool
EditorRoutes::leave_notify (GdkEventCrossing*)
{
selection_countdown = 0;
if (old_focus) {
old_focus->grab_focus ();
old_focus = 0;
}
Keyboard::magic_widget_drop_focus ();
return false;
}
void
EditorRoutes::set_session (Session* s)
{
@ -242,12 +308,12 @@ EditorRoutes::on_tv_mute_enable_toggled (std::string const & path_string)
Gtk::TreeModel::Row row = *_model->get_iter (Gtk::TreeModel::Path (path_string));
TimeAxisView *tv = row[_columns.tv];
AudioTimeAxisView *atv = dynamic_cast<AudioTimeAxisView*> (tv);
if (atv != 0) {
RouteTimeAxisView *rtv = dynamic_cast<RouteTimeAxisView*> (tv);
if (rtv != 0) {
boost::shared_ptr<RouteList> rl (new RouteList);
rl->push_back (atv->route());
_session->set_mute (rl, !atv->route()->muted(), Session::rt_cleanup);
rl->push_back (rtv->route());
_session->set_mute (rl, !rtv->route()->muted(), Session::rt_cleanup);
}
}
@ -815,10 +881,22 @@ bool
EditorRoutes::key_press (GdkEventKey* ev)
{
TreeViewColumn *col;
boost::shared_ptr<RouteList> rl (new RouteList);
TreePath path;
cerr << "our key press\n";
switch (ev->keyval) {
case GDK_Tab:
case GDK_ISO_Left_Tab:
/* If we appear to be editing something, leave that cleanly and appropriately.
*/
if (name_editable) {
name_editable->editing_done ();
name_editable = 0;
}
col = _display.get_column (5); // select&focus on name column
if (Keyboard::modifier_state_equals (ev->state, Keyboard::TertiaryModifier)) {
@ -830,6 +908,26 @@ EditorRoutes::key_press (GdkEventKey* ev)
return true;
break;
case 'm':
if (get_relevant_routes (rl)) {
_session->set_mute (rl, !rl->front()->muted(), Session::rt_cleanup);
}
return true;
break;
case 's':
if (get_relevant_routes (rl)) {
_session->set_solo (rl, !rl->front()->soloed(), Session::rt_cleanup);
}
return true;
break;
case 'r':
if (get_relevant_routes (rl)) {
_session->set_record_enabled (rl, !rl->front()->record_enabled(), Session::rt_cleanup);
}
break;
default:
break;
}
@ -837,6 +935,49 @@ EditorRoutes::key_press (GdkEventKey* ev)
return false;
}
bool
EditorRoutes::get_relevant_routes (boost::shared_ptr<RouteList> rl)
{
TimeAxisView* tv;
RouteTimeAxisView* rtv;
RefPtr<TreeSelection> selection = _display.get_selection();
TreePath path;
TreeIter iter;
if (selection->count_selected_rows() != 0) {
/* use selection */
RefPtr<TreeModel> tm = RefPtr<TreeModel>::cast_dynamic (_model);
iter = selection->get_selected (tm);
} else {
/* use mouse pointer */
int x, y;
int bx, by;
_display.get_pointer (x, y);
_display.convert_widget_to_bin_window_coords (x, y, bx, by);
if (_display.get_path_at_pos (bx, by, path)) {
iter = _model->get_iter (path);
}
}
if (iter) {
tv = (*iter)[_columns.tv];
if (tv) {
rtv = dynamic_cast<RouteTimeAxisView*>(tv);
if (rtv) {
rl->push_back (rtv->route());
}
}
}
return !rl->empty();
}
bool
EditorRoutes::button_press (GdkEventButton* ev)
{
@ -877,9 +1018,16 @@ EditorRoutes::button_press (GdkEventButton* ev)
}
bool
EditorRoutes::selection_filter (Glib::RefPtr<TreeModel> const &, TreeModel::Path const &path , bool already_selected)
EditorRoutes::selection_filter (Glib::RefPtr<TreeModel> const &, TreeModel::Path const &path , bool selected)
{
cerr << path.to_string() << " is " << (already_selected ? " already selected " : " not selected ") << endl;
if (selection_countdown) {
if (--selection_countdown == 0) {
return true;
} else {
/* no selection yet ... */
return false;
}
}
return true;
}
@ -1167,10 +1315,19 @@ EditorRoutes::clear ()
_display.set_model (_model);
}
void
EditorRoutes::name_edit_started (CellEditable* ce, const Glib::ustring&)
{
name_editable = ce;
}
void
EditorRoutes::name_edit (std::string const & path, std::string const & new_text)
{
name_editable = 0;
TreeIter iter = _model->get_iter (path);
if (!iter) {
return;
}

View File

@ -137,8 +137,18 @@ private:
bool _redisplay_does_not_reset_order_keys;
Gtk::Menu* _menu;
Gtk::Widget* old_focus;
uint32_t selection_countdown;
Gtk::CellEditable* name_editable;
bool key_press (GdkEventKey* ev);
bool focus_in (GdkEventFocus*);
bool focus_out (GdkEventFocus*);
bool enter_notify (GdkEventCrossing*);
bool leave_notify (GdkEventCrossing*);
void name_edit_started (Gtk::CellEditable*, const Glib::ustring&);
bool get_relevant_routes (boost::shared_ptr<ARDOUR::RouteList> rl);
};
#endif /* __ardour_gtk_editor_route_h__ */