Make send automation work (#4734).
[ardour.git] / gtk2_ardour / utils.cc
index b19e43fe7c5867cd4d780a89151c675edcce2694..96bee1a87ba0b951067f2f7c8226f3fc73ce9065 100644 (file)
@@ -40,7 +40,6 @@
 #include "pbd/file_utils.h"
 
 #include <gtkmm2ext/utils.h>
-#include "ardour/configuration.h"
 #include "ardour/rc_configuration.h"
 
 #include "ardour/filesystem_paths.h"
@@ -63,99 +62,6 @@ using Gtkmm2ext::Keyboard;
 
 sigc::signal<void>  DPIReset;
 
-int
-pixel_width (const string& str, Pango::FontDescription& font)
-{
-       Label foo;
-       Glib::RefPtr<Pango::Layout> layout = foo.create_pango_layout ("");
-
-       layout->set_font_description (font);
-       layout->set_text (str);
-
-       int width, height;
-       Gtkmm2ext::get_ink_pixel_size (layout, width, height);
-       return width;
-}
-
-string
-fit_to_pixels (const string& str, int pixel_width, Pango::FontDescription& font, int& actual_width, bool with_ellipses)
-{
-       Label foo;
-       Glib::RefPtr<Pango::Layout> layout = foo.create_pango_layout ("");
-       string::size_type shorter_by = 0;
-       string txt;
-
-       layout->set_font_description (font);
-
-       actual_width = 0;
-
-       string ustr = str;
-       string::iterator last = ustr.end();
-       --last; /* now points at final entry */
-
-       txt = ustr;
-
-       while (!ustr.empty()) {
-
-               layout->set_text (txt);
-
-               int width, height;
-               Gtkmm2ext::get_ink_pixel_size (layout, width, height);
-
-               if (width < pixel_width) {
-                       actual_width = width;
-                       break;
-               }
-
-               ustr.erase (last--);
-               shorter_by++;
-
-               if (with_ellipses && shorter_by > 3) {
-                       txt = ustr;
-                       txt += "...";
-               } else {
-                       txt = ustr;
-               }
-       }
-
-       return txt;
-}
-
-/** Try to fit a string into a given horizontal space by ellipsizing it.
- *  @param cr Cairo context in which the text will be plotted.
- *  @param name Text.
- *  @param avail Available horizontal space.
- *  @return (Text, possibly ellipsized) and (horizontal size of text)
- */
-
-std::pair<std::string, double>
-fit_to_pixels (cairo_t* cr, std::string name, double avail)
-{
-       /* XXX hopefully there exists a more efficient way of doing this */
-
-       bool abbreviated = false;
-       uint32_t width = 0;
-
-       while (1) {
-               cairo_text_extents_t ext;
-               cairo_text_extents (cr, name.c_str(), &ext);
-
-               if (ext.width < avail || name.length() <= 4) {
-                       width = ext.width;
-                       break;
-               }
-
-               if (abbreviated) {
-                       name = name.substr (0, name.length() - 4) + "...";
-               } else {
-                       name = name.substr (0, name.length() - 3) + "...";
-                       abbreviated = true;
-               }
-       }
-
-       return std::make_pair (name, width);
-}
-
 
 /** Add an element to a menu, settings its sensitivity.
  * @param m Menu to add to.
@@ -392,112 +298,6 @@ rgba_from_style (string style, uint32_t r, uint32_t g, uint32_t b, uint32_t a, s
        }
 }
 
-
-Gdk::Color
-color_from_style (string widget_style_name, int state, string attr)
-{
-       GtkStyle* style;
-
-       style = gtk_rc_get_style_by_paths (gtk_settings_get_default(),
-                                          widget_style_name.c_str(),
-                                          0, G_TYPE_NONE);
-
-       if (!style) {
-               error << string_compose (_("no style found for %1, using red"), style) << endmsg;
-               return Gdk::Color ("red");
-       }
-
-       if (attr == "fg") {
-               return Gdk::Color (&style->fg[state]);
-       }
-
-       if (attr == "bg") {
-               return Gdk::Color (&style->bg[state]);
-       }
-
-       if (attr == "light") {
-               return Gdk::Color (&style->light[state]);
-       }
-
-       if (attr == "dark") {
-               return Gdk::Color (&style->dark[state]);
-       }
-
-       if (attr == "mid") {
-               return Gdk::Color (&style->mid[state]);
-       }
-
-       if (attr == "text") {
-               return Gdk::Color (&style->text[state]);
-       }
-
-       if (attr == "base") {
-               return Gdk::Color (&style->base[state]);
-       }
-
-       if (attr == "text_aa") {
-               return Gdk::Color (&style->text_aa[state]);
-       }
-
-       error << string_compose (_("unknown style attribute %1 requested for color; using \"red\""), attr) << endmsg;
-       return Gdk::Color ("red");
-}
-
-Glib::RefPtr<Gdk::GC>
-gc_from_style (string widget_style_name, int state, string attr)
-{
-        GtkStyle* style;
-
-        style = gtk_rc_get_style_by_paths (gtk_settings_get_default(),
-                                           widget_style_name.c_str(),
-                                           0, G_TYPE_NONE);
-
-        if (!style) {
-                error << string_compose (_("no style found for %1, using red"), style) << endmsg;
-               Glib::RefPtr<Gdk::GC> ret = Gdk::GC::create();
-               ret->set_rgb_fg_color(Gdk::Color("red"));
-                return ret;
-        }
-
-        if (attr == "fg") {
-                return Glib::wrap(style->fg_gc[state]);
-        }
-
-        if (attr == "bg") {
-                return Glib::wrap(style->bg_gc[state]);
-        }
-
-        if (attr == "light") {
-                return Glib::wrap(style->light_gc[state]);
-        }
-
-        if (attr == "dark") {
-                return Glib::wrap(style->dark_gc[state]);
-        }
-
-        if (attr == "mid") {
-                return Glib::wrap(style->mid_gc[state]);
-        }
-
-        if (attr == "text") {
-                return Glib::wrap(style->text_gc[state]);
-        }
-
-        if (attr == "base") {
-                return Glib::wrap(style->base_gc[state]);
-        }
-
-        if (attr == "text_aa") {
-                return Glib::wrap(style->text_aa_gc[state]);
-        }
-
-        error << string_compose (_("unknown style attribute %1 requested for color; using \"red\""), attr) << endmsg;
-       Glib::RefPtr<Gdk::GC> ret = Gdk::GC::create();
-       ret->set_rgb_fg_color(Gdk::Color("red"));
-        return ret;
-}
-
-
 bool
 canvas_item_visible (ArdourCanvas::Item* item)
 {
@@ -550,13 +350,14 @@ key_press_focus_accelerator_handler (Gtk::Window& window, GdkEventKey* ev)
 #endif
 
 
-        DEBUG_TRACE (DEBUG::Accelerators, string_compose ("Win = %1 Key event: code = %2  state = %3 special handling ? %4 magic widget focus ? %5 allow_activation ? %6\n",
+        DEBUG_TRACE (DEBUG::Accelerators, string_compose ("Win = %1 focus = %7 Key event: code = %2  state = %3 special handling ? %4 magic widget focus ? %5 allow_activation ? %6\n",
                                                           win,
                                                           ev->keyval,
                                                           ev->state,
                                                           special_handling_of_unmodified_accelerators,
                                                           Keyboard::some_magic_widget_has_focus(),
-                                                          allow_activating));
+                                                          allow_activating,
+                                                         focus));
 
        /* This exists to allow us to override the way GTK handles
           key events. The normal sequence is:
@@ -615,7 +416,32 @@ key_press_focus_accelerator_handler (Gtk::Window& window, GdkEventKey* ev)
                uint32_t fakekey = ev->keyval;
 
                if (Gtkmm2ext::possibly_translate_keyval_to_make_legal_accelerator (fakekey)) {
-                       if (allow_activating && gtk_accel_groups_activate(G_OBJECT(win), fakekey, GdkModifierType(ev->state))) {
+                       DEBUG_TRACE (DEBUG::Accelerators, string_compose ("\tactivate (was %1 now %2) without special hanlding of unmodified accels\n",
+                                                                         ev->keyval, fakekey));
+
+                       GdkModifierType mod = GdkModifierType (ev->state);
+
+                       mod = GdkModifierType (mod & gtk_accelerator_get_default_mod_mask());
+#ifdef GTKOSX
+                       /* GTK on OS X is currently (February 2012) setting both
+                          the Meta and Mod2 bits in the event modifier state if 
+                          the Command key is down.
+
+                          gtk_accel_groups_activate() does not invoke any of the logic
+                          that gtk_window_activate_key() will that sorts out that stupid
+                          state of affairs, and as a result it fails to find a match
+                          for the key event and the current set of accelerators.
+
+                          to fix this, if the meta bit is set, remove the mod2 bit
+                          from the modifier. this assumes that our bindings use Primary
+                          which will have set the meta bit in the accelerator entry.
+                       */
+                       if (mod & GDK_META_MASK) {
+                               mod = GdkModifierType (mod & ~GDK_MOD2_MASK);
+                       }
+#endif
+
+                       if (allow_activating && gtk_accel_groups_activate(G_OBJECT(win), fakekey, mod)) {
                                DEBUG_TRACE (DEBUG::Accelerators, "\taccel group activated by fakekey\n");
                                return true;
                        }
@@ -667,8 +493,7 @@ get_xpm (std::string name)
 {
        if (!xpm_map[name]) {
 
-               SearchPath spath(ARDOUR::ardour_search_path());
-               spath += ARDOUR::system_data_search_path();
+               SearchPath spath(ARDOUR::ardour_data_search_path());
 
                spath.add_subdirectory_to_paths("pixmaps");
 
@@ -694,15 +519,14 @@ get_icon_path (const char* cname)
        string name = cname;
        name += X_(".png");
 
-       SearchPath spath(ARDOUR::ardour_search_path());
-       spath += ARDOUR::system_data_search_path();
+       SearchPath spath(ARDOUR::ardour_data_search_path());
 
        spath.add_subdirectory_to_paths("icons");
 
        sys::path data_file_path;
 
        if (!find_file_in_search_path (spath, name, data_file_path)) {
-               fatal << string_compose (_("cannot find icon image for %1"), name) << endmsg;
+               fatal << string_compose (_("cannot find icon image for %1 using %2"), name, spath.to_string()) << endmsg;
        }
 
        return data_file_path.to_string();