add keybinding editor

git-svn-id: svn://localhost/ardour2/trunk@2543 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
Paul Davis 2007-10-12 01:54:35 +00:00
parent 02196886bb
commit 29f0d9732e
13 changed files with 264 additions and 20 deletions

View File

@ -167,6 +167,7 @@ gtk-custom-hruler.c
gtk-custom-ruler.c
io_selector.cc
keyboard.cc
keyeditor.cc
ladspa_pluginui.cc
latency_gui.cc
location_ui.cc

View File

@ -153,19 +153,28 @@ ActionManager::lookup_entry (const ustring accel_path, Gtk::AccelKey& key)
void
ActionManager::get_all_actions (vector<string>& names, vector<string>& paths, vector<string>& keys, vector<AccelKey>& bindings)
{
ListHandle<RefPtr<ActionGroup> > uim_groups = ui_manager->get_action_groups ();
for (ListHandle<RefPtr<ActionGroup> >::iterator g = uim_groups.begin(); g != uim_groups.end(); ++g) {
ListHandle<RefPtr<Action> > group_actions = (*g)->get_actions();
for (ListHandle<RefPtr<Action> >::iterator a = group_actions.begin(); a != group_actions.end(); ++a) {
/* the C++ API for functions used here appears to be broken in
gtkmm2.6, so we fall back to the C level.
*/
GList* list = gtk_ui_manager_get_action_groups (ui_manager->gobj());
GList* node;
GList* acts;
for (node = list; node; node = g_list_next (node)) {
GtkActionGroup* group = (GtkActionGroup*) node->data;
for (acts = gtk_action_group_list_actions (group); acts; acts = g_list_next (acts)) {
GtkAction* action = (GtkAction*) acts->data;
Glib::RefPtr<Action> act = Glib::wrap (action, true);
string accel_path = act->get_accel_path ();
ustring label = act->property_label();
ustring accel_path;
accel_path = (*a)->get_accel_path();
names.push_back ((*a)->get_name());
names.push_back (label);
paths.push_back (accel_path);
AccelKey key;

View File

@ -27,6 +27,8 @@
#include <gtkmm/actiongroup.h>
#include <gtkmm/accelkey.h>
#include <ardour/configuration.h>
namespace Gtk {
class UIManager;
}

View File

@ -233,6 +233,7 @@
<menuitem action='ToggleOptionsEditor'/>
<menuitem action='ToggleInspector'/>
<menuitem action='ToggleLocations'/>
<menuitem action='ToggleKeyEditor'/>
<menuitem action='ToggleThemeManager'/>
<menuitem action='ToggleBigClock'/>
<separator/>

View File

@ -91,7 +91,7 @@ style "default_base" = "medium_text"
GtkTreeView::vertical-padding = 0
GtkTreeView::horizontal-padding = 0
GtkTreeView::even-row-color = { 0, 0, 0 }
GtkTreeView::odd-row-color = { 0, 0, 0 }
GtkTreeView::odd-row-color = { 0.06, 0.06, 0.10 }
fg[NORMAL] = { 0.80, 0.80, 0.80 }
fg[ACTIVE] = { 0.80, 0.80, 0.80 }

View File

@ -91,7 +91,7 @@ style "default_base" = "medium_text"
GtkTreeView::vertical-padding = 0
GtkTreeView::horizontal-padding = 0
GtkTreeView::even-row-color = { 0.70, 0.70, 0.70 }
GtkTreeView::odd-row-color = { 0.70, 0.70, 0.70 }
GtkTreeView::odd-row-color = { 0.64, 0.64, 0.64 }
fg[NORMAL] = { 0.30, 0.30, 0.40 }
fg[ACTIVE] = { 0.30, 0.30, 0.40 }

View File

@ -69,6 +69,7 @@ class AudioClock;
class PublicEditor;
class Keyboard;
class OptionEditor;
class KeyEditor;
class Mixer_UI;
class ConnectionEditor;
class RouteParams_UI;
@ -154,6 +155,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI
PublicEditor& the_editor(){return *editor;}
Mixer_UI* the_mixer() { return mixer; }
void toggle_key_editor ();
void toggle_location_window ();
void toggle_theme_manager ();
void toggle_big_clock_window ();
@ -620,6 +622,10 @@ class ARDOUR_UI : public Gtkmm2ext::UI
static UIConfiguration *ui_config;
ThemeManager *theme_manager;
/* Key bindings editor */
KeyEditor *key_editor;
/* Options window */
OptionEditor *option_editor;

View File

@ -78,8 +78,6 @@ ARDOUR_UI::setup_windows ()
theme_manager->signal_unmap().connect (bind (sigc::ptr_fun(&ActionManager::uncheck_toggleaction), X_("<Actions>/Common/ToggleThemeManager")));
top_packer.pack_start (transport_frame, false, false);
#ifdef TOP_MENUBAR
HBox* status_bar_packer = manage (new HBox);
@ -95,6 +93,8 @@ ARDOUR_UI::setup_windows ()
top_packer.pack_start (menu_bar_base, false, false);
#endif
top_packer.pack_start (transport_frame, false, false);
editor->add_toplevel_controls (top_packer);
return 0;

View File

@ -35,6 +35,7 @@
#include "route_params_ui.h"
#include "sfdb_ui.h"
#include "theme_manager.h"
#include "keyeditor.h"
#include "i18n.h"
@ -325,6 +326,27 @@ ARDOUR_UI::toggle_location_window ()
}
}
void
ARDOUR_UI::toggle_key_editor ()
{
if (key_editor == 0) {
key_editor = new KeyEditor;
key_editor->signal_unmap().connect (sigc::bind (sigc::ptr_fun(&ActionManager::uncheck_toggleaction), X_("<Actions>/Common/ToggleKeyEditor")));
}
RefPtr<Action> act = ActionManager::get_action (X_("Common"), X_("ToggleKeyEditor"));
if (act) {
RefPtr<ToggleAction> tact = RefPtr<ToggleAction>::cast_dynamic(act);
if (tact->get_active()) {
key_editor->show_all ();
key_editor->present ();
} else {
key_editor->hide ();
}
}
}
void
ARDOUR_UI::toggle_theme_manager ()
{

View File

@ -204,8 +204,6 @@ ARDOUR_UI::install_actions ()
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_toggle_action (common_actions, X_("ToggleBigClock"), _("Big Clock"), mem_fun(*this, &ARDOUR_UI::toggle_big_clock_window));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_toggle_action (common_actions, X_("ToggleThemeManager"), _("Theme Manager"), mem_fun(*this, &ARDOUR_UI::toggle_theme_manager));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("AddAudioTrack"), _("Add Audio Track"), bind (mem_fun(*this, &ARDOUR_UI::session_add_audio_track), 1, 1, ARDOUR::Normal, 1));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("AddAudioBus"), _("Add Audio Bus"), bind (mem_fun(*this, &ARDOUR_UI::session_add_audio_bus), 1, 1, 1));
@ -220,6 +218,8 @@ ARDOUR_UI::install_actions ()
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::register_action (common_actions, X_("About"), _("About"), mem_fun(*this, &ARDOUR_UI::show_splash));
ActionManager::register_toggle_action (common_actions, X_("ToggleThemeManager"), _("Theme Manager"), mem_fun(*this, &ARDOUR_UI::toggle_theme_manager));
ActionManager::register_toggle_action (common_actions, X_("ToggleKeyEditor"), _("Keybindings"), mem_fun(*this, &ARDOUR_UI::toggle_key_editor));
Glib::RefPtr<ActionGroup> transport_actions = ActionGroup::create (X_("Transport"));

159
gtk2_ardour/keyeditor.cc Normal file
View File

@ -0,0 +1,159 @@
#include <map>
#include <gtkmm/stock.h>
#include <gtkmm/accelkey.h>
#include <gtkmm/accelmap.h>
#include <gtkmm/uimanager.h>
#include <pbd/strsplit.h>
#include "actions.h"
#include "keyboard.h"
#include "keyeditor.h"
#include "i18n.h"
using namespace std;
using namespace Gtk;
using namespace Gdk;
KeyEditor::KeyEditor ()
: ArdourDialog (_("Keybinding Editor"), false)
{
model = TreeStore::create(columns);
view.set_model (model);
view.append_column (_("Action"), columns.action);
view.append_column (_("Binding"), columns.binding);
view.set_headers_visible (true);
view.get_selection()->set_mode (SELECTION_SINGLE);
view.set_reorderable (false);
view.set_size_request (300,200);
view.set_enable_search (false);
view.set_rules_hint (true);
view.set_name (X_("KeyEditorTree"));
view.get_selection()->signal_changed().connect (mem_fun (*this, &KeyEditor::action_selected));
scroller.add (view);
scroller.set_policy (Gtk::POLICY_NEVER, Gtk::POLICY_AUTOMATIC);
get_vbox()->pack_start (scroller);
scroller.show ();
view.show ();
}
void
KeyEditor::on_show ()
{
populate ();
view.get_selection()->unselect_all ();
ArdourDialog::on_show ();
}
void
KeyEditor::on_unmap ()
{
ArdourDialog::on_unmap ();
}
void
KeyEditor::action_selected ()
{
}
bool
KeyEditor::on_key_release_event (GdkEventKey* ev)
{
TreeModel::iterator i = view.get_selection()->get_selected();
if (i != model->children().end()) {
string path = (*i)[columns.path];
bool result = AccelMap::change_entry (path,
ev->keyval,
(ModifierType) ev->state,
true);
if (result) {
bool known;
AccelKey key;
known = ActionManager::lookup_entry (path, key);
if (known) {
(*i)[columns.binding] = ActionManager::ui_manager->get_accel_group()->name (key.get_key(), Gdk::ModifierType (key.get_mod()));
} else {
(*i)[columns.binding] = string();
}
}
}
return true;
}
void
KeyEditor::populate ()
{
vector<string> paths;
vector<string> labels;
vector<string> keys;
vector<AccelKey> bindings;
typedef std::map<string,TreeIter> NodeMap;
NodeMap nodes;
NodeMap::iterator r;
ActionManager::get_all_actions (labels, paths, keys, bindings);
vector<string>::iterator k;
vector<string>::iterator p;
vector<string>::iterator l;
model->clear ();
for (l = labels.begin(), k = keys.begin(), p = paths.begin(); l != labels.end(); ++k, ++p, ++l) {
TreeModel::Row row;
vector<string> parts;
parts.clear ();
split (*p, parts, '/');
if (parts.empty()) {
continue;
}
if ((r = nodes.find (parts[1])) == nodes.end()) {
/* top level is missing */
TreeIter rowp;
TreeModel::Row parent;
rowp = model->append();
nodes[parts[1]] = rowp;
parent = *(rowp);
parent[columns.action] = parts[1];
row = *(model->append (parent.children()));
} else {
row = *(model->append ((*r->second)->children()));
}
/* add this action */
row[columns.action] = (*l);
row[columns.path] = (*p);
if (*k == ActionManager::unbound_string) {
row[columns.binding] = string();
} else {
row[columns.binding] = (*k);
}
}
}

44
gtk2_ardour/keyeditor.h Normal file
View File

@ -0,0 +1,44 @@
#ifndef __ardour_gtk_key_editor_h__
#define __ardour_gtk_key_editor_h__
#include <string>
#include <gtkmm/treeview.h>
#include <gtkmm/treestore.h>
#include <gtkmm/scrolledwindow.h>
#include <glibmm/ustring.h>
#include "ardour_dialog.h"
class KeyEditor : public ArdourDialog
{
public:
KeyEditor ();
protected:
void on_show ();
void on_unmap ();
bool on_key_release_event (GdkEventKey*);
private:
struct KeyEditorColumns : public Gtk::TreeModel::ColumnRecord {
KeyEditorColumns () {
add (action);
add (binding);
add (path);
}
Gtk::TreeModelColumn<Glib::ustring> action;
Gtk::TreeModelColumn<std::string> binding;
Gtk::TreeModelColumn<std::string> path;
};
Gtk::ScrolledWindow scroller;
Gtk::TreeView view;
Glib::RefPtr<Gtk::TreeStore> model;
KeyEditorColumns columns;
void action_selected ();
void populate ();
};
#endif /* __ardour_gtk_key_editor_h__ */

View File

@ -49,7 +49,7 @@ split (string str, vector<string>& result, char splitchar)
remaining = str;
while ((pos = remaining.find_first_of (':')) != string::npos) {
while ((pos = remaining.find_first_of (splitchar)) != string::npos) {
result.push_back (remaining.substr (0, pos));
remaining = remaining.substr (pos+1);
}
@ -87,7 +87,7 @@ split (ustring str, vector<ustring>& result, char splitchar)
remaining = str;
while ((pos = remaining.find_first_of (':')) != ustring::npos) {
while ((pos = remaining.find_first_of (splitchar)) != ustring::npos) {
result.push_back (remaining.substr (0, pos));
remaining = remaining.substr (pos+1);
}