comparison src/gui_mac.c @ 1012:be8e2719caa6 v7.0.138

updated for version 7.0-138
author vimboss
date Tue, 17 Oct 2006 10:51:57 +0000
parents 31208ed42de9
children 965805580982
comparison
equal deleted inserted replaced
1011:6e03ee418b50 1012:be8e2719caa6
2012 EventHandlerCallRef nextHandler, 2012 EventHandlerCallRef nextHandler,
2013 EventRef theEvent, 2013 EventRef theEvent,
2014 void *data) 2014 void *data)
2015 { 2015 {
2016 /* Multibyte-friendly key event handler */ 2016 /* Multibyte-friendly key event handler */
2017 OSStatus e = -1; 2017 OSStatus err = -1;
2018 UInt32 actualSize; 2018 UInt32 actualSize;
2019 UniChar *text; 2019 UniChar *text;
2020 char_u result[INLINE_KEY_BUFFER_SIZE]; 2020 char_u result[INLINE_KEY_BUFFER_SIZE];
2021 short len = 0; 2021 short len = 0;
2022 UInt32 key_sym; 2022 UInt32 key_sym;
2023 char charcode; 2023 char charcode;
2024 int key_char; 2024 int key_char;
2025 UInt32 modifiers; 2025 UInt32 modifiers, vimModifiers;
2026 size_t encLen; 2026 size_t encLen;
2027 char_u *to = NULL; 2027 char_u *to = NULL;
2028 Boolean isSpecial = FALSE; 2028 Boolean isSpecial = FALSE;
2029 int i; 2029 int i;
2030 EventRef keyEvent;
2030 2031
2031 /* Mask the mouse (as per user setting) */ 2032 /* Mask the mouse (as per user setting) */
2032 if (p_mh) 2033 if (p_mh)
2033 ObscureCursor(); 2034 ObscureCursor();
2034 2035
2035 do 2036 /* Don't use the keys when the dialog wants them. */
2036 { 2037 if (dialog_busy)
2037 /* Don't use the keys when the dialog wants them. */ 2038 return eventNotHandledErr;
2038 if (dialog_busy) 2039
2039 break; 2040 if (noErr != GetEventParameter(theEvent, kEventParamTextInputSendText,
2040 2041 typeUnicodeText, NULL, 0, &actualSize, NULL))
2041 if (noErr != GetEventParameter(theEvent, kEventParamTextInputSendText, 2042 return eventNotHandledErr;
2042 typeUnicodeText, NULL, 0, &actualSize, NULL)) 2043
2043 break; 2044 text = (UniChar *)alloc(actualSize);
2044 2045 if (!text)
2045 text = (UniChar *)alloc(actualSize); 2046 return eventNotHandledErr;
2046 2047
2047 if (text) 2048 err = GetEventParameter(theEvent, kEventParamTextInputSendText,
2048 { 2049 typeUnicodeText, NULL, actualSize, NULL, text);
2049 do 2050 require_noerr(err, done);
2050 { 2051
2051 if (noErr != GetEventParameter(theEvent, 2052 err = GetEventParameter(theEvent, kEventParamTextInputSendKeyboardEvent,
2052 kEventParamTextInputSendText, 2053 typeEventRef, NULL, sizeof(EventRef), NULL, &keyEvent);
2053 typeUnicodeText, NULL, actualSize, NULL, text)) 2054 require_noerr(err, done);
2054 break; 2055
2055 EventRef keyEvent; 2056 err = GetEventParameter(keyEvent, kEventParamKeyModifiers,
2056 if (noErr != GetEventParameter(theEvent, 2057 typeUInt32, NULL, sizeof(UInt32), NULL, &modifiers);
2057 kEventParamTextInputSendKeyboardEvent, 2058 require_noerr(err, done);
2058 typeEventRef, NULL, sizeof(EventRef), NULL, &keyEvent)) 2059
2059 break; 2060 err = GetEventParameter(keyEvent, kEventParamKeyCode,
2060 if (noErr != GetEventParameter(keyEvent, 2061 typeUInt32, NULL, sizeof(UInt32), NULL, &key_sym);
2061 kEventParamKeyModifiers, 2062 require_noerr(err, done);
2062 typeUInt32, NULL, sizeof(UInt32), NULL, &modifiers)) 2063
2063 break; 2064 err = GetEventParameter(keyEvent, kEventParamKeyMacCharCodes,
2064 if (noErr != GetEventParameter(keyEvent, 2065 typeChar, NULL, sizeof(char), NULL, &charcode);
2065 kEventParamKeyCode, 2066 require_noerr(err, done);
2066 typeUInt32, NULL, sizeof(UInt32), NULL, &key_sym)) 2067
2067 break;
2068 if (noErr != GetEventParameter(keyEvent,
2069 kEventParamKeyMacCharCodes,
2070 typeChar, NULL, sizeof(char), NULL, &charcode))
2071 break;
2072
2073 key_char = charcode;
2074
2075 if (modifiers & controlKey)
2076 {
2077 if ((modifiers & ~(controlKey|shiftKey)) == 0
2078 && (key_char == '2' || key_char == '6'))
2079 {
2080 /* CTRL-^ and CTRL-@ don't work in the normal way. */
2081 if (key_char == '2')
2082 key_char = Ctrl_AT;
2083 else
2084 key_char = Ctrl_HAT;
2085
2086 text[0] = (UniChar)key_char;
2087 modifiers = 0;
2088 }
2089 }
2090
2091 if (modifiers & cmdKey)
2092 #ifndef USE_CMD_KEY 2068 #ifndef USE_CMD_KEY
2093 break; /* Let system handle Cmd+... */ 2069 if (modifiers & cmdKey)
2094 #else 2070 goto done; /* Let system handle Cmd+... */
2095 { 2071 #endif
2096 /* Intercept CMD-. */ 2072
2097 if (key_char == '.') 2073 key_char = charcode;
2098 got_int = TRUE; 2074 vimModifiers = EventModifiers2VimModifiers(modifiers);
2099 2075
2100 /* Convert the modifiers */ 2076 /* Find the special key (eg., for cursor keys) */
2101 modifiers = EventModifiers2VimModifiers(modifiers); 2077 if (actualSize <= sizeof(UniChar) &&
2102 2078 ((text[0] < 0x20) || (text[0] == 0x7f)))
2103 /* Following code to simplify and consolidate modifiers 2079 {
2104 * taken liberally from gui_w48.c */ 2080 for (i = 0; special_keys[i].key_sym != (KeySym)0; ++i)
2105 2081 if (special_keys[i].key_sym == key_sym)
2106 key_char = simplify_key(key_char, (int *)&modifiers); 2082 {
2107 2083 key_char = TO_SPECIAL(special_keys[i].vim_code0,
2108 /* remove SHIFT for keys that are already shifted, e.g., 2084 special_keys[i].vim_code1);
2109 * '(' and '*' */ 2085 key_char = simplify_key(key_char,
2110 if (key_char < 0x100 && 2086 (int *)&vimModifiers);
2111 !isalpha(key_char) && isprint(key_char)) 2087 isSpecial = TRUE;
2112 modifiers &= ~MOD_MASK_SHIFT; 2088 break;
2113 2089 }
2114 /* Interpret META, include SHIFT, etc. */ 2090 }
2115 key_char = extract_modifiers(key_char, (int *)&modifiers); 2091
2116 if (key_char == CSI) 2092 /* Intercept CMD-. and CTRL-c */
2117 key_char = K_CSI; 2093 if (((modifiers & controlKey) && key_char == 'c') ||
2118 2094 ((modifiers & cmdKey) && key_char == '.'))
2119 if (modifiers) 2095 got_int = TRUE;
2120 { 2096
2121 result[len++] = CSI; 2097 if (!isSpecial)
2122 result[len++] = KS_MODIFIER; 2098 {
2123 result[len++] = modifiers; 2099 /* remove SHIFT for keys that are already shifted, e.g.,
2124 } 2100 * '(' and '*' */
2125 2101 if (key_char < 0x100 && !isalpha(key_char) && isprint(key_char))
2126 isSpecial = TRUE; 2102 vimModifiers &= ~MOD_MASK_SHIFT;
2127 } 2103
2128 #endif 2104 /* remove CTRL from keys that already have it */
2129 else 2105 if (key_char < 0x20)
2130 { 2106 vimModifiers &= ~MOD_MASK_CTRL;
2131 /* Find the special key (eg., for cursor keys) */ 2107
2132 if (!(actualSize > sizeof(UniChar)) && 2108 /* don't process unicode characters here */
2133 ((text[0] < 0x20) || (text[0] == 0x7f))) 2109 if (!IS_SPECIAL(key_char))
2134 { 2110 {
2135 for (i = 0; special_keys[i].key_sym != (KeySym)0; ++i) 2111 /* Following code to simplify and consolidate vimModifiers
2136 if (special_keys[i].key_sym == key_sym) 2112 * taken liberally from gui_w48.c */
2137 { 2113 key_char = simplify_key(key_char, (int *)&vimModifiers);
2138 key_char = TO_SPECIAL(special_keys[i].vim_code0, 2114
2139 special_keys[i].vim_code1); 2115 /* Interpret META, include SHIFT, etc. */
2140 key_char = simplify_key(key_char, 2116 key_char = extract_modifiers(key_char, (int *)&vimModifiers);
2141 (int *)&modifiers); 2117 if (key_char == CSI)
2142 isSpecial = TRUE; 2118 key_char = K_CSI;
2143 break; 2119
2144 } 2120 if (IS_SPECIAL(key_char))
2145 } 2121 isSpecial = TRUE;
2146 } 2122 }
2147 2123 }
2148 if (isSpecial && IS_SPECIAL(key_char)) 2124
2149 { 2125 if (vimModifiers)
2150 result[len++] = CSI; 2126 {
2151 result[len++] = K_SECOND(key_char); 2127 result[len++] = CSI;
2152 result[len++] = K_THIRD(key_char); 2128 result[len++] = KS_MODIFIER;
2153 } 2129 result[len++] = vimModifiers;
2154 else 2130 }
2155 { 2131
2156 encLen = actualSize; 2132 if (isSpecial && IS_SPECIAL(key_char))
2157 to = mac_utf16_to_enc(text, actualSize, &encLen); 2133 {
2158 } 2134 result[len++] = CSI;
2159 2135 result[len++] = K_SECOND(key_char);
2160 if (to) 2136 result[len++] = K_THIRD(key_char);
2161 { 2137 }
2162 /* This is basically add_to_input_buf_csi() */ 2138 else
2163 for (i = 0; i < encLen && len < (INLINE_KEY_BUFFER_SIZE-1); ++i) 2139 {
2164 { 2140 encLen = actualSize;
2165 result[len++] = to[i]; 2141 to = mac_utf16_to_enc(text, actualSize, &encLen);
2166 if (to[i] == CSI) 2142 if (to)
2167 { 2143 {
2168 result[len++] = KS_EXTRA; 2144 /* This is basically add_to_input_buf_csi() */
2169 result[len++] = (int)KE_CSI; 2145 for (i = 0; i < encLen && len < (INLINE_KEY_BUFFER_SIZE-1); ++i)
2170 } 2146 {
2171 } 2147 result[len++] = to[i];
2172 vim_free(to); 2148 if (to[i] == CSI)
2173 } 2149 {
2174 2150 result[len++] = KS_EXTRA;
2175 add_to_input_buf(result, len); 2151 result[len++] = (int)KE_CSI;
2176 e = noErr; 2152 }
2177 } 2153 }
2178 while (0); 2154 vim_free(to);
2179 2155 }
2180 vim_free(text); 2156 }
2181 if (e == noErr) 2157
2182 { 2158 add_to_input_buf(result, len);
2183 /* Fake event to wake up WNE (required to get 2159 err = noErr;
2184 * key repeat working */ 2160
2185 PostEvent(keyUp, 0); 2161 done:
2186 return noErr; 2162 vim_free(text);
2187 } 2163 if (err == noErr)
2188 } 2164 {
2189 } 2165 /* Fake event to wake up WNE (required to get
2190 while (0); 2166 * key repeat working */
2191 2167 PostEvent(keyUp, 0);
2192 return CallNextEventHandler(nextHandler, theEvent); 2168 return noErr;
2169 }
2170
2171 return eventNotHandledErr;
2193 } 2172 }
2194 #else 2173 #else
2195 void 2174 void
2196 gui_mac_doKeyEvent(EventRecord *theEvent) 2175 gui_mac_doKeyEvent(EventRecord *theEvent)
2197 { 2176 {
5746 CntxMenu = menu->submenu_handle; 5725 CntxMenu = menu->submenu_handle;
5747 5726
5748 /* TODO: Get the text selection from Vim */ 5727 /* TODO: Get the text selection from Vim */
5749 5728
5750 /* Call to Handle Popup */ 5729 /* Call to Handle Popup */
5751 status = ContextualMenuSelect(CntxMenu, where, false, kCMHelpItemNoHelp, HelpName, NULL, &CntxType, &CntxMenuID, &CntxMenuItem); 5730 status = ContextualMenuSelect(CntxMenu, where, false, kCMHelpItemNoHelp,
5731 HelpName, NULL, &CntxType, &CntxMenuID, &CntxMenuItem);
5752 5732
5753 if (status == noErr) 5733 if (status == noErr)
5754 { 5734 {
5755 if (CntxType == kCMMenuItemSelected) 5735 if (CntxType == kCMMenuItemSelected)
5756 { 5736 {
5757 /* Handle the menu CntxMenuID, CntxMenuItem */ 5737 /* Handle the menu CntxMenuID, CntxMenuItem */
5758 /* The submenu can be handle directly by gui_mac_handle_menu */ 5738 /* The submenu can be handle directly by gui_mac_handle_menu */
5759 /* But what about the current menu, is the menu changed by ContextualMenuSelect */ 5739 /* But what about the current menu, is the menu changed by
5740 * ContextualMenuSelect */
5760 gui_mac_handle_menu((CntxMenuID << 16) + CntxMenuItem); 5741 gui_mac_handle_menu((CntxMenuID << 16) + CntxMenuItem);
5761 } 5742 }
5762 else if (CntxMenuID == kCMShowHelpSelected) 5743 else if (CntxMenuID == kCMShowHelpSelected)
5763 { 5744 {
5764 /* Should come up with the help */ 5745 /* Should come up with the help */