]> asedeno.scripts.mit.edu Git - PuTTY.git/commitdiff
On OS X, be able to configure either Option or Command as Meta.
authorSimon Tatham <anakin@pobox.com>
Tue, 1 Sep 2015 18:00:25 +0000 (19:00 +0100)
committerSimon Tatham <anakin@pobox.com>
Tue, 1 Sep 2015 18:12:19 +0000 (19:12 +0100)
Personally I like using Command as the Esc-prefixing Meta key in
terminal sessions, because it occupies the same physical keyboard
position as the Alt key that I'm used to using on non-Macs. OS X
Terminal uses Option for that purpose (freeing up Command for the
conventional Mac keyboard shortcuts, of course), so I anticipate
differences of opinion.

Hence, here's a pair of OSX-specific config options which permit a
user to set either, or neither, or both of those modifier keys to
function as the terminal Meta key.

putty.h
settings.c
unix/gtkcfg.c
unix/gtkwin.c
unix/unix.h

diff --git a/putty.h b/putty.h
index 4d15448d0fc47560c08ecf7225a0baf4d2876f5c..15ec5b9906c8a92e79690bb75a67e84b2c08dc57 100644 (file)
--- a/putty.h
+++ b/putty.h
@@ -751,6 +751,8 @@ void cleanup_exit(int);
     X(INT, NONE, erase_to_scrollback) \
     X(INT, NONE, compose_key) \
     X(INT, NONE, ctrlaltkeys) \
+    X(INT, NONE, osx_option_meta) \
+    X(INT, NONE, osx_command_meta) \
     X(STR, NONE, wintitle) /* initial window title */ \
     /* Terminal options */ \
     X(INT, NONE, savelines) \
index de74a2b7ae5d7b2f98bb493686c3c947139540ea..07ee4123b532f78e34189dfc9c2cb005c1558a0a 100644 (file)
@@ -531,6 +531,10 @@ void save_open_settings(void *sesskey, Conf *conf)
     write_setting_i(sesskey, "AltOnly", conf_get_int(conf, CONF_alt_only));
     write_setting_i(sesskey, "ComposeKey", conf_get_int(conf, CONF_compose_key));
     write_setting_i(sesskey, "CtrlAltKeys", conf_get_int(conf, CONF_ctrlaltkeys));
+#ifdef OSX_META_KEY_CONFIG
+    write_setting_i(sesskey, "OSXOptionMeta", conf_get_int(conf, CONF_osx_option_meta));
+    write_setting_i(sesskey, "OSXCommandMeta", conf_get_int(conf, CONF_osx_command_meta));
+#endif
     write_setting_i(sesskey, "TelnetKey", conf_get_int(conf, CONF_telnet_keyboard));
     write_setting_i(sesskey, "TelnetRet", conf_get_int(conf, CONF_telnet_newline));
     write_setting_i(sesskey, "LocalEcho", conf_get_int(conf, CONF_localecho));
@@ -833,6 +837,10 @@ void load_open_settings(void *sesskey, Conf *conf)
     gppi(sesskey, "AltOnly", 0, conf, CONF_alt_only);
     gppi(sesskey, "ComposeKey", 0, conf, CONF_compose_key);
     gppi(sesskey, "CtrlAltKeys", 1, conf, CONF_ctrlaltkeys);
+#ifdef OSX_META_KEY_CONFIG
+    gppi(sesskey, "OSXOptionMeta", 1, conf, CONF_osx_option_meta);
+    gppi(sesskey, "OSXCommandMeta", 0, conf, CONF_osx_command_meta);
+#endif
     gppi(sesskey, "TelnetKey", 0, conf, CONF_telnet_keyboard);
     gppi(sesskey, "TelnetRet", 1, conf, CONF_telnet_newline);
     gppi(sesskey, "LocalEcho", AUTO, conf, CONF_localecho);
index 958a3f6653e6a4571ab03c4ced9ffabd6566b960..4307176f13698b8fea65cd9819176830004bfe3d 100644 (file)
@@ -129,6 +129,22 @@ void gtk_setup_config_box(struct controlbox *b, int midsession, void *win)
                  conf_checkbox_handler,
                  I(CONF_utf8_override));
 
+#ifdef OSX_META_KEY_CONFIG
+    /*
+     * On OS X, there are multiple reasonable opinions about whether
+     * Option or Command (or both, or neither) should act as a Meta
+     * key, or whether they should have their normal OS functions.
+     */
+    s = ctrl_getset(b, "Terminal/Keyboard", "meta",
+                   "Choose the Meta key:");
+    ctrl_checkbox(s, "Option key acts as Meta", 'p',
+                 HELPCTX(no_help),
+                 conf_checkbox_handler, I(CONF_osx_option_meta));
+    ctrl_checkbox(s, "Command key acts as Meta", 'm',
+                 HELPCTX(no_help),
+                 conf_checkbox_handler, I(CONF_osx_command_meta));
+#endif
+
     if (!midsession) {
         /*
          * Allow the user to specify the window class as part of the saved
index 3d7486c434a8c26540c771075767934d382d380b..8e8090540b4fe3c856855bf8f025d2f747d4b140 100644 (file)
@@ -133,6 +133,7 @@ struct gui_data {
     int window_border;
     int cursor_type;
     int drawtype;
+    int meta_mod_mask;
 };
 
 static void cache_conf_values(struct gui_data *inst)
@@ -140,6 +141,15 @@ static void cache_conf_values(struct gui_data *inst)
     inst->bold_style = conf_get_int(inst->conf, CONF_bold_style);
     inst->window_border = conf_get_int(inst->conf, CONF_window_border);
     inst->cursor_type = conf_get_int(inst->conf, CONF_cursor_type);
+#ifdef OSX_META_KEY_CONFIG
+    inst->meta_mod_mask = 0;
+    if (conf_get_int(inst->conf, CONF_osx_option_meta))
+        inst->meta_mod_mask |= GDK_MOD1_MASK;
+    if (conf_get_int(inst->conf, CONF_osx_command_meta))
+        inst->meta_mod_mask |= GDK_MOD2_MASK;
+#else
+    inst->meta_mod_mask = GDK_MOD1_MASK;
+#endif
 }
 
 struct draw_ctx {
@@ -834,12 +844,12 @@ gint key_event(GtkWidget *widget, GdkEventKey *event, gpointer data)
        }
 
        /*
-        * If we're seeing a numberpad key press with Mod1 down,
+        * If we're seeing a numberpad key press with Meta down,
         * consider adding it to alt_keycode if that's sensible.
-        * Anything _else_ with Mod1 down cancels any possibility
+        * Anything _else_ with Meta down cancels any possibility
         * of an ALT keycode: we set alt_keycode to -2.
         */
-       if ((event->state & GDK_MOD1_MASK) && inst->alt_keycode != -2) {
+       if ((event->state & inst->meta_mod_mask) && inst->alt_keycode != -2) {
            int digit = -1;
            switch (event->keyval) {
              case GDK_KEY_KP_0: case GDK_KEY_KP_Insert: digit = 0; break;
@@ -1030,7 +1040,7 @@ gint key_event(GtkWidget *widget, GdkEventKey *event, gpointer data)
            output[lenof(output)-1] = '\0';
            end = strlen(output);
        }
-       if (event->state & GDK_MOD1_MASK) {
+       if (event->state & inst->meta_mod_mask) {
            start = 0;
            if (end == 1) end = 0;
        } else
@@ -1515,7 +1525,7 @@ gboolean button_internal(struct gui_data *inst, guint32 timestamp,
 
     shift = state & GDK_SHIFT_MASK;
     ctrl = state & GDK_CONTROL_MASK;
-    alt = state & GDK_MOD1_MASK;
+    alt = state & inst->meta_mod_mask;
 
     raw_mouse_mode =
         send_raw_mouse && !(shift && conf_get_int(inst->conf,
@@ -1613,7 +1623,7 @@ gint motion_event(GtkWidget *widget, GdkEventMotion *event, gpointer data)
 
     shift = event->state & GDK_SHIFT_MASK;
     ctrl = event->state & GDK_CONTROL_MASK;
-    alt = event->state & GDK_MOD1_MASK;
+    alt = event->state & inst->meta_mod_mask;
     if (event->state & GDK_BUTTON1_MASK)
        button = MBT_LEFT;
     else if (event->state & GDK_BUTTON2_MASK)
index 6f97901af82228a80d4e6dd657a4032edefacdd3..3fe7d7f6626970471988c5499b9f7a7d5ba427b8 100644 (file)
@@ -24,6 +24,7 @@
 #define NOT_X_WINDOWS /* of course, all the X11 stuff should be disabled */
 #define NO_PTY_PRE_INIT /* OS X gets very huffy if we try to set[ug]id */
 #define SET_NONBLOCK_VIA_OPENPT /* work around missing fcntl functionality */
+#define OSX_META_KEY_CONFIG /* two possible Meta keys to choose from */
 #endif
 
 struct Filename {