| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "views/controls/textfield/native_textfield_win.h" | 5 #include "views/controls/textfield/native_textfield_win.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "base/i18n/rtl.h" | 9 #include "base/i18n/rtl.h" |
| 10 #include "base/string_util.h" | 10 #include "base/string_util.h" |
| (...skipping 470 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 481 CHILDID_SELF, PROPID_ACC_VALUE, value.c_str()); | 481 CHILDID_SELF, PROPID_ACC_VALUE, value.c_str()); |
| 482 | 482 |
| 483 ::NotifyWinEvent(EVENT_OBJECT_VALUECHANGE, m_hWnd, OBJID_CLIENT, | 483 ::NotifyWinEvent(EVENT_OBJECT_VALUECHANGE, m_hWnd, OBJID_CLIENT, |
| 484 CHILDID_SELF); | 484 CHILDID_SELF); |
| 485 } | 485 } |
| 486 | 486 |
| 487 //////////////////////////////////////////////////////////////////////////////// | 487 //////////////////////////////////////////////////////////////////////////////// |
| 488 // NativeTextfieldWin, private: | 488 // NativeTextfieldWin, private: |
| 489 | 489 |
| 490 void NativeTextfieldWin::OnChar(TCHAR ch, UINT repeat_count, UINT flags) { | 490 void NativeTextfieldWin::OnChar(TCHAR ch, UINT repeat_count, UINT flags) { |
| 491 HandleKeystroke(GetCurrentMessage()->message, ch, repeat_count, flags); | 491 HandleKeystroke(); |
| 492 } | 492 } |
| 493 | 493 |
| 494 void NativeTextfieldWin::OnContextMenu(HWND window, const POINT& point) { | 494 void NativeTextfieldWin::OnContextMenu(HWND window, const POINT& point) { |
| 495 POINT p(point); | 495 POINT p(point); |
| 496 if (point.x == -1 || point.y == -1) { | 496 if (point.x == -1 || point.y == -1) { |
| 497 GetCaretPos(&p); | 497 GetCaretPos(&p); |
| 498 MapWindowPoints(HWND_DESKTOP, &p, 1); | 498 MapWindowPoints(HWND_DESKTOP, &p, 1); |
| 499 } | 499 } |
| 500 BuildContextMenu(); | 500 BuildContextMenu(); |
| 501 context_menu_->RunContextMenuAt(gfx::Point(p)); | 501 context_menu_->RunContextMenuAt(gfx::Point(p)); |
| (...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 680 | 680 |
| 681 case VK_PROCESSKEY: | 681 case VK_PROCESSKEY: |
| 682 // This key event is consumed by an IME. | 682 // This key event is consumed by an IME. |
| 683 // We ignore this event because an IME sends WM_IME_COMPOSITION messages | 683 // We ignore this event because an IME sends WM_IME_COMPOSITION messages |
| 684 // when it updates the CRichEditCtrl text. | 684 // when it updates the CRichEditCtrl text. |
| 685 return; | 685 return; |
| 686 } | 686 } |
| 687 | 687 |
| 688 // CRichEditCtrl changes its text on WM_KEYDOWN instead of WM_CHAR for many | 688 // CRichEditCtrl changes its text on WM_KEYDOWN instead of WM_CHAR for many |
| 689 // different keys (backspace, ctrl-v, ...), so we call this in both cases. | 689 // different keys (backspace, ctrl-v, ...), so we call this in both cases. |
| 690 HandleKeystroke(GetCurrentMessage()->message, key, repeat_count, flags); | 690 HandleKeystroke(); |
| 691 } | 691 } |
| 692 | 692 |
| 693 void NativeTextfieldWin::OnLButtonDblClk(UINT keys, const CPoint& point) { | 693 void NativeTextfieldWin::OnLButtonDblClk(UINT keys, const CPoint& point) { |
| 694 // Save the double click info for later triple-click detection. | 694 // Save the double click info for later triple-click detection. |
| 695 tracking_double_click_ = true; | 695 tracking_double_click_ = true; |
| 696 double_click_point_ = point; | 696 double_click_point_ = point; |
| 697 double_click_time_ = GetCurrentMessage()->time; | 697 double_click_time_ = GetCurrentMessage()->time; |
| 698 | 698 |
| 699 ScopedFreeze freeze(this, GetTextObjectModel()); | 699 ScopedFreeze freeze(this, GetTextObjectModel()); |
| 700 OnBeforePossibleChange(); | 700 OnBeforePossibleChange(); |
| (...skipping 223 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 924 // useful, so we discard most. Exceptions: | 924 // useful, so we discard most. Exceptions: |
| 925 // * ctrl-alt-<xxx>, which is sometimes important, generates WM_CHAR instead | 925 // * ctrl-alt-<xxx>, which is sometimes important, generates WM_CHAR instead |
| 926 // of WM_SYSCHAR, so it doesn't need to be handled here. | 926 // of WM_SYSCHAR, so it doesn't need to be handled here. |
| 927 // * alt-space gets translated by the default WM_SYSCHAR handler to a | 927 // * alt-space gets translated by the default WM_SYSCHAR handler to a |
| 928 // WM_SYSCOMMAND to open the application context menu, so we need to allow | 928 // WM_SYSCOMMAND to open the application context menu, so we need to allow |
| 929 // it through. | 929 // it through. |
| 930 if (ch == VK_SPACE) | 930 if (ch == VK_SPACE) |
| 931 SetMsgHandled(false); | 931 SetMsgHandled(false); |
| 932 } | 932 } |
| 933 | 933 |
| 934 void NativeTextfieldWin::HandleKeystroke(UINT message, | 934 void NativeTextfieldWin::HandleKeystroke() { |
| 935 TCHAR key, | 935 const MSG* msg = GetCurrentMessage(); |
| 936 UINT repeat_count, | |
| 937 UINT flags) { | |
| 938 ScopedFreeze freeze(this, GetTextObjectModel()); | 936 ScopedFreeze freeze(this, GetTextObjectModel()); |
| 939 | 937 |
| 940 Textfield::Controller* controller = textfield_->GetController(); | 938 Textfield::Controller* controller = textfield_->GetController(); |
| 941 bool handled = false; | 939 bool handled = false; |
| 942 if (controller) { | 940 if (controller) { |
| 943 ui::EventType type; | 941 KeyEvent event(*msg); |
| 944 switch (message) { | 942 handled = controller->HandleKeyEvent(textfield_, event); |
| 945 case WM_KEYDOWN: | |
| 946 case WM_SYSKEYDOWN: | |
| 947 case WM_CHAR: | |
| 948 case WM_SYSCHAR: | |
| 949 type = ui::ET_KEY_PRESSED; | |
| 950 break; | |
| 951 case WM_KEYUP: | |
| 952 case WM_SYSKEYUP: | |
| 953 type = ui::ET_KEY_RELEASED; | |
| 954 break; | |
| 955 default: | |
| 956 NOTREACHED() << "Unknown message:" << message; | |
| 957 // Passing through to avoid crash on release build. | |
| 958 type = ui::ET_KEY_PRESSED; | |
| 959 } | |
| 960 KeyEvent key_event(type, | |
| 961 ui::KeyboardCodeForWindowsKeyCode(key), | |
| 962 KeyEvent::GetKeyStateFlags(), | |
| 963 repeat_count, | |
| 964 flags, | |
| 965 message); | |
| 966 handled = controller->HandleKeyEvent(textfield_, key_event); | |
| 967 } | 943 } |
| 968 | 944 |
| 969 if (!handled) { | 945 if (!handled) { |
| 970 OnBeforePossibleChange(); | 946 OnBeforePossibleChange(); |
| 971 | 947 |
| 972 if (key == ui::VKEY_HOME || key == ui::VKEY_END) { | 948 if (msg->wParam == ui::VKEY_HOME || msg->wParam == ui::VKEY_END) { |
| 973 // DefWindowProc() might reset the keyboard layout when it receives a | 949 // DefWindowProc() might reset the keyboard layout when it receives a |
| 974 // keydown event for VKEY_HOME or VKEY_END. When the window was created | 950 // keydown event for VKEY_HOME or VKEY_END. When the window was created |
| 975 // with WS_EX_LAYOUTRTL and the current keyboard layout is not a RTL one, | 951 // with WS_EX_LAYOUTRTL and the current keyboard layout is not a RTL one, |
| 976 // if the input text is pure LTR text, the layout changes to the first RTL | 952 // if the input text is pure LTR text, the layout changes to the first RTL |
| 977 // keyboard layout in keyboard layout queue; if the input text is | 953 // keyboard layout in keyboard layout queue; if the input text is |
| 978 // bidirectional text, the layout changes to the keyboard layout of the | 954 // bidirectional text, the layout changes to the keyboard layout of the |
| 979 // first RTL character in input text. When the window was created without | 955 // first RTL character in input text. When the window was created without |
| 980 // WS_EX_LAYOUTRTL and the current keyboard layout is not a LTR one, if | 956 // WS_EX_LAYOUTRTL and the current keyboard layout is not a LTR one, if |
| 981 // the input text is pure RTL text, the layout changes to English; if the | 957 // the input text is pure RTL text, the layout changes to English; if the |
| 982 // input text is bidirectional text, the layout changes to the keyboard | 958 // input text is bidirectional text, the layout changes to the keyboard |
| 983 // layout of the first LTR character in input text. Such keyboard layout | 959 // layout of the first LTR character in input text. Such keyboard layout |
| 984 // change behavior is surprising and inconsistent with keyboard behavior | 960 // change behavior is surprising and inconsistent with keyboard behavior |
| 985 // elsewhere, so reset the layout in this case. | 961 // elsewhere, so reset the layout in this case. |
| 986 HKL layout = GetKeyboardLayout(0); | 962 HKL layout = GetKeyboardLayout(0); |
| 987 DefWindowProc(message, key, MAKELPARAM(repeat_count, flags)); | 963 DefWindowProc(msg->message, msg->wParam, msg->lParam); |
| 988 ActivateKeyboardLayout(layout, KLF_REORDER); | 964 ActivateKeyboardLayout(layout, KLF_REORDER); |
| 989 } else { | 965 } else { |
| 990 DefWindowProc(message, key, MAKELPARAM(repeat_count, flags)); | 966 DefWindowProc(msg->message, msg->wParam, msg->lParam); |
| 991 } | 967 } |
| 992 | 968 |
| 993 // CRichEditCtrl automatically turns on IMF_AUTOKEYBOARD when the user | 969 // CRichEditCtrl automatically turns on IMF_AUTOKEYBOARD when the user |
| 994 // inputs an RTL character, making it difficult for the user to control | 970 // inputs an RTL character, making it difficult for the user to control |
| 995 // what language is set as they type. Force this off to make the edit's | 971 // what language is set as they type. Force this off to make the edit's |
| 996 // behavior more stable. | 972 // behavior more stable. |
| 997 const int lang_options = SendMessage(EM_GETLANGOPTIONS, 0, 0); | 973 const int lang_options = SendMessage(EM_GETLANGOPTIONS, 0, 0); |
| 998 if (lang_options & IMF_AUTOKEYBOARD) | 974 if (lang_options & IMF_AUTOKEYBOARD) |
| 999 SendMessage(EM_SETLANGOPTIONS, 0, lang_options & ~IMF_AUTOKEYBOARD); | 975 SendMessage(EM_SETLANGOPTIONS, 0, lang_options & ~IMF_AUTOKEYBOARD); |
| 1000 | 976 |
| (...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1162 NativeTextfieldWrapper* NativeTextfieldWrapper::CreateWrapper( | 1138 NativeTextfieldWrapper* NativeTextfieldWrapper::CreateWrapper( |
| 1163 Textfield* field) { | 1139 Textfield* field) { |
| 1164 if (NativeTextfieldViews::IsTextfieldViewsEnabled()) { | 1140 if (NativeTextfieldViews::IsTextfieldViewsEnabled()) { |
| 1165 return new NativeTextfieldViews(field); | 1141 return new NativeTextfieldViews(field); |
| 1166 } else { | 1142 } else { |
| 1167 return new NativeTextfieldWin(field); | 1143 return new NativeTextfieldWin(field); |
| 1168 } | 1144 } |
| 1169 } | 1145 } |
| 1170 | 1146 |
| 1171 } // namespace views | 1147 } // namespace views |
| OLD | NEW |