summaryrefslogtreecommitdiff
path: root/chromium/ui
diff options
context:
space:
mode:
authorAndras Becsi <andras.becsi@digia.com>2013-12-11 21:33:03 +0100
committerAndras Becsi <andras.becsi@digia.com>2013-12-13 12:34:07 +0100
commitf2a33ff9cbc6d19943f1c7fbddd1f23d23975577 (patch)
tree0586a32aa390ade8557dfd6b4897f43a07449578 /chromium/ui
parent5362912cdb5eea702b68ebe23702468d17c3017a (diff)
downloadqtwebengine-chromium-f2a33ff9cbc6d19943f1c7fbddd1f23d23975577.tar.gz
Update Chromium to branch 1650 (31.0.1650.63)
Change-Id: I57d8c832eaec1eb2364e0a8e7352a6dd354db99f Reviewed-by: Jocelyn Turcotte <jocelyn.turcotte@digia.com>
Diffstat (limited to 'chromium/ui')
-rw-r--r--chromium/ui/OWNERS6
-rw-r--r--chromium/ui/android/java/WindowOpenDisposition.template11
-rw-r--r--chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_down.9.pngbin341 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_up.9.pngbin354 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-hdpi/color_picker_advanced_select_handle.pngbin1800 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_down.9.pngbin289 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_up.9.pngbin288 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-nodpi/divider_horizontal_bright.9.pngbin109 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_down.9.pngbin514 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_up.9.pngbin501 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable-xhdpi/color_picker_advanced_select_handle.pngbin2422 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable/autofill_popup_background.xml13
-rw-r--r--chromium/ui/android/java/res/drawable/autofill_popup_background_down.9.pngbin335 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable/autofill_popup_background_up.9.pngbin326 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable/color_picker_advanced_select_handle.pngbin1176 -> 0 bytes
-rw-r--r--chromium/ui/android/java/res/drawable/color_picker_border.xml10
-rw-r--r--chromium/ui/android/java/res/layout/autofill_text.xml34
-rw-r--r--chromium/ui/android/java/res/layout/color_picker_advanced_component.xml46
-rw-r--r--chromium/ui/android/java/res/layout/color_picker_dialog_content.xml56
-rw-r--r--chromium/ui/android/java/res/layout/color_picker_dialog_title.xml41
-rw-r--r--chromium/ui/android/java/res/values-v17/styles.xml13
-rw-r--r--chromium/ui/android/java/res/values/colors.xml10
-rw-r--r--chromium/ui/android/java/res/values/dimens.xml15
-rw-r--r--chromium/ui/android/java/res/values/strings.xml16
-rw-r--r--chromium/ui/android/java/res/values/values.xml11
-rw-r--r--chromium/ui/android/java/resource_map/OWNERS13
-rw-r--r--chromium/ui/android/java/resource_map/org/chromium/ui/R.java59
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/Clipboard.java111
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvanced.java252
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvancedComponent.java94
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ColorPickerDialog.java166
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ColorPickerMoreButton.java56
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ColorPickerSimple.java189
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/LocalizationUtils.java96
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/OnColorChangedListener.java17
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/SelectFileDialog.java248
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/UiUtils.java99
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ViewAndroid.java87
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/ViewAndroidDelegate.java34
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/WindowAndroid.java206
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillListAdapter.java54
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillPopup.java214
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillSuggestion.java26
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/gfx/BitmapHelper.java69
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/gfx/DeviceDisplayInfo.java135
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureBridge.java64
-rw-r--r--chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureListener.java40
-rw-r--r--chromium/ui/android/java/strings/android_ui_strings.grd125
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_am.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_ar.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_bg.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_ca.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_cs.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_da.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_de.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_el.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_en-GB.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_es-419.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_es.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_fa.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_fi.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_fil.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_fr.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_hi.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_hr.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_hu.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_id.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_it.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_iw.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_ja.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_ko.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_lt.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_lv.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_nl.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_no.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_pl.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_pt-BR.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_pt-PT.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_ro.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_ru.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_sk.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_sl.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_sr.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_sv.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_sw.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_th.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_tr.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_uk.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_vi.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_zh-CN.xtb7
-rw-r--r--chromium/ui/android/java/strings/translations/android_ui_strings_zh-TW.xtb7
-rw-r--r--chromium/ui/android/ui_jni_registrar.cc34
-rw-r--r--chromium/ui/android/ui_jni_registrar.h21
-rw-r--r--chromium/ui/android/window_android.cc17
-rw-r--r--chromium/ui/android/window_android.h12
-rw-r--r--chromium/ui/app_list/app_list.gyp9
-rw-r--r--chromium/ui/app_list/app_list_item_model.cc6
-rw-r--r--chromium/ui/app_list/app_list_item_model.h8
-rw-r--r--chromium/ui/app_list/app_list_menu.cc44
-rw-r--r--chromium/ui/app_list/app_list_menu.h10
-rw-r--r--chromium/ui/app_list/app_list_model.cc22
-rw-r--r--chromium/ui/app_list/app_list_model.h33
-rw-r--r--chromium/ui/app_list/app_list_model_observer.h8
-rw-r--r--chromium/ui/app_list/app_list_view_delegate.h22
-rw-r--r--chromium/ui/app_list/cocoa/app_list_view_controller.h5
-rw-r--r--chromium/ui/app_list/cocoa/app_list_view_controller.mm72
-rw-r--r--chromium/ui/app_list/cocoa/app_list_view_controller_unittest.mm25
-rw-r--r--chromium/ui/app_list/cocoa/apps_grid_controller.mm5
-rw-r--r--chromium/ui/app_list/cocoa/apps_grid_controller_unittest.mm72
-rw-r--r--chromium/ui/app_list/cocoa/apps_grid_view_item.h4
-rw-r--r--chromium/ui/app_list/cocoa/apps_grid_view_item.mm27
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_box_controller.h2
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_box_controller.mm25
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_box_controller_unittest.mm147
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_results_controller.h17
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_results_controller.mm16
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_results_controller_unittest.mm43
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_results_model_bridge.h10
-rw-r--r--chromium/ui/app_list/cocoa/apps_search_results_model_bridge.mm49
-rw-r--r--chromium/ui/app_list/cocoa/current_user_menu_item_view.h24
-rw-r--r--chromium/ui/app_list/cocoa/current_user_menu_item_view.mm85
-rw-r--r--chromium/ui/app_list/pagination_model.cc14
-rw-r--r--chromium/ui/app_list/pagination_model.h14
-rw-r--r--chromium/ui/app_list/search_result.h7
-rw-r--r--chromium/ui/app_list/signin_delegate.cc14
-rw-r--r--chromium/ui/app_list/signin_delegate.h11
-rw-r--r--chromium/ui/app_list/signin_delegate_observer.h24
-rw-r--r--chromium/ui/app_list/views/app_list_item_view.cc8
-rw-r--r--chromium/ui/app_list/views/app_list_item_view.h3
-rw-r--r--chromium/ui/app_list/views/app_list_main_view.cc28
-rw-r--r--chromium/ui/app_list/views/app_list_main_view.h15
-rw-r--r--chromium/ui/app_list/views/app_list_menu_views.cc113
-rw-r--r--chromium/ui/app_list/views/app_list_menu_views.h7
-rw-r--r--chromium/ui/app_list/views/app_list_view.cc204
-rw-r--r--chromium/ui/app_list/views/app_list_view.h64
-rw-r--r--chromium/ui/app_list/views/apps_grid_view.cc75
-rw-r--r--chromium/ui/app_list/views/apps_grid_view.h8
-rw-r--r--chromium/ui/app_list/views/apps_grid_view_delegate.h (renamed from chromium/ui/app_list/apps_grid_view_delegate.h)8
-rw-r--r--chromium/ui/app_list/views/apps_grid_view_unittest.cc63
-rw-r--r--chromium/ui/app_list/views/contents_view.cc9
-rw-r--r--chromium/ui/app_list/views/contents_view.h5
-rw-r--r--chromium/ui/app_list/views/page_switcher.cc17
-rw-r--r--chromium/ui/app_list/views/search_box_view.cc29
-rw-r--r--chromium/ui/app_list/views/search_box_view.h4
-rw-r--r--chromium/ui/app_list/views/search_box_view_delegate.h (renamed from chromium/ui/app_list/search_box_view_delegate.h)8
-rw-r--r--chromium/ui/app_list/views/search_result_list_view.cc4
-rw-r--r--chromium/ui/app_list/views/search_result_list_view_delegate.h (renamed from chromium/ui/app_list/search_result_list_view_delegate.h)8
-rw-r--r--chromium/ui/app_list/views/search_result_view.cc22
-rw-r--r--chromium/ui/aura/aura.gyp14
-rw-r--r--chromium/ui/aura/bench/DEPS1
-rw-r--r--chromium/ui/aura/bench/bench_main.cc46
-rw-r--r--chromium/ui/aura/client/cursor_client.h7
-rw-r--r--chromium/ui/aura/demo/demo_main.cc17
-rw-r--r--chromium/ui/aura/device_list_updater_aurax11.cc2
-rw-r--r--chromium/ui/aura/env.cc10
-rw-r--r--chromium/ui/aura/env.h6
-rw-r--r--chromium/ui/aura/gestures/gesture_recognizer_unittest.cc83
-rw-r--r--chromium/ui/aura/remote_root_window_host_win.cc46
-rw-r--r--chromium/ui/aura/remote_root_window_host_win.h19
-rw-r--r--chromium/ui/aura/root_window.cc139
-rw-r--r--chromium/ui/aura/root_window.h27
-rw-r--r--chromium/ui/aura/root_window_host.h11
-rw-r--r--chromium/ui/aura/root_window_host_mac.h29
-rw-r--r--chromium/ui/aura/root_window_host_mac.mm218
-rw-r--r--chromium/ui/aura/root_window_host_ozone.cc13
-rw-r--r--chromium/ui/aura/root_window_host_ozone.h5
-rw-r--r--chromium/ui/aura/root_window_host_win.cc9
-rw-r--r--chromium/ui/aura/root_window_host_win.h7
-rw-r--r--chromium/ui/aura/root_window_host_x11.cc97
-rw-r--r--chromium/ui/aura/root_window_host_x11.h8
-rw-r--r--chromium/ui/aura/root_window_mac.h37
-rw-r--r--chromium/ui/aura/root_window_mac.mm35
-rw-r--r--chromium/ui/aura/root_window_unittest.cc177
-rw-r--r--chromium/ui/aura/root_window_view_mac.h21
-rw-r--r--chromium/ui/aura/root_window_view_mac.mm16
-rw-r--r--chromium/ui/aura/window.cc47
-rw-r--r--chromium/ui/aura/window.h4
-rw-r--r--chromium/ui/aura/window_delegate.h14
-rw-r--r--chromium/ui/aura/window_unittest.cc12
-rw-r--r--chromium/ui/base/accelerators/accelerator.cc14
-rw-r--r--chromium/ui/base/accelerators/accelerator.h4
-rw-r--r--chromium/ui/base/accelerators/accelerator_manager.h2
-rw-r--r--chromium/ui/base/accelerators/accelerator_manager_unittest.cc4
-rw-r--r--chromium/ui/base/accelerators/platform_accelerator_gtk.cc29
-rw-r--r--chromium/ui/base/accessibility/accessible_text_utils.cc2
-rw-r--r--chromium/ui/base/accessibility/accessible_text_utils.h2
-rw-r--r--chromium/ui/base/accessibility/accessible_view_state.h8
-rw-r--r--chromium/ui/base/base_window.cc16
-rw-r--r--chromium/ui/base/base_window.h6
-rw-r--r--chromium/ui/base/clipboard/clipboard_aurax11.cc56
-rw-r--r--chromium/ui/base/clipboard/clipboard_gtk.cc10
-rw-r--r--chromium/ui/base/clipboard/clipboard_unittest.cc13
-rw-r--r--chromium/ui/base/cocoa/appkit_utils.h35
-rw-r--r--chromium/ui/base/cocoa/appkit_utils.mm41
-rw-r--r--chromium/ui/base/cocoa/cocoa_event_utils.mm2
-rw-r--r--chromium/ui/base/cocoa/cocoa_event_utils_unittest.mm2
-rw-r--r--chromium/ui/base/cocoa/controls/hyperlink_button_cell.mm8
-rw-r--r--chromium/ui/base/cocoa/controls/hyperlink_button_cell_unittest.mm12
-rw-r--r--chromium/ui/base/cocoa/events_mac.mm6
-rw-r--r--chromium/ui/base/cocoa/events_mac_unittest.mm4
-rw-r--r--chromium/ui/base/cocoa/focus_window_set.h3
-rw-r--r--chromium/ui/base/cocoa/focus_window_set.mm43
-rw-r--r--chromium/ui/base/cocoa/menu_controller.mm5
-rw-r--r--chromium/ui/base/cursor/cursor.h5
-rw-r--r--chromium/ui/base/cursor/cursor_loader_win.cc7
-rw-r--r--chromium/ui/base/cursor/cursor_loader_x11.cc6
-rw-r--r--chromium/ui/base/cursor/cursors_aura.cc114
-rw-r--r--chromium/ui/base/cursor/cursors_aura.h7
-rw-r--r--chromium/ui/base/default_theme_provider.cc4
-rw-r--r--chromium/ui/base/default_theme_provider.h2
-rw-r--r--chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11.cc21
-rw-r--r--chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11_unittest.cc43
-rw-r--r--chromium/ui/base/events/event_conversion_gtk.cc33
-rw-r--r--chromium/ui/base/events/event_conversion_gtk.h20
-rw-r--r--chromium/ui/base/gestures/gesture_configuration.cc4
-rw-r--r--chromium/ui/base/gestures/gesture_configuration.h1
-rw-r--r--chromium/ui/base/gestures/gesture_point.cc8
-rw-r--r--chromium/ui/base/gestures/gesture_point.h10
-rw-r--r--chromium/ui/base/gestures/gesture_recognizer.h4
-rw-r--r--chromium/ui/base/gestures/gesture_recognizer_impl.cc6
-rw-r--r--chromium/ui/base/gestures/gesture_recognizer_impl.h2
-rw-r--r--chromium/ui/base/gestures/gesture_sequence.cc78
-rw-r--r--chromium/ui/base/gestures/gesture_sequence.h7
-rw-r--r--chromium/ui/base/gestures/gesture_types.h2
-rw-r--r--chromium/ui/base/gestures/gestures.dot18
-rw-r--r--chromium/ui/base/gtk/event_synthesis_gtk.cc2
-rw-r--r--chromium/ui/base/gtk/event_synthesis_gtk.h2
-rw-r--r--chromium/ui/base/gtk/gtk_expanded_container.cc2
-rw-r--r--chromium/ui/base/gtk/gtk_floating_container.cc2
-rw-r--r--chromium/ui/base/gtk/gtk_im_context_util.cc2
-rw-r--r--chromium/ui/base/gtk/gtk_windowing.cc2
-rw-r--r--chromium/ui/base/ime/character_composer.cc6
-rw-r--r--chromium/ui/base/ime/character_composer_unittest.cc2
-rw-r--r--chromium/ui/base/ime/composition_text.cc2
-rw-r--r--chromium/ui/base/ime/composition_text.h4
-rw-r--r--chromium/ui/base/ime/dummy_input_method.cc11
-rw-r--r--chromium/ui/base/ime/dummy_input_method.h4
-rw-r--r--chromium/ui/base/ime/dummy_input_method_delegate.cc26
-rw-r--r--chromium/ui/base/ime/dummy_input_method_delegate.h36
-rw-r--r--chromium/ui/base/ime/dummy_text_input_client.cc101
-rw-r--r--chromium/ui/base/ime/dummy_text_input_client.h49
-rw-r--r--chromium/ui/base/ime/fake_input_method.cc60
-rw-r--r--chromium/ui/base/ime/fake_input_method.h7
-rw-r--r--chromium/ui/base/ime/ime.gypi2
-rw-r--r--chromium/ui/base/ime/ime_test_support.gypi2
-rw-r--r--chromium/ui/base/ime/ime_unittests.gypi24
-rw-r--r--chromium/ui/base/ime/input_method.h26
-rw-r--r--chromium/ui/base/ime/input_method_base.cc38
-rw-r--r--chromium/ui/base/ime/input_method_base.h9
-rw-r--r--chromium/ui/base/ime/input_method_base_unittest.cc383
-rw-r--r--chromium/ui/base/ime/input_method_delegate.h4
-rw-r--r--chromium/ui/base/ime/input_method_ibus.cc280
-rw-r--r--chromium/ui/base/ime/input_method_ibus.h51
-rw-r--r--chromium/ui/base/ime/input_method_ibus_unittest.cc866
-rw-r--r--chromium/ui/base/ime/input_method_imm32.cc20
-rw-r--r--chromium/ui/base/ime/input_method_imm32.h5
-rw-r--r--chromium/ui/base/ime/input_method_initializer.cc22
-rw-r--r--chromium/ui/base/ime/input_method_tsf.cc24
-rw-r--r--chromium/ui/base/ime/input_method_tsf.h6
-rw-r--r--chromium/ui/base/ime/input_method_win.cc42
-rw-r--r--chromium/ui/base/ime/input_method_win.h4
-rw-r--r--chromium/ui/base/ime/mock_input_method.cc29
-rw-r--r--chromium/ui/base/ime/mock_input_method.h5
-rw-r--r--chromium/ui/base/ime/text_input_client.h14
-rw-r--r--chromium/ui/base/ime/win/imm32_manager.cc4
-rw-r--r--chromium/ui/base/ime/win/tsf_bridge.cc69
-rw-r--r--chromium/ui/base/ime/win/tsf_event_router.cc32
-rw-r--r--chromium/ui/base/ime/win/tsf_event_router.h8
-rw-r--r--chromium/ui/base/ime/win/tsf_input_scope.cc56
-rw-r--r--chromium/ui/base/ime/win/tsf_input_scope.h18
-rw-r--r--chromium/ui/base/ime/win/tsf_input_scope_unittest.cc121
-rw-r--r--chromium/ui/base/ime/win/tsf_text_store.cc11
-rw-r--r--chromium/ui/base/ime/win/tsf_text_store.h4
-rw-r--r--chromium/ui/base/ime/win/tsf_text_store_unittest.cc282
-rw-r--r--chromium/ui/base/keycodes/OWNERS4
-rw-r--r--chromium/ui/base/keycodes/keyboard_code_conversion_android.h17
-rw-r--r--chromium/ui/base/keycodes/keyboard_code_conversion_win.h19
-rw-r--r--chromium/ui/base/keycodes/keyboard_code_conversion_x.h31
-rw-r--r--chromium/ui/base/keycodes/keycode_converter.cc115
-rw-r--r--chromium/ui/base/keycodes/keycode_converter.h87
-rw-r--r--chromium/ui/base/keycodes/keycode_converter_data.h379
-rw-r--r--chromium/ui/base/keycodes/keycode_converter_unittest.cc110
-rw-r--r--chromium/ui/base/keycodes/usb_keycode_map.h409
-rw-r--r--chromium/ui/base/keycodes/usb_keycode_map_unittest.cc92
-rw-r--r--chromium/ui/base/l10n/l10n_util.cc26
-rw-r--r--chromium/ui/base/l10n/l10n_util.h8
-rw-r--r--chromium/ui/base/l10n/l10n_util_plurals.cc64
-rw-r--r--chromium/ui/base/l10n/l10n_util_plurals.h30
-rw-r--r--chromium/ui/base/l10n/l10n_util_win.cc4
-rw-r--r--chromium/ui/base/l10n/l10n_util_win_unittest.cc2
-rw-r--r--chromium/ui/base/l10n/time_format.cc44
-rw-r--r--chromium/ui/base/layout.cc7
-rw-r--r--chromium/ui/base/layout.h1
-rw-r--r--chromium/ui/base/layout_unittest.cc6
-rw-r--r--chromium/ui/base/models/list_selection_model.h2
-rw-r--r--chromium/ui/base/models/menu_model.cc6
-rw-r--r--chromium/ui/base/models/menu_model.h10
-rw-r--r--chromium/ui/base/models/simple_menu_model.cc79
-rw-r--r--chromium/ui/base/models/simple_menu_model.h12
-rw-r--r--chromium/ui/base/resource/resource_bundle.cc19
-rw-r--r--chromium/ui/base/resource/resource_bundle_android.cc2
-rw-r--r--chromium/ui/base/resource/resource_bundle_auralinux.cc3
-rw-r--r--chromium/ui/base/resource/resource_bundle_gtk.cc4
-rw-r--r--chromium/ui/base/resource/resource_bundle_mac.mm2
-rw-r--r--chromium/ui/base/resource/resource_bundle_win.cc4
-rw-r--r--chromium/ui/base/sequential_id_generator.cc82
-rw-r--r--chromium/ui/base/sequential_id_generator.h60
-rw-r--r--chromium/ui/base/sequential_id_generator_unittest.cc62
-rw-r--r--chromium/ui/base/strings/app_locale_settings.grd14
-rw-r--r--chromium/ui/base/strings/app_locale_settings_ja.xtb2
-rw-r--r--chromium/ui/base/strings/app_locale_settings_ko.xtb2
-rw-r--r--chromium/ui/base/strings/app_locale_settings_zh-CN.xtb2
-rw-r--r--chromium/ui/base/strings/app_locale_settings_zh-TW.xtb2
-rw-r--r--chromium/ui/base/strings/ui_strings.grd31
-rw-r--r--chromium/ui/base/strings/ui_strings_am.xtb45
-rw-r--r--chromium/ui/base/strings/ui_strings_ar.xtb9
-rw-r--r--chromium/ui/base/strings/ui_strings_bg.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_bn.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ca.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_cs.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_da.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_de.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_el.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_en-GB.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_es-419.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_es.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_et.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_fa.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_fi.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_fil.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_fr.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_gu.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_hi.xtb9
-rw-r--r--chromium/ui/base/strings/ui_strings_hr.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_hu.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_id.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_it.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_iw.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ja.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_kn.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ko.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_lt.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_lv.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ml.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_mr.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ms.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_nl.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_no.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_pl.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_pt-BR.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_pt-PT.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ro.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_ru.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_sk.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_sl.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_sr.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_sv.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_sw.xtb17
-rw-r--r--chromium/ui/base/strings/ui_strings_ta.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_te.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_th.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_tr.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_uk.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_vi.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_zh-CN.xtb7
-rw-r--r--chromium/ui/base/strings/ui_strings_zh-TW.xtb7
-rw-r--r--chromium/ui/base/theme_provider.h2
-rw-r--r--chromium/ui/base/touch/touch_factory_x11.cc48
-rw-r--r--chromium/ui/base/touch/touch_factory_x11.h11
-rw-r--r--chromium/ui/base/ui_base_switches.cc12
-rw-r--r--chromium/ui/base/ui_base_switches.h4
-rw-r--r--chromium/ui/base/ui_base_switches_util.cc9
-rw-r--r--chromium/ui/base/ui_base_switches_util.h2
-rw-r--r--chromium/ui/base/ui_base_types.cc2
-rw-r--r--chromium/ui/base/win/events_win.cc12
-rw-r--r--chromium/ui/base/win/foreground_helper.cc2
-rw-r--r--chromium/ui/base/win/foreground_helper.h4
-rw-r--r--chromium/ui/base/win/hidden_window.cc4
-rw-r--r--chromium/ui/base/win/hwnd_subclass.cc12
-rw-r--r--chromium/ui/base/win/hwnd_subclass_unittest.cc6
-rw-r--r--chromium/ui/base/win/mouse_wheel_util.cc6
-rw-r--r--chromium/ui/base/win/shell.cc16
-rw-r--r--chromium/ui/base/win/shell.h5
-rw-r--r--chromium/ui/base/window_open_disposition.cc2
-rw-r--r--chromium/ui/base/x/active_window_watcher_x.cc4
-rw-r--r--chromium/ui/base/x/device_data_manager.cc13
-rw-r--r--chromium/ui/base/x/device_data_manager.h2
-rw-r--r--chromium/ui/base/x/events_x.cc68
-rw-r--r--chromium/ui/base/x/events_x_unittest.cc31
-rw-r--r--chromium/ui/base/x/selection_requestor.cc4
-rw-r--r--chromium/ui/base/x/selection_utils.cc7
-rw-r--r--chromium/ui/base/x/x11_atom_cache.cc2
-rw-r--r--chromium/ui/base/x/x11_error_tracker.cc37
-rw-r--r--chromium/ui/base/x/x11_error_tracker.h33
-rw-r--r--chromium/ui/base/x/x11_error_tracker_gtk.cc29
-rw-r--r--chromium/ui/base/x/x11_util.cc223
-rw-r--r--chromium/ui/base/x/x11_util.h62
-rw-r--r--chromium/ui/compositor/DEPS1
-rw-r--r--chromium/ui/compositor/OWNERS3
-rw-r--r--chromium/ui/compositor/compositor.cc77
-rw-r--r--chromium/ui/compositor/compositor.gyp6
-rw-r--r--chromium/ui/compositor/compositor.h30
-rw-r--r--chromium/ui/compositor/compositor_switches.cc19
-rw-r--r--chromium/ui/compositor/compositor_switches.h4
-rw-r--r--chromium/ui/compositor/context_provider_from_context_factory.cc76
-rw-r--r--chromium/ui/compositor/context_provider_from_context_factory.h45
-rw-r--r--chromium/ui/compositor/debug_utils.cc3
-rw-r--r--chromium/ui/compositor/dip_util.cc1
-rw-r--r--chromium/ui/compositor/float_animation_curve_adapter.cc9
-rw-r--r--chromium/ui/compositor/float_animation_curve_adapter.h6
-rw-r--r--chromium/ui/compositor/layer.cc33
-rw-r--r--chromium/ui/compositor/layer.h23
-rw-r--r--chromium/ui/compositor/layer_animation_element.cc203
-rw-r--r--chromium/ui/compositor/layer_animation_element.h30
-rw-r--r--chromium/ui/compositor/layer_animation_element_unittest.cc73
-rw-r--r--chromium/ui/compositor/layer_animation_sequence.cc19
-rw-r--r--chromium/ui/compositor/layer_animation_sequence.h11
-rw-r--r--chromium/ui/compositor/layer_animation_sequence_unittest.cc16
-rw-r--r--chromium/ui/compositor/layer_animator.cc10
-rw-r--r--chromium/ui/compositor/layer_animator.h15
-rw-r--r--chromium/ui/compositor/layer_animator_unittest.cc37
-rw-r--r--chromium/ui/compositor/run_all_unittests.cc8
-rw-r--r--chromium/ui/compositor/scoped_layer_animation_settings.cc88
-rw-r--r--chromium/ui/compositor/scoped_layer_animation_settings.h19
-rw-r--r--chromium/ui/compositor/test_web_graphics_context_3d.cc220
-rw-r--r--chromium/ui/compositor/test_web_graphics_context_3d.h450
-rw-r--r--chromium/ui/compositor/transform_animation_curve_adapter.cc63
-rw-r--r--chromium/ui/compositor/transform_animation_curve_adapter.h38
-rw-r--r--chromium/ui/compositor/transform_animation_curve_adapter_unittest.cc59
-rw-r--r--chromium/ui/events/OWNERS (renamed from chromium/ui/base/events/OWNERS)0
-rw-r--r--chromium/ui/events/event.cc (renamed from chromium/ui/base/events/event.cc)36
-rw-r--r--chromium/ui/events/event.h (renamed from chromium/ui/base/events/event.h)43
-rw-r--r--chromium/ui/events/event_constants.h (renamed from chromium/ui/base/events/event_constants.h)6
-rw-r--r--chromium/ui/events/event_dispatcher.cc (renamed from chromium/ui/base/events/event_dispatcher.cc)2
-rw-r--r--chromium/ui/events/event_dispatcher.h (renamed from chromium/ui/base/events/event_dispatcher.h)18
-rw-r--r--chromium/ui/events/event_dispatcher_unittest.cc (renamed from chromium/ui/base/events/event_dispatcher_unittest.cc)6
-rw-r--r--chromium/ui/events/event_handler.cc (renamed from chromium/ui/base/events/event_handler.cc)6
-rw-r--r--chromium/ui/events/event_handler.h (renamed from chromium/ui/base/events/event_handler.h)12
-rw-r--r--chromium/ui/events/event_target.cc (renamed from chromium/ui/base/events/event_target.cc)4
-rw-r--r--chromium/ui/events/event_target.h (renamed from chromium/ui/base/events/event_target.h)12
-rw-r--r--chromium/ui/events/event_unittest.cc (renamed from chromium/ui/base/events/event_unittest.cc)2
-rw-r--r--chromium/ui/events/event_utils.cc (renamed from chromium/ui/base/events/event_utils.cc)4
-rw-r--r--chromium/ui/events/event_utils.h (renamed from chromium/ui/base/events/event_utils.h)75
-rw-r--r--chromium/ui/events/events_export.h33
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion.cc (renamed from chromium/ui/base/keycodes/keyboard_code_conversion.cc)4
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion.h (renamed from chromium/ui/base/keycodes/keyboard_code_conversion.h)12
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_android.cc (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_android.cc)2
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_android.h17
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_gtk.cc (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_gtk.cc)6
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_gtk.h (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_gtk.h)16
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_mac.h (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_mac.h)14
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_mac.mm (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_mac.mm)2
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_win.cc (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_win.cc)2
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_win.h19
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_x.cc (renamed from chromium/ui/base/keycodes/keyboard_code_conversion_x.cc)2
-rw-r--r--chromium/ui/events/keycodes/keyboard_code_conversion_x.h31
-rw-r--r--chromium/ui/events/keycodes/keyboard_codes.h (renamed from chromium/ui/base/keycodes/keyboard_codes.h)10
-rw-r--r--chromium/ui/events/keycodes/keyboard_codes_posix.h (renamed from chromium/ui/base/keycodes/keyboard_codes_posix.h)6
-rw-r--r--chromium/ui/events/keycodes/keyboard_codes_win.h (renamed from chromium/ui/base/keycodes/keyboard_codes_win.h)6
-rw-r--r--chromium/ui/events/latency_info.cc (renamed from chromium/ui/base/latency_info.cc)2
-rw-r--r--chromium/ui/events/latency_info.h (renamed from chromium/ui/base/latency_info.h)10
-rw-r--r--chromium/ui/events/latency_info_unittest.cc (renamed from chromium/ui/base/latency_info_unittest.cc)2
-rw-r--r--chromium/ui/events/ozone/OWNERS (renamed from chromium/ui/base/ozone/OWNERS)0
-rw-r--r--chromium/ui/events/ozone/evdev/key_event_converter_ozone.cc (renamed from chromium/ui/base/ozone/evdev/key_event_converter_ozone.cc)6
-rw-r--r--chromium/ui/events/ozone/evdev/key_event_converter_ozone.h (renamed from chromium/ui/base/ozone/evdev/key_event_converter_ozone.h)9
-rw-r--r--chromium/ui/events/ozone/evdev/touch_event_converter_ozone.cc (renamed from chromium/ui/base/ozone/evdev/touch_event_converter_ozone.cc)25
-rw-r--r--chromium/ui/events/ozone/evdev/touch_event_converter_ozone.h (renamed from chromium/ui/base/ozone/evdev/touch_event_converter_ozone.h)17
-rw-r--r--chromium/ui/events/ozone/evdev/touch_event_converter_ozone_unittest.cc (renamed from chromium/ui/base/ozone/evdev/touch_event_converter_ozone_unittest.cc)4
-rw-r--r--chromium/ui/events/ozone/event_converter_ozone.cc (renamed from chromium/ui/base/ozone/event_converter_ozone.cc)4
-rw-r--r--chromium/ui/events/ozone/event_converter_ozone.h (renamed from chromium/ui/base/ozone/event_converter_ozone.h)6
-rw-r--r--chromium/ui/events/ozone/event_factory_delegate_ozone.h (renamed from chromium/ui/base/ozone/event_factory_delegate_ozone.h)6
-rw-r--r--chromium/ui/events/ozone/event_factory_ozone.cc (renamed from chromium/ui/base/ozone/event_factory_ozone.cc)13
-rw-r--r--chromium/ui/events/ozone/event_factory_ozone.h (renamed from chromium/ui/base/ozone/event_factory_ozone.h)10
-rw-r--r--chromium/ui/events/ozone/events_ozone.cc (renamed from chromium/ui/base/ozone/events_ozone.cc)6
-rw-r--r--chromium/ui/gfx/android/device_display_info.h2
-rw-r--r--chromium/ui/gfx/android/java_bitmap.cc45
-rw-r--r--chromium/ui/gfx/android/java_bitmap.h3
-rw-r--r--chromium/ui/gfx/animation/animation.cc (renamed from chromium/ui/base/animation/animation.cc)12
-rw-r--r--chromium/ui/gfx/animation/animation.h (renamed from chromium/ui/base/animation/animation.h)14
-rw-r--r--chromium/ui/gfx/animation/animation_container.cc (renamed from chromium/ui/base/animation/animation_container.cc)10
-rw-r--r--chromium/ui/gfx/animation/animation_container.h (renamed from chromium/ui/base/animation/animation_container.h)14
-rw-r--r--chromium/ui/gfx/animation/animation_container_element.h (renamed from chromium/ui/base/animation/animation_container_element.h)14
-rw-r--r--chromium/ui/gfx/animation/animation_container_observer.h (renamed from chromium/ui/base/animation/animation_container_observer.h)14
-rw-r--r--chromium/ui/gfx/animation/animation_container_unittest.cc (renamed from chromium/ui/base/animation/animation_container_unittest.cc)13
-rw-r--r--chromium/ui/gfx/animation/animation_delegate.h (renamed from chromium/ui/base/animation/animation_delegate.h)14
-rw-r--r--chromium/ui/gfx/animation/animation_unittest.cc (renamed from chromium/ui/base/animation/animation_unittest.cc)10
-rw-r--r--chromium/ui/gfx/animation/linear_animation.cc (renamed from chromium/ui/base/animation/linear_animation.cc)10
-rw-r--r--chromium/ui/gfx/animation/linear_animation.h (renamed from chromium/ui/base/animation/linear_animation.h)12
-rw-r--r--chromium/ui/gfx/animation/multi_animation.cc (renamed from chromium/ui/base/animation/multi_animation.cc)8
-rw-r--r--chromium/ui/gfx/animation/multi_animation.h (renamed from chromium/ui/base/animation/multi_animation.h)16
-rw-r--r--chromium/ui/gfx/animation/multi_animation_unittest.cc (renamed from chromium/ui/base/animation/multi_animation_unittest.cc)9
-rw-r--r--chromium/ui/gfx/animation/slide_animation.cc (renamed from chromium/ui/base/animation/slide_animation.cc)6
-rw-r--r--chromium/ui/gfx/animation/slide_animation.h (renamed from chromium/ui/base/animation/slide_animation.h)18
-rw-r--r--chromium/ui/gfx/animation/slide_animation_unittest.cc (renamed from chromium/ui/base/animation/slide_animation_unittest.cc)9
-rw-r--r--chromium/ui/gfx/animation/test_animation_delegate.h (renamed from chromium/ui/base/animation/test_animation_delegate.h)12
-rw-r--r--chromium/ui/gfx/animation/throb_animation.cc (renamed from chromium/ui/base/animation/throb_animation.cc)6
-rw-r--r--chromium/ui/gfx/animation/throb_animation.h (renamed from chromium/ui/base/animation/throb_animation.h)14
-rw-r--r--chromium/ui/gfx/animation/tween.cc (renamed from chromium/ui/base/animation/tween.cc)6
-rw-r--r--chromium/ui/gfx/animation/tween.h (renamed from chromium/ui/base/animation/tween.h)14
-rw-r--r--chromium/ui/gfx/blit.h2
-rw-r--r--chromium/ui/gfx/box_f.cc2
-rw-r--r--chromium/ui/gfx/break_list.h15
-rw-r--r--chromium/ui/gfx/break_list_unittest.cc82
-rw-r--r--chromium/ui/gfx/canvas.cc258
-rw-r--r--chromium/ui/gfx/canvas.h227
-rw-r--r--chromium/ui/gfx/canvas_android.cc26
-rw-r--r--chromium/ui/gfx/canvas_mac.mm89
-rw-r--r--chromium/ui/gfx/canvas_paint.h2
-rw-r--r--chromium/ui/gfx/canvas_paint_win.cc6
-rw-r--r--chromium/ui/gfx/canvas_paint_win.h2
-rw-r--r--chromium/ui/gfx/canvas_skia.cc154
-rw-r--r--chromium/ui/gfx/canvas_unittest_mac.mm84
-rw-r--r--chromium/ui/gfx/codec/OWNERS2
-rw-r--r--chromium/ui/gfx/codec/jpeg_codec.h2
-rw-r--r--chromium/ui/gfx/codec/png_codec.cc85
-rw-r--r--chromium/ui/gfx/codec/png_codec.h38
-rw-r--r--chromium/ui/gfx/codec/png_codec_unittest.cc47
-rw-r--r--chromium/ui/gfx/color_analysis.h2
-rw-r--r--chromium/ui/gfx/color_profile.h2
-rw-r--r--chromium/ui/gfx/color_profile_win.cc2
-rw-r--r--chromium/ui/gfx/color_utils.h2
-rw-r--r--chromium/ui/gfx/display.cc4
-rw-r--r--chromium/ui/gfx/display.h6
-rw-r--r--chromium/ui/gfx/display_observer.h2
-rw-r--r--chromium/ui/gfx/favicon_size.h2
-rw-r--r--chromium/ui/gfx/font.h2
-rw-r--r--chromium/ui/gfx/font_list.h2
-rw-r--r--chromium/ui/gfx/font_render_params_linux.h2
-rw-r--r--chromium/ui/gfx/font_smoothing_win.cc6
-rw-r--r--chromium/ui/gfx/gdi_util.h2
-rw-r--r--chromium/ui/gfx/gdk_compat.h (renamed from chromium/ui/base/gtk/gdk_x_compat.h)6
-rw-r--r--chromium/ui/gfx/gfx_export.h33
-rw-r--r--chromium/ui/gfx/gfx_paths.h2
-rw-r--r--chromium/ui/gfx/gpu_memory_buffer.h2
-rw-r--r--chromium/ui/gfx/gtk_compat.h (renamed from chromium/ui/base/gtk/gtk_compat.h)6
-rw-r--r--chromium/ui/gfx/gtk_native_view_id_manager.cc4
-rw-r--r--chromium/ui/gfx/gtk_native_view_id_manager.h2
-rw-r--r--chromium/ui/gfx/gtk_preserve_window.cc2
-rw-r--r--chromium/ui/gfx/gtk_preserve_window.h2
-rw-r--r--chromium/ui/gfx/gtk_util.h2
-rw-r--r--chromium/ui/gfx/icon_util.h2
-rw-r--r--chromium/ui/gfx/icon_util_unittest.cc2
-rw-r--r--chromium/ui/gfx/image/cairo_cached_surface.h2
-rw-r--r--chromium/ui/gfx/image/canvas_image_source.h2
-rw-r--r--chromium/ui/gfx/image/image.cc2
-rw-r--r--chromium/ui/gfx/image/image.h2
-rw-r--r--chromium/ui/gfx/image/image_family.h2
-rw-r--r--chromium/ui/gfx/image/image_png_rep.h2
-rw-r--r--chromium/ui/gfx/image/image_skia.h2
-rw-r--r--chromium/ui/gfx/image/image_skia_operations.h2
-rw-r--r--chromium/ui/gfx/image/image_skia_rep.h2
-rw-r--r--chromium/ui/gfx/image/image_skia_source.h2
-rw-r--r--chromium/ui/gfx/image/image_skia_util_ios.h2
-rw-r--r--chromium/ui/gfx/image/image_skia_util_mac.h2
-rw-r--r--chromium/ui/gfx/image/image_util.h2
-rw-r--r--chromium/ui/gfx/insets.h2
-rw-r--r--chromium/ui/gfx/insets_base.h2
-rw-r--r--chromium/ui/gfx/insets_f.h2
-rw-r--r--chromium/ui/gfx/interpolated_transform.cc5
-rw-r--r--chromium/ui/gfx/interpolated_transform_unittest.cc8
-rw-r--r--chromium/ui/gfx/native_widget_types.h5
-rw-r--r--chromium/ui/gfx/ozone/OWNERS1
-rw-r--r--chromium/ui/gfx/ozone/surface_factory_ozone.cc (renamed from chromium/ui/base/ozone/surface_factory_ozone.cc)20
-rw-r--r--chromium/ui/gfx/ozone/surface_factory_ozone.h (renamed from chromium/ui/base/ozone/surface_factory_ozone.h)44
-rw-r--r--chromium/ui/gfx/pango_util.cc33
-rw-r--r--chromium/ui/gfx/pango_util.h2
-rw-r--r--chromium/ui/gfx/path.h2
-rw-r--r--chromium/ui/gfx/path_win.h2
-rw-r--r--chromium/ui/gfx/path_x11.h2
-rw-r--r--chromium/ui/gfx/platform_font.h2
-rw-r--r--chromium/ui/gfx/platform_font_pango.cc70
-rw-r--r--chromium/ui/gfx/platform_font_pango.h15
-rw-r--r--chromium/ui/gfx/platform_font_pango_unittest.cc4
-rw-r--r--chromium/ui/gfx/platform_font_win.cc6
-rw-r--r--chromium/ui/gfx/platform_font_win.h2
-rw-r--r--chromium/ui/gfx/point.h2
-rw-r--r--chromium/ui/gfx/point3_f.h2
-rw-r--r--chromium/ui/gfx/point_base.h2
-rw-r--r--chromium/ui/gfx/point_f.h2
-rw-r--r--chromium/ui/gfx/quad_f.h3
-rw-r--r--chromium/ui/gfx/range/OWNERS (renamed from chromium/ui/base/range/OWNERS)0
-rw-r--r--chromium/ui/gfx/range/range.cc (renamed from chromium/ui/base/range/range.cc)9
-rw-r--r--chromium/ui/gfx/range/range.h (renamed from chromium/ui/base/range/range.h)15
-rw-r--r--chromium/ui/gfx/range/range_mac.mm (renamed from chromium/ui/base/range/range_mac.mm)4
-rw-r--r--chromium/ui/gfx/range/range_mac_unittest.mm (renamed from chromium/ui/base/range/range_mac_unittest.mm)12
-rw-r--r--chromium/ui/gfx/range/range_unittest.cc (renamed from chromium/ui/base/range/range_unittest.cc)70
-rw-r--r--chromium/ui/gfx/range/range_win.cc (renamed from chromium/ui/base/range/range_win.cc)4
-rw-r--r--chromium/ui/gfx/range/range_win_unittest.cc (renamed from chromium/ui/base/range/range_win_unittest.cc)16
-rw-r--r--chromium/ui/gfx/rect_conversions.cc1
-rw-r--r--chromium/ui/gfx/render_text.cc176
-rw-r--r--chromium/ui/gfx/render_text.h117
-rw-r--r--chromium/ui/gfx/render_text_linux.cc33
-rw-r--r--chromium/ui/gfx/render_text_linux.h4
-rw-r--r--chromium/ui/gfx/render_text_mac.cc15
-rw-r--r--chromium/ui/gfx/render_text_mac.h4
-rw-r--r--chromium/ui/gfx/render_text_unittest.cc199
-rw-r--r--chromium/ui/gfx/render_text_win.cc556
-rw-r--r--chromium/ui/gfx/render_text_win.h18
-rw-r--r--chromium/ui/gfx/safe_integer_conversions.h2
-rw-r--r--chromium/ui/gfx/scoped_gobject.h (renamed from chromium/ui/base/gtk/scoped_gobject.h)6
-rw-r--r--chromium/ui/gfx/scoped_ns_graphics_context_save_gstate_mac.h2
-rw-r--r--chromium/ui/gfx/screen.h21
-rw-r--r--chromium/ui/gfx/screen_android.cc14
-rw-r--r--chromium/ui/gfx/screen_gtk.cc84
-rw-r--r--chromium/ui/gfx/screen_ios.mm15
-rw-r--r--chromium/ui/gfx/screen_mac.mm15
-rw-r--r--chromium/ui/gfx/screen_win.cc76
-rw-r--r--chromium/ui/gfx/screen_win.h9
-rw-r--r--chromium/ui/gfx/scrollbar_size.h2
-rw-r--r--chromium/ui/gfx/selection_model.cc11
-rw-r--r--chromium/ui/gfx/selection_model.h10
-rw-r--r--chromium/ui/gfx/shadow_value.h2
-rw-r--r--chromium/ui/gfx/size.h2
-rw-r--r--chromium/ui/gfx/size_base.h2
-rw-r--r--chromium/ui/gfx/size_f.h2
-rw-r--r--chromium/ui/gfx/skbitmap_operations.h2
-rw-r--r--chromium/ui/gfx/skia_util.h2
-rw-r--r--chromium/ui/gfx/skia_utils_gtk.h2
-rw-r--r--chromium/ui/gfx/switches.cc8
-rw-r--r--chromium/ui/gfx/switches.h6
-rw-r--r--chromium/ui/gfx/sys_color_change_listener.cc8
-rw-r--r--chromium/ui/gfx/sys_color_change_listener.h2
-rw-r--r--chromium/ui/gfx/text_elider.cc (renamed from chromium/ui/base/text/text_elider.cc)213
-rw-r--r--chromium/ui/gfx/text_elider.h (renamed from chromium/ui/base/text/text_elider.h)54
-rw-r--r--chromium/ui/gfx/text_elider_unittest.cc (renamed from chromium/ui/base/text/text_elider_unittest.cc)77
-rw-r--r--chromium/ui/gfx/text_utils.h9
-rw-r--r--chromium/ui/gfx/text_utils_android.cc16
-rw-r--r--chromium/ui/gfx/text_utils_ios.mm22
-rw-r--r--chromium/ui/gfx/text_utils_skia.cc15
-rw-r--r--chromium/ui/gfx/transform.cc299
-rw-r--r--chromium/ui/gfx/transform.h68
-rw-r--r--chromium/ui/gfx/transform_unittest.cc54
-rw-r--r--chromium/ui/gfx/transform_util.cc113
-rw-r--r--chromium/ui/gfx/transform_util.h14
-rw-r--r--chromium/ui/gfx/transform_util_unittest.cc2
-rw-r--r--chromium/ui/gfx/utf16_indexing.cc (renamed from chromium/ui/base/text/utf16_indexing.cc)6
-rw-r--r--chromium/ui/gfx/utf16_indexing.h (renamed from chromium/ui/base/text/utf16_indexing.h)12
-rw-r--r--chromium/ui/gfx/utf16_indexing_unittest.cc (renamed from chromium/ui/base/text/utf16_indexing_unittest.cc)6
-rw-r--r--chromium/ui/gfx/vector2d.h2
-rw-r--r--chromium/ui/gfx/vector2d_f.h2
-rw-r--r--chromium/ui/gfx/vector3d_f.h2
-rw-r--r--chromium/ui/gfx/win/dpi.cc (renamed from chromium/ui/base/win/dpi.cc)60
-rw-r--r--chromium/ui/gfx/win/dpi.h (renamed from chromium/ui/base/win/dpi.h)37
-rw-r--r--chromium/ui/gfx/win/hwnd_util.cc (renamed from chromium/ui/base/win/hwnd_util.cc)23
-rw-r--r--chromium/ui/gfx/win/hwnd_util.h (renamed from chromium/ui/base/win/hwnd_util.h)13
-rw-r--r--chromium/ui/gfx/win/scoped_set_map_mode.h (renamed from chromium/ui/base/win/scoped_set_map_mode.h)10
-rw-r--r--chromium/ui/gfx/win/singleton_hwnd.cc (renamed from chromium/ui/base/win/singleton_hwnd.cc)8
-rw-r--r--chromium/ui/gfx/win/singleton_hwnd.h (renamed from chromium/ui/base/win/singleton_hwnd.h)12
-rw-r--r--chromium/ui/gfx/win/window_impl.cc (renamed from chromium/ui/base/win/window_impl.cc)22
-rw-r--r--chromium/ui/gfx/win/window_impl.h (renamed from chromium/ui/base/win/window_impl.h)12
-rw-r--r--chromium/ui/gfx/x/x11_types.cc16
-rw-r--r--chromium/ui/gfx/x/x11_types.h25
-rw-r--r--chromium/ui/gl/android/gl_jni_registrar.cc30
-rw-r--r--chromium/ui/gl/android/gl_jni_registrar.h23
-rw-r--r--chromium/ui/gl/android/scoped_java_surface.cc4
-rw-r--r--chromium/ui/gl/android/scoped_java_surface.h4
-rw-r--r--chromium/ui/gl/android/surface_texture.cc (renamed from chromium/ui/gl/android/surface_texture_bridge.cc)44
-rw-r--r--chromium/ui/gl/android/surface_texture.h (renamed from chromium/ui/gl/android/surface_texture_bridge.h)22
-rw-r--r--chromium/ui/gl/android/surface_texture_listener.cc2
-rw-r--r--chromium/ui/gl/android/surface_texture_listener.h2
-rwxr-xr-xchromium/ui/gl/generate_bindings.py13
-rw-r--r--chromium/ui/gl/gl.gyp9
-rw-r--r--chromium/ui/gl/gl_bindings.h4
-rw-r--r--chromium/ui/gl/gl_context_android.cc28
-rw-r--r--chromium/ui/gl/gl_fence.cc3
-rw-r--r--chromium/ui/gl/gl_image.h4
-rw-r--r--chromium/ui/gl/gl_image_android.cc7
-rw-r--r--chromium/ui/gl/gl_image_mac.cc7
-rw-r--r--chromium/ui/gl/gl_image_ozone.cc4
-rw-r--r--chromium/ui/gl/gl_image_shm.cc31
-rw-r--r--chromium/ui/gl/gl_image_shm.h3
-rw-r--r--chromium/ui/gl/gl_image_win.cc7
-rw-r--r--chromium/ui/gl/gl_image_x11.cc7
-rw-r--r--chromium/ui/gl/gl_implementation_ozone.cc4
-rw-r--r--chromium/ui/gl/gl_implementation_win.cc51
-rw-r--r--chromium/ui/gl/gl_surface_egl.cc23
-rw-r--r--chromium/ui/gl/gl_surface_glx.cc208
-rw-r--r--chromium/ui/gl/gl_surface_glx.h36
-rw-r--r--chromium/ui/gl/gl_switches.cc4
-rw-r--r--chromium/ui/gl/gl_switches.h1
-rw-r--r--chromium/ui/keyboard/keyboard.gyp13
-rw-r--r--chromium/ui/keyboard/keyboard_controller.cc64
-rw-r--r--chromium/ui/keyboard/keyboard_controller.h10
-rw-r--r--chromium/ui/keyboard/keyboard_controller_proxy.cc51
-rw-r--r--chromium/ui/keyboard/keyboard_controller_proxy.h6
-rw-r--r--chromium/ui/keyboard/keyboard_controller_unittest.cc117
-rw-r--r--chromium/ui/keyboard/keyboard_resources.grd3
-rw-r--r--chromium/ui/keyboard/keyboard_ui_controller.cc5
-rw-r--r--chromium/ui/keyboard/keyboard_ui_handler.cc88
-rw-r--r--chromium/ui/keyboard/keyboard_ui_handler.h12
-rw-r--r--chromium/ui/keyboard/keyboard_util.cc80
-rw-r--r--chromium/ui/keyboard/keyboard_util.h15
-rw-r--r--chromium/ui/keyboard/resources/OWNERS1
-rw-r--r--chromium/ui/keyboard/resources/api_adapter.js21
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-altkey-data.html19
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-key-base.html59
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-key-codes.html180
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-key-sequence.html24
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-key.html69
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-keyboard.html173
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-keyset.html9
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-row.html7
-rw-r--r--chromium/ui/keyboard/resources/elements/kb-shift-key.html186
-rw-r--r--chromium/ui/keyboard/resources/index.html16
-rw-r--r--chromium/ui/keyboard/resources/layouts/dvorak.html38
-rw-r--r--chromium/ui/keyboard/resources/layouts/numeric.html28
-rw-r--r--chromium/ui/keyboard/resources/layouts/qwerty.html52
-rw-r--r--chromium/ui/keyboard/resources/layouts/symbol-altkeys.js13
-rw-r--r--chromium/ui/keyboard/resources/layouts/webui_qwerty.html16
-rw-r--r--chromium/ui/keyboard/resources/main.css46
-rw-r--r--chromium/ui/keyboard/resources/manifest.json2
-rw-r--r--chromium/ui/keyboard/resources/webui/api_adapter.js75
-rw-r--r--chromium/ui/keyboard/resources/webui/main.css10
-rw-r--r--chromium/ui/keyboard/resources/webui_index.html3
-rw-r--r--chromium/ui/linux_ui/linux_ui_export.h36
-rw-r--r--chromium/ui/message_center/cocoa/notification_controller.h11
-rw-r--r--chromium/ui/message_center/cocoa/notification_controller.mm233
-rw-r--r--chromium/ui/message_center/cocoa/notification_controller_unittest.mm40
-rw-r--r--chromium/ui/message_center/cocoa/popup_collection_unittest.mm23
-rw-r--r--chromium/ui/message_center/cocoa/popup_controller_unittest.mm2
-rw-r--r--chromium/ui/message_center/cocoa/tray_controller.mm2
-rw-r--r--chromium/ui/message_center/cocoa/tray_view_controller.h6
-rw-r--r--chromium/ui/message_center/cocoa/tray_view_controller.mm19
-rw-r--r--chromium/ui/message_center/cocoa/tray_view_controller_unittest.mm16
-rw-r--r--chromium/ui/message_center/dummy_message_center.cc3
-rw-r--r--chromium/ui/message_center/fake_message_center.cc17
-rw-r--r--chromium/ui/message_center/fake_message_center.h11
-rw-r--r--chromium/ui/message_center/fake_notifier_settings_provider.cc4
-rw-r--r--chromium/ui/message_center/fake_notifier_settings_provider.h3
-rw-r--r--chromium/ui/message_center/message_center.cc5
-rw-r--r--chromium/ui/message_center/message_center.gyp3
-rw-r--r--chromium/ui/message_center/message_center.h47
-rw-r--r--chromium/ui/message_center/message_center_impl.cc232
-rw-r--r--chromium/ui/message_center/message_center_impl.h27
-rw-r--r--chromium/ui/message_center/message_center_impl_unittest.cc345
-rw-r--r--chromium/ui/message_center/message_center_observer.h10
-rw-r--r--chromium/ui/message_center/message_center_style.cc6
-rw-r--r--chromium/ui/message_center/message_center_style.h11
-rw-r--r--chromium/ui/message_center/message_center_tray.cc95
-rw-r--r--chromium/ui/message_center/message_center_tray.h19
-rw-r--r--chromium/ui/message_center/message_center_tray_unittest.cc11
-rw-r--r--chromium/ui/message_center/message_center_types.h21
-rw-r--r--chromium/ui/message_center/notification.cc40
-rw-r--r--chromium/ui/message_center/notification.h30
-rw-r--r--chromium/ui/message_center/notification_blocker.cc31
-rw-r--r--chromium/ui/message_center/notification_blocker.h51
-rw-r--r--chromium/ui/message_center/notification_list.cc123
-rw-r--r--chromium/ui/message_center/notification_list.h32
-rw-r--r--chromium/ui/message_center/notification_list_unittest.cc193
-rw-r--r--chromium/ui/message_center/notifier_settings.cc38
-rw-r--r--chromium/ui/message_center/notifier_settings.h22
-rw-r--r--chromium/ui/message_center/views/bounded_label.cc18
-rw-r--r--chromium/ui/message_center/views/bounded_label.h4
-rw-r--r--chromium/ui/message_center/views/bounded_label_unittest.cc17
-rw-r--r--chromium/ui/message_center/views/message_center_view.cc38
-rw-r--r--chromium/ui/message_center/views/message_center_view.h18
-rw-r--r--chromium/ui/message_center/views/message_center_view_unittest.cc2
-rw-r--r--chromium/ui/message_center/views/message_popup_collection.cc34
-rw-r--r--chromium/ui/message_center/views/message_popup_collection_unittest.cc29
-rw-r--r--chromium/ui/message_center/views/message_view.cc32
-rw-r--r--chromium/ui/message_center/views/notification_view.cc46
-rw-r--r--chromium/ui/message_center/views/notification_view.h1
-rw-r--r--chromium/ui/message_center/views/notifier_settings_view.cc5
-rw-r--r--chromium/ui/message_center/views/toast_contents_view.cc36
-rw-r--r--chromium/ui/message_center/views/toast_contents_view.h22
-rw-r--r--chromium/ui/metro_viewer/metro_viewer_messages.h12
-rw-r--r--chromium/ui/native_theme/common_theme.cc22
-rw-r--r--chromium/ui/native_theme/common_theme.h7
-rw-r--r--chromium/ui/native_theme/native_theme.cc24
-rw-r--r--chromium/ui/native_theme/native_theme.h9
-rw-r--r--chromium/ui/native_theme/native_theme_win.cc4
-rw-r--r--chromium/ui/resources/default_100_percent/common/drag_tip_copy.pngbin0 -> 1039 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/drag_tip_link.pngbin0 -> 517 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/drag_tip_move.pngbin0 -> 382 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/drag_tip_nodrop.pngbin0 -> 1256 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/notification_clear_all_disabled.pngbin125 -> 124 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/alias_big.pngbin0 -> 2358 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/cell_big.pngbin0 -> 509 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/context_menu_big.pngbin0 -> 1325 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/copy_big.pngbin0 -> 2413 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/crosshair_big.pngbin0 -> 164 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/fleur_big.pngbin0 -> 1765 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/hand2_big.pngbin0 -> 1384 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/hand3_big.pngbin0 -> 1401 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/help_big.pngbin0 -> 1768 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/left_ptr_big.pngbin0 -> 1084 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/move_big.pngbin0 -> 1166 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/nodrop_big.pngbin0 -> 2636 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/sb_h_double_arrow_big.pngbin0 -> 828 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/sb_v_double_arrow_big.pngbin0 -> 800 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/top_left_corner_big.pngbin0 -> 1000 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/top_right_corner_big.pngbin0 -> 991 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/xterm_big.pngbin0 -> 488 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/xterm_horiz_big.pngbin0 -> 495 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/zoom_in_big.pngbin0 -> 2287 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/common/pointers/zoom_out_big.pngbin0 -> 2243 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_attention.pngbin1163 -> 181 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_attention_pressed.pngbin1123 -> 157 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention.pngbin1315 -> 273 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention_pressed.pngbin1183 -> 209 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty.pngbin1297 -> 240 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty_pressed.pngbin1200 -> 201 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_empty.pngbin1153 -> 170 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/mac/notification_tray_empty_pressed.pngbin1128 -> 157 bytes
-rw-r--r--chromium/ui/resources/default_100_percent/win/app_list_user_indicator.pngbin0 -> 143 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/common/drag_tip_copy.pngbin0 -> 3285 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/common/drag_tip_link.pngbin0 -> 1187 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/common/drag_tip_move.pngbin0 -> 749 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/common/drag_tip_nodrop.pngbin0 -> 4101 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_attention.pngbin1332 -> 299 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_attention_pressed.pngbin1262 -> 242 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention.pngbin1563 -> 462 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention_pressed.pngbin1398 -> 361 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty.pngbin1542 -> 385 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty_pressed.pngbin1401 -> 335 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_empty.pngbin1309 -> 258 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/mac/notification_tray_empty_pressed.pngbin1271 -> 243 bytes
-rw-r--r--chromium/ui/resources/default_200_percent/win/app_list_user_indicator.pngbin0 -> 465 bytes
-rw-r--r--chromium/ui/resources/resource_check/resource_scale_factors.py24
-rw-r--r--chromium/ui/resources/ui_resources.grd65
-rw-r--r--chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.cc24
-rw-r--r--chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.h21
-rw-r--r--chromium/ui/shell_dialogs/select_file_dialog_win.cc12
-rw-r--r--chromium/ui/snapshot/OWNERS5
-rw-r--r--chromium/ui/snapshot/snapshot_android.cc18
-rw-r--r--chromium/ui/surface/accelerated_surface_win.cc30
-rw-r--r--chromium/ui/surface/accelerated_surface_win.h8
-rw-r--r--chromium/ui/surface/transport_dib.h5
-rw-r--r--chromium/ui/surface/transport_dib_gtk.cc2
-rw-r--r--chromium/ui/ui.gyp230
-rw-r--r--chromium/ui/ui_unittests.gypi41
-rw-r--r--chromium/ui/ui_unittests.isolate1
-rw-r--r--chromium/ui/views/accessibility/native_view_accessibility.cc4
-rw-r--r--chromium/ui/views/accessibility/native_view_accessibility.h15
-rw-r--r--chromium/ui/views/accessibility/native_view_accessibility_win.cc229
-rw-r--r--chromium/ui/views/accessibility/native_view_accessibility_win.h16
-rw-r--r--chromium/ui/views/accessibility/native_view_accessibility_win_unittest.cc59
-rw-r--r--chromium/ui/views/animation/bounds_animator.cc12
-rw-r--r--chromium/ui/views/animation/bounds_animator.h52
-rw-r--r--chromium/ui/views/animation/bounds_animator_unittest.cc12
-rw-r--r--chromium/ui/views/animation/scroll_animator.cc10
-rw-r--r--chromium/ui/views/animation/scroll_animator.h16
-rw-r--r--chromium/ui/views/bubble/bubble_border.cc64
-rw-r--r--chromium/ui/views/bubble/bubble_delegate.cc72
-rw-r--r--chromium/ui/views/bubble/bubble_delegate.h26
-rw-r--r--chromium/ui/views/bubble/bubble_frame_view.cc32
-rw-r--r--chromium/ui/views/bubble/bubble_frame_view.h4
-rw-r--r--chromium/ui/views/bubble/tray_bubble_view.cc71
-rw-r--r--chromium/ui/views/bubble/tray_bubble_view.h16
-rw-r--r--chromium/ui/views/color_chooser/color_chooser_view.cc4
-rw-r--r--chromium/ui/views/controls/button/blue_button.cc12
-rw-r--r--chromium/ui/views/controls/button/blue_button.h3
-rw-r--r--chromium/ui/views/controls/button/custom_button.cc12
-rw-r--r--chromium/ui/views/controls/button/custom_button.h14
-rw-r--r--chromium/ui/views/controls/button/image_button.cc8
-rw-r--r--chromium/ui/views/controls/button/image_button.h3
-rw-r--r--chromium/ui/views/controls/button/label_button.cc19
-rw-r--r--chromium/ui/views/controls/button/label_button.h8
-rw-r--r--chromium/ui/views/controls/button/label_button_border.cc24
-rw-r--r--chromium/ui/views/controls/button/menu_button.cc10
-rw-r--r--chromium/ui/views/controls/button/menu_button.h4
-rw-r--r--chromium/ui/views/controls/button/text_button.cc6
-rw-r--r--chromium/ui/views/controls/button/text_button.h4
-rw-r--r--chromium/ui/views/controls/combobox/combobox.cc396
-rw-r--r--chromium/ui/views/controls/combobox/combobox.h97
-rw-r--r--chromium/ui/views/controls/combobox/combobox_unittest.cc310
-rw-r--r--chromium/ui/views/controls/combobox/native_combobox_views.cc435
-rw-r--r--chromium/ui/views/controls/combobox/native_combobox_views.h115
-rw-r--r--chromium/ui/views/controls/combobox/native_combobox_views_unittest.cc194
-rw-r--r--chromium/ui/views/controls/combobox/native_combobox_win.cc218
-rw-r--r--chromium/ui/views/controls/combobox/native_combobox_win.h58
-rw-r--r--chromium/ui/views/controls/combobox/native_combobox_wrapper.h76
-rw-r--r--chromium/ui/views/controls/glow_hover_controller.cc10
-rw-r--r--chromium/ui/views/controls/glow_hover_controller.h16
-rw-r--r--chromium/ui/views/controls/label.cc67
-rw-r--r--chromium/ui/views/controls/label.h22
-rw-r--r--chromium/ui/views/controls/label_unittest.cc16
-rw-r--r--chromium/ui/views/controls/link.cc4
-rw-r--r--chromium/ui/views/controls/menu/menu_config.cc37
-rw-r--r--chromium/ui/views/controls/menu/menu_config.h3
-rw-r--r--chromium/ui/views/controls/menu/menu_controller.cc258
-rw-r--r--chromium/ui/views/controls/menu/menu_controller.h26
-rw-r--r--chromium/ui/views/controls/menu/menu_host.cc5
-rw-r--r--chromium/ui/views/controls/menu/menu_host.h1
-rw-r--r--chromium/ui/views/controls/menu/menu_item_view.cc62
-rw-r--r--chromium/ui/views/controls/menu/menu_item_view.h8
-rw-r--r--chromium/ui/views/controls/menu/menu_win.cc6
-rw-r--r--chromium/ui/views/controls/menu/native_menu_win.cc10
-rw-r--r--chromium/ui/views/controls/menu/submenu_view.cc2
-rw-r--r--chromium/ui/views/controls/native/native_view_host.cc12
-rw-r--r--chromium/ui/views/controls/native/native_view_host.h4
-rw-r--r--chromium/ui/views/controls/native/native_view_host_aura.cc4
-rw-r--r--chromium/ui/views/controls/native/native_view_host_unittest.cc45
-rw-r--r--chromium/ui/views/controls/native/native_view_host_win.cc6
-rw-r--r--chromium/ui/views/controls/native_control.cc10
-rw-r--r--chromium/ui/views/controls/native_control.h2
-rw-r--r--chromium/ui/views/controls/native_control_win.cc6
-rw-r--r--chromium/ui/views/controls/prefix_selector.cc28
-rw-r--r--chromium/ui/views/controls/prefix_selector.h12
-rw-r--r--chromium/ui/views/controls/scroll_view.cc2
-rw-r--r--chromium/ui/views/controls/scrollbar/base_scroll_bar.cc4
-rw-r--r--chromium/ui/views/controls/scrollbar/bitmap_scroll_bar.cc2
-rw-r--r--chromium/ui/views/controls/scrollbar/native_scroll_bar.cc2
-rw-r--r--chromium/ui/views/controls/scrollbar/native_scroll_bar_views.cc2
-rw-r--r--chromium/ui/views/controls/scrollbar/overlay_scroll_bar.cc8
-rw-r--r--chromium/ui/views/controls/scrollbar/overlay_scroll_bar.h4
-rw-r--r--chromium/ui/views/controls/slider.cc8
-rw-r--r--chromium/ui/views/controls/slider.h13
-rw-r--r--chromium/ui/views/controls/styled_label.cc16
-rw-r--r--chromium/ui/views/controls/styled_label.h18
-rw-r--r--chromium/ui/views/controls/styled_label_listener.h4
-rw-r--r--chromium/ui/views/controls/styled_label_unittest.cc26
-rw-r--r--chromium/ui/views/controls/tabbed_pane/tabbed_pane.cc4
-rw-r--r--chromium/ui/views/controls/table/table_view.cc2
-rw-r--r--chromium/ui/views/controls/table/table_view_observer.h2
-rw-r--r--chromium/ui/views/controls/textfield/native_textfield_views.cc62
-rw-r--r--chromium/ui/views/controls/textfield/native_textfield_views.h25
-rw-r--r--chromium/ui/views/controls/textfield/native_textfield_views_unittest.cc101
-rw-r--r--chromium/ui/views/controls/textfield/native_textfield_win.cc27
-rw-r--r--chromium/ui/views/controls/textfield/native_textfield_win.h12
-rw-r--r--chromium/ui/views/controls/textfield/native_textfield_wrapper.h14
-rw-r--r--chromium/ui/views/controls/textfield/textfield.cc25
-rw-r--r--chromium/ui/views/controls/textfield/textfield.h16
-rw-r--r--chromium/ui/views/controls/textfield/textfield_controller.cc2
-rw-r--r--chromium/ui/views/controls/textfield/textfield_views_model.cc52
-rw-r--r--chromium/ui/views/controls/textfield/textfield_views_model.h15
-rw-r--r--chromium/ui/views/controls/textfield/textfield_views_model_unittest.cc124
-rw-r--r--chromium/ui/views/controls/tree/tree_view.cc4
-rw-r--r--chromium/ui/views/controls/tree/tree_view_controller.h2
-rw-r--r--chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_aurax11.cc2
-rw-r--r--chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_win.cc2
-rw-r--r--chromium/ui/views/controls/webview/web_dialog_view.cc4
-rw-r--r--chromium/ui/views/controls/webview/webview.cc176
-rw-r--r--chromium/ui/views/controls/webview/webview.h34
-rw-r--r--chromium/ui/views/corewm/capture_controller.cc139
-rw-r--r--chromium/ui/views/corewm/capture_controller.h87
-rw-r--r--chromium/ui/views/corewm/capture_controller_unittest.cc169
-rw-r--r--chromium/ui/views/corewm/compound_event_filter.cc9
-rw-r--r--chromium/ui/views/corewm/compound_event_filter.h4
-rw-r--r--chromium/ui/views/corewm/compound_event_filter_unittest.cc4
-rw-r--r--chromium/ui/views/corewm/corewm_switches.cc19
-rw-r--r--chromium/ui/views/corewm/corewm_switches.h8
-rw-r--r--chromium/ui/views/corewm/cursor_manager.cc25
-rw-r--r--chromium/ui/views/corewm/cursor_manager.h7
-rw-r--r--chromium/ui/views/corewm/cursor_manager_unittest.cc19
-rw-r--r--chromium/ui/views/corewm/desktop_capture_controller_unittest.cc176
-rw-r--r--chromium/ui/views/corewm/focus_controller.cc9
-rw-r--r--chromium/ui/views/corewm/focus_controller_unittest.cc27
-rw-r--r--chromium/ui/views/corewm/input_method_event_filter.cc2
-rw-r--r--chromium/ui/views/corewm/input_method_event_filter.h2
-rw-r--r--chromium/ui/views/corewm/native_cursor_manager.h5
-rw-r--r--chromium/ui/views/corewm/native_cursor_manager_delegate.h3
-rw-r--r--chromium/ui/views/corewm/tooltip_controller.cc44
-rw-r--r--chromium/ui/views/corewm/tooltip_controller.h2
-rw-r--r--chromium/ui/views/corewm/tooltip_controller_unittest.cc139
-rw-r--r--chromium/ui/views/corewm/window_animations.cc4
-rw-r--r--chromium/ui/views/corewm/window_animations_unittest.cc2
-rw-r--r--chromium/ui/views/corewm/window_modality_controller.cc2
-rw-r--r--chromium/ui/views/corewm/window_modality_controller.h2
-rw-r--r--chromium/ui/views/event_utils.h25
-rw-r--r--chromium/ui/views/event_utils_aura.cc51
-rw-r--r--chromium/ui/views/event_utils_win.cc59
-rw-r--r--chromium/ui/views/examples/content_client/examples_browser_main_parts.cc2
-rw-r--r--chromium/ui/views/examples/example_base.h2
-rw-r--r--chromium/ui/views/examples/multiline_example.cc71
-rw-r--r--chromium/ui/views/examples/multiline_example.h12
-rw-r--r--chromium/ui/views/examples/textfield_example.cc8
-rw-r--r--chromium/ui/views/focus/accelerator_handler.h8
-rw-r--r--chromium/ui/views/focus/accelerator_handler_win.cc6
-rw-r--r--chromium/ui/views/focus/focus_manager.cc20
-rw-r--r--chromium/ui/views/focus/focus_manager.h12
-rw-r--r--chromium/ui/views/focus/focus_manager_unittest.cc83
-rw-r--r--chromium/ui/views/focus/focus_manager_unittest_win.cc2
-rw-r--r--chromium/ui/views/ime/input_method_base.cc2
-rw-r--r--chromium/ui/views/ime/input_method_bridge.cc20
-rw-r--r--chromium/ui/views/ime/input_method_bridge.h14
-rw-r--r--chromium/ui/views/ime/input_method_bridge_unittest.cc40
-rw-r--r--chromium/ui/views/ime/mock_input_method.cc4
-rw-r--r--chromium/ui/views/layout/grid_layout.cc3
-rw-r--r--chromium/ui/views/linux_ui/OWNERS (renamed from chromium/ui/linux_ui/OWNERS)0
-rw-r--r--chromium/ui/views/linux_ui/linux_ui.cc (renamed from chromium/ui/linux_ui/linux_ui.cc)12
-rw-r--r--chromium/ui/views/linux_ui/linux_ui.gyp (renamed from chromium/ui/linux_ui/linux_ui.gyp)2
-rw-r--r--chromium/ui/views/linux_ui/linux_ui.h (renamed from chromium/ui/linux_ui/linux_ui.h)37
-rw-r--r--chromium/ui/views/linux_ui/status_icon_linux.cc (renamed from chromium/ui/linux_ui/status_icon_linux.cc)9
-rw-r--r--chromium/ui/views/linux_ui/status_icon_linux.h (renamed from chromium/ui/linux_ui/status_icon_linux.h)19
-rw-r--r--chromium/ui/views/linux_ui/window_button_order_observer.h29
-rw-r--r--chromium/ui/views/mouse_constants.cc12
-rw-r--r--chromium/ui/views/mouse_constants.h25
-rw-r--r--chromium/ui/views/mouse_watcher.cc4
-rw-r--r--chromium/ui/views/mouse_watcher_view_host.cc2
-rw-r--r--chromium/ui/views/native_theme_delegate.h2
-rw-r--r--chromium/ui/views/run_all_unittests.cc8
-rw-r--r--chromium/ui/views/touchui/touch_selection_controller_impl.cc6
-rw-r--r--chromium/ui/views/touchui/touch_selection_controller_impl_unittest.cc40
-rw-r--r--chromium/ui/views/view.cc65
-rw-r--r--chromium/ui/views/view.h30
-rw-r--r--chromium/ui/views/view_unittest.cc172
-rw-r--r--chromium/ui/views/views.gyp67
-rw-r--r--chromium/ui/views/widget/aero_tooltip_manager.cc8
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_activation_client.cc190
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_activation_client.h90
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_capture_client.cc88
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_capture_client.h44
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_capture_client_unittest.cc231
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_cursor_loader_updater_aurax11.cc8
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.cc13
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.h1
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_drop_target_win.cc9
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.cc29
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.h46
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_focus_rules.cc10
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_focus_rules.h6
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.cc5
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.h3
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc334
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.h28
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura_unittest.cc27
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_root_window_host.h5
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_root_window_host_ozone.cc22
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.cc121
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.h15
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.cc145
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.h15
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_screen_ozone.cc15
-rw-r--r--chromium/ui/views/widget/desktop_aura/desktop_screen_x11.cc28
-rw-r--r--chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.cc37
-rw-r--r--chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.h43
-rw-r--r--chromium/ui/views/widget/desktop_aura/x11_desktop_handler.cc9
-rw-r--r--chromium/ui/views/widget/desktop_aura/x11_desktop_handler.h3
-rw-r--r--chromium/ui/views/widget/desktop_aura/x11_desktop_window_move_client.cc4
-rw-r--r--chromium/ui/views/widget/desktop_aura/x11_whole_screen_move_loop.cc16
-rw-r--r--chromium/ui/views/widget/desktop_aura/x11_window_event_filter.cc15
-rw-r--r--chromium/ui/views/widget/desktop_aura/x11_window_event_filter.h11
-rw-r--r--chromium/ui/views/widget/drop_helper.cc2
-rw-r--r--chromium/ui/views/widget/monitor_win.cc3
-rw-r--r--chromium/ui/views/widget/native_widget_aura.cc170
-rw-r--r--chromium/ui/views/widget/native_widget_aura.h16
-rw-r--r--chromium/ui/views/widget/native_widget_aura_unittest.cc2
-rw-r--r--chromium/ui/views/widget/native_widget_delegate.h5
-rw-r--r--chromium/ui/views/widget/native_widget_private.h3
-rw-r--r--chromium/ui/views/widget/native_widget_win.cc88
-rw-r--r--chromium/ui/views/widget/native_widget_win.h6
-rw-r--r--chromium/ui/views/widget/root_view.cc38
-rw-r--r--chromium/ui/views/widget/root_view.h12
-rw-r--r--chromium/ui/views/widget/root_view_test_helper.h33
-rw-r--r--chromium/ui/views/widget/root_view_unittest.cc55
-rw-r--r--chromium/ui/views/widget/tooltip_manager.cc15
-rw-r--r--chromium/ui/views/widget/tooltip_manager.h4
-rw-r--r--chromium/ui/views/widget/tooltip_manager_aura.cc5
-rw-r--r--chromium/ui/views/widget/tooltip_manager_win.cc26
-rw-r--r--chromium/ui/views/widget/widget.cc104
-rw-r--r--chromium/ui/views/widget/widget.h65
-rw-r--r--chromium/ui/views/widget/widget_delegate.cc4
-rw-r--r--chromium/ui/views/widget/widget_delegate.h5
-rw-r--r--chromium/ui/views/widget/widget_interactive_uitest.cc445
-rw-r--r--chromium/ui/views/widget/widget_observer.h2
-rw-r--r--chromium/ui/views/widget/widget_unittest.cc884
-rw-r--r--chromium/ui/views/win/fullscreen_handler.cc5
-rw-r--r--chromium/ui/views/win/hwnd_message_handler.cc172
-rw-r--r--chromium/ui/views/win/hwnd_message_handler.h40
-rw-r--r--chromium/ui/views/win/hwnd_message_handler_delegate.h9
-rw-r--r--chromium/ui/views/window/dialog_client_view.cc15
-rw-r--r--chromium/ui/views/window/dialog_client_view.h3
-rw-r--r--chromium/ui/views/window/dialog_client_view_unittest.cc60
-rw-r--r--chromium/ui/views/window/dialog_delegate.cc15
-rw-r--r--chromium/ui/views/window/frame_buttons.h19
-rw-r--r--chromium/ui/webui/resources/css/apps/common.css169
-rw-r--r--chromium/ui/webui/resources/css/apps/topbutton_bar.css61
-rw-r--r--chromium/ui/webui/resources/css/overlay.css2
-rw-r--r--chromium/ui/webui/resources/css/tree.css2
-rw-r--r--chromium/ui/webui/resources/css/widgets.css2
-rw-r--r--chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close.pngbin0 -> 240 bytes
-rw-r--r--chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_hover.pngbin0 -> 311 bytes
-rw-r--r--chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_pressed.pngbin0 -> 295 bytes
-rw-r--r--chromium/ui/webui/resources/images/apps/button_butter_bar_close.pngbin0 -> 172 bytes
-rw-r--r--chromium/ui/webui/resources/images/apps/button_butter_bar_close_hover.pngbin0 -> 182 bytes
-rw-r--r--chromium/ui/webui/resources/images/apps/button_butter_bar_close_pressed.pngbin0 -> 198 bytes
-rw-r--r--chromium/ui/webui/resources/images/guest_icon_standalone.pngbin1862 -> 0 bytes
-rw-r--r--chromium/ui/webui/resources/images/question_mark.pngbin0 -> 327 bytes
-rw-r--r--chromium/ui/webui/resources/js/cr.js19
-rw-r--r--chromium/ui/webui/resources/js/cr/event_target.js5
-rw-r--r--chromium/ui/webui/resources/js/cr/ui/context_menu_button.js14
-rw-r--r--chromium/ui/webui/resources/js/cr/ui/list.js4
-rw-r--r--chromium/ui/webui/resources/js/util.js20
-rw-r--r--chromium/ui/webui/resources/js/webui_resource_test.js204
-rw-r--r--chromium/ui/webui/resources/webui_resources.grd164
-rw-r--r--chromium/ui/webui/web_ui_util.cc6
1087 files changed, 19086 insertions, 15631 deletions
diff --git a/chromium/ui/OWNERS b/chromium/ui/OWNERS
index b88f27bdc51..585112d131a 100644
--- a/chromium/ui/OWNERS
+++ b/chromium/ui/OWNERS
@@ -4,6 +4,12 @@ sky@chromium.org
# Mac stuff
thakis@chromium.org
+# Android
+per-file *android*=bulach@chromium.org
+per-file *android*=tedchoc@chromium.org
+per-file *android*=yfriedman@chromium.org
+per-file *android*=newt@chromium.org
+
per-file *.isolate=csharp@chromium.org
per-file *.isolate=maruel@chromium.org
diff --git a/chromium/ui/android/java/WindowOpenDisposition.template b/chromium/ui/android/java/WindowOpenDisposition.template
deleted file mode 100644
index 91be4d9536f..00000000000
--- a/chromium/ui/android/java/WindowOpenDisposition.template
+++ /dev/null
@@ -1,11 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-public class WindowOpenDisposition {
-#define WINDOW_OPEN_DISPOSITION(label, value) public static final int label = value;
-#include "ui/base/window_open_disposition_list.h"
-#undef WINDOW_OPEN_DISPOSITION
-} \ No newline at end of file
diff --git a/chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_down.9.png b/chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_down.9.png
deleted file mode 100644
index 62478fcf66c..00000000000
--- a/chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_down.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_up.9.png b/chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_up.9.png
deleted file mode 100644
index 290f5260677..00000000000
--- a/chromium/ui/android/java/res/drawable-hdpi/autofill_popup_background_up.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-hdpi/color_picker_advanced_select_handle.png b/chromium/ui/android/java/res/drawable-hdpi/color_picker_advanced_select_handle.png
deleted file mode 100644
index be2dc681114..00000000000
--- a/chromium/ui/android/java/res/drawable-hdpi/color_picker_advanced_select_handle.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_down.9.png b/chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_down.9.png
deleted file mode 100644
index 0fb3b87b8fd..00000000000
--- a/chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_down.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_up.9.png b/chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_up.9.png
deleted file mode 100644
index 4ab1786471b..00000000000
--- a/chromium/ui/android/java/res/drawable-ldpi/autofill_popup_background_up.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-nodpi/divider_horizontal_bright.9.png b/chromium/ui/android/java/res/drawable-nodpi/divider_horizontal_bright.9.png
deleted file mode 100644
index 24f2a3f1fa4..00000000000
--- a/chromium/ui/android/java/res/drawable-nodpi/divider_horizontal_bright.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_down.9.png b/chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_down.9.png
deleted file mode 100644
index ab4d02cd382..00000000000
--- a/chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_down.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_up.9.png b/chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_up.9.png
deleted file mode 100644
index cf3f9e65264..00000000000
--- a/chromium/ui/android/java/res/drawable-xhdpi/autofill_popup_background_up.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable-xhdpi/color_picker_advanced_select_handle.png b/chromium/ui/android/java/res/drawable-xhdpi/color_picker_advanced_select_handle.png
deleted file mode 100644
index 058b30b731b..00000000000
--- a/chromium/ui/android/java/res/drawable-xhdpi/color_picker_advanced_select_handle.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable/autofill_popup_background.xml b/chromium/ui/android/java/res/drawable/autofill_popup_background.xml
deleted file mode 100644
index 0f8d38babdf..00000000000
--- a/chromium/ui/android/java/res/drawable/autofill_popup_background.xml
+++ /dev/null
@@ -1,13 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-
-<selector xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:state_above_anchor="true"
- android:drawable="@drawable/autofill_popup_background_up" />
- <item android:drawable="@drawable/autofill_popup_background_down" />
-</selector> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/drawable/autofill_popup_background_down.9.png b/chromium/ui/android/java/res/drawable/autofill_popup_background_down.9.png
deleted file mode 100644
index 2022fd74388..00000000000
--- a/chromium/ui/android/java/res/drawable/autofill_popup_background_down.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable/autofill_popup_background_up.9.png b/chromium/ui/android/java/res/drawable/autofill_popup_background_up.9.png
deleted file mode 100644
index 62fc5a6bf98..00000000000
--- a/chromium/ui/android/java/res/drawable/autofill_popup_background_up.9.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable/color_picker_advanced_select_handle.png b/chromium/ui/android/java/res/drawable/color_picker_advanced_select_handle.png
deleted file mode 100644
index 3cdca907c95..00000000000
--- a/chromium/ui/android/java/res/drawable/color_picker_advanced_select_handle.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/android/java/res/drawable/color_picker_border.xml b/chromium/ui/android/java/res/drawable/color_picker_border.xml
deleted file mode 100644
index b48be9bb41c..00000000000
--- a/chromium/ui/android/java/res/drawable/color_picker_border.xml
+++ /dev/null
@@ -1,10 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-<shape xmlns:android="http://schemas.android.com/apk/res/android"
- android:shape="rectangle">
- <solid android:color="#00000000"/>
- <stroke android:width="1px" android:color="@color/color_picker_border_color" />
-</shape> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/layout/autofill_text.xml b/chromium/ui/android/java/res/layout/autofill_text.xml
deleted file mode 100644
index 4a69862a916..00000000000
--- a/chromium/ui/android/java/res/layout/autofill_text.xml
+++ /dev/null
@@ -1,34 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-
-<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:id="@+id/autofill_menu_text"
- android:layout_width="fill_parent"
- android:layout_height="44dp"
- android:minHeight="44dp"
- android:orientation="vertical"
- android:gravity="center_vertical">
- <TextView android:id="@+id/autofill_label"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:ellipsize="end"
- android:singleLine="true"
- android:textSize="18sp"
- android:includeFontPadding="false"
- android:layout_marginStart="10dp"
- android:layout_marginEnd="10dp"/>
- <TextView android:id="@+id/autofill_sublabel"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:textSize="14sp"
- android:textColor="#8b8b8b"
- android:ellipsize="end"
- android:singleLine="true"
- android:includeFontPadding="false"
- android:layout_marginStart="10dp"
- android:layout_marginEnd="10dp"/>
-</LinearLayout>
diff --git a/chromium/ui/android/java/res/layout/color_picker_advanced_component.xml b/chromium/ui/android/java/res/layout/color_picker_advanced_component.xml
deleted file mode 100644
index a51c055b1b1..00000000000
--- a/chromium/ui/android/java/res/layout/color_picker_advanced_component.xml
+++ /dev/null
@@ -1,46 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
- Copyright 2013 The Chromium Authors. All rights reserved.
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content">
-
- <TextView
- android:id="@+id/text"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_marginStart="@dimen/color_picker_gradient_margin"
- android:layout_marginEnd="@dimen/color_picker_gradient_margin"
- android:textAppearance="@android:style/TextAppearance.Medium"
- android:textIsSelectable="false" />
-
- <FrameLayout
- android:id="@+id/gradient_border"
- android:layout_width="match_parent"
- android:layout_height="50dp"
- android:layout_below="@id/text"
- android:layout_marginStart="@dimen/color_picker_gradient_margin"
- android:layout_marginEnd="@dimen/color_picker_gradient_margin"
- android:layout_marginTop="3dp"
- android:background="@drawable/color_picker_border"
- android:padding="1dp" >
-
- <View
- android:id="@+id/gradient"
- android:layout_width="match_parent"
- android:layout_height="match_parent" />
- </FrameLayout>
-
- <SeekBar
- android:id="@+id/seek_bar"
- android:layout_width="match_parent"
- android:layout_height="75dp"
- android:layout_below="@id/text"
- android:progressDrawable="@android:color/transparent"
- android:thumb="@drawable/color_picker_advanced_select_handle"
- android:translationY="25dp" />
-
-</RelativeLayout> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/layout/color_picker_dialog_content.xml b/chromium/ui/android/java/res/layout/color_picker_dialog_content.xml
deleted file mode 100644
index 8aa4dbaeffd..00000000000
--- a/chromium/ui/android/java/res/layout/color_picker_dialog_content.xml
+++ /dev/null
@@ -1,56 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
- Copyright 2013 The Chromium Authors. All rights reserved.
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="match_parent">
-
- <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:orientation="vertical"
- android:padding="15dp">
-
- <org.chromium.ui.ColorPickerAdvanced
- android:id="@+id/color_picker_advanced"
- android:layout_width="match_parent"
- android:layout_height="wrap_content" />
-
- <FrameLayout
- android:id="@+id/color_picker_simple_border"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:background="@drawable/color_picker_border"
- android:paddingStart="1px"
- android:paddingEnd="1px"
- android:paddingTop="1px">
-
- <org.chromium.ui.ColorPickerSimple
- android:id="@+id/color_picker_simple"
- android:layout_width="match_parent"
- android:layout_height="100dp"/>
- </FrameLayout>
-
- <FrameLayout
- android:id="@+id/more_colors_button_border"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_below="@+id/color_picker_simple_border"
- android:background="@drawable/color_picker_border"
- android:padding="1px">
-
- <org.chromium.ui.ColorPickerMoreButton
- android:id="@+id/more_colors_button"
- style="?android:attr/buttonBarButtonStyle"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:minHeight="48dp"
- android:textAppearance="?android:attr/textAppearanceSmall"
- android:text="@string/color_picker_button_more" />
- </FrameLayout>
-
- </RelativeLayout>
-</ScrollView> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/layout/color_picker_dialog_title.xml b/chromium/ui/android/java/res/layout/color_picker_dialog_title.xml
deleted file mode 100644
index d97cafb9197..00000000000
--- a/chromium/ui/android/java/res/layout/color_picker_dialog_title.xml
+++ /dev/null
@@ -1,41 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-
-<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:paddingBottom="15dp"
- android:paddingStart="20dp"
- android:paddingEnd="20dp"
- android:paddingTop="15dp" >
-
- <TextView
- android:id="@+id/title"
- style="?android:attr/textAppearanceLarge"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_toStartOf="@+id/selected_color_view_border"
- android:layout_centerVertical="true"
- android:textColor="#33B5E5"
- android:ellipsize="end"
- android:singleLine="true" />
-
- <FrameLayout
- android:layout_width="40dp"
- android:layout_height="40dp"
- android:layout_alignParentEnd="true"
- android:id="@+id/selected_color_view_border"
- android:background="@drawable/color_picker_border"
- android:padding="2px">
-
- <View
- android:id="@+id/selected_color_view"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:background="@android:color/black" />
- </FrameLayout>
-
-</RelativeLayout> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/values-v17/styles.xml b/chromium/ui/android/java/res/values-v17/styles.xml
deleted file mode 100644
index 8295ddf644d..00000000000
--- a/chromium/ui/android/java/res/values-v17/styles.xml
+++ /dev/null
@@ -1,13 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-
-<resources>
- <style name="AutofillPopupWindow" parent="@android:style/Widget.ListPopupWindow">
- <item name="android:popupBackground">@drawable/autofill_popup_background</item>
- </style>
-</resources> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/values/colors.xml b/chromium/ui/android/java/res/values/colors.xml
deleted file mode 100644
index be5896dac2d..00000000000
--- a/chromium/ui/android/java/res/values/colors.xml
+++ /dev/null
@@ -1,10 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-<resources>
- <color name="color_picker_border_color">#B0B0B0</color>
-</resources>
-
diff --git a/chromium/ui/android/java/res/values/dimens.xml b/chromium/ui/android/java/res/values/dimens.xml
deleted file mode 100644
index ed863728627..00000000000
--- a/chromium/ui/android/java/res/values/dimens.xml
+++ /dev/null
@@ -1,15 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-<resources>
-
- <!--
- 14.5 = Seekbar thumb width - border width, but it depends on the width
- of the seek bar icon.
- -->
- <dimen name="color_picker_gradient_margin">14.5dp</dimen>
-
-</resources> \ No newline at end of file
diff --git a/chromium/ui/android/java/res/values/strings.xml b/chromium/ui/android/java/res/values/strings.xml
deleted file mode 100644
index 850bcc5c5e6..00000000000
--- a/chromium/ui/android/java/res/values/strings.xml
+++ /dev/null
@@ -1,16 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (c) 2012 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-
-<!-- DO NOT ADD STRINGS HERE.
-
- Android ui strings now live in
- ui/android/java/strings/android_ui_strings.grd
-
- See http://www.chromium.org/developers/design-documents/ui-localization
--->
-
-<resources/>
diff --git a/chromium/ui/android/java/res/values/values.xml b/chromium/ui/android/java/res/values/values.xml
deleted file mode 100644
index 046cf8b15e1..00000000000
--- a/chromium/ui/android/java/res/values/values.xml
+++ /dev/null
@@ -1,11 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright 2013 The Chromium Authors. All rights reserved.
-
- Use of this source code is governed by a BSD-style license that can be
- found in the LICENSE file.
--->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android">
- <!-- AutofillPopup constants -->
- <item type="id" name="autofill_popup_window" />
-</resources> \ No newline at end of file
diff --git a/chromium/ui/android/java/resource_map/OWNERS b/chromium/ui/android/java/resource_map/OWNERS
deleted file mode 100644
index d85278d5ee5..00000000000
--- a/chromium/ui/android/java/resource_map/OWNERS
+++ /dev/null
@@ -1,13 +0,0 @@
-# Changes in this folder are guaranteed to affect the downstream
-# android_webview build. Adding one of the folks from the below list to the
-# review gives us time to prepare a matching change ahead of time so that our
-# downstream build can continue running smoothly.
-set noparent
-
-benm@chromium.org
-boliu@chomium.org
-joth@chromium.org
-mkosiba@chromium.org
-mnaganov@chromium.org
-primiano@chromium.org
-torne@chromium.org
diff --git a/chromium/ui/android/java/resource_map/org/chromium/ui/R.java b/chromium/ui/android/java/resource_map/org/chromium/ui/R.java
deleted file mode 100644
index c722c145b2b..00000000000
--- a/chromium/ui/android/java/resource_map/org/chromium/ui/R.java
+++ /dev/null
@@ -1,59 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-/**
- * Provide Android internal resources to Chrome's ui layer. This allows classes
- * that access resources via org.chromium.ui.R to function properly in webview.
- * In a normal Chrome build, ui resources live in a res folder in the ui layer
- * and the org.chromium.ui.R class is generated at build time based on these
- * resources. In webview, resources live in the Android framework and can't be
- * accessed directly from the ui layer. Instead, we copy resources needed by ui
- * into the Android framework and use this R class to map resources IDs from
- * org.chromium.ui.R to com.android.internal.R.
- */
-public final class R {
- public static final class string {
- public static int low_memory_error;
- public static int opening_file_error;
- public static int color_picker_button_more;
- public static int color_picker_hue;
- public static int color_picker_saturation;
- public static int color_picker_value;
- public static int color_picker_button_set;
- public static int color_picker_button_cancel;
- public static int color_picker_dialog_title;
- }
- public static final class id {
- public static int autofill_label;
- public static int autofill_popup_window;
- public static int autofill_sublabel;
- public static int selected_color_view;
- public static int title;
- public static int more_colors_button;
- public static int color_picker_advanced;
- public static int color_picker_simple;
- public static int more_colors_button_border;
- public static int color_picker_simple_border;
- public static int gradient;
- public static int text;
- public static int seek_bar;
- }
- public static final class layout {
- public static int autofill_text;
- public static int color_picker_dialog_title;
- public static int color_picker_dialog_content;
- public static int color_picker_advanced_component;
- }
- public static final class drawable {
- public static int color_picker_advanced_select_handle;
- }
- public static final class style {
- public static int AutofillPopupWindow;
- }
- public static final class color {
- public static int color_picker_border_color;
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/Clipboard.java b/chromium/ui/android/java/src/org/chromium/ui/Clipboard.java
deleted file mode 100644
index a66fa3d91dd..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/Clipboard.java
+++ /dev/null
@@ -1,111 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import org.chromium.base.CalledByNative;
-import org.chromium.base.JNINamespace;
-
-import android.content.ClipData;
-import android.content.ClipboardManager;
-import android.content.Context;
-import android.text.TextUtils;
-
-/**
- * Simple proxy that provides C++ code with an access pathway to the Android
- * clipboard.
- */
-@JNINamespace("ui")
-public class Clipboard {
- // Necessary for coercing clipboard contents to text if they require
- // access to network resources, etceteras (e.g., URI in clipboard)
- private final Context mContext;
-
- private final ClipboardManager mClipboardManager;
-
- /**
- * Use the factory constructor instead.
- *
- * @param context for accessing the clipboard
- */
- private Clipboard(final Context context) {
- mContext = context;
- mClipboardManager = (ClipboardManager)
- context.getSystemService(Context.CLIPBOARD_SERVICE);
- }
-
- /**
- * Returns a new Clipboard object bound to the specified context.
- *
- * @param context for accessing the clipboard
- * @return the new object
- */
- @CalledByNative
- private static Clipboard create(final Context context) {
- return new Clipboard(context);
- }
-
- /**
- * Emulates the behavior of the now-deprecated
- * {@link android.text.ClipboardManager#getText()} by invoking
- * {@link android.content.ClipData.Item#coerceToText(Context)} on the first
- * item in the clipboard (if any) and returning the result as a string.
- * <p>
- * This is quite different than simply calling {@link Object#toString()} on
- * the clip; consumers of this API should familiarize themselves with the
- * process described in
- * {@link android.content.ClipData.Item#coerceToText(Context)} before using
- * this method.
- *
- * @return a string representation of the first item on the clipboard, if
- * the clipboard currently has an item and coercion of the item into
- * a string is possible; otherwise, <code>null</code>
- */
- @SuppressWarnings("javadoc")
- @CalledByNative
- private String getCoercedText() {
- final ClipData clip = mClipboardManager.getPrimaryClip();
- if (clip != null && clip.getItemCount() > 0) {
- final CharSequence sequence = clip.getItemAt(0).coerceToText(mContext);
- if (sequence != null) {
- return sequence.toString();
- }
- }
- return null;
- }
-
- /**
- * Emulates the behavior of the now-deprecated
- * {@link android.text.ClipboardManager#setText(CharSequence)}, setting the
- * clipboard's current primary clip to a plain-text clip that consists of
- * the specified string.
- *
- * @param text will become the content of the clipboard's primary clip
- */
- @SuppressWarnings("javadoc")
- @CalledByNative
- private void setText(final String text) {
- mClipboardManager.setPrimaryClip(ClipData.newPlainText(null, text));
- }
-
- /**
- * Approximates the behavior of the now-deprecated
- * {@link android.text.ClipboardManager#hasText()}, returning true if and
- * only if the clipboard has a primary clip and that clip contains a plain
- * non-empty text entry (without attempting coercion - URLs and intents
- * will cause this method to return false).
- *
- * @return as described above
- */
- @SuppressWarnings("javadoc")
- @CalledByNative
- private boolean hasPlainText() {
- final ClipData clip = mClipboardManager.getPrimaryClip();
- if (clip != null && clip.getItemCount() > 0) {
- final CharSequence text = clip.getItemAt(0).getText();
- return !TextUtils.isEmpty(text);
- }
- return false;
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvanced.java b/chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvanced.java
deleted file mode 100644
index 91800eaa8f6..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvanced.java
+++ /dev/null
@@ -1,252 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.content.Context;
-import android.graphics.Color;
-import android.util.AttributeSet;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.accessibility.AccessibilityEvent;
-import android.widget.LinearLayout;
-import android.widget.SeekBar;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-
-/**
- * Represents a more advanced way for the user to choose a color, based on selecting each of
- * the Hue, Saturation and Value attributes.
- */
-public class ColorPickerAdvanced extends LinearLayout implements OnSeekBarChangeListener {
- private static final int HUE_SEEK_BAR_MAX = 360;
-
- private static final int HUE_COLOR_COUNT = 7;
-
- private static final int SATURATION_SEEK_BAR_MAX = 100;
-
- private static final int SATURATION_COLOR_COUNT = 2;
-
- private static final int VALUE_SEEK_BAR_MAX = 100;
-
- private static final int VALUE_COLOR_COUNT = 2;
-
- ColorPickerAdvancedComponent mHueDetails;
-
- ColorPickerAdvancedComponent mSaturationDetails;
-
- ColorPickerAdvancedComponent mValueDetails;
-
- private OnColorChangedListener mOnColorChangedListener;
-
- private int mCurrentColor;
-
- private final float[] mCurrentHsvValues = new float[3];
-
- public ColorPickerAdvanced(Context context, AttributeSet attrs) {
- super(context, attrs);
- init();
- }
-
- public ColorPickerAdvanced(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- init();
- }
-
- public ColorPickerAdvanced(Context context) {
- super(context);
- init();
- }
-
- /**
- * Initializes all the views and variables in the advanced view.
- */
- private void init() {
- setOrientation(LinearLayout.VERTICAL);
-
- mHueDetails = createAndAddNewGradient(R.string.color_picker_hue,
- HUE_SEEK_BAR_MAX, this);
- mSaturationDetails = createAndAddNewGradient(R.string.color_picker_saturation,
- SATURATION_SEEK_BAR_MAX, this);
- mValueDetails = createAndAddNewGradient(R.string.color_picker_value,
- VALUE_SEEK_BAR_MAX, this);
-
- refreshGradientComponents();
- }
-
- /**
- * Creates a new GradientDetails object from the parameters provided, initializes it,
- * and adds it to this advanced view.
- *
- * @param textResourceId The text to display for the label.
- * @param seekBarMax The maximum value of the seek bar for the gradient.
- * @param seekBarListener Object listening to when the user changes the seek bar.
- *
- * @return A new GradientDetails object initialized with the given parameters.
- */
- public ColorPickerAdvancedComponent createAndAddNewGradient(int textResourceId,
- int seekBarMax,
- OnSeekBarChangeListener seekBarListener) {
- LayoutInflater inflater = (LayoutInflater) getContext()
- .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- View newComponent = inflater.inflate(R.layout.color_picker_advanced_component, null);
- addView(newComponent);
-
- return new ColorPickerAdvancedComponent(newComponent,
- textResourceId,
- seekBarMax,
- seekBarListener);
- }
-
- /**
- * Sets the listener for when the user changes the color.
- *
- * @param onColorChangedListener The object listening for the change in color.
- */
- public void setListener(OnColorChangedListener onColorChangedListener) {
- mOnColorChangedListener = onColorChangedListener;
- }
-
- /**
- * @return The color the user has currently chosen.
- */
- public int getColor() {
- return mCurrentColor;
- }
-
- /**
- * Sets the color that the user has currently chosen.
- *
- * @param color The currently chosen color.
- */
- public void setColor(int color) {
- mCurrentColor = color;
- Color.colorToHSV(mCurrentColor, mCurrentHsvValues);
- refreshGradientComponents();
- }
-
- /**
- * Notifies the listener, if there is one, of a change in the selected color.
- */
- private void notifyColorChanged() {
- if (mOnColorChangedListener != null) {
- mOnColorChangedListener.onColorChanged(getColor());
- }
- }
-
- /**
- * Callback for when a slider is updated on the advanced view.
- *
- * @param seekBar The color slider that was updated.
- * @param progress The new value of the color slider.
- * @param fromUser Whether it was the user the changed the value, or whether
- * we were setting it up.
- */
- @Override
- public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
- if (fromUser) {
- mCurrentHsvValues[0] = mHueDetails.getValue();
- mCurrentHsvValues[1] = mSaturationDetails.getValue() / 100.0f;
- mCurrentHsvValues[2] = mValueDetails.getValue() / 100.0f;
-
- mCurrentColor = Color.HSVToColor(mCurrentHsvValues);
-
- updateHueGradient();
- updateSaturationGradient();
- updateValueGradient();
-
- notifyColorChanged();
- }
- }
-
- /**
- * Updates only the hue gradient display with the hue value for the
- * currently selected color.
- */
- private void updateHueGradient() {
- float[] tempHsvValues = new float[3];
- tempHsvValues[1] = mCurrentHsvValues[1];
- tempHsvValues[2] = mCurrentHsvValues[2];
-
- int[] newColors = new int[HUE_COLOR_COUNT];
-
- for (int i = 0; i < HUE_COLOR_COUNT; ++i) {
- tempHsvValues[0] = i * 60.0f;
- newColors[i] = Color.HSVToColor(tempHsvValues);
- }
- mHueDetails.setGradientColors(newColors);
- }
-
- /**
- * Updates only the saturation gradient display with the saturation value
- * for the currently selected color.
- */
- private void updateSaturationGradient() {
- float[] tempHsvValues = new float[3];
- tempHsvValues[0] = mCurrentHsvValues[0];
- tempHsvValues[1] = 0.0f;
- tempHsvValues[2] = mCurrentHsvValues[2];
-
- int[] newColors = new int[SATURATION_COLOR_COUNT];
-
- newColors[0] = Color.HSVToColor(tempHsvValues);
-
- tempHsvValues[1] = 1.0f;
- newColors[1] = Color.HSVToColor(tempHsvValues);
- mSaturationDetails.setGradientColors(newColors);
- }
-
- /**
- * Updates only the Value gradient display with the Value amount for
- * the currently selected color.
- */
- private void updateValueGradient() {
- float[] tempHsvValues = new float[3];
- tempHsvValues[0] = mCurrentHsvValues[0];
- tempHsvValues[1] = mCurrentHsvValues[1];
- tempHsvValues[2] = 0.0f;
-
- int[] newColors = new int[VALUE_COLOR_COUNT];
-
- newColors[0] = Color.HSVToColor(tempHsvValues);
-
- tempHsvValues[2] = 1.0f;
- newColors[1] = Color.HSVToColor(tempHsvValues);
- mValueDetails.setGradientColors(newColors);
- }
-
- /**
- * Updates all the gradient displays to show the currently selected color.
- */
- private void refreshGradientComponents() {
- // Round and bound the saturation value.
- int saturationValue = Math.round(mCurrentHsvValues[1] * 100.0f);
- saturationValue = Math.min(saturationValue, SATURATION_SEEK_BAR_MAX);
- saturationValue = Math.max(saturationValue, 0);
-
- // Round and bound the Value amount.
- int valueValue = Math.round(mCurrentHsvValues[2] * 100.0f);
- valueValue = Math.min(valueValue, VALUE_SEEK_BAR_MAX);
- valueValue = Math.max(valueValue, 0);
-
- // Don't need to round the hue value since its possible values match the seek bar
- // range directly.
- mHueDetails.setValue(mCurrentHsvValues[0]);
- mSaturationDetails.setValue(saturationValue);
- mValueDetails.setValue(valueValue);
-
- updateHueGradient();
- updateSaturationGradient();
- updateValueGradient();
- }
-
- @Override
- public void onStartTrackingTouch(SeekBar seekBar) {
- // Do nothing.
- }
-
- @Override
- public void onStopTrackingTouch(SeekBar seekBar) {
- // Do nothing.
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvancedComponent.java b/chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvancedComponent.java
deleted file mode 100644
index 1e679d5fe8f..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerAdvancedComponent.java
+++ /dev/null
@@ -1,94 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.content.Context;
-import android.graphics.drawable.GradientDrawable;
-import android.graphics.drawable.GradientDrawable.Orientation;
-import android.os.Build;
-import android.view.View;
-import android.widget.SeekBar;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-import android.widget.TextView;
-import org.chromium.base.ApiCompatibilityUtils;
-
-/**
- * Encapsulates a single gradient view of the HSV color display, including its label, gradient
- * view and seek bar.
- *
- * Mirrors a "color_picker_advanced_component" layout.
- */
-public class ColorPickerAdvancedComponent {
- // The view that displays the gradient.
- private final View mGradientView;
- // The seek bar that allows the user to change the value of this component.
- private final SeekBar mSeekBar;
- // The set of colors to interpolate the gradient through.
- private int[] mGradientColors;
- // The Drawable that represents the gradient.
- private GradientDrawable mGradientDrawable;
- // The text label for the component.
- private final TextView mText;
-
- /**
- * Initializes the views.
- *
- * @param rootView View that contains all the content, such as the label, gradient view, etc.
- * @param textResourceId The resource ID of the text to show on the label.
- * @param seekBarMax The range of the seek bar.
- * @param seekBarListener The listener for when the seek bar value changes.
- */
- ColorPickerAdvancedComponent(final View rootView,
- final int textResourceId,
- final int seekBarMax,
- final OnSeekBarChangeListener seekBarListener) {
- mGradientView = rootView.findViewById(R.id.gradient);
- mText = (TextView) rootView.findViewById(R.id.text);
- mText.setText(textResourceId);
- mGradientDrawable = new GradientDrawable(GradientDrawable.Orientation.LEFT_RIGHT, null);
- mSeekBar = (SeekBar) rootView.findViewById(R.id.seek_bar);
- mSeekBar.setOnSeekBarChangeListener(seekBarListener);
- mSeekBar.setMax(seekBarMax);
- // Setting the thumb offset means the seek bar thumb can move all the way to each end
- // of the gradient view.
- Context context = rootView.getContext();
- int offset = context.getResources()
- .getDrawable(R.drawable.color_picker_advanced_select_handle)
- .getIntrinsicWidth();
- mSeekBar.setThumbOffset(offset / 2);
- }
-
- /**
- * @return The value represented by this component, maintained by the seek bar progress.
- */
- public float getValue() {
- return mSeekBar.getProgress();
- }
-
- /**
- * Sets the value of the component (by setting the seek bar value).
- *
- * @param newValue The value to give the component.
- */
- public void setValue(float newValue) {
- mSeekBar.setProgress((int) newValue);
- }
-
- /**
- * Sets the colors for the gradient view to interpolate through.
- *
- * @param newColors The set of colors representing the interpolation points for the gradient.
- */
- public void setGradientColors(int[] newColors) {
- mGradientColors = newColors.clone();
- if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
- Orientation currentOrientation = Orientation.LEFT_RIGHT;
- mGradientDrawable = new GradientDrawable(currentOrientation, mGradientColors);
- } else {
- mGradientDrawable.setColors(mGradientColors);
- }
- ApiCompatibilityUtils.setBackgroundForView(mGradientView, mGradientDrawable);
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerDialog.java b/chromium/ui/android/java/src/org/chromium/ui/ColorPickerDialog.java
deleted file mode 100644
index 58f1e0a3023..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerDialog.java
+++ /dev/null
@@ -1,166 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.app.AlertDialog;
-import android.app.Dialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.widget.Button;
-import android.widget.TextView;
-
-/**
- * UI for the color chooser that shows on the Android platform as a result of
- * &lt;input type=color &gt; form element.
- */
-public class ColorPickerDialog extends AlertDialog implements OnColorChangedListener {
- private final ColorPickerAdvanced mAdvancedColorPicker;
-
- private final ColorPickerSimple mSimpleColorPicker;
-
- private final Button mMoreButton;
-
- // The view up in the corner that shows the user the color they've currently selected.
- private final View mCurrentColorView;
-
- private final OnColorChangedListener mListener;
-
- private final int mInitialColor;
-
- private int mCurrentColor;
-
- /**
- * @param context The context the dialog is to run in.
- * @param theme The theme to display the dialog in.
- * @param listener The object to notify when the color is set.
- * @param color The initial color to set.
- */
- public ColorPickerDialog(Context context, OnColorChangedListener listener, int color) {
- super(context, 0);
-
- mListener = listener;
- mInitialColor = color;
- mCurrentColor = mInitialColor;
-
- // Initialize title
- LayoutInflater inflater = (LayoutInflater) context
- .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- View title = inflater.inflate(R.layout.color_picker_dialog_title, null);
- setCustomTitle(title);
-
- mCurrentColorView = title.findViewById(R.id.selected_color_view);
-
- TextView titleText = (TextView) title.findViewById(R.id.title);
- titleText.setText(R.string.color_picker_dialog_title);
-
- // Initialize Set/Cancel buttons
- String positiveButtonText = context.getString(R.string.color_picker_button_set);
- setButton(BUTTON_POSITIVE, positiveButtonText,
- new Dialog.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialogInterface, int i) {
- tryNotifyColorSet(mCurrentColor);
- }
- });
-
- // Note that with the color picker there's not really any such thing as
- // "cancelled".
- // The color picker flow only finishes when we return a color, so we
- // have to always
- // return something. The concept of "cancelled" in this case just means
- // returning
- // the color that we were initialized with.
- String negativeButtonText = context.getString(R.string.color_picker_button_cancel);
- setButton(BUTTON_NEGATIVE, negativeButtonText,
- new Dialog.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialogInterface, int i) {
- tryNotifyColorSet(mInitialColor);
- }
- });
-
- setOnCancelListener(new DialogInterface.OnCancelListener() {
- @Override
- public void onCancel(DialogInterface arg0) {
- tryNotifyColorSet(mInitialColor);
- }
- });
-
- // Initialize main content view
- View content = inflater.inflate(R.layout.color_picker_dialog_content, null);
- setView(content);
-
- // Initialize More button.
- mMoreButton = (Button) content.findViewById(R.id.more_colors_button);
- mMoreButton.setOnClickListener(new Button.OnClickListener() {
- @Override
- public void onClick(View v) {
- showAdvancedView();
- }
- });
-
- // Initialize advanced color view (hidden initially).
- mAdvancedColorPicker =
- (ColorPickerAdvanced) content.findViewById(R.id.color_picker_advanced);
- mAdvancedColorPicker.setVisibility(View.GONE);
-
- // Initialize simple color view (default view).
- mSimpleColorPicker = (ColorPickerSimple) content.findViewById(R.id.color_picker_simple);
- mSimpleColorPicker.init(this);
-
- updateCurrentColor(mInitialColor);
- }
-
- /**
- * Listens to the ColorPicker for when the user has changed the selected color, and
- * updates the current color (the color shown in the title) accordingly.
- *
- * @param color The new color chosen by the user.
- */
- @Override
- public void onColorChanged(int color) {
- updateCurrentColor(color);
- }
-
- /**
- * Hides the simple view (the default) and shows the advanced one instead, hiding the
- * "More" button at the same time.
- */
- private void showAdvancedView() {
- // Only need to hide the borders, not the Views themselves, since the Views are
- // contained within the borders.
- View buttonBorder = findViewById(R.id.more_colors_button_border);
- buttonBorder.setVisibility(View.GONE);
-
- View simpleViewBorder = findViewById(R.id.color_picker_simple_border);
- simpleViewBorder.setVisibility(View.GONE);
-
- mAdvancedColorPicker.setVisibility(View.VISIBLE);
- mAdvancedColorPicker.setListener(this);
- mAdvancedColorPicker.setColor(mCurrentColor);
- }
-
- /**
- * Tries to notify any listeners that the color has been set.
- */
- private void tryNotifyColorSet(int color) {
- if (mListener != null) {
- mListener.onColorChanged(color);
- }
- }
-
- /**
- * Updates the internal cache of the currently selected color, updating the colorful little
- * box in the title at the same time.
- */
- private void updateCurrentColor(int color) {
- mCurrentColor = color;
- if (mCurrentColorView != null) {
- mCurrentColorView.setBackgroundColor(color);
- }
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerMoreButton.java b/chromium/ui/android/java/src/org/chromium/ui/ColorPickerMoreButton.java
deleted file mode 100644
index a982afd9e54..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerMoreButton.java
+++ /dev/null
@@ -1,56 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.util.AttributeSet;
-import android.widget.Button;
-
-/**
- * Simple class that draws a white border around a button, purely for a UI change.
- */
-public class ColorPickerMoreButton extends Button {
-
- // A cache for the paint used to draw the border, so it doesn't have to be created in
- // every onDraw() call.
- private Paint mBorderPaint;
-
- public ColorPickerMoreButton(Context context, AttributeSet attrs) {
- super(context, attrs);
- init();
- }
-
- public ColorPickerMoreButton(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- init();
- }
-
- /**
- * Sets up the paint to use for drawing the border.
- */
- public void init() {
- mBorderPaint = new Paint();
- mBorderPaint.setStyle(Paint.Style.STROKE);
- mBorderPaint.setColor(Color.WHITE);
- // Set the width to one pixel.
- mBorderPaint.setStrokeWidth(1.0f);
- // And make sure the border doesn't bleed into the outside.
- mBorderPaint.setAntiAlias(false);
- }
-
- /**
- * Draws the border around the edge of the button.
- *
- * @param canvas The canvas to draw on.
- */
- @Override
- protected void onDraw(Canvas canvas) {
- canvas.drawRect(0.5f, 0.5f, getWidth() - 1.5f, getHeight() - 1.5f, mBorderPaint);
- super.onDraw(canvas);
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerSimple.java b/chromium/ui/android/java/src/org/chromium/ui/ColorPickerSimple.java
deleted file mode 100644
index 979405a4078..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ColorPickerSimple.java
+++ /dev/null
@@ -1,189 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-package org.chromium.ui;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.view.View;
-
-
-/**
- * Draws a grid of (predefined) colors and allows the user to choose one of
- * those colors.
- */
-public class ColorPickerSimple extends View {
- private static final int ROW_COUNT = 2;
-
- private static final int COLUMN_COUNT = 4;
-
- private static final int GRID_CELL_COUNT = ROW_COUNT * COLUMN_COUNT;
-
- private static final int[] COLORS = { Color.RED,
- Color.CYAN,
- Color.BLUE,
- Color.GREEN,
- Color.MAGENTA,
- Color.YELLOW,
- Color.BLACK,
- Color.WHITE
- };
-
- private Paint mBorderPaint;
-
- private Rect[] mBounds;
-
- private Paint[] mPaints;
-
- private OnColorChangedListener mOnColorTouchedListener;
-
- private int mLastTouchedXPosition;
-
- private int mLastTouchedYPosition;
-
- public ColorPickerSimple(Context context) {
- super(context);
- }
-
- public ColorPickerSimple(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public ColorPickerSimple(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- }
-
- /**
- * Initializes the listener and precalculates the grid and color positions.
- *
- * @param onColorChangedListener The listener that gets notified when the user touches
- * a color.
- */
- public void init(OnColorChangedListener onColorChangedListener) {
- mOnColorTouchedListener = onColorChangedListener;
-
- // This will get calculated when the layout size is updated.
- mBounds = null;
-
- mPaints = new Paint[GRID_CELL_COUNT];
- for (int i = 0; i < GRID_CELL_COUNT; ++i) {
- Paint newPaint = new Paint();
- newPaint.setColor(COLORS[i]);
- mPaints[i] = newPaint;
- }
-
- mBorderPaint = new Paint();
- int borderColor = getContext().getResources().getColor(R.color.color_picker_border_color);
- mBorderPaint.setColor(borderColor);
-
- // Responds to the user touching the grid and works out which color has been chosen as
- // a result, depending on the X,Y coordinate. Note that we respond to the click event
- // here, but the onClick() method doesn't provide us with the X,Y coordinates, so we
- // track them in onTouchEvent() below. This way the grid reacts properly to touch events
- // whereas if we put this onClick() code in onTouchEvent below then we get some strange
- // interactions with the ScrollView in the parent ColorPickerDialog.
- setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View v) {
- if (mOnColorTouchedListener != null && getWidth() > 0 && getHeight() > 0) {
- int column = mLastTouchedXPosition * COLUMN_COUNT / getWidth();
- int row = mLastTouchedYPosition * ROW_COUNT / getHeight();
-
- int colorIndex = (row * COLUMN_COUNT) + column;
- if (colorIndex >= 0 && colorIndex < COLORS.length) {
- mOnColorTouchedListener.onColorChanged(COLORS[colorIndex]);
- }
- }
- }
- });
- }
-
- /**
- * Draws the grid of colors, based on the rectangles calculated in onSizeChanged().
- * Also draws borders in between the colored rectangles.
- *
- * @param canvas The canvas the colors are drawn onto.
- */
- @Override
- public void onDraw(Canvas canvas) {
- if (mBounds == null || mPaints == null) {
- return;
- }
-
- canvas.drawColor(Color.WHITE);
-
- // Draw the actual colored rectangles.
- for (int i = 0; i < GRID_CELL_COUNT; ++i) {
- canvas.drawRect(mBounds[i], mPaints[i]);
- }
-
- // Draw 1px borders between the rows.
- for (int i = 0; i < ROW_COUNT - 1; ++i) {
- canvas.drawLine(0,
- mBounds[i * COLUMN_COUNT].bottom + 1,
- getWidth(),
- mBounds[i * COLUMN_COUNT].bottom + 1,
- mBorderPaint);
- }
-
- // Draw 1px borders between the columns.
- for (int j = 0; j < COLUMN_COUNT - 1; ++j) {
- canvas.drawLine(mBounds[j].right + 1,
- 0,
- mBounds[j].right + 1,
- getHeight(),
- mBorderPaint);
- }
- }
-
- /**
- * Stores the X,Y coordinates of the touch so that we can use them in the onClick() listener
- * above to work out where the click was on the grid.
- *
- * @param event The MotionEvent the X,Y coordinates are retrieved from.
- */
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (event.getAction() == MotionEvent.ACTION_DOWN) {
- mLastTouchedXPosition = (int) event.getX();
- mLastTouchedYPosition = (int) event.getY();
- }
- return super.onTouchEvent(event);
- }
-
- /**
- * Recalculates the color grid with the new sizes.
- */
- @Override
- protected void onSizeChanged(int width, int height, int oldw, int oldh) {
- calculateGrid(width, height);
- }
-
- /**
- * Calculates the sizes and positions of the cells in the grid, splitting
- * them up as evenly as possible. Leaves 3 pixels between each cell so that
- * we can draw a border between them as well, and leaves a pixel around the
- * edge.
- */
- private void calculateGrid(final int width, final int height) {
- mBounds = new Rect[GRID_CELL_COUNT];
-
- for (int i = 0; i < ROW_COUNT; ++i) {
- for (int j = 0; j < COLUMN_COUNT; ++j) {
- int left = j * (width + 1) / COLUMN_COUNT + 1;
- int right = (j + 1) * (width + 1) / COLUMN_COUNT - 2;
-
- int top = i * (height + 1) / ROW_COUNT + 1;
- int bottom = (i + 1) * (height + 1) / ROW_COUNT - 2;
-
- Rect rect = new Rect(left, top, right, bottom);
- mBounds[(i * COLUMN_COUNT) + j] = rect;
- }
- }
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/LocalizationUtils.java b/chromium/ui/android/java/src/org/chromium/ui/LocalizationUtils.java
deleted file mode 100644
index f421d8939f1..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/LocalizationUtils.java
+++ /dev/null
@@ -1,96 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import org.chromium.base.CalledByNative;
-import org.chromium.base.JNINamespace;
-
-import android.os.Build;
-import android.text.TextUtils;
-import android.view.View;
-
-import java.util.Locale;
-
-/**
- * This class provides the locale related methods for the native library.
- */
-@JNINamespace("l10n_util")
-public class LocalizationUtils {
-
- // This is mirrored from base/i18n/rtl.h. Please keep in sync.
- public static final int UNKNOWN_DIRECTION = 0;
- public static final int RIGHT_TO_LEFT = 1;
- public static final int LEFT_TO_RIGHT = 2;
-
- private LocalizationUtils() { /* cannot be instantiated */ }
-
- /**
- * @return the default locale, translating Android deprecated
- * language codes into the modern ones used by Chromium.
- */
- @CalledByNative
- public static String getDefaultLocale() {
- Locale locale = Locale.getDefault();
- String language = locale.getLanguage();
- String country = locale.getCountry();
-
- // Android uses deprecated lanuages codes for Hebrew and Indonesian but Chromium uses the
- // updated codes. Also, Android uses "tl" while Chromium uses "fil" for Tagalog/Filipino.
- // So apply a mapping.
- // See http://developer.android.com/reference/java/util/Locale.html
- if ("iw".equals(language)) {
- language = "he";
- } else if ("in".equals(language)) {
- language = "id";
- } else if ("tl".equals(language)) {
- language = "fil";
- }
- return country.isEmpty() ? language : language + "-" + country;
- }
-
- @CalledByNative
- private static Locale getJavaLocale(String language, String country, String variant) {
- return new Locale(language, country, variant);
- }
-
- @CalledByNative
- private static String getDisplayNameForLocale(Locale locale, Locale displayLocale) {
- return locale.getDisplayName(displayLocale);
- }
-
- /**
- * @return true if the system default layout direction is RTL, false otherwise.
- * RTL layout support is from Jelly Bean MR1, so if the version is lower
- * than that, it is always false.
- */
- public static boolean isSystemLayoutDirectionRtl() {
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
- return TextUtils.getLayoutDirectionFromLocale(Locale.getDefault())
- == View.LAYOUT_DIRECTION_RTL;
- }
- return false;
- }
-
- /**
- * Jni binding to base::i18n::IsRTL.
- * @return true if the current locale is right to left.
- */
- public static boolean isRtl() {
- return nativeIsRTL();
- }
-
- /**
- * Jni binding to base::i18n::GetFirstStrongCharacterDirection
- * @param string String to decide the direction.
- * @return One of the UNKNOWN_DIRECTION, RIGHT_TO_LEFT, and LEFT_TO_RIGHT.
- */
- public static int getFirstStrongCharacterDirection(String string) {
- return nativeGetFirstStrongCharacterDirection(string);
- }
-
- private static native boolean nativeIsRTL();
-
- private static native int nativeGetFirstStrongCharacterDirection(String string);
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/OnColorChangedListener.java b/chromium/ui/android/java/src/org/chromium/ui/OnColorChangedListener.java
deleted file mode 100644
index 4caa3cf05bb..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/OnColorChangedListener.java
+++ /dev/null
@@ -1,17 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-package org.chromium.ui;
-
-/**
- * The callback used to indicate the user changed the color.
- */
-public interface OnColorChangedListener {
-
- /**
- * Called upon a color change.
- *
- * @param color The color that was set.
- */
- void onColorChanged(int color);
-} \ No newline at end of file
diff --git a/chromium/ui/android/java/src/org/chromium/ui/SelectFileDialog.java b/chromium/ui/android/java/src/org/chromium/ui/SelectFileDialog.java
deleted file mode 100644
index 91533b52cf0..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/SelectFileDialog.java
+++ /dev/null
@@ -1,248 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.app.Activity;
-import android.content.ContentResolver;
-import android.content.Intent;
-import android.database.Cursor;
-import android.net.Uri;
-import android.os.Environment;
-import android.provider.MediaStore;
-import android.text.TextUtils;
-
-import java.io.File;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-
-import org.chromium.base.CalledByNative;
-import org.chromium.base.JNINamespace;
-import org.chromium.ui.WindowAndroid;
-
-/**
- * A dialog that is triggered from a file input field that allows a user to select a file based on
- * a set of accepted file types. The path of the selected file is passed to the native dialog.
- */
-@JNINamespace("ui")
-class SelectFileDialog implements WindowAndroid.IntentCallback{
- private static final String IMAGE_TYPE = "image/";
- private static final String VIDEO_TYPE = "video/";
- private static final String AUDIO_TYPE = "audio/";
- private static final String ALL_IMAGE_TYPES = IMAGE_TYPE + "*";
- private static final String ALL_VIDEO_TYPES = VIDEO_TYPE + "*";
- private static final String ALL_AUDIO_TYPES = AUDIO_TYPE + "*";
- private static final String ANY_TYPES = "*/*";
- private static final String CAPTURE_IMAGE_DIRECTORY = "browser-photos";
-
- private final int mNativeSelectFileDialog;
- private List<String> mFileTypes;
- private boolean mCapture;
- private Uri mCameraOutputUri;
-
- private SelectFileDialog(int nativeSelectFileDialog) {
- mNativeSelectFileDialog = nativeSelectFileDialog;
- }
-
- /**
- * Creates and starts an intent based on the passed fileTypes and capture value.
- * @param fileTypes MIME types requested (i.e. "image/*")
- * @param capture The capture value as described in http://www.w3.org/TR/html-media-capture/
- * @param window The WindowAndroid that can show intents
- */
- @CalledByNative
- private void selectFile(String[] fileTypes, boolean capture, WindowAndroid window) {
- mFileTypes = new ArrayList<String>(Arrays.asList(fileTypes));
- mCapture = capture;
-
- Intent chooser = new Intent(Intent.ACTION_CHOOSER);
- Intent camera = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
- mCameraOutputUri = Uri.fromFile(getFileForImageCapture());
- camera.putExtra(MediaStore.EXTRA_OUTPUT, mCameraOutputUri);
- Intent camcorder = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
- Intent soundRecorder = new Intent(
- MediaStore.Audio.Media.RECORD_SOUND_ACTION);
-
- // Quick check - if the |capture| parameter is set and |fileTypes| has the appropriate MIME
- // type, we should just launch the appropriate intent. Otherwise build up a chooser based on
- // the accept type and then display that to the user.
- if (captureCamera()) {
- if (window.showIntent(camera, this, R.string.low_memory_error)) return;
- } else if (captureCamcorder()) {
- if (window.showIntent(camcorder, this, R.string.low_memory_error)) return;
- } else if (captureMicrophone()) {
- if (window.showIntent(soundRecorder, this, R.string.low_memory_error)) return;
- }
-
- Intent getContentIntent = new Intent(Intent.ACTION_GET_CONTENT);
- getContentIntent.addCategory(Intent.CATEGORY_OPENABLE);
- ArrayList<Intent> extraIntents = new ArrayList<Intent>();
- if (!noSpecificType()) {
- // Create a chooser based on the accept type that was specified in the webpage. Note
- // that if the web page specified multiple accept types, we will have built a generic
- // chooser above.
- if (shouldShowImageTypes()) {
- extraIntents.add(camera);
- getContentIntent.setType(ALL_IMAGE_TYPES);
- } else if (shouldShowVideoTypes()) {
- extraIntents.add(camcorder);
- getContentIntent.setType(ALL_VIDEO_TYPES);
- } else if (shouldShowAudioTypes()) {
- extraIntents.add(soundRecorder);
- getContentIntent.setType(ALL_AUDIO_TYPES);
- }
- }
-
- if (extraIntents.isEmpty()) {
- // We couldn't resolve an accept type, so fallback to a generic chooser.
- getContentIntent.setType(ANY_TYPES);
- extraIntents.add(camera);
- extraIntents.add(camcorder);
- extraIntents.add(soundRecorder);
- }
-
- chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS,
- extraIntents.toArray(new Intent[] { }));
-
- chooser.putExtra(Intent.EXTRA_INTENT, getContentIntent);
-
- if (!window.showIntent(chooser, this, R.string.low_memory_error)) {
- onFileNotSelected();
- }
- }
-
- /**
- * Get a file for the image capture in the CAPTURE_IMAGE_DIRECTORY directory.
- */
- private File getFileForImageCapture() {
- File externalDataDir = Environment.getExternalStoragePublicDirectory(
- Environment.DIRECTORY_DCIM);
- File cameraDataDir = new File(externalDataDir.getAbsolutePath() +
- File.separator + CAPTURE_IMAGE_DIRECTORY);
- if (!cameraDataDir.exists() && !cameraDataDir.mkdirs()) {
- cameraDataDir = externalDataDir;
- }
- File photoFile = new File(cameraDataDir.getAbsolutePath() +
- File.separator + System.currentTimeMillis() + ".jpg");
- return photoFile;
- }
-
- /**
- * Callback method to handle the intent results and pass on the path to the native
- * SelectFileDialog.
- * @param window The window that has access to the application activity.
- * @param resultCode The result code whether the intent returned successfully.
- * @param contentResolver The content resolver used to extract the path of the selected file.
- * @param results The results of the requested intent.
- */
- @Override
- public void onIntentCompleted(WindowAndroid window, int resultCode,
- ContentResolver contentResolver, Intent results) {
- if (resultCode != Activity.RESULT_OK) {
- onFileNotSelected();
- return;
- }
- boolean success = false;
- if (results == null) {
- // If we have a successful return but no data, then assume this is the camera returning
- // the photo that we requested.
- nativeOnFileSelected(mNativeSelectFileDialog, mCameraOutputUri.getPath());
- success = true;
-
- // Broadcast to the media scanner that there's a new photo on the device so it will
- // show up right away in the gallery (rather than waiting until the next time the media
- // scanner runs).
- window.sendBroadcast(new Intent(
- Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, mCameraOutputUri));
- } else {
- // We get back a content:// URI from the system if the user picked a file from the
- // gallery. The ContentView has functionality that will convert that content:// URI to
- // a file path on disk that Chromium understands.
- Cursor c = contentResolver.query(results.getData(),
- new String[] { MediaStore.MediaColumns.DATA }, null, null, null);
- if (c != null) {
- if (c.getCount() == 1) {
- c.moveToFirst();
- String path = c.getString(0);
- if (path != null) {
- // Not all providers support the MediaStore.DATA column. For example,
- // Gallery3D (com.android.gallery3d.provider) does not support it for
- // Picasa Web Album images.
- nativeOnFileSelected(mNativeSelectFileDialog, path);
- success = true;
- }
- }
- c.close();
- }
- }
- if (!success) {
- onFileNotSelected();
- window.showError(R.string.opening_file_error);
- }
- }
-
- private void onFileNotSelected() {
- nativeOnFileNotSelected(mNativeSelectFileDialog);
- }
-
- private boolean noSpecificType() {
- // We use a single Intent to decide the type of the file chooser we display to the user,
- // which means we can only give it a single type. If there are multiple accept types
- // specified, we will fallback to a generic chooser (unless a capture parameter has been
- // specified, in which case we'll try to satisfy that first.
- return mFileTypes.size() != 1 || mFileTypes.contains(ANY_TYPES);
- }
-
- private boolean shouldShowTypes(String allTypes, String specificType) {
- if (noSpecificType() || mFileTypes.contains(allTypes)) return true;
- return acceptSpecificType(specificType);
- }
-
- private boolean shouldShowImageTypes() {
- return shouldShowTypes(ALL_IMAGE_TYPES,IMAGE_TYPE);
- }
-
- private boolean shouldShowVideoTypes() {
- return shouldShowTypes(ALL_VIDEO_TYPES, VIDEO_TYPE);
- }
-
- private boolean shouldShowAudioTypes() {
- return shouldShowTypes(ALL_AUDIO_TYPES, AUDIO_TYPE);
- }
-
- private boolean acceptsSpecificType(String type) {
- return mFileTypes.size() == 1 && TextUtils.equals(mFileTypes.get(0), type);
- }
-
- private boolean captureCamera() {
- return mCapture && acceptsSpecificType(ALL_IMAGE_TYPES);
- }
-
- private boolean captureCamcorder() {
- return mCapture && acceptsSpecificType(ALL_VIDEO_TYPES);
- }
-
- private boolean captureMicrophone() {
- return mCapture && acceptsSpecificType(ALL_AUDIO_TYPES);
- }
-
- private boolean acceptSpecificType(String accept) {
- for (String type : mFileTypes) {
- if (type.startsWith(accept)) {
- return true;
- }
- }
- return false;
- }
-
- @CalledByNative
- private static SelectFileDialog create(int nativeSelectFileDialog) {
- return new SelectFileDialog(nativeSelectFileDialog);
- }
-
- private native void nativeOnFileSelected(int nativeSelectFileDialogImpl,
- String filePath);
- private native void nativeOnFileNotSelected(int nativeSelectFileDialogImpl);
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/UiUtils.java b/chromium/ui/android/java/src/org/chromium/ui/UiUtils.java
deleted file mode 100644
index 4a9fe15e79f..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/UiUtils.java
+++ /dev/null
@@ -1,99 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.content.Context;
-import android.graphics.Rect;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.inputmethod.InputMethodManager;
-
-/**
- * Utility functions for common Android UI tasks.
- * This class is not supposed to be instantiated.
- */
-public class UiUtils {
- /**
- * Guards this class from being instantiated.
- */
- private UiUtils() {
- }
-
- /** The minimum size of the bottom margin below the app to detect a keyboard. */
- private static float KEYBOARD_DETECT_BOTTOM_THRESHOLD_DP = 100;
-
- /**
- * Shows the software keyboard if necessary.
- * @param view The currently focused {@link View}, which would receive soft keyboard input.
- */
- public static void showKeyboard(View view) {
- InputMethodManager imm =
- (InputMethodManager) view.getContext().getSystemService(
- Context.INPUT_METHOD_SERVICE);
- // Only shows soft keyboard if there isn't an open physical keyboard.
- imm.showSoftInput(view, InputMethodManager.SHOW_IMPLICIT);
- }
-
- /**
- * Hides the keyboard.
- * @param view The {@link View} that is currently accepting input.
- * @return Whether the keyboard was visible before.
- */
- public static boolean hideKeyboard(View view) {
- InputMethodManager imm =
- (InputMethodManager) view.getContext().getSystemService(
- Context.INPUT_METHOD_SERVICE);
- return imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
- }
-
- public static boolean isKeyboardShowing(Context context, View view) {
- View rootView = view.getRootView();
- if (rootView == null) return false;
- Rect appRect = new Rect();
- rootView.getWindowVisibleDisplayFrame(appRect);
- final float screenHeight = context.getResources().getDisplayMetrics().heightPixels;
- final float bottomMargin = Math.abs(appRect.bottom - screenHeight);
- final float density = context.getResources().getDisplayMetrics().density;
- return bottomMargin > KEYBOARD_DETECT_BOTTOM_THRESHOLD_DP * density;
- }
-
- /**
- * Inserts a {@link View} into a {@link ViewGroup} after directly before a given {@View}.
- * @param container The {@link View} to add newView to.
- * @param newView The new {@link View} to add.
- * @param existingView The {@link View} to insert the newView before.
- * @return The index where newView was inserted, or -1 if it was not inserted.
- */
- public static int insertBefore(ViewGroup container, View newView, View existingView) {
- return insertView(container, newView, existingView, false);
- }
-
- /**
- * Inserts a {@link View} into a {@link ViewGroup} after directly after a given {@View}.
- * @param container The {@link View} to add newView to.
- * @param newView The new {@link View} to add.
- * @param existingView The {@link View} to insert the newView after.
- * @return The index where newView was inserted, or -1 if it was not inserted.
- */
- public static int insertAfter(ViewGroup container, View newView, View existingView) {
- return insertView(container, newView, existingView, true);
- }
-
- private static int insertView(
- ViewGroup container, View newView, View existingView, boolean after) {
- // See if the view has already been added.
- int index = container.indexOfChild(newView);
- if (index >= 0) return index;
-
- // Find the location of the existing view.
- index = container.indexOfChild(existingView);
- if (index < 0) return -1;
-
- // Add the view.
- if (after) index++;
- container.addView(newView, index);
- return index;
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ViewAndroid.java b/chromium/ui/android/java/src/org/chromium/ui/ViewAndroid.java
deleted file mode 100644
index 97c8e1dcfd3..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ViewAndroid.java
+++ /dev/null
@@ -1,87 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.view.View;
-
-import org.chromium.base.JNINamespace;
-import org.chromium.ui.ViewAndroidDelegate;
-import org.chromium.ui.WindowAndroid;
-
-/**
- * From the Chromium architecture point of view, ViewAndroid and its native counterpart
- * serve purpose of representing Android view where Chrome expects to have a cross platform
- * handle to the system view type. As Views are Java object on Android, this ViewAndroid
- * and its native counterpart provide the expected abstractions on the C++ side and allow
- * it to be flexibly glued to an actual Android Java View at runtime.
- *
- * It should only be used where access to Android Views is needed from the C++ code.
- */
-@JNINamespace("ui")
-public class ViewAndroid {
- // Native pointer to the c++ ViewAndroid object.
- private int mNativeViewAndroid = 0;
- private final ViewAndroidDelegate mViewAndroidDelegate;
- private final WindowAndroid mWindowAndroid;
- private int mKeepScreenOnCount;
- private View mKeepScreenOnView;
-
- /**
- * Constructs a View object.
- */
- public ViewAndroid(WindowAndroid nativeWindow, ViewAndroidDelegate viewAndroidDelegate) {
- mWindowAndroid = nativeWindow;
- mViewAndroidDelegate = viewAndroidDelegate;
- mNativeViewAndroid = nativeInit(mWindowAndroid.getNativePointer());
- }
-
- public ViewAndroidDelegate getViewAndroidDelegate() {
- return mViewAndroidDelegate;
- }
-
- /**
- * Destroys the c++ ViewAndroid object if one has been created.
- */
- public void destroy() {
- if (mNativeViewAndroid != 0) {
- nativeDestroy(mNativeViewAndroid);
- mNativeViewAndroid = 0;
- }
- }
-
- /**
- * Returns a pointer to the c++ AndroidWindow object.
- * @return A pointer to the c++ AndroidWindow.
- */
- public int getNativePointer() {
- return mNativeViewAndroid;
- }
-
- /**
- * Set KeepScreenOn flag. If the flag already set, increase mKeepScreenOnCount.
- */
- public void incrementKeepScreenOnCount() {
- mKeepScreenOnCount++;
- if (mKeepScreenOnCount == 1) {
- mKeepScreenOnView = mViewAndroidDelegate.acquireAnchorView();
- mKeepScreenOnView.setKeepScreenOn(true);
- }
- }
-
- /**
- * Decrease mKeepScreenOnCount, if it is decreased to 0, remove the flag.
- */
- public void decrementKeepScreenOnCount() {
- assert mKeepScreenOnCount > 0;
- mKeepScreenOnCount--;
- if (mKeepScreenOnCount == 0) {
- mViewAndroidDelegate.releaseAnchorView(mKeepScreenOnView);
- mKeepScreenOnView = null;
- }
- }
-
- private native int nativeInit(int windowPtr);
- private native void nativeDestroy(int nativeViewAndroid);
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/ViewAndroidDelegate.java b/chromium/ui/android/java/src/org/chromium/ui/ViewAndroidDelegate.java
deleted file mode 100644
index 531dce880a5..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/ViewAndroidDelegate.java
+++ /dev/null
@@ -1,34 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.view.View;
-
-/**
- * Interface to acquire and release anchor views from the implementing View.
- */
-public interface ViewAndroidDelegate {
-
- /**
- * @return An anchor view that can be used to anchor decoration views like Autofill popup.
- */
- View acquireAnchorView();
-
- /**
- * Set the anchor view to specified position and width (all units in dp).
- * @param view The anchor view that needs to be positioned.
- * @param x X coordinate of the top left corner of the anchor view.
- * @param y Y coordinate of the top left corner of the anchor view.
- * @param width The width of the anchor view.
- * @param height The height of the anchor view.
- */
- void setAnchorViewPosition(View view, float x, float y, float width, float height);
-
- /**
- * Release given anchor view.
- * @param anchorView The anchor view that needs to be released.
- */
- void releaseAnchorView(View anchorView);
-} \ No newline at end of file
diff --git a/chromium/ui/android/java/src/org/chromium/ui/WindowAndroid.java b/chromium/ui/android/java/src/org/chromium/ui/WindowAndroid.java
deleted file mode 100644
index 3fec6007b3c..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/WindowAndroid.java
+++ /dev/null
@@ -1,206 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui;
-
-import android.app.Activity;
-import android.content.ActivityNotFoundException;
-import android.content.ContentResolver;
-import android.content.Context;
-import android.content.Intent;
-import android.os.Bundle;
-import android.util.SparseArray;
-import android.widget.Toast;
-
-import java.util.HashMap;
-
-import org.chromium.base.JNINamespace;
-
-/**
- * The window base class that has the minimum functionality.
- */
-@JNINamespace("ui")
-public class WindowAndroid {
-
- // Native pointer to the c++ WindowAndroid object.
- private int mNativeWindowAndroid = 0;
-
- // Constants used for intent request code bounding.
- private static final int REQUEST_CODE_PREFIX = 1000;
- private static final int REQUEST_CODE_RANGE_SIZE = 100;
- // A string used as a key to store intent errors in a bundle
- static final String WINDOW_CALLBACK_ERRORS = "window_callback_errors";
-
- private int mNextRequestCode = 0;
- protected Activity mActivity;
- protected SparseArray<IntentCallback> mOutstandingIntents;
- protected HashMap<Integer, String> mIntentErrors;
-
- /**
- * @param activity
- */
- public WindowAndroid(Activity activity) {
- mActivity = activity;
- mOutstandingIntents = new SparseArray<IntentCallback>();
- mIntentErrors = new HashMap<Integer, String>();
-
- }
-
- /**
- * Shows an intent and returns the results to the callback object.
- * @param intent The intent that needs to be showed.
- * @param callback The object that will receive the results for the intent.
- * @param errorId The ID of error string to be show if activity is paused before intent
- * results.
- * @return Whether the intent was shown.
- */
- public boolean showIntent(Intent intent, IntentCallback callback, int errorId) {
- int requestCode = REQUEST_CODE_PREFIX + mNextRequestCode;
- mNextRequestCode = (mNextRequestCode + 1) % REQUEST_CODE_RANGE_SIZE;
-
- try {
- mActivity.startActivityForResult(intent, requestCode);
- } catch (ActivityNotFoundException e) {
- return false;
- }
-
- mOutstandingIntents.put(requestCode, callback);
- mIntentErrors.put(requestCode, mActivity.getString(errorId));
-
- return true;
- }
-
- /**
- * Displays an error message with a provided error message string.
- * @param error The error message string to be displayed.
- */
- public void showError(String error) {
- if (error != null) {
- Toast.makeText(mActivity, error, Toast.LENGTH_SHORT).show();
- }
- }
-
- /**
- * Displays an error message from the given resource id.
- * @param resId The error message string's resource id.
- */
- public void showError(int resId) {
- showError(mActivity.getString(resId));
- }
-
- /**
- * Displays an error message for a nonexistent callback.
- * @param error The error message string to be displayed.
- */
- protected void showCallbackNonExistentError(String error) {
- showError(error);
- }
-
- /**
- * Broadcasts the given intent to all interested BroadcastReceivers.
- */
- public void sendBroadcast(Intent intent) {
- mActivity.sendBroadcast(intent);
- }
-
- /**
- * TODO(nileshagrawal): Stop returning Activity Context crbug.com/233440.
- * @return Activity context.
- */
- @Deprecated
- public Context getContext() {
- return mActivity;
- }
-
- /**
- * Saves the error messages that should be shown if any pending intents would return
- * after the application has been put onPause.
- * @param bundle The bundle to save the information in onPause
- */
- public void saveInstanceState(Bundle bundle) {
- bundle.putSerializable(WINDOW_CALLBACK_ERRORS, mIntentErrors);
- }
-
- /**
- * Restores the error messages that should be shown if any pending intents would return
- * after the application has been put onPause.
- * @param bundle The bundle to restore the information from onResume
- */
- public void restoreInstanceState(Bundle bundle) {
- if (bundle == null) return;
-
- Object errors = bundle.getSerializable(WINDOW_CALLBACK_ERRORS);
- if (errors instanceof HashMap) {
- @SuppressWarnings("unchecked")
- HashMap<Integer, String> intentErrors = (HashMap<Integer, String>) errors;
- mIntentErrors = intentErrors;
- }
- }
-
- /**
- * Responds to the intent result if the intent was created by the native window.
- * @param requestCode Request code of the requested intent.
- * @param resultCode Result code of the requested intent.
- * @param data The data returned by the intent.
- * @return Boolean value of whether the intent was started by the native window.
- */
- public boolean onActivityResult(int requestCode, int resultCode, Intent data) {
- IntentCallback callback = mOutstandingIntents.get(requestCode);
- mOutstandingIntents.delete(requestCode);
- String errorMessage = mIntentErrors.remove(requestCode);
-
- if (callback != null) {
- callback.onIntentCompleted(this, resultCode,
- mActivity.getContentResolver(), data);
- return true;
- } else {
- if (errorMessage != null) {
- showCallbackNonExistentError(errorMessage);
- return true;
- }
- }
- return false;
- }
-
- /**
- * An interface that intent callback objects have to implement.
- */
- public interface IntentCallback {
- /**
- * Handles the data returned by the requested intent.
- * @param window A window reference.
- * @param resultCode Result code of the requested intent.
- * @param contentResolver An instance of ContentResolver class for accessing returned data.
- * @param data The data returned by the intent.
- */
- public void onIntentCompleted(WindowAndroid window, int resultCode,
- ContentResolver contentResolver, Intent data);
- }
-
- /**
- * Destroys the c++ WindowAndroid object if one has been created.
- */
- public void destroy() {
- if (mNativeWindowAndroid != 0) {
- nativeDestroy(mNativeWindowAndroid);
- mNativeWindowAndroid = 0;
- }
- }
-
- /**
- * Returns a pointer to the c++ AndroidWindow object and calls the initializer if
- * the object has not been previously initialized.
- * @return A pointer to the c++ AndroidWindow.
- */
- public int getNativePointer() {
- if (mNativeWindowAndroid == 0) {
- mNativeWindowAndroid = nativeInit();
- }
- return mNativeWindowAndroid;
- }
-
- private native int nativeInit();
- private native void nativeDestroy(int nativeWindowAndroid);
-
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillListAdapter.java b/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillListAdapter.java
deleted file mode 100644
index 62203dc70a8..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillListAdapter.java
+++ /dev/null
@@ -1,54 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-
-package org.chromium.ui.autofill;
-
-import android.content.Context;
-import android.text.TextUtils;
-
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ArrayAdapter;
-import android.widget.TextView;
-
-import org.chromium.ui.R;
-
-import java.util.ArrayList;
-
-/**
- * Autofill suggestion adapter for AutofillWindow.
- */
-public class AutofillListAdapter extends ArrayAdapter<AutofillSuggestion> {
- private Context mContext;
-
- AutofillListAdapter(Context context, ArrayList<AutofillSuggestion> objects) {
- super(context, R.layout.autofill_text, objects);
- mContext = context;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- View layout = convertView;
- if (convertView == null) {
- LayoutInflater inflater =
- (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- layout = inflater.inflate(R.layout.autofill_text, null);
- }
- TextView labelView = (TextView) layout.findViewById(R.id.autofill_label);
- labelView.setText(getItem(position).mLabel);
-
- TextView sublabelView = (TextView) layout.findViewById(R.id.autofill_sublabel);
- CharSequence sublabel = getItem(position).mSublabel;
- if (TextUtils.isEmpty(sublabel)) {
- sublabelView.setVisibility(View.GONE);
- } else {
- sublabelView.setText(sublabel);
- sublabelView.setVisibility(View.VISIBLE);
- }
-
- return layout;
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillPopup.java b/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillPopup.java
deleted file mode 100644
index 0483b027215..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillPopup.java
+++ /dev/null
@@ -1,214 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui.autofill;
-
-import android.content.Context;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.text.TextUtils;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.View.OnLayoutChangeListener;
-import android.widget.AdapterView;
-import android.widget.ListPopupWindow;
-import android.widget.TextView;
-
-import java.util.ArrayList;
-
-import org.chromium.ui.R;
-import org.chromium.ui.ViewAndroidDelegate;
-
-/**
- * The Autofill suggestion popup that lists relevant suggestions.
- */
-public class AutofillPopup extends ListPopupWindow implements AdapterView.OnItemClickListener {
-
- /**
- * Constants defining types of Autofill suggestion entries.
- * Has to be kept in sync with enum in WebAutofillClient.h
- *
- * Not supported: MenuItemIDWarningMessage, MenuItemIDSeparator, MenuItemIDClearForm, and
- * MenuItemIDAutofillOptions.
- */
- private static final int ITEM_ID_AUTOCOMPLETE_ENTRY = 0;
- private static final int ITEM_ID_PASSWORD_ENTRY = -2;
- private static final int ITEM_ID_DATA_LIST_ENTRY = -6;
-
- private static final int TEXT_PADDING_DP = 30;
-
- private final AutofillPopupDelegate mAutofillCallback;
- private final Context mContext;
- private final ViewAndroidDelegate mViewAndroidDelegate;
- private View mAnchorView;
- private float mAnchorWidth;
- private float mAnchorHeight;
- private float mAnchorX;
- private float mAnchorY;
- private Paint mLabelViewPaint;
- private Paint mSublabelViewPaint;
- private OnLayoutChangeListener mLayoutChangeListener;
-
- /**
- * An interface to handle the touch interaction with an AutofillPopup object.
- */
- public interface AutofillPopupDelegate {
- /**
- * Requests the controller to hide AutofillPopup.
- */
- public void requestHide();
-
- /**
- * Handles the selection of an Autofill suggestion from an AutofillPopup.
- * @param listIndex The index of the selected Autofill suggestion.
- */
- public void suggestionSelected(int listIndex);
- }
-
- /**
- * Creates an AutofillWindow with specified parameters.
- * @param context Application context.
- * @param viewAndroidDelegate View delegate used to add and remove views.
- * @param autofillCallback A object that handles the calls to the native AutofillPopupView.
- */
- public AutofillPopup(Context context, ViewAndroidDelegate viewAndroidDelegate,
- AutofillPopupDelegate autofillCallback) {
- super(context, null, 0, R.style.AutofillPopupWindow);
- mContext = context;
- mViewAndroidDelegate = viewAndroidDelegate ;
- mAutofillCallback = autofillCallback;
-
- setOnItemClickListener(this);
-
- mAnchorView = mViewAndroidDelegate.acquireAnchorView();
- mAnchorView.setId(R.id.autofill_popup_window);
- mAnchorView.setTag(this);
-
- mViewAndroidDelegate.setAnchorViewPosition(mAnchorView, mAnchorX, mAnchorY, mAnchorWidth,
- mAnchorHeight);
-
- mLayoutChangeListener = new OnLayoutChangeListener() {
- @Override
- public void onLayoutChange(View v, int left, int top, int right, int bottom,
- int oldLeft, int oldTop, int oldRight, int oldBottom) {
- if (v == mAnchorView) AutofillPopup.this.show();
- }
- };
-
- mAnchorView.addOnLayoutChangeListener(mLayoutChangeListener);
- setAnchorView(mAnchorView);
- }
-
- @Override
- public void show() {
- // An ugly hack to keep the popup from expanding on top of the keyboard.
- setInputMethodMode(INPUT_METHOD_NEEDED);
- super.show();
- }
-
- /**
- * Sets the location and the size of the anchor view that the AutofillPopup will use to attach
- * itself.
- * @param x X coordinate of the top left corner of the anchor view.
- * @param y Y coordinate of the top left corner of the anchor view.
- * @param width The width of the anchor view.
- * @param height The height of the anchor view.
- */
- public void setAnchorRect(float x, float y, float width, float height) {
- mAnchorWidth = width;
- mAnchorHeight = height;
- mAnchorX = x;
- mAnchorY = y;
- if (mAnchorView != null) {
- mViewAndroidDelegate.setAnchorViewPosition(mAnchorView, mAnchorX, mAnchorY,
- mAnchorWidth, mAnchorHeight);
- }
- }
-
- /**
- * Sets the Autofill suggestions to display in the popup and shows the popup.
- * @param suggestions Autofill suggestion data.
- */
- public void show(AutofillSuggestion[] suggestions) {
- // Remove the AutofillSuggestions with IDs that are not supported by Android
- ArrayList<AutofillSuggestion> cleanedData = new ArrayList<AutofillSuggestion>();
- for (int i = 0; i < suggestions.length; i++) {
- int itemId = suggestions[i].mUniqueId;
- if (itemId > 0 || itemId == ITEM_ID_AUTOCOMPLETE_ENTRY ||
- itemId == ITEM_ID_PASSWORD_ENTRY || itemId == ITEM_ID_DATA_LIST_ENTRY) {
- cleanedData.add(suggestions[i]);
- }
- }
- setAdapter(new AutofillListAdapter(mContext, cleanedData));
- // Once the mAnchorRect is resized and placed correctly, it will show the Autofill popup.
- mAnchorWidth = Math.max(getDesiredWidth(cleanedData), mAnchorWidth);
- mViewAndroidDelegate.setAnchorViewPosition(mAnchorView, mAnchorX, mAnchorY, mAnchorWidth,
- mAnchorHeight);
- }
-
- /**
- * Overrides the default dismiss behavior to request the controller to dismiss the view.
- */
- @Override
- public void dismiss() {
- mAutofillCallback.requestHide();
- }
-
- /**
- * Hides the popup and removes the anchor view from the ContainerView.
- */
- public void hide() {
- super.dismiss();
- mAnchorView.removeOnLayoutChangeListener(mLayoutChangeListener);
- mAnchorView.setTag(null);
- mViewAndroidDelegate.releaseAnchorView(mAnchorView);
- }
-
- /**
- * Get desired popup window width by calculating the maximum text length from Autofill data.
- * @param data Autofill suggestion data.
- * @return The popup window width in DIP.
- */
- private float getDesiredWidth(ArrayList<AutofillSuggestion> data) {
- if (mLabelViewPaint == null || mSublabelViewPaint == null) {
- LayoutInflater inflater =
- (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- View layout = inflater.inflate(R.layout.autofill_text, null);
- TextView labelView = (TextView) layout.findViewById(R.id.autofill_label);
- mLabelViewPaint = labelView.getPaint();
- TextView sublabelView = (TextView) layout.findViewById(R.id.autofill_sublabel);
- mSublabelViewPaint = sublabelView.getPaint();
- }
-
- float maxTextWidth = 0;
- Rect bounds = new Rect();
- for (int i = 0; i < data.size(); ++i) {
- bounds.setEmpty();
- String label = data.get(i).mLabel;
- if (!TextUtils.isEmpty(label)) {
- mLabelViewPaint.getTextBounds(label, 0, label.length(), bounds);
- }
- float labelWidth = bounds.width();
-
- bounds.setEmpty();
- String sublabel = data.get(i).mSublabel;
- if (!TextUtils.isEmpty(sublabel)) {
- mSublabelViewPaint.getTextBounds(sublabel, 0, sublabel.length(), bounds);
- }
-
- float localMax = Math.max(labelWidth, bounds.width());
- maxTextWidth = Math.max(maxTextWidth, localMax);
- }
- // Scale it down to make it unscaled by screen density.
- maxTextWidth = maxTextWidth / mContext.getResources().getDisplayMetrics().density;
- // Adding padding.
- return maxTextWidth + TEXT_PADDING_DP;
- }
-
- @Override
- public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
- mAutofillCallback.suggestionSelected(position);
- }
-
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillSuggestion.java b/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillSuggestion.java
deleted file mode 100644
index 51669ea5603..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/autofill/AutofillSuggestion.java
+++ /dev/null
@@ -1,26 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui.autofill;
-
-/**
- * Autofill suggestion container used to store information needed for each Autofill popup entry.
- */
-public class AutofillSuggestion {
- final String mLabel;
- final String mSublabel;
- final int mUniqueId;
-
- /**
- * Constructs a Autofill suggestion container.
- * @param name The name of the Autofill suggestion.
- * @param label The describing label of the Autofill suggestion.
- * @param uniqueId The unique id used to identify the Autofill suggestion.
- */
- public AutofillSuggestion(String name, String label, int uniqueId) {
- mLabel = name;
- mSublabel = label;
- mUniqueId = uniqueId;
- }
-} \ No newline at end of file
diff --git a/chromium/ui/android/java/src/org/chromium/ui/gfx/BitmapHelper.java b/chromium/ui/android/java/src/org/chromium/ui/gfx/BitmapHelper.java
deleted file mode 100644
index 97511a176a8..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/gfx/BitmapHelper.java
+++ /dev/null
@@ -1,69 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui.gfx;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import org.chromium.base.CalledByNative;
-import org.chromium.base.JNINamespace;
-
-@JNINamespace("ui")
-public class BitmapHelper {
- @CalledByNative
- public static Bitmap createBitmap(int width, int height) {
- return Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
- }
-
- /**
- * Decode and sample down a bitmap resource to the requested width and height.
- *
- * @param name The resource name of the bitmap to decode.
- * @param reqWidth The requested width of the resulting bitmap.
- * @param reqHeight The requested height of the resulting bitmap.
- * @return A bitmap sampled down from the original with the same aspect ratio and dimensions.
- * that are equal to or greater than the requested width and height.
- */
- @CalledByNative
- private static Bitmap decodeDrawableResource(String name,
- int reqWidth,
- int reqHeight) {
- Resources res = Resources.getSystem();
- int resId = res.getIdentifier(name, null, null);
-
- final BitmapFactory.Options options = new BitmapFactory.Options();
- options.inJustDecodeBounds = true;
- BitmapFactory.decodeResource(res, resId, options);
-
- options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);
-
- options.inJustDecodeBounds = false;
- return BitmapFactory.decodeResource(res, resId, options);
- }
-
- // http://developer.android.com/training/displaying-bitmaps/load-bitmap.html
- private static int calculateInSampleSize(BitmapFactory.Options options,
- int reqWidth,
- int reqHeight) {
- // Raw height and width of image
- final int height = options.outHeight;
- final int width = options.outWidth;
- int inSampleSize = 1;
-
- if (height > reqHeight || width > reqWidth) {
-
- // Calculate ratios of height and width to requested height and width
- final int heightRatio = Math.round((float) height / (float) reqHeight);
- final int widthRatio = Math.round((float) width / (float) reqWidth);
-
- // Choose the smallest ratio as inSampleSize value, this will guarantee
- // a final image with both dimensions larger than or equal to the
- // requested height and width.
- inSampleSize = heightRatio < widthRatio ? heightRatio : widthRatio;
- }
-
- return inSampleSize;
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/gfx/DeviceDisplayInfo.java b/chromium/ui/android/java/src/org/chromium/ui/gfx/DeviceDisplayInfo.java
deleted file mode 100644
index 088c9c2476e..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/gfx/DeviceDisplayInfo.java
+++ /dev/null
@@ -1,135 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui.gfx;
-
-import android.content.Context;
-import android.graphics.PixelFormat;
-import android.os.Build;
-import android.util.DisplayMetrics;
-import android.view.Display;
-import android.view.WindowManager;
-
-import org.chromium.base.CalledByNative;
-import org.chromium.base.JNINamespace;
-
-/**
- * This class facilitates access to android information typically only
- * available using the Java SDK, including {@link Display} properties.
- *
- * Currently the information consists of very raw display information (height, width, DPI scale)
- * regarding the main display.
- */
-@JNINamespace("gfx")
-public class DeviceDisplayInfo {
-
-
- private final Context mAppContext;
- private final WindowManager mWinManager;
-
- private DeviceDisplayInfo(Context context) {
- mAppContext = context.getApplicationContext();
- mWinManager = (WindowManager) mAppContext.getSystemService(Context.WINDOW_SERVICE);
- }
-
- /**
- * @return Display height in physical pixels.
- */
- @CalledByNative
- public int getDisplayHeight() {
- return getMetrics().heightPixels;
- }
-
- /**
- * @return Display width in physical pixels.
- */
- @CalledByNative
- public int getDisplayWidth() {
- return getMetrics().widthPixels;
- }
-
- @SuppressWarnings("deprecation")
- private int getPixelFormat() {
- if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1) {
- return getDisplay().getPixelFormat();
- }
- // JellyBean MR1 and later always uses RGBA_8888.
- return PixelFormat.RGBA_8888;
- }
-
- /**
- * @return Bits per pixel.
- */
- @CalledByNative
- public int getBitsPerPixel() {
- int format = getPixelFormat();
- PixelFormat info = new PixelFormat();
- PixelFormat.getPixelFormatInfo(format, info);
- return info.bitsPerPixel;
- }
-
- /**
- * @return Bits per component.
- */
- @SuppressWarnings("deprecation")
- @CalledByNative
- public int getBitsPerComponent() {
- int format = getPixelFormat();
- switch (format) {
- case PixelFormat.RGBA_4444:
- return 4;
-
- case PixelFormat.RGBA_5551:
- return 5;
-
- case PixelFormat.RGBA_8888:
- case PixelFormat.RGBX_8888:
- case PixelFormat.RGB_888:
- return 8;
-
- case PixelFormat.RGB_332:
- return 2;
-
- case PixelFormat.RGB_565:
- return 5;
-
- // Non-RGB formats.
- case PixelFormat.A_8:
- case PixelFormat.LA_88:
- case PixelFormat.L_8:
- return 0;
-
- // Unknown format. Use 8 as a sensible default.
- default:
- return 8;
- }
- }
-
- /**
- * @return A scaling factor for the Density Independent Pixel unit.
- * 1.0 is 160dpi, 0.75 is 120dpi, 2.0 is 320dpi.
- */
- @CalledByNative
- public double getDIPScale() {
- return getMetrics().density;
- }
-
- private Display getDisplay() {
- return mWinManager.getDefaultDisplay();
- }
-
- private DisplayMetrics getMetrics() {
- return mAppContext.getResources().getDisplayMetrics();
- }
-
- /**
- * Creates DeviceDisplayInfo for a given Context.
- * @param context A context to use.
- * @return DeviceDisplayInfo associated with a given Context.
- */
- @CalledByNative
- public static DeviceDisplayInfo create(Context context) {
- return new DeviceDisplayInfo(context);
- }
-}
diff --git a/chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureBridge.java b/chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureBridge.java
deleted file mode 100644
index 2333a01bb2f..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureBridge.java
+++ /dev/null
@@ -1,64 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui.gfx;
-
-import android.graphics.SurfaceTexture;
-import android.os.Build;
-
-import org.chromium.base.CalledByNative;
-import org.chromium.base.JNINamespace;
-
-/**
- * Wrapper class for the underlying platform's SurfaceTexture in order to
- * provide a stable JNI API.
- */
-@JNINamespace("gfx")
-class SurfaceTextureBridge {
- @CalledByNative
- private static SurfaceTexture create(int textureId) {
- return new SurfaceTexture(textureId);
- }
-
- @CalledByNative
- private static void destroy(SurfaceTexture surfaceTexture) {
- surfaceTexture.setOnFrameAvailableListener(null);
- surfaceTexture.release();
- }
-
- @CalledByNative
- private static void setFrameAvailableCallback(SurfaceTexture surfaceTexture,
- int nativeSurfaceTextureListener) {
- surfaceTexture.setOnFrameAvailableListener(
- new SurfaceTextureListener(nativeSurfaceTextureListener));
- }
-
- @CalledByNative
- private static void updateTexImage(SurfaceTexture surfaceTexture) {
- surfaceTexture.updateTexImage();
- }
-
- @CalledByNative
- private static void setDefaultBufferSize(SurfaceTexture surfaceTexture, int width,
- int height) {
- surfaceTexture.setDefaultBufferSize(width, height);
- }
-
- @CalledByNative
- private static void getTransformMatrix(SurfaceTexture surfaceTexture, float[] matrix) {
- surfaceTexture.getTransformMatrix(matrix);
- }
-
- @CalledByNative
- private static void attachToGLContext(SurfaceTexture surfaceTexture, int texName) {
- assert Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN;
- surfaceTexture.attachToGLContext(texName);
- }
-
- @CalledByNative
- private static void detachFromGLContext(SurfaceTexture surfaceTexture) {
- assert Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN;
- surfaceTexture.detachFromGLContext();
- }
-} \ No newline at end of file
diff --git a/chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureListener.java b/chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureListener.java
deleted file mode 100644
index 1b77370e4b6..00000000000
--- a/chromium/ui/android/java/src/org/chromium/ui/gfx/SurfaceTextureListener.java
+++ /dev/null
@@ -1,40 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-package org.chromium.ui.gfx;
-
-import android.graphics.SurfaceTexture;
-
-import org.chromium.base.JNINamespace;
-
-/**
- * Listener to an android SurfaceTexture object for frame availability.
- */
-@JNINamespace("gfx")
-class SurfaceTextureListener implements SurfaceTexture.OnFrameAvailableListener {
- // Used to determine the class instance to dispatch the native call to.
- private final int mNativeSurfaceTextureListener;
-
- SurfaceTextureListener(int nativeSurfaceTextureListener) {
- assert nativeSurfaceTextureListener != 0;
- mNativeSurfaceTextureListener = nativeSurfaceTextureListener;
- }
-
- @Override
- public void onFrameAvailable(SurfaceTexture surfaceTexture) {
- nativeFrameAvailable(mNativeSurfaceTextureListener);
- }
-
- @Override
- protected void finalize() throws Throwable {
- try {
- nativeDestroy(mNativeSurfaceTextureListener);
- } finally {
- super.finalize();
- }
- }
-
- private native void nativeFrameAvailable(int nativeSurfaceTextureListener);
- private native void nativeDestroy(int nativeSurfaceTextureListener);
-}
diff --git a/chromium/ui/android/java/strings/android_ui_strings.grd b/chromium/ui/android/java/strings/android_ui_strings.grd
deleted file mode 100644
index ee2f2d4cdf7..00000000000
--- a/chromium/ui/android/java/strings/android_ui_strings.grd
+++ /dev/null
@@ -1,125 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<grit current_release="1" latest_public_release="0">
- <release allow_pseudo="false" seq="1">
- <messages fallback_to_english="true">
- <message desc="Error shown when the browser is restarted due to low memory during a file picker operation. [CHAR-LIMIT=NONE]" name="IDS_LOW_MEMORY_ERROR">
- Unable to complete previous operation due to low memory
- </message>
- <message desc="Toast when the browser is unable to open a file for upload. [CHAR-LIMIT=32]" name="IDS_OPENING_FILE_ERROR">
- Failed to open selected file
- </message>
- <message desc="Text for ColorPicker button to go to advanced view. [CHAR-LIMIT=20]" name="IDS_COLOR_PICKER_BUTTON_MORE">
- More
- </message>
- <message desc="Label for hue slider in ColorPicker." name="IDS_COLOR_PICKER_HUE">
- Hue
- </message>
- <message desc="Label for saturation slider in ColorPicker." name="IDS_COLOR_PICKER_SATURATION">
- Saturation
- </message>
- <message desc="Label for value slider in ColorPicker." name="IDS_COLOR_PICKER_VALUE">
- Value
- </message>
- <message desc="Label for button in ColorPicker dialog for user to accept the currently chosen color. [CHAR-LIMIT=20]" name="IDS_COLOR_PICKER_BUTTON_SET">
- Set
- </message>
- <message desc="Label for button in ColorPicker dialog for user to cancel picking a color. [CHAR-LIMIT=20]" name="IDS_COLOR_PICKER_BUTTON_CANCEL">
- Cancel
- </message>
- <message desc="Title of ColorPicker dialog. [CHAR-LIMIT=20]" name="IDS_COLOR_PICKER_DIALOG_TITLE">
- Select color
- </message>
- </messages>
- </release>
- <translations>
- <file lang="am" path="translations/android_ui_strings_am.xtb" />
- <file lang="ar" path="translations/android_ui_strings_ar.xtb" />
- <file lang="bg" path="translations/android_ui_strings_bg.xtb" />
- <file lang="ca" path="translations/android_ui_strings_ca.xtb" />
- <file lang="cs" path="translations/android_ui_strings_cs.xtb" />
- <file lang="da" path="translations/android_ui_strings_da.xtb" />
- <file lang="de" path="translations/android_ui_strings_de.xtb" />
- <file lang="el" path="translations/android_ui_strings_el.xtb" />
- <file lang="en-GB" path="translations/android_ui_strings_en-GB.xtb" />
- <file lang="es" path="translations/android_ui_strings_es.xtb" />
- <file lang="es-419" path="translations/android_ui_strings_es-419.xtb" />
- <file lang="fa" path="translations/android_ui_strings_fa.xtb" />
- <file lang="fi" path="translations/android_ui_strings_fi.xtb" />
- <file lang="fil" path="translations/android_ui_strings_fil.xtb" />
- <file lang="fr" path="translations/android_ui_strings_fr.xtb" />
- <file lang="hi" path="translations/android_ui_strings_hi.xtb" />
- <file lang="hr" path="translations/android_ui_strings_hr.xtb" />
- <file lang="hu" path="translations/android_ui_strings_hu.xtb" />
- <file lang="id" path="translations/android_ui_strings_id.xtb" />
- <file lang="it" path="translations/android_ui_strings_it.xtb" />
- <file lang="iw" path="translations/android_ui_strings_iw.xtb" />
- <file lang="ja" path="translations/android_ui_strings_ja.xtb" />
- <file lang="ko" path="translations/android_ui_strings_ko.xtb" />
- <file lang="lt" path="translations/android_ui_strings_lt.xtb" />
- <file lang="lv" path="translations/android_ui_strings_lv.xtb" />
- <file lang="nl" path="translations/android_ui_strings_nl.xtb" />
- <file lang="no" path="translations/android_ui_strings_no.xtb" />
- <file lang="pl" path="translations/android_ui_strings_pl.xtb" />
- <file lang="pt-BR" path="translations/android_ui_strings_pt-BR.xtb" />
- <file lang="pt-PT" path="translations/android_ui_strings_pt-PT.xtb" />
- <file lang="ro" path="translations/android_ui_strings_ro.xtb" />
- <file lang="ru" path="translations/android_ui_strings_ru.xtb" />
- <file lang="sk" path="translations/android_ui_strings_sk.xtb" />
- <file lang="sl" path="translations/android_ui_strings_sl.xtb" />
- <file lang="sr" path="translations/android_ui_strings_sr.xtb" />
- <file lang="sv" path="translations/android_ui_strings_sv.xtb" />
- <file lang="sw" path="translations/android_ui_strings_sw.xtb" />
- <file lang="th" path="translations/android_ui_strings_th.xtb" />
- <file lang="tr" path="translations/android_ui_strings_tr.xtb" />
- <file lang="uk" path="translations/android_ui_strings_uk.xtb" />
- <file lang="vi" path="translations/android_ui_strings_vi.xtb" />
- <file lang="zh-CN" path="translations/android_ui_strings_zh-CN.xtb" />
- <file lang="zh-TW" path="translations/android_ui_strings_zh-TW.xtb" />
- </translations>
- <outputs>
- <output filename="values-am/android_ui_strings.xml" lang="am" type="android" />
- <output filename="values-ar/android_ui_strings.xml" lang="ar" type="android" />
- <output filename="values-bg/android_ui_strings.xml" lang="bg" type="android" />
- <output filename="values-ca/android_ui_strings.xml" lang="ca" type="android" />
- <output filename="values-cs/android_ui_strings.xml" lang="cs" type="android" />
- <output filename="values-da/android_ui_strings.xml" lang="da" type="android" />
- <output filename="values-de/android_ui_strings.xml" lang="de" type="android" />
- <output filename="values-el/android_ui_strings.xml" lang="el" type="android" />
- <output filename="values/android_ui_strings.xml" lang="en" type="android" />
- <output filename="values-en-rGB/android_ui_strings.xml" lang="en-GB" type="android" />
- <output filename="values-es/android_ui_strings.xml" lang="es" type="android" />
- <output filename="values-es-rUS/android_ui_strings.xml" lang="es-419" type="android" />
- <output filename="values-fa/android_ui_strings.xml" lang="fa" type="android" />
- <output filename="values-fi/android_ui_strings.xml" lang="fi" type="android" />
- <output filename="values-tl/android_ui_strings.xml" lang="fil" type="android" />
- <output filename="values-fr/android_ui_strings.xml" lang="fr" type="android" />
- <output filename="values-hi/android_ui_strings.xml" lang="hi" type="android" />
- <output filename="values-hr/android_ui_strings.xml" lang="hr" type="android" />
- <output filename="values-hu/android_ui_strings.xml" lang="hu" type="android" />
- <output filename="values-in/android_ui_strings.xml" lang="id" type="android" />
- <output filename="values-it/android_ui_strings.xml" lang="it" type="android" />
- <output filename="values-iw/android_ui_strings.xml" lang="iw" type="android" />
- <output filename="values-ja/android_ui_strings.xml" lang="ja" type="android" />
- <output filename="values-ko/android_ui_strings.xml" lang="ko" type="android" />
- <output filename="values-lt/android_ui_strings.xml" lang="lt" type="android" />
- <output filename="values-lv/android_ui_strings.xml" lang="lv" type="android" />
- <output filename="values-nl/android_ui_strings.xml" lang="nl" type="android" />
- <output filename="values-nb/android_ui_strings.xml" lang="no" type="android" />
- <output filename="values-pl/android_ui_strings.xml" lang="pl" type="android" />
- <output filename="values-pt-rBR/android_ui_strings.xml" lang="pt-BR" type="android" />
- <output filename="values-pt-rPT/android_ui_strings.xml" lang="pt-PT" type="android" />
- <output filename="values-ro/android_ui_strings.xml" lang="ro" type="android" />
- <output filename="values-ru/android_ui_strings.xml" lang="ru" type="android" />
- <output filename="values-sk/android_ui_strings.xml" lang="sk" type="android" />
- <output filename="values-sl/android_ui_strings.xml" lang="sl" type="android" />
- <output filename="values-sr/android_ui_strings.xml" lang="sr" type="android" />
- <output filename="values-sv/android_ui_strings.xml" lang="sv" type="android" />
- <output filename="values-sw/android_ui_strings.xml" lang="sw" type="android" />
- <output filename="values-th/android_ui_strings.xml" lang="th" type="android" />
- <output filename="values-tr/android_ui_strings.xml" lang="tr" type="android" />
- <output filename="values-uk/android_ui_strings.xml" lang="uk" type="android" />
- <output filename="values-vi/android_ui_strings.xml" lang="vi" type="android" />
- <output filename="values-zh-rCN/android_ui_strings.xml" lang="zh-CN" type="android" />
- <output filename="values-zh-rTW/android_ui_strings.xml" lang="zh-TW" type="android" />
- </outputs>
-</grit>
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_am.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_am.xtb
deleted file mode 100644
index 5009378fbdb..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_am.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="am">
-<translation id="7658239707568436148">ሰርዝ</translation>
-<translation id="6727102863431372879">አዘጋጅ</translation>
-<translation id="6042308850641462728">ተጨማሪ</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_ar.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_ar.xtb
deleted file mode 100644
index 20d74b0896c..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_ar.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="ar">
-<translation id="7658239707568436148">إلغاء</translation>
-<translation id="6727102863431372879">تعيين</translation>
-<translation id="6042308850641462728">المزيد</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_bg.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_bg.xtb
deleted file mode 100644
index 3f7f0eebb0c..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_bg.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="bg">
-<translation id="7658239707568436148">Отказ</translation>
-<translation id="6727102863431372879">Задаване</translation>
-<translation id="6042308850641462728">Още</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_ca.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_ca.xtb
deleted file mode 100644
index b19aac4fc3e..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_ca.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="ca">
-<translation id="7658239707568436148">Cancel·la</translation>
-<translation id="6727102863431372879">Configura</translation>
-<translation id="6042308850641462728">Més</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_cs.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_cs.xtb
deleted file mode 100644
index b39bcf81dcc..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_cs.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="cs">
-<translation id="7658239707568436148">Zrušit</translation>
-<translation id="6727102863431372879">Nastavit</translation>
-<translation id="6042308850641462728">Více</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_da.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_da.xtb
deleted file mode 100644
index bdc4393844d..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_da.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="da">
-<translation id="7658239707568436148">Annuller</translation>
-<translation id="6727102863431372879">Angiv</translation>
-<translation id="6042308850641462728">Mere</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_de.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_de.xtb
deleted file mode 100644
index 3226fe1c64b..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_de.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="de">
-<translation id="7658239707568436148">Abbrechen</translation>
-<translation id="6727102863431372879">Festlegen</translation>
-<translation id="6042308850641462728">Mehr</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_el.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_el.xtb
deleted file mode 100644
index 23bcfbbc582..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_el.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="el">
-<translation id="7658239707568436148">Ακύρωση</translation>
-<translation id="6727102863431372879">Ορισμός</translation>
-<translation id="6042308850641462728">Περισσότερα</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_en-GB.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_en-GB.xtb
deleted file mode 100644
index 760ecfbba68..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_en-GB.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="en-GB">
-<translation id="7658239707568436148">Cancel</translation>
-<translation id="6727102863431372879">Set</translation>
-<translation id="6042308850641462728">More</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_es-419.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_es-419.xtb
deleted file mode 100644
index a72fce86599..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_es-419.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="es-419">
-<translation id="7658239707568436148">Cancelar</translation>
-<translation id="6727102863431372879">Establecer</translation>
-<translation id="6042308850641462728">Más</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_es.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_es.xtb
deleted file mode 100644
index 13d9dcb1077..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_es.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="es">
-<translation id="7658239707568436148">Cancelar</translation>
-<translation id="6727102863431372879">Establecer</translation>
-<translation id="6042308850641462728">Más</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_fa.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_fa.xtb
deleted file mode 100644
index a5250a0b344..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_fa.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="fa">
-<translation id="7658239707568436148">لغو</translation>
-<translation id="6727102863431372879">تنظیم</translation>
-<translation id="6042308850641462728">بیشتر</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_fi.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_fi.xtb
deleted file mode 100644
index 432a6308fe4..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_fi.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="fi">
-<translation id="7658239707568436148">Peruuta</translation>
-<translation id="6727102863431372879">Aseta</translation>
-<translation id="6042308850641462728">Lisää</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_fil.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_fil.xtb
deleted file mode 100644
index 43d1a8dc4ba..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_fil.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="fil">
-<translation id="7658239707568436148">Kanselahin</translation>
-<translation id="6727102863431372879">Itakda</translation>
-<translation id="6042308850641462728">Higit pa</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_fr.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_fr.xtb
deleted file mode 100644
index 0996b594dd4..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_fr.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="fr">
-<translation id="7658239707568436148">Annuler</translation>
-<translation id="6727102863431372879">Définir</translation>
-<translation id="6042308850641462728">Plus</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_hi.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_hi.xtb
deleted file mode 100644
index ecd9dfd37bd..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_hi.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="hi">
-<translation id="7658239707568436148">रद्द करें</translation>
-<translation id="6727102863431372879">सेट करें</translation>
-<translation id="6042308850641462728">अधिक</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_hr.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_hr.xtb
deleted file mode 100644
index 39ab27b13b8..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_hr.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="hr">
-<translation id="7658239707568436148">Odustani</translation>
-<translation id="6727102863431372879">Postavi</translation>
-<translation id="6042308850641462728">Više</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_hu.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_hu.xtb
deleted file mode 100644
index cf229bc45dd..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_hu.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="hu">
-<translation id="7658239707568436148">Mégse</translation>
-<translation id="6727102863431372879">Beállítás</translation>
-<translation id="6042308850641462728">Hosszabban</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_id.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_id.xtb
deleted file mode 100644
index 7f11b4549d6..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_id.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="id">
-<translation id="7658239707568436148">Batal</translation>
-<translation id="6727102863431372879">Setel</translation>
-<translation id="6042308850641462728">Lainnya</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_it.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_it.xtb
deleted file mode 100644
index 3bd89fe29f6..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_it.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="it">
-<translation id="7658239707568436148">Annulla</translation>
-<translation id="6727102863431372879">Imposta</translation>
-<translation id="6042308850641462728">Più</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_iw.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_iw.xtb
deleted file mode 100644
index ea0a9849a65..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_iw.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="iw">
-<translation id="7658239707568436148">ביטול</translation>
-<translation id="6727102863431372879">הגדר</translation>
-<translation id="6042308850641462728">עוד</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_ja.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_ja.xtb
deleted file mode 100644
index 18989640fd4..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_ja.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="ja">
-<translation id="7658239707568436148">キャンセル</translation>
-<translation id="6727102863431372879">設定</translation>
-<translation id="6042308850641462728">詳細表示</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_ko.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_ko.xtb
deleted file mode 100644
index 3667057117d..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_ko.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="ko">
-<translation id="7658239707568436148">취소</translation>
-<translation id="6727102863431372879">설정</translation>
-<translation id="6042308850641462728">더보기</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_lt.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_lt.xtb
deleted file mode 100644
index 73968166e3d..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_lt.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="lt">
-<translation id="7658239707568436148">Atšaukti</translation>
-<translation id="6727102863431372879">Nustatyti</translation>
-<translation id="6042308850641462728">Daugiau</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_lv.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_lv.xtb
deleted file mode 100644
index 4d9f44c4938..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_lv.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="lv">
-<translation id="7658239707568436148">Atcelt</translation>
-<translation id="6727102863431372879">Iestatīt</translation>
-<translation id="6042308850641462728">Vairāk</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_nl.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_nl.xtb
deleted file mode 100644
index c3a47d4977a..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_nl.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="nl">
-<translation id="7658239707568436148">Annuleren</translation>
-<translation id="6727102863431372879">Instellen</translation>
-<translation id="6042308850641462728">Meer</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_no.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_no.xtb
deleted file mode 100644
index c91bc537447..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_no.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="no">
-<translation id="7658239707568436148">Avbryt</translation>
-<translation id="6727102863431372879">Angi</translation>
-<translation id="6042308850641462728">Mer</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_pl.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_pl.xtb
deleted file mode 100644
index 1fa6f0e3650..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_pl.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="pl">
-<translation id="7658239707568436148">Anuluj</translation>
-<translation id="6727102863431372879">Ustaw</translation>
-<translation id="6042308850641462728">Więcej</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_pt-BR.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_pt-BR.xtb
deleted file mode 100644
index 0c5f3f8a018..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_pt-BR.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="pt-BR">
-<translation id="7658239707568436148">Cancelar</translation>
-<translation id="6727102863431372879">Definir</translation>
-<translation id="6042308850641462728">Mais</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_pt-PT.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_pt-PT.xtb
deleted file mode 100644
index 2f315afe1f0..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_pt-PT.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="pt-PT">
-<translation id="7658239707568436148">Cancelar</translation>
-<translation id="6727102863431372879">Definir</translation>
-<translation id="6042308850641462728">Mais</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_ro.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_ro.xtb
deleted file mode 100644
index e0b2c506830..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_ro.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="ro">
-<translation id="7658239707568436148">Anulaţi</translation>
-<translation id="6727102863431372879">Setați</translation>
-<translation id="6042308850641462728">Mai mult</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_ru.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_ru.xtb
deleted file mode 100644
index 827ac4b0dd2..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_ru.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="ru">
-<translation id="7658239707568436148">Отмена</translation>
-<translation id="6727102863431372879">Установить</translation>
-<translation id="6042308850641462728">Подробнее...</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_sk.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_sk.xtb
deleted file mode 100644
index 50599a2f56c..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_sk.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="sk">
-<translation id="7658239707568436148">Zrušiť</translation>
-<translation id="6727102863431372879">Nastaviť</translation>
-<translation id="6042308850641462728">Viac</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_sl.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_sl.xtb
deleted file mode 100644
index 57093451693..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_sl.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="sl">
-<translation id="7658239707568436148">Prekliči</translation>
-<translation id="6727102863431372879">Nastavi</translation>
-<translation id="6042308850641462728">Več</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_sr.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_sr.xtb
deleted file mode 100644
index 9475544e08d..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_sr.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="sr">
-<translation id="7658239707568436148">Откажи</translation>
-<translation id="6727102863431372879">Постави</translation>
-<translation id="6042308850641462728">Више</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_sv.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_sv.xtb
deleted file mode 100644
index 092959a0d06..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_sv.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="sv">
-<translation id="7658239707568436148">Avbryt</translation>
-<translation id="6727102863431372879">Ange</translation>
-<translation id="6042308850641462728">Mer</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_sw.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_sw.xtb
deleted file mode 100644
index 1de7db27052..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_sw.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="sw">
-<translation id="7658239707568436148">Ghairi</translation>
-<translation id="6727102863431372879">Weka</translation>
-<translation id="6042308850641462728">Zaidi</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_th.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_th.xtb
deleted file mode 100644
index d8aec042ac6..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_th.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="th">
-<translation id="7658239707568436148">ยกเลิก</translation>
-<translation id="6727102863431372879">ตั้งค่า</translation>
-<translation id="6042308850641462728">เพิ่มเติม</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_tr.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_tr.xtb
deleted file mode 100644
index 2a37f797deb..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_tr.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="tr">
-<translation id="7658239707568436148">İptal</translation>
-<translation id="6727102863431372879">Ayarla</translation>
-<translation id="6042308850641462728">Daha fazla</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_uk.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_uk.xtb
deleted file mode 100644
index b9a0ae2ab81..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_uk.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="uk">
-<translation id="7658239707568436148">Скасувати</translation>
-<translation id="6727102863431372879">Встановити</translation>
-<translation id="6042308850641462728">Більше</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_vi.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_vi.xtb
deleted file mode 100644
index c66fb60ae74..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_vi.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="vi">
-<translation id="7658239707568436148">Hủy</translation>
-<translation id="6727102863431372879">Đặt</translation>
-<translation id="6042308850641462728">Thêm</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_zh-CN.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_zh-CN.xtb
deleted file mode 100644
index 8228c71b152..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_zh-CN.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="zh-CN">
-<translation id="7658239707568436148">取消</translation>
-<translation id="6727102863431372879">设置</translation>
-<translation id="6042308850641462728">更多</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/java/strings/translations/android_ui_strings_zh-TW.xtb b/chromium/ui/android/java/strings/translations/android_ui_strings_zh-TW.xtb
deleted file mode 100644
index edf79b55e95..00000000000
--- a/chromium/ui/android/java/strings/translations/android_ui_strings_zh-TW.xtb
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" ?>
-<!DOCTYPE translationbundle>
-<translationbundle lang="zh-TW">
-<translation id="7658239707568436148">取消</translation>
-<translation id="6727102863431372879">設定</translation>
-<translation id="6042308850641462728">詳細資訊</translation>
-</translationbundle> \ No newline at end of file
diff --git a/chromium/ui/android/ui_jni_registrar.cc b/chromium/ui/android/ui_jni_registrar.cc
deleted file mode 100644
index 8216e01578e..00000000000
--- a/chromium/ui/android/ui_jni_registrar.cc
+++ /dev/null
@@ -1,34 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/android/ui_jni_registrar.h"
-
-#include "base/android/jni_android.h"
-#include "base/android/jni_registrar.h"
-#include "ui/android/view_android.h"
-#include "ui/android/window_android.h"
-#include "ui/base/clipboard/clipboard_android_initialization.h"
-#include "ui/base/l10n/l10n_util_android.h"
-#include "ui/gfx/android/device_display_info.h"
-#include "ui/gfx/android/java_bitmap.h"
-
-namespace ui {
-namespace android {
-
-static base::android::RegistrationMethod kUiRegisteredMethods[] = {
- { "Clipboard", ui::RegisterClipboardAndroid },
- { "DeviceDisplayInfo", gfx::DeviceDisplayInfo::RegisterDeviceDisplayInfo },
- { "JavaBitmap", gfx::JavaBitmap::RegisterJavaBitmap },
- { "LocalizationUtils", l10n_util::RegisterLocalizationUtil },
- { "ViewAndroid", ui::ViewAndroid::RegisterViewAndroid },
- { "WindowAndroid", ui::WindowAndroid::RegisterWindowAndroid },
-};
-
-bool RegisterJni(JNIEnv* env) {
- return RegisterNativeMethods(env, kUiRegisteredMethods,
- arraysize(kUiRegisteredMethods));
-}
-
-} // namespace android
-} // namespace ui
diff --git a/chromium/ui/android/ui_jni_registrar.h b/chromium/ui/android/ui_jni_registrar.h
deleted file mode 100644
index f40ed407823..00000000000
--- a/chromium/ui/android/ui_jni_registrar.h
+++ /dev/null
@@ -1,21 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_ANDROID_UI_JNI_REGISTRAR_H_
-#define UI_ANDROID_UI_JNI_REGISTRAR_H_
-
-#include <jni.h>
-
-#include "ui/base/ui_export.h"
-
-namespace ui {
-namespace android {
-
-// Register all JNI bindings necessary for chrome.
-UI_EXPORT bool RegisterJni(JNIEnv* env);
-
-} // namespace android
-} // namespace ui
-
-#endif // UI_ANDROID_UI_JNI_REGISTRAR_H_
diff --git a/chromium/ui/android/window_android.cc b/chromium/ui/android/window_android.cc
index 1f2ccb2f972..439268fd336 100644
--- a/chromium/ui/android/window_android.cc
+++ b/chromium/ui/android/window_android.cc
@@ -5,6 +5,7 @@
#include "ui/android/window_android.h"
#include "base/android/jni_android.h"
+#include "base/android/jni_array.h"
#include "base/android/jni_helper.h"
#include "base/android/scoped_java_ref.h"
#include "jni/WindowAndroid_jni.h"
@@ -33,6 +34,22 @@ bool WindowAndroid::RegisterWindowAndroid(JNIEnv* env) {
WindowAndroid::~WindowAndroid() {
}
+bool WindowAndroid::GrabSnapshot(
+ int content_x, int content_y, int width, int height,
+ std::vector<unsigned char>* png_representation) {
+ JNIEnv* env = AttachCurrentThread();
+ ScopedJavaLocalRef<jbyteArray> result =
+ Java_WindowAndroid_grabSnapshot(env, GetJavaObject().obj(),
+ content_x + content_offset_.x(),
+ content_y + content_offset_.y(),
+ width, height);
+ if (result.is_null())
+ return false;
+ base::android::JavaByteArrayToByteVector(
+ env, result.obj(), png_representation);
+ return true;
+}
+
// ----------------------------------------------------------------------------
// Native JNI methods
// ----------------------------------------------------------------------------
diff --git a/chromium/ui/android/window_android.h b/chromium/ui/android/window_android.h
index c1c5c44c2d2..14b1f09e222 100644
--- a/chromium/ui/android/window_android.h
+++ b/chromium/ui/android/window_android.h
@@ -6,9 +6,11 @@
#define UI_ANDROID_WINDOW_ANDROID_H_
#include <jni.h>
+#include <vector>
#include "base/android/jni_helper.h"
#include "base/android/scoped_java_ref.h"
#include "ui/base/ui_export.h"
+#include "ui/gfx/vector2d_f.h"
namespace ui {
@@ -23,10 +25,20 @@ class UI_EXPORT WindowAndroid {
static bool RegisterWindowAndroid(JNIEnv* env);
+ // The content offset is used to translate snapshots to the correct part of
+ // the window.
+ void set_content_offset(const gfx::Vector2dF& content_offset) {
+ content_offset_ = content_offset;
+ }
+
+ bool GrabSnapshot(int content_x, int content_y, int width, int height,
+ std::vector<unsigned char>* png_representation);
+
private:
~WindowAndroid();
JavaObjectWeakGlobalRef weak_java_window_;
+ gfx::Vector2dF content_offset_;
DISALLOW_COPY_AND_ASSIGN(WindowAndroid);
};
diff --git a/chromium/ui/app_list/app_list.gyp b/chromium/ui/app_list/app_list.gyp
index 35b4663a624..1d968712349 100644
--- a/chromium/ui/app_list/app_list.gyp
+++ b/chromium/ui/app_list/app_list.gyp
@@ -36,7 +36,6 @@
'app_list_model.h',
'app_list_model_observer.h',
'app_list_view_delegate.h',
- 'apps_grid_view_delegate.h',
'cocoa/app_list_pager_view.h',
'cocoa/app_list_pager_view.mm',
'cocoa/app_list_view_controller.h',
@@ -58,8 +57,6 @@
'cocoa/apps_search_results_model_bridge.mm',
'cocoa/blue_label_button.h',
'cocoa/blue_label_button.mm',
- 'cocoa/current_user_menu_item_view.h',
- 'cocoa/current_user_menu_item_view.mm',
'cocoa/item_drag_controller.h',
'cocoa/item_drag_controller.mm',
'cocoa/scroll_view_with_no_scrollbars.h',
@@ -72,13 +69,10 @@
'search_box_model.cc',
'search_box_model.h',
'search_box_model_observer.h',
- 'search_box_view_delegate.h',
'search_result.cc',
'search_result.h',
- 'search_result_list_view_delegate.h',
'signin_delegate.cc',
'signin_delegate.h',
- 'signin_delegate_observer.h',
'views/app_list_background.cc',
'views/app_list_background.h',
'views/app_list_drag_and_drop_host.h',
@@ -92,6 +86,7 @@
'views/app_list_view.h',
'views/apps_grid_view.cc',
'views/apps_grid_view.h',
+ 'views/apps_grid_view_delegate.h',
'views/cached_label.cc',
'views/cached_label.h',
'views/contents_view.cc',
@@ -104,10 +99,12 @@
'views/pulsing_block_view.h',
'views/search_box_view.cc',
'views/search_box_view.h',
+ 'views/search_box_view_delegate.h',
'views/search_result_actions_view.cc',
'views/search_result_actions_view.h',
'views/search_result_list_view.cc',
'views/search_result_list_view.h',
+ 'views/search_result_list_view_delegate.h',
'views/search_result_view.cc',
'views/search_result_view.h',
'views/search_result_view_delegate.h',
diff --git a/chromium/ui/app_list/app_list_item_model.cc b/chromium/ui/app_list/app_list_item_model.cc
index c9aedb59be8..65b87a33ab4 100644
--- a/chromium/ui/app_list/app_list_item_model.cc
+++ b/chromium/ui/app_list/app_list_item_model.cc
@@ -24,11 +24,13 @@ void AppListItemModel::SetIcon(const gfx::ImageSkia& icon, bool has_shadow) {
FOR_EACH_OBSERVER(AppListItemModelObserver, observers_, ItemIconChanged());
}
-void AppListItemModel::SetTitle(const std::string& title) {
- if (title_ == title)
+void AppListItemModel::SetTitleAndFullName(const std::string& title,
+ const std::string& full_name) {
+ if (title_ == title && full_name_ == full_name)
return;
title_ = title;
+ full_name_ = full_name;
FOR_EACH_OBSERVER(AppListItemModelObserver, observers_, ItemTitleChanged());
}
diff --git a/chromium/ui/app_list/app_list_item_model.h b/chromium/ui/app_list/app_list_item_model.h
index d437564ef75..e9675a83ee1 100644
--- a/chromium/ui/app_list/app_list_item_model.h
+++ b/chromium/ui/app_list/app_list_item_model.h
@@ -31,8 +31,10 @@ class APP_LIST_EXPORT AppListItemModel {
const gfx::ImageSkia& icon() const { return icon_; }
bool has_shadow() const { return has_shadow_; }
- void SetTitle(const std::string& title);
+ void SetTitleAndFullName(const std::string& title,
+ const std::string& full_name);
const std::string& title() const { return title_; }
+ const std::string& full_name() const { return full_name_; }
void SetHighlighted(bool highlighted);
bool highlighted() const { return highlighted_; }
@@ -49,7 +51,8 @@ class APP_LIST_EXPORT AppListItemModel {
void AddObserver(AppListItemModelObserver* observer);
void RemoveObserver(AppListItemModelObserver* observer);
- // Returns the context menu model for this item.
+ // Returns the context menu model for this item, or NULL if there is currently
+ // no menu for the item (e.g. during install).
// Note the returned menu model is owned by this item.
virtual ui::MenuModel* GetContextMenuModel();
@@ -57,6 +60,7 @@ class APP_LIST_EXPORT AppListItemModel {
gfx::ImageSkia icon_;
bool has_shadow_;
std::string title_;
+ std::string full_name_;
bool highlighted_;
bool is_installing_;
int percent_downloaded_;
diff --git a/chromium/ui/app_list/app_list_menu.cc b/chromium/ui/app_list/app_list_menu.cc
index 95d6ac38d91..896bcf91965 100644
--- a/chromium/ui/app_list/app_list_menu.cc
+++ b/chromium/ui/app_list/app_list_menu.cc
@@ -4,6 +4,7 @@
#include "ui/app_list/app_list_menu.h"
+#include "grit/ui_resources.h"
#include "grit/ui_strings.h"
#include "ui/app_list/app_list_view_delegate.h"
#include "ui/base/l10n/l10n_util.h"
@@ -12,17 +13,40 @@
namespace app_list {
-AppListMenu::AppListMenu(AppListViewDelegate* delegate)
+AppListMenu::AppListMenu(AppListViewDelegate* delegate,
+ const AppListModel::Users& users)
: menu_model_(this),
- delegate_(delegate) {
+ delegate_(delegate),
+ users_(users) {
InitMenu();
}
AppListMenu::~AppListMenu() {}
void AppListMenu::InitMenu() {
- menu_model_.AddItem(CURRENT_USER, base::string16());
- menu_model_.AddSeparator(ui::NORMAL_SEPARATOR);
+ // User selector menu section. We don't show the user selector if there is
+ // only 1 user.
+ if (users_.size() > 1) {
+ for (size_t i = 0; i < users_.size(); ++i) {
+#if defined(OS_MACOSX)
+ menu_model_.AddRadioItem(SELECT_PROFILE + i,
+ users_[i].email.empty() ? users_[i].name
+ : users_[i].email,
+ 0 /* group_id */);
+#elif defined(OS_WIN)
+ menu_model_.AddItem(SELECT_PROFILE + i, users_[i].name);
+ int menu_index = menu_model_.GetIndexOfCommandId(SELECT_PROFILE + i);
+ menu_model_.SetSublabel(menu_index, users_[i].email);
+ // Use custom check mark.
+ if (users_[i].active) {
+ ui::ResourceBundle& rb = ui::ResourceBundle::GetSharedInstance();
+ menu_model_.SetIcon(menu_index, gfx::Image(*rb.GetImageSkiaNamed(
+ IDR_APP_LIST_USER_INDICATOR)));
+ }
+#endif
+ }
+ menu_model_.AddSeparator(ui::NORMAL_SEPARATOR);
+ }
menu_model_.AddItem(SHOW_SETTINGS, l10n_util::GetStringUTF16(
IDS_APP_LIST_OPEN_SETTINGS));
@@ -35,7 +59,12 @@ void AppListMenu::InitMenu() {
}
bool AppListMenu::IsCommandIdChecked(int command_id) const {
+#if defined(OS_MACOSX)
+ DCHECK_LT(static_cast<unsigned>(command_id) - SELECT_PROFILE, users_.size());
+ return users_[command_id - SELECT_PROFILE].active;
+#else
return false;
+#endif
}
bool AppListMenu::IsCommandIdEnabled(int command_id) const {
@@ -48,9 +77,12 @@ bool AppListMenu::GetAcceleratorForCommandId(int command_id,
}
void AppListMenu::ExecuteCommand(int command_id, int event_flags) {
+ if (command_id >= SELECT_PROFILE) {
+ delegate_->ShowForProfileByPath(
+ users_[command_id - SELECT_PROFILE].profile_path);
+ return;
+ }
switch (command_id) {
- case CURRENT_USER:
- break; // Do nothing.
case SHOW_SETTINGS:
delegate_->OpenSettings();
break;
diff --git a/chromium/ui/app_list/app_list_menu.h b/chromium/ui/app_list/app_list_menu.h
index ff4be49e4c5..fa42b936d1d 100644
--- a/chromium/ui/app_list/app_list_menu.h
+++ b/chromium/ui/app_list/app_list_menu.h
@@ -5,6 +5,7 @@
#ifndef UI_APP_LIST_APP_LIST_MENU_H_
#define UI_APP_LIST_APP_LIST_MENU_H_
+#include "ui/app_list/app_list_model.h"
#include "ui/base/models/simple_menu_model.h"
namespace app_list {
@@ -17,13 +18,17 @@ class AppListViewDelegate;
class AppListMenu : public ui::SimpleMenuModel::Delegate {
public:
enum AppListMenuCommands {
- CURRENT_USER,
SHOW_SETTINGS,
SHOW_HELP,
SHOW_FEEDBACK,
+ // |SELECT_PROFILE| must remain the last enum because values greater than
+ // |SELECT_PROFILE| are used to indicate a profile index.
+ SELECT_PROFILE,
};
- explicit AppListMenu(AppListViewDelegate* delegate);
+ AppListMenu(
+ AppListViewDelegate* delegate,
+ const AppListModel::Users& users);
virtual ~AppListMenu();
ui::SimpleMenuModel* menu_model() { return &menu_model_; }
@@ -40,6 +45,7 @@ class AppListMenu : public ui::SimpleMenuModel::Delegate {
ui::SimpleMenuModel menu_model_;
AppListViewDelegate* delegate_;
+ AppListModel::Users users_;
DISALLOW_COPY_AND_ASSIGN(AppListMenu);
};
diff --git a/chromium/ui/app_list/app_list_model.cc b/chromium/ui/app_list/app_list_model.cc
index 4f473efbc36..d8e3c8bc016 100644
--- a/chromium/ui/app_list/app_list_model.cc
+++ b/chromium/ui/app_list/app_list_model.cc
@@ -11,10 +11,15 @@
namespace app_list {
+AppListModel::User::User() : active(false) {}
+
+AppListModel::User::~User() {}
+
AppListModel::AppListModel()
: apps_(new Apps),
search_box_(new SearchBoxModel),
results_(new SearchResults),
+ signed_in_(false),
status_(STATUS_NORMAL) {
}
@@ -39,4 +44,21 @@ void AppListModel::SetStatus(Status status) {
OnAppListModelStatusChanged());
}
+void AppListModel::SetUsers(const Users& users) {
+ users_ = users;
+ FOR_EACH_OBSERVER(AppListModelObserver,
+ observers_,
+ OnAppListModelUsersChanged());
+}
+
+void AppListModel::SetSignedIn(bool signed_in) {
+ if (signed_in_ == signed_in)
+ return;
+
+ signed_in_ = signed_in;
+ FOR_EACH_OBSERVER(AppListModelObserver,
+ observers_,
+ OnAppListModelSigninStatusChanged());
+}
+
} // namespace app_list
diff --git a/chromium/ui/app_list/app_list_model.h b/chromium/ui/app_list/app_list_model.h
index 4c46a012329..1145a3683fb 100644
--- a/chromium/ui/app_list/app_list_model.h
+++ b/chromium/ui/app_list/app_list_model.h
@@ -5,9 +5,13 @@
#ifndef UI_APP_LIST_APP_LIST_MODEL_H_
#define UI_APP_LIST_APP_LIST_MODEL_H_
+#include <vector>
+
#include "base/basictypes.h"
+#include "base/files/file_path.h"
#include "base/memory/scoped_ptr.h"
#include "base/observer_list.h"
+#include "base/strings/string16.h"
#include "ui/app_list/app_list_export.h"
#include "ui/base/models/list_model.h"
@@ -24,6 +28,24 @@ class SearchResult;
// the model for SearchBoxView. SearchResults owns a list of SearchResult.
class APP_LIST_EXPORT AppListModel {
public:
+ // A user of the app list.
+ struct APP_LIST_EXPORT User {
+ User();
+ ~User();
+
+ // Whether or not this user is the current user of the app list.
+ bool active;
+
+ // The name of this user.
+ base::string16 name;
+
+ // The email address of this user.
+ base::string16 email;
+
+ // The path to this user's profile directory.
+ base::FilePath profile_path;
+ };
+
enum Status {
STATUS_NORMAL,
STATUS_SYNCING, // Syncing apps or installing synced apps.
@@ -31,6 +53,7 @@ class APP_LIST_EXPORT AppListModel {
typedef ui::ListModel<AppListItemModel> Apps;
typedef ui::ListModel<SearchResult> SearchResults;
+ typedef std::vector<User> Users;
AppListModel();
~AppListModel();
@@ -39,11 +62,18 @@ class APP_LIST_EXPORT AppListModel {
void RemoveObserver(AppListModelObserver* observer);
void SetStatus(Status status);
+ void SetUsers(const Users& profile_menu_items);
+ void SetSignedIn(bool signed_in);
Apps* apps() { return apps_.get(); }
SearchBoxModel* search_box() { return search_box_.get(); }
SearchResults* results() { return results_.get(); }
Status status() const { return status_; }
+ bool signed_in() const { return signed_in_; }
+
+ const Users& users() const {
+ return users_;
+ }
private:
scoped_ptr<Apps> apps_;
@@ -51,6 +81,9 @@ class APP_LIST_EXPORT AppListModel {
scoped_ptr<SearchBoxModel> search_box_;
scoped_ptr<SearchResults> results_;
+ Users users_;
+
+ bool signed_in_;
Status status_;
ObserverList<AppListModelObserver> observers_;
diff --git a/chromium/ui/app_list/app_list_model_observer.h b/chromium/ui/app_list/app_list_model_observer.h
index c843894c12f..e409fa7fb43 100644
--- a/chromium/ui/app_list/app_list_model_observer.h
+++ b/chromium/ui/app_list/app_list_model_observer.h
@@ -12,7 +12,13 @@ namespace app_list {
class APP_LIST_EXPORT AppListModelObserver {
public:
// Invoked when AppListModel's status has changed.
- virtual void OnAppListModelStatusChanged() = 0;
+ virtual void OnAppListModelStatusChanged() {}
+
+ // Invoked when AppListModel's profile menu items have changed.
+ virtual void OnAppListModelUsersChanged() {}
+
+ // Invoked when AppListModel's current user's signin status has changed.
+ virtual void OnAppListModelSigninStatusChanged() {}
protected:
virtual ~AppListModelObserver() {}
diff --git a/chromium/ui/app_list/app_list_view_delegate.h b/chromium/ui/app_list/app_list_view_delegate.h
index bd7e3d3837f..3979e63684d 100644
--- a/chromium/ui/app_list/app_list_view_delegate.h
+++ b/chromium/ui/app_list/app_list_view_delegate.h
@@ -29,9 +29,15 @@ class APP_LIST_EXPORT AppListViewDelegate {
// AppListView owns the delegate.
virtual ~AppListViewDelegate() {}
- // Invoked to set the model that AppListView uses.
+ // Sets the delegate to use the profile at |profile_path|. This is currently
+ // only used by non-Ash Windows.
+ virtual void SetProfileByPath(const base::FilePath& profile_path) = 0;
+
+ // Invoked to initialize the model that AppListView uses. This binds the given
+ // model to this AppListViewDelegate and makes the AppListViewDelegate
+ // responsible for updating the model.
// Note that AppListView owns the model.
- virtual void SetModel(AppListModel* model) = 0;
+ virtual void InitModel(AppListModel* model) = 0;
// Gets the SigninDelegate for the app list. Owned by the AppListViewDelegate.
virtual SigninDelegate* GetSigninDelegate() = 0;
@@ -70,18 +76,9 @@ class APP_LIST_EXPORT AppListViewDelegate {
// Invoked when the app list is closing.
virtual void ViewClosing() = 0;
- // Invoked when the app list's activated state changes.
- virtual void ViewActivationChanged(bool active) = 0;
-
// Returns the icon to be displayed in the window and taskbar.
virtual gfx::ImageSkia GetWindowIcon() = 0;
- // Returns the name of the current user.
- virtual base::string16 GetCurrentUserName() = 0;
-
- // Returns the email of the current user.
- virtual base::string16 GetCurrentUserEmail() = 0;
-
// Open the settings UI.
virtual void OpenSettings() = 0;
@@ -90,6 +87,9 @@ class APP_LIST_EXPORT AppListViewDelegate {
// Open the feedback UI.
virtual void OpenFeedback() = 0;
+
+ // Shows the app list for the profile specified by |profile_path|.
+ virtual void ShowForProfileByPath(const base::FilePath& profile_path) = 0;
};
} // namespace app_list
diff --git a/chromium/ui/app_list/cocoa/app_list_view_controller.h b/chromium/ui/app_list/cocoa/app_list_view_controller.h
index 2815e0a223a..b993a67683b 100644
--- a/chromium/ui/app_list/cocoa/app_list_view_controller.h
+++ b/chromium/ui/app_list/cocoa/app_list_view_controller.h
@@ -17,7 +17,7 @@
namespace app_list {
class AppListViewDelegate;
class AppListModel;
-class SigninDelegateObserverBridge;
+class AppListModelObserverBridge;
}
@class AppListPagerView;
@@ -46,7 +46,8 @@ APP_LIST_EXPORT
base::scoped_nsobject<NSView> contentsView_;
scoped_ptr<app_list::AppListViewDelegate> delegate_;
- scoped_ptr<app_list::SigninDelegateObserverBridge> signin_observer_bridge_;
+ scoped_ptr<app_list::AppListModelObserverBridge>
+ app_list_model_observer_bridge_;
BOOL showingSearchResults_;
}
diff --git a/chromium/ui/app_list/cocoa/app_list_view_controller.mm b/chromium/ui/app_list/cocoa/app_list_view_controller.mm
index e4647216642..5e5eea5c655 100644
--- a/chromium/ui/app_list/cocoa/app_list_view_controller.mm
+++ b/chromium/ui/app_list/cocoa/app_list_view_controller.mm
@@ -6,12 +6,13 @@
#include "base/mac/foundation_util.h"
#include "base/strings/string_util.h"
+#include "base/strings/sys_string_conversions.h"
#include "skia/ext/skia_utils_mac.h"
#include "ui/app_list/app_list_constants.h"
#include "ui/app_list/app_list_model.h"
+#include "ui/app_list/app_list_model_observer.h"
#include "ui/app_list/app_list_view_delegate.h"
#include "ui/app_list/signin_delegate.h"
-#include "ui/app_list/signin_delegate_observer.h"
#import "ui/app_list/cocoa/app_list_pager_view.h"
#import "ui/app_list/cocoa/apps_grid_controller.h"
#import "ui/app_list/cocoa/signin_view_controller.h"
@@ -75,34 +76,44 @@ const NSTimeInterval kResultsAnimationDuration = 0.2;
- (void)loadAndSetView;
- (void)revealSearchResults:(BOOL)show;
-- (app_list::SigninDelegate*)signinDelegate;
@end
namespace app_list {
-class SigninDelegateObserverBridge : public SigninDelegateObserver {
+class AppListModelObserverBridge : public AppListModelObserver {
public:
- SigninDelegateObserverBridge(AppListViewController* parent)
- : parent_(parent) {
- [parent_ signinDelegate]->AddObserver(this);
- }
-
- virtual ~SigninDelegateObserverBridge() {
- [parent_ signinDelegate]->RemoveObserver(this);
- }
+ AppListModelObserverBridge(AppListViewController* parent);
+ virtual ~AppListModelObserverBridge();
private:
- // SigninDelegateObserver override:
- virtual void OnSigninSuccess() OVERRIDE {
- [parent_ onSigninStatusChanged];
- }
+ // Overridden from app_list::AppListModelObserver:
+ virtual void OnAppListModelUsersChanged() OVERRIDE;
+ virtual void OnAppListModelSigninStatusChanged() OVERRIDE;
AppListViewController* parent_; // Weak. Owns us.
- DISALLOW_COPY_AND_ASSIGN(SigninDelegateObserverBridge);
+ DISALLOW_COPY_AND_ASSIGN(AppListModelObserverBridge);
};
+AppListModelObserverBridge::AppListModelObserverBridge(
+ AppListViewController* parent)
+ : parent_(parent) {
+ [[parent_ appsGridController] model]->AddObserver(this);
+}
+
+AppListModelObserverBridge::~AppListModelObserverBridge() {
+ [[parent_ appsGridController] model]->RemoveObserver(this);
+}
+
+void AppListModelObserverBridge::OnAppListModelUsersChanged() {
+ [parent_ onSigninStatusChanged];
+}
+
+void AppListModelObserverBridge::OnAppListModelSigninStatusChanged() {
+ [parent_ onSigninStatusChanged];
+}
+
} // namespace app_list
@implementation AppListViewController
@@ -148,7 +159,7 @@ class SigninDelegateObserverBridge : public SigninDelegateObserver {
withTestModel:(scoped_ptr<app_list::AppListModel>)newModel {
if (delegate_) {
// First clean up, in reverse order.
- signin_observer_bridge_.reset();
+ app_list_model_observer_bridge_.reset();
[appsSearchResultsController_ setDelegate:nil];
[appsSearchBoxController_ setDelegate:nil];
}
@@ -158,6 +169,8 @@ class SigninDelegateObserverBridge : public SigninDelegateObserver {
[appsGridController_ setModel:newModel.Pass()];
[appsSearchBoxController_ setDelegate:self];
[appsSearchResultsController_ setDelegate:self];
+ app_list_model_observer_bridge_.reset(
+ new app_list::AppListModelObserverBridge(self));
[self onSigninStatusChanged];
}
@@ -316,14 +329,21 @@ class SigninDelegateObserverBridge : public SigninDelegateObserver {
[appsSearchBoxController_ clearSearch];
}
+- (void)redoSearch {
+ [self modelTextDidChange];
+}
+
- (void)onSigninStatusChanged {
[appsSearchBoxController_ rebuildMenu];
- app_list::SigninDelegate* signinDelegate = [self signinDelegate];
- BOOL needsSignin = signinDelegate && signinDelegate->NeedSignin();
- if (!needsSignin) {
- [[signinViewController_ view] removeFromSuperview];
- signin_observer_bridge_.reset();
- signinViewController_.reset();
+ app_list::SigninDelegate* signinDelegate =
+ delegate_ ? delegate_->GetSigninDelegate() : NULL;
+ BOOL show_signin_view =
+ signinDelegate && ![appsGridController_ model]->signed_in();
+
+ [[signinViewController_ view] removeFromSuperview];
+ signinViewController_.reset();
+
+ if (!show_signin_view) {
[backgroundView_ setHidden:NO];
return;
}
@@ -333,13 +353,7 @@ class SigninDelegateObserverBridge : public SigninDelegateObserver {
[[SigninViewController alloc] initWithFrame:[backgroundView_ frame]
cornerRadius:kBubbleCornerRadius
delegate:signinDelegate]);
- signin_observer_bridge_.reset(
- new app_list::SigninDelegateObserverBridge(self));
[[self view] addSubview:[signinViewController_ view]];
}
-- (app_list::SigninDelegate*)signinDelegate {
- return delegate_ ? delegate_->GetSigninDelegate() : NULL;
-}
-
@end
diff --git a/chromium/ui/app_list/cocoa/app_list_view_controller_unittest.mm b/chromium/ui/app_list/cocoa/app_list_view_controller_unittest.mm
index 70769aba759..2836ceb2399 100644
--- a/chromium/ui/app_list/cocoa/app_list_view_controller_unittest.mm
+++ b/chromium/ui/app_list/cocoa/app_list_view_controller_unittest.mm
@@ -67,22 +67,6 @@ class AppListViewControllerTest : public AppsGridControllerTestHelper,
DISALLOW_COPY_AND_ASSIGN(AppListViewControllerTest);
};
-// Helper class allowing NeedSignin() to return true during SetUp(), to test an
-// initial state where signin is required, and the regular view starts hidden.
-class AppListViewControllerSigninTest : public AppListViewControllerTest {
- public:
- AppListViewControllerSigninTest() : needs_signin_(true) {}
-
- // SigninDelegate override:
- virtual bool NeedSignin() OVERRIDE { return needs_signin_; }
-
- protected:
- bool needs_signin_;
-
- private:
- DISALLOW_COPY_AND_ASSIGN(AppListViewControllerSigninTest);
-};
-
TEST_VIEW(AppListViewControllerTest, [app_list_view_controller_ view]);
// Test that adding and removing pages updates the pager.
@@ -136,13 +120,16 @@ TEST_F(AppListViewControllerTest, SignedIn) {
}
// Test the view when signin is required.
-TEST_F(AppListViewControllerSigninTest, NeedsSignin) {
+TEST_F(AppListViewControllerTest, NeedsSignin) {
+ // Begin the test with a signed out app list.
+ scoped_ptr<AppListModel> new_model(new AppListModel);
+ new_model->SetSignedIn(false);
+ ResetModel(new_model.Pass());
EXPECT_EQ(2u, [[[app_list_view_controller_ view] subviews] count]);
EXPECT_TRUE([[app_list_view_controller_ backgroundView] isHidden]);
// Simulate signing in, should enter the SignedIn state.
- needs_signin_ = false;
- NotifySigninSuccess();
+ model()->SetSignedIn(true);
EXPECT_EQ(1u, [[[app_list_view_controller_ view] subviews] count]);
EXPECT_FALSE([[app_list_view_controller_ backgroundView] isHidden]);
}
diff --git a/chromium/ui/app_list/cocoa/apps_grid_controller.mm b/chromium/ui/app_list/cocoa/apps_grid_controller.mm
index d32a7913397..851653e6837 100644
--- a/chromium/ui/app_list/cocoa/apps_grid_controller.mm
+++ b/chromium/ui/app_list/cocoa/apps_grid_controller.mm
@@ -213,7 +213,7 @@ class AppsGridDelegateBridge : public ui::ListModelObserver {
scoped_ptr<app_list::AppListModel> newModel(new app_list::AppListModel);
delegate_ = newDelegate;
if (delegate_)
- delegate_->SetModel(newModel.get()); // Populates items.
+ delegate_->InitModel(newModel.get()); // Populates items.
[self setModel:newModel.Pass()];
}
@@ -546,9 +546,6 @@ class AppsGridDelegateBridge : public ui::ListModelObserver {
}
[self updatePages:start];
-
- for (size_t i = start; i < start + count; ++i)
- [[self itemAtIndex:i] onInitialModelBuilt];
}
- (void)listItemsRemoved:(size_t)start
diff --git a/chromium/ui/app_list/cocoa/apps_grid_controller_unittest.mm b/chromium/ui/app_list/cocoa/apps_grid_controller_unittest.mm
index 1e331bc6dfb..d4f73d68196 100644
--- a/chromium/ui/app_list/cocoa/apps_grid_controller_unittest.mm
+++ b/chromium/ui/app_list/cocoa/apps_grid_controller_unittest.mm
@@ -122,17 +122,27 @@ class AppsGridControllerTest : public AppsGridControllerTestHelper {
class AppListItemWithMenu : public AppListItemModel {
public:
- AppListItemWithMenu(const std::string& title) : menu_model_(NULL) {
- SetTitle(title);
+ AppListItemWithMenu(const std::string& title)
+ : menu_model_(NULL),
+ menu_ready_(true) {
+ SetTitleAndFullName(title, title);
menu_model_.AddItem(0, UTF8ToUTF16("Menu For: " + title));
}
+ void SetMenuReadyForTesting(bool ready) {
+ menu_ready_ = ready;
+ }
+
virtual ui::MenuModel* GetContextMenuModel() OVERRIDE {
+ if (!menu_ready_)
+ return NULL;
+
return &menu_model_;
}
private:
ui::SimpleMenuModel menu_model_;
+ bool menu_ready_;
DISALLOW_COPY_AND_ASSIGN(AppListItemWithMenu);
};
@@ -424,7 +434,7 @@ TEST_F(AppsGridControllerTest, ModelUpdates) {
// Update the title via the ItemModelObserver.
app_list::AppListItemModel* item_model = model()->apps()->GetItemAt(2);
- item_model->SetTitle("UpdatedItem");
+ item_model->SetTitleAndFullName("UpdatedItem", "UpdatedItem");
EXPECT_NSEQ(@"UpdatedItem", [button title]);
EXPECT_EQ(std::string("|Item 0,Item 1,UpdatedItem|"), GetViewContent());
@@ -457,7 +467,7 @@ TEST_F(AppsGridControllerTest, ModelUpdates) {
EXPECT_EQ(std::string("|Item 0,Item 2|"), GetViewContent());
// Test inserting in the middle.
- model()->apps()->AddAt(1, model()->CreateItem("Item One"));
+ model()->apps()->AddAt(1, model()->CreateItem("Item One", "Item One"));
EXPECT_EQ(3u, [apps_grid_controller_ itemCount]);
EXPECT_EQ(std::string("|Item 0,Item One,Item 2|"), GetViewContent());
@@ -891,8 +901,9 @@ TEST_F(AppsGridControllerTest, ScrollingWhileDragging) {
}
TEST_F(AppsGridControllerTest, ContextMenus) {
+ AppListItemWithMenu* item_two_model = new AppListItemWithMenu("Item Two");
model()->apps()->AddAt(0, new AppListItemWithMenu("Item One"));
- model()->apps()->AddAt(1, new AppListItemWithMenu("Item Two"));
+ model()->apps()->AddAt(1, item_two_model);
EXPECT_EQ(2u, [apps_grid_controller_ itemCount]);
NSCollectionView* page = [apps_grid_controller_ collectionViewAtPageIndex:0];
@@ -903,55 +914,16 @@ TEST_F(AppsGridControllerTest, ContextMenus) {
EXPECT_EQ(1, [menu numberOfItems]);
EXPECT_NSEQ(@"Menu For: Item One", [[menu itemAtIndex:0] title]);
+ // Test a context menu request while the item is still installing.
+ item_two_model->SetMenuReadyForTesting(false);
+ menu = [page menuForEvent:mouse_at_cell_1];
+ EXPECT_EQ(nil, menu);
+
+ item_two_model->SetMenuReadyForTesting(true);
menu = [page menuForEvent:mouse_at_cell_1];
EXPECT_EQ(1, [menu numberOfItems]);
EXPECT_NSEQ(@"Menu For: Item Two", [[menu itemAtIndex:0] title]);
}
-TEST_F(AppsGridControllerTest, HighlightedOnFirstShow) {
- scoped_ptr<AppListTestModel> test_model(new AppListTestModel);
- test_model->PopulateApps(kItemsPerPage * 3);
-
- // Manipulate the second item on the second page.
- const size_t kTestItemIndex = kItemsPerPage + 1;
-
- // When shown for the first time during an in-progress install, item should be
- // visible, but not selected.
- AppListItemModel* test_item = test_model->apps()->GetItemAt(kTestItemIndex);
- test_item->SetHighlighted(true);
- test_item->SetIsInstalling(true);
- EXPECT_EQ(0u, [apps_grid_controller_ visiblePage]);
- ResetModel(test_model.PassAs<AppListModel>());
- EXPECT_EQ(3u, [apps_grid_controller_ pageCount]);
- EXPECT_EQ(1u, [apps_grid_controller_ visiblePage]);
- EXPECT_EQ(NSNotFound, [apps_grid_controller_ selectedItemIndex]);
-
- // Updating download progress should add a progress bar lazily.
- NSView* containerView = [GetItemViewAt(kTestItemIndex) superview];
- EXPECT_EQ(1u, [[containerView subviews] count]);
- test_item->SetPercentDownloaded(50);
- EXPECT_EQ(2u, [[containerView subviews] count]);
-
- // Completing install should remove the progress bar, and select the item.
- test_item->SetIsInstalling(false);
- EXPECT_EQ(1u, [[containerView subviews] count]);
- EXPECT_EQ(kTestItemIndex, [apps_grid_controller_ selectedItemIndex]);
-
- // Reset to unconstructed state.
- ResetModel(scoped_ptr<AppListModel>());
- EXPECT_EQ(0u, [apps_grid_controller_ visiblePage]);
- EXPECT_EQ(1u, [apps_grid_controller_ pageCount]);
- EXPECT_EQ(NSNotFound, [apps_grid_controller_ selectedItemIndex]);
-
- // If shown after install completes, item should also be selected.
- test_model.reset(new AppListTestModel);
- test_model->PopulateApps(kItemsPerPage * 3);
- test_model->apps()->GetItemAt(kTestItemIndex)->SetHighlighted(true);
- ResetModel(test_model.PassAs<AppListModel>());
- EXPECT_EQ(3u, [apps_grid_controller_ pageCount]);
- EXPECT_EQ(1u, [apps_grid_controller_ visiblePage]);
- EXPECT_EQ(kTestItemIndex, [apps_grid_controller_ selectedItemIndex]);
-}
-
} // namespace test
} // namespace app_list
diff --git a/chromium/ui/app_list/cocoa/apps_grid_view_item.h b/chromium/ui/app_list/cocoa/apps_grid_view_item.h
index d968e0cb5cd..b42eec18761 100644
--- a/chromium/ui/app_list/cocoa/apps_grid_view_item.h
+++ b/chromium/ui/app_list/cocoa/apps_grid_view_item.h
@@ -50,10 +50,6 @@ APP_LIST_EXPORT
// the initial snapshot are restored.
- (NSBitmapImageRep*)dragRepresentationForRestore:(BOOL)isRestore;
-// Called the first time an item is added to the grid view, once the grid view
-// is consistent with items being added at the same time.
-- (void)onInitialModelBuilt;
-
@end
#endif // UI_APP_LIST_COCOA_APPS_GRID_VIEW_ITEM_H_
diff --git a/chromium/ui/app_list/cocoa/apps_grid_view_item.mm b/chromium/ui/app_list/cocoa/apps_grid_view_item.mm
index 34fe975ebca..b6e4fb53a27 100644
--- a/chromium/ui/app_list/cocoa/apps_grid_view_item.mm
+++ b/chromium/ui/app_list/cocoa/apps_grid_view_item.mm
@@ -99,8 +99,12 @@ ItemModelObserverBridge::~ItemModelObserverBridge() {
NSMenu* ItemModelObserverBridge::GetContextMenu() {
if (!context_menu_controller_) {
+ ui::MenuModel* menu_model = model_->GetContextMenuModel();
+ if (!menu_model)
+ return nil;
+
context_menu_controller_.reset(
- [[MenuController alloc] initWithModel:model_->GetContextMenuModel()
+ [[MenuController alloc] initWithModel:menu_model
useWithPopUpButtonCell:NO]);
}
return [context_menu_controller_ menu];
@@ -255,6 +259,18 @@ void ItemModelObserverBridge::ItemPercentDownloadedChanged() {
[[NSAttributedString alloc] initWithString:buttonTitle
attributes:titleAttributes]);
[[self button] setAttributedTitle:attributedTitle];
+
+ // If the app does not specify a distinct short name manifest property, check
+ // whether the title would be truncted in the NSButton. If it would be
+ // truncated, add a tooltip showing the full name.
+ NSRect titleRect =
+ [[[self button] cell] titleRectForBounds:[[self button] bounds]];
+ if ([self model]->title() == [self model]->full_name() &&
+ [attributedTitle size].width < NSWidth(titleRect)) {
+ [[self view] removeAllToolTips];
+ } else {
+ [[self view] setToolTip:base::SysUTF8ToNSString([self model]->full_name())];
+ }
}
- (void)updateButtonImage {
@@ -271,6 +287,7 @@ void ItemModelObserverBridge::ItemPercentDownloadedChanged() {
}
- (void)setModel:(app_list::AppListItemModel*)itemModel {
+ [trackingArea_.get() clearOwner];
if (!itemModel) {
observerBridge_.reset();
return;
@@ -335,14 +352,6 @@ void ItemModelObserverBridge::ItemPercentDownloadedChanged() {
return imageRep;
}
-- (void)onInitialModelBuilt {
- if ([self model]->highlighted()) {
- [self ensureVisible];
- if (![self model]->is_installing())
- [self setSelected:YES];
- }
-}
-
- (void)ensureVisible {
NSCollectionView* collectionView = [self collectionView];
AppsGridController* gridController =
diff --git a/chromium/ui/app_list/cocoa/apps_search_box_controller.h b/chromium/ui/app_list/cocoa/apps_search_box_controller.h
index d28c67a62e8..b8a86e57f7b 100644
--- a/chromium/ui/app_list/cocoa/apps_search_box_controller.h
+++ b/chromium/ui/app_list/cocoa/apps_search_box_controller.h
@@ -13,6 +13,7 @@
namespace app_list {
class AppListMenu;
+class AppListModel;
class AppListViewDelegate;
class SearchBoxModel;
class SearchBoxModelObserverBridge;
@@ -26,6 +27,7 @@ class SearchBoxModelObserverBridge;
- (app_list::AppListViewDelegate*)appListDelegate;
- (app_list::SearchBoxModel*)searchBoxModel;
+- (app_list::AppListModel*)appListModel;
- (void)modelTextDidChange;
@end
diff --git a/chromium/ui/app_list/cocoa/apps_search_box_controller.mm b/chromium/ui/app_list/cocoa/apps_search_box_controller.mm
index 4f02a20c56b..2fa9928b207 100644
--- a/chromium/ui/app_list/cocoa/apps_search_box_controller.mm
+++ b/chromium/ui/app_list/cocoa/apps_search_box_controller.mm
@@ -10,7 +10,7 @@
#include "grit/ui_resources.h"
#import "third_party/GTM/AppKit/GTMNSBezierPath+RoundRect.h"
#include "ui/app_list/app_list_menu.h"
-#import "ui/app_list/cocoa/current_user_menu_item_view.h"
+#include "ui/app_list/app_list_model.h"
#include "ui/app_list/search_box_model.h"
#include "ui/app_list/search_box_model_observer.h"
#import "ui/base/cocoa/controls/hover_image_menu_button.h"
@@ -110,6 +110,7 @@ void SearchBoxModelObserverBridge::TextChanged() {
// it is changed in tests to establish a particular state.
[[parent_ searchTextField]
setStringValue:base::SysUTF16ToNSString(GetModel()->text())];
+ [[parent_ delegate] modelTextDidChange];
}
} // namespace app_list
@@ -158,6 +159,10 @@ void SearchBoxModelObserverBridge::TextChanged() {
if (![delegate_ appListDelegate])
return;
+ [menuController_ setModel:NULL];
+ appListMenu_.reset(
+ new app_list::AppListMenu([delegate_ appListDelegate],
+ [delegate_ appListModel]->users()));
menuController_.reset([[AppListMenuController alloc]
initWithSearchBoxController:self]);
[menuButton_ setMenu:[menuController_ menu]]; // Menu will populate here.
@@ -173,10 +178,6 @@ void SearchBoxModelObserverBridge::TextChanged() {
return;
bridge_.reset(new app_list::SearchBoxModelObserverBridge(self));
- if (![delegate_ appListDelegate])
- return;
-
- appListMenu_.reset(new app_list::AppListMenu([delegate_ appListDelegate]));
[self rebuildMenu];
}
@@ -371,20 +372,6 @@ void SearchBoxModelObserverBridge::TextChanged() {
return self;
}
-- (void)addItemToMenu:(NSMenu*)menu
- atIndex:(NSInteger)index
- fromModel:(ui::MenuModel*)model {
- [super addItemToMenu:menu
- atIndex:index
- fromModel:model];
- if (model->GetCommandIdAt(index) != app_list::AppListMenu::CURRENT_USER)
- return;
-
- base::scoped_nsobject<NSView> customItemView([[CurrentUserMenuItemView alloc]
- initWithDelegate:[[searchBoxController_ delegate] appListDelegate]]);
- [[menu itemAtIndex:index] setView:customItemView];
-}
-
- (NSRect)confinementRectForMenu:(NSMenu*)menu
onScreen:(NSScreen*)screen {
NSPopUpButton* menuButton = [searchBoxController_ menuControl];
diff --git a/chromium/ui/app_list/cocoa/apps_search_box_controller_unittest.mm b/chromium/ui/app_list/cocoa/apps_search_box_controller_unittest.mm
index d702549e7a1..d410380c856 100644
--- a/chromium/ui/app_list/cocoa/apps_search_box_controller_unittest.mm
+++ b/chromium/ui/app_list/cocoa/apps_search_box_controller_unittest.mm
@@ -9,16 +9,18 @@
#include "base/strings/utf_string_conversions.h"
#import "testing/gtest_mac.h"
#include "ui/app_list/app_list_menu.h"
-#import "ui/app_list/cocoa/current_user_menu_item_view.h"
+#include "ui/app_list/app_list_model_observer.h"
#include "ui/app_list/search_box_model.h"
#include "ui/app_list/test/app_list_test_model.h"
#include "ui/app_list/test/app_list_test_view_delegate.h"
+#import "ui/base/cocoa/menu_controller.h"
#import "ui/base/test/ui_cocoa_test_helper.h"
@interface TestAppsSearchBoxDelegate : NSObject<AppsSearchBoxDelegate> {
@private
app_list::SearchBoxModel searchBoxModel_;
app_list::test::AppListTestViewDelegate appListDelegate_;
+ app_list::test::AppListTestModel appListModel_;
int textChangeCount_;
}
@@ -30,6 +32,18 @@
@synthesize textChangeCount = textChangeCount_;
+- (id)init {
+ if ((self = [super init])) {
+ app_list::AppListModel::Users users(2);
+ users[0].name = ASCIIToUTF16("user1");
+ users[1].name = ASCIIToUTF16("user2");
+ users[1].email = ASCIIToUTF16("user2@chromium.org");
+ users[1].active = true;
+ appListModel_.SetUsers(users);
+ }
+ return self;
+}
+
- (app_list::SearchBoxModel*)searchBoxModel {
return &searchBoxModel_;
}
@@ -52,12 +66,17 @@
return 3;
}
+- (app_list::AppListModel*)appListModel {
+ return &appListModel_;
+}
+
@end
namespace app_list {
namespace test {
-class AppsSearchBoxControllerTest : public ui::CocoaTest {
+class AppsSearchBoxControllerTest : public ui::CocoaTest,
+ public AppListModelObserver {
public:
AppsSearchBoxControllerTest() {
Init();
@@ -69,12 +88,14 @@ class AppsSearchBoxControllerTest : public ui::CocoaTest {
NSMakeRect(0, 0, 400, 100)]);
delegate_.reset([[TestAppsSearchBoxDelegate alloc] init]);
[apps_search_box_controller_ setDelegate:delegate_];
+ [delegate_ appListModel]->AddObserver(this);
ui::CocoaTest::SetUp();
[[test_window() contentView] addSubview:[apps_search_box_controller_ view]];
}
virtual void TearDown() OVERRIDE {
+ [delegate_ appListModel]->RemoveObserver(this);
[apps_search_box_controller_ setDelegate:nil];
ui::CocoaTest::TearDown();
}
@@ -87,6 +108,13 @@ class AppsSearchBoxControllerTest : public ui::CocoaTest {
}
protected:
+ // Overridden from app_list::AppListModelObserver:
+ virtual void OnAppListModelUsersChanged() OVERRIDE {
+ [apps_search_box_controller_ rebuildMenu];
+ }
+
+ virtual void OnAppListModelSigninStatusChanged() OVERRIDE {}
+
base::scoped_nsobject<TestAppsSearchBoxDelegate> delegate_;
base::scoped_nsobject<AppsSearchBoxController> apps_search_box_controller_;
@@ -109,28 +137,57 @@ TEST_F(AppsSearchBoxControllerTest, SearchBoxModel) {
model->SetText(search_text);
EXPECT_NSEQ(base::SysUTF16ToNSString(search_text),
[[apps_search_box_controller_ searchTextField] stringValue]);
- // Updates coming via the model should not notify the delegate.
- EXPECT_EQ(0, [delegate_ textChangeCount]);
+ // Updates coming via the model should notify the delegate.
+ EXPECT_EQ(1, [delegate_ textChangeCount]);
// Updates from the view should update the model and notify the delegate.
[apps_search_box_controller_ clearSearch];
EXPECT_EQ(base::string16(), model->text());
EXPECT_NSEQ([NSString string],
[[apps_search_box_controller_ searchTextField] stringValue]);
- EXPECT_EQ(1, [delegate_ textChangeCount]);
+ EXPECT_EQ(2, [delegate_ textChangeCount]);
- // Test pressing escape clears the search.
+ // Test pressing escape clears the search. First add some text.
model->SetText(search_text);
+ EXPECT_EQ(3, [delegate_ textChangeCount]);
+
EXPECT_NSEQ(base::SysUTF16ToNSString(search_text),
[[apps_search_box_controller_ searchTextField] stringValue]);
SimulateKeyAction(@selector(complete:));
EXPECT_NSEQ([NSString string],
[[apps_search_box_controller_ searchTextField] stringValue]);
- EXPECT_EQ(2, [delegate_ textChangeCount]);
+ EXPECT_EQ(4, [delegate_ textChangeCount]);
}
-// Test the popup menu items.
+// Test the popup menu items when there is only one user..
+TEST_F(AppsSearchBoxControllerTest, SearchBoxMenuSingleUser) {
+ // Set a single user. We need to set the delegate again because the
+ // AppListModel observer isn't hooked up in these tests.
+ [delegate_ appListModel]->SetUsers(app_list::AppListModel::Users(1));
+ [apps_search_box_controller_ setDelegate:delegate_];
+
+ NSPopUpButton* menu_control = [apps_search_box_controller_ menuControl];
+ EXPECT_TRUE([apps_search_box_controller_ appListMenu]);
+ ui::MenuModel* menu_model
+ = [apps_search_box_controller_ appListMenu]->menu_model();
+ // Add one to the item count to account for the blank, first item that Cocoa
+ // has in its popup menus.
+ EXPECT_EQ(menu_model->GetItemCount() + 1,
+ [[menu_control menu] numberOfItems]);
+
+ // All command ids should be less than |SELECT_PROFILE| as no user menu items
+ // are being shown.
+ for (int i = 0; i < menu_model->GetItemCount(); ++i)
+ EXPECT_LT(menu_model->GetCommandIdAt(i), AppListMenu::SELECT_PROFILE);
+
+ // The number of items should match the index that starts profile items.
+ EXPECT_EQ(AppListMenu::SELECT_PROFILE, menu_model->GetItemCount());
+}
+
+// Test the popup menu items for the multi-profile case.
TEST_F(AppsSearchBoxControllerTest, SearchBoxMenu) {
+ const app_list::AppListModel::Users& users =
+ [delegate_ appListModel]->users();
NSPopUpButton* menu_control = [apps_search_box_controller_ menuControl];
EXPECT_TRUE([apps_search_box_controller_ appListMenu]);
ui::MenuModel* menu_model
@@ -140,14 +197,31 @@ TEST_F(AppsSearchBoxControllerTest, SearchBoxMenu) {
EXPECT_EQ(menu_model->GetItemCount() + 1,
[[menu_control menu] numberOfItems]);
- // The CURRENT_USER item should contain our custom view.
ui::MenuModel* found_menu_model = menu_model;
int index;
+ MenuController* controller = [[menu_control menu] delegate];
+
+ // The first user item is an unchecked label.
+ EXPECT_TRUE(ui::MenuModel::GetModelAndIndexForCommandId(
+ AppListMenu::SELECT_PROFILE, &menu_model, &index));
+ EXPECT_EQ(found_menu_model, menu_model);
+ NSMenuItem* unchecked_user_item = [[menu_control menu] itemAtIndex:index + 1];
+ [controller validateUserInterfaceItem:unchecked_user_item];
+ // The profile name should be shown if there is no email available.
+ EXPECT_NSEQ(base::SysUTF16ToNSString(users[0].name),
+ [unchecked_user_item title]);
+ EXPECT_EQ(NSOffState, [unchecked_user_item state]);
+
+ // The second user item is a checked label because it is the active profile.
EXPECT_TRUE(ui::MenuModel::GetModelAndIndexForCommandId(
- AppListMenu::CURRENT_USER, &menu_model, &index));
+ AppListMenu::SELECT_PROFILE + 1, &menu_model, &index));
EXPECT_EQ(found_menu_model, menu_model);
- NSMenuItem* current_user_item = [[menu_control menu] itemAtIndex:index + 1];
- EXPECT_TRUE([current_user_item view]);
+ NSMenuItem* checked_user_item = [[menu_control menu] itemAtIndex:index + 1];
+ [controller validateUserInterfaceItem:checked_user_item];
+ // The email is shown when available.
+ EXPECT_NSEQ(base::SysUTF16ToNSString(users[1].email),
+ [checked_user_item title]);
+ EXPECT_EQ(NSOnState, [checked_user_item state]);
// A regular item should have just the label.
EXPECT_TRUE(ui::MenuModel::GetModelAndIndexForCommandId(
@@ -159,30 +233,33 @@ TEST_F(AppsSearchBoxControllerTest, SearchBoxMenu) {
[settings_item title]);
}
-// Test initialization and display of the custom menu item that shows the
-// currently signed-in user. This is a non-interactive view.
-class AppsSearchBoxCustomMenuItemTest : public ui::CocoaTest {
- public:
- AppsSearchBoxCustomMenuItemTest() {
- Init();
- }
-
- virtual void SetUp() OVERRIDE {
- scoped_ptr<AppListViewDelegate> delegate(new AppListTestViewDelegate);
- current_user_menu_item_.reset([[[CurrentUserMenuItemView alloc]
- initWithDelegate:delegate.get()] retain]);
- ui::CocoaTest::SetUp();
- [[test_window() contentView] addSubview:current_user_menu_item_];
- }
-
- protected:
- base::scoped_nsobject<NSView> current_user_menu_item_;
-
- private:
- DISALLOW_COPY_AND_ASSIGN(AppsSearchBoxCustomMenuItemTest);
-};
+// Test adding another user, and changing an existing one.
+TEST_F(AppsSearchBoxControllerTest, SearchBoxMenuChangingUsers) {
+ app_list::AppListModel::Users users = [delegate_ appListModel]->users();
+ EXPECT_EQ(2u, users.size());
+ ui::MenuModel* menu_model
+ = [apps_search_box_controller_ appListMenu]->menu_model();
+ // Adding one to account for the empty item at index 0 in Cocoa popup menus.
+ int non_user_items = menu_model->GetItemCount() - users.size() + 1;
-TEST_VIEW(AppsSearchBoxCustomMenuItemTest, current_user_menu_item_);
+ NSPopUpButton* menu_control = [apps_search_box_controller_ menuControl];
+ EXPECT_EQ(2, [[menu_control menu] numberOfItems] - non_user_items);
+ EXPECT_NSEQ(base::SysUTF16ToNSString(users[0].name),
+ [[[menu_control menu] itemAtIndex:1] title]);
+
+ users[0].name = ASCIIToUTF16("renamed user");
+ app_list::AppListModel::User new_user;
+ new_user.name = ASCIIToUTF16("user3");
+ users.push_back(new_user);
+ [delegate_ appListModel]->SetUsers(users);
+
+ // Should now be an extra item, and it should have correct titles.
+ EXPECT_EQ(3, [[menu_control menu] numberOfItems] - non_user_items);
+ EXPECT_NSEQ(base::SysUTF16ToNSString(users[0].name),
+ [[[menu_control menu] itemAtIndex:1] title]);
+ EXPECT_NSEQ(base::SysUTF16ToNSString(new_user.name),
+ [[[menu_control menu] itemAtIndex:3] title]);
+}
} // namespace test
} // namespace app_list
diff --git a/chromium/ui/app_list/cocoa/apps_search_results_controller.h b/chromium/ui/app_list/cocoa/apps_search_results_controller.h
index b69fc511938..52290c7824c 100644
--- a/chromium/ui/app_list/cocoa/apps_search_results_controller.h
+++ b/chromium/ui/app_list/cocoa/apps_search_results_controller.h
@@ -10,20 +10,21 @@
#include "base/mac/scoped_nsobject.h"
#include "base/memory/scoped_ptr.h"
#include "ui/app_list/app_list_export.h"
+#include "ui/app_list/app_list_model.h"
#import "ui/base/cocoa/tracking_area.h"
namespace app_list {
-class AppListModel;
class AppsSearchResultsModelBridge;
class SearchResult;
}
@class AppsSearchResultsCell;
-@protocol AppsSearchResultsDelegate
+@protocol AppsSearchResultsDelegate<NSObject>
- (app_list::AppListModel*)appListModel;
- (void)openResult:(app_list::SearchResult*)result;
+- (void)redoSearch;
@end
@@ -40,10 +41,12 @@ APP_LIST_EXPORT
NSPoint lastMouseDownInView_;
NSInteger hoveredRowIndex_;
scoped_ptr<app_list::AppsSearchResultsModelBridge> bridge_;
- id<AppsSearchResultsDelegate> delegate_; // Weak. Owns us.
+ NSObject<AppsSearchResultsDelegate>* delegate_; // Weak. Owns us.
}
-@property(assign, nonatomic) id<AppsSearchResultsDelegate> delegate;
+@property(assign, nonatomic) NSObject<AppsSearchResultsDelegate>* delegate;
+@property(readonly, nonatomic) app_list::AppListModel::SearchResults* results;
+@property(readonly, nonatomic) NSTableView* tableView;
- (id)initWithAppsSearchResultsFrameSize:(NSSize)size;
@@ -53,10 +56,4 @@ APP_LIST_EXPORT
@end
-@interface AppsSearchResultsController (TestingAPI)
-
-- (NSTableView*)tableView;
-
-@end
-
#endif // UI_APP_LIST_COCOA_APPS_SEARCH_RESULTS_CONTROLLER_H_
diff --git a/chromium/ui/app_list/cocoa/apps_search_results_controller.mm b/chromium/ui/app_list/cocoa/apps_search_results_controller.mm
index b22d836ab11..314f079e8ad 100644
--- a/chromium/ui/app_list/cocoa/apps_search_results_controller.mm
+++ b/chromium/ui/app_list/cocoa/apps_search_results_controller.mm
@@ -86,6 +86,15 @@ const NSBackgroundStyle kBackgroundHovered = NSBackgroundStyleRaised;
return self;
}
+- (app_list::AppListModel::SearchResults*)results {
+ DCHECK([delegate_ appListModel]);
+ return [delegate_ appListModel]->results();
+}
+
+- (NSTableView*)tableView {
+ return tableView_;
+}
+
- (void)setDelegate:(id<AppsSearchResultsDelegate>)newDelegate {
bridge_.reset();
delegate_ = newDelegate;
@@ -95,8 +104,7 @@ const NSBackgroundStyle kBackgroundHovered = NSBackgroundStyleRaised;
return;
}
- bridge_.reset(new app_list::AppsSearchResultsModelBridge(
- appListModel->results(), tableView_));
+ bridge_.reset(new app_list::AppsSearchResultsModelBridge(self));
[tableView_ reloadData];
}
@@ -116,10 +124,6 @@ const NSBackgroundStyle kBackgroundHovered = NSBackgroundStyleRaised;
return NO;
}
-- (NSTableView*)tableView {
- return tableView_;
-}
-
- (void)loadAndSetViewWithResultsFrameSize:(NSSize)size {
tableView_.reset(
[[AppsSearchResultsTableView alloc] initWithFrame:NSZeroRect]);
diff --git a/chromium/ui/app_list/cocoa/apps_search_results_controller_unittest.mm b/chromium/ui/app_list/cocoa/apps_search_results_controller_unittest.mm
index 14ce5d26ca5..3645e1e19de 100644
--- a/chromium/ui/app_list/cocoa/apps_search_results_controller_unittest.mm
+++ b/chromium/ui/app_list/cocoa/apps_search_results_controller_unittest.mm
@@ -5,6 +5,7 @@
#import "ui/app_list/cocoa/apps_search_results_controller.h"
#include "base/mac/scoped_nsobject.h"
+#include "base/message_loop/message_loop.h"
#include "base/strings/stringprintf.h"
#include "base/strings/sys_string_conversions.h"
#include "base/strings/utf_string_conversions.h"
@@ -20,15 +21,18 @@
@private
app_list::test::AppListTestModel appListModel_;
app_list::SearchResult* lastOpenedResult_;
+ int redoSearchCount_;
}
@property(readonly, nonatomic) app_list::SearchResult* lastOpenedResult;
+@property(readonly, nonatomic) int redoSearchCount;
@end
@implementation TestAppsSearchResultsDelegate
@synthesize lastOpenedResult = lastOpenedResult_;
+@synthesize redoSearchCount = redoSearchCount_;
- (app_list::AppListModel*)appListModel {
return &appListModel_;
@@ -38,6 +42,10 @@
lastOpenedResult_ = result;
}
+- (void)redoSearch {
+ ++redoSearchCount_;
+}
+
@end
namespace app_list {
@@ -48,19 +56,28 @@ const int kDefaultResultsCount = 3;
class SearchResultWithMenu : public SearchResult {
public:
- SearchResultWithMenu(const std::string& title,
- const std::string& details) : menu_model_(NULL) {
+ SearchResultWithMenu(const std::string& title, const std::string& details)
+ : menu_model_(NULL),
+ menu_ready_(true) {
set_title(ASCIIToUTF16(title));
set_details(ASCIIToUTF16(details));
menu_model_.AddItem(0, UTF8ToUTF16("Menu For: " + title));
}
+ void SetMenuReadyForTesting(bool ready) {
+ menu_ready_ = ready;
+ }
+
virtual ui::MenuModel* GetContextMenuModel() OVERRIDE {
+ if (!menu_ready_)
+ return NULL;
+
return &menu_model_;
}
private:
ui::SimpleMenuModel menu_model_;
+ bool menu_ready_;
DISALLOW_COPY_AND_ASSIGN(SearchResultWithMenu);
};
@@ -87,6 +104,12 @@ class AppsSearchResultsControllerTest : public ui::CocoaTest {
row:index];
}
+ void SetMenuReadyAt(size_t index, bool ready) {
+ SearchResultWithMenu* result =
+ static_cast<SearchResultWithMenu*>(ModelResultAt(index));
+ result->SetMenuReadyForTesting(ready);
+ }
+
BOOL SimulateKeyAction(SEL c) {
return [apps_search_results_controller_ handleCommandBySelector:c];
}
@@ -260,10 +283,26 @@ TEST_F(AppsSearchResultsControllerTest, ContextMenus) {
EXPECT_EQ(1, [menu numberOfItems]);
EXPECT_NSEQ(@"Menu For: Result 0", [[menu itemAtIndex:0] title]);
+ // Test a context menu request while the item is still installing.
+ SetMenuReadyAt(1, false);
+ menu = [table_view menuForEvent:mouse_in_row_1];
+ EXPECT_EQ(nil, menu);
+
+ SetMenuReadyAt(1, true);
menu = [table_view menuForEvent:mouse_in_row_1];
EXPECT_EQ(1, [menu numberOfItems]);
EXPECT_NSEQ(@"Menu For: Result 1", [[menu itemAtIndex:0] title]);
}
+// Test that observing a search result item uninstall performs the search again.
+TEST_F(AppsSearchResultsControllerTest, UninstallRedperformsSearch) {
+ base::MessageLoopForUI message_loop;
+ EXPECT_EQ(0, [delegate_ redoSearchCount]);
+ ModelResultAt(0)->NotifyItemUninstalled();
+ message_loop.PostTask(FROM_HERE, base::MessageLoop::QuitClosure());
+ message_loop.Run();
+ EXPECT_EQ(1, [delegate_ redoSearchCount]);
+}
+
} // namespace test
} // namespace app_list
diff --git a/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.h b/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.h
index e1d70ac37ce..8939d260efb 100644
--- a/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.h
+++ b/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.h
@@ -7,11 +7,10 @@
#include "base/mac/scoped_nsobject.h"
#include "base/memory/scoped_vector.h"
-#include "ui/app_list/app_list_model.h"
#include "ui/base/models/list_model_observer.h"
@class NSMenu;
-@class NSTableView;
+@class AppsSearchResultsController;
namespace app_list {
@@ -19,8 +18,8 @@ namespace app_list {
// and updating the NSTableView where they are displayed.
class AppsSearchResultsModelBridge : public ui::ListModelObserver {
public:
- AppsSearchResultsModelBridge(AppListModel::SearchResults* results_model,
- NSTableView* results_table_view);
+ explicit AppsSearchResultsModelBridge(
+ AppsSearchResultsController* results_controller);
virtual ~AppsSearchResultsModelBridge();
// Returns the context menu for the item at |index| in the search results
@@ -40,8 +39,7 @@ class AppsSearchResultsModelBridge : public ui::ListModelObserver {
virtual void ListItemMoved(size_t index, size_t target_index) OVERRIDE;
virtual void ListItemsChanged(size_t start, size_t count) OVERRIDE;
- AppListModel::SearchResults* results_; // Weak. Owned by AppListModel.
- base::scoped_nsobject<NSTableView> table_view_;
+ AppsSearchResultsController* parent_; // Weak. Owns us.
ScopedVector<ItemObserver> item_observers_;
DISALLOW_COPY_AND_ASSIGN(AppsSearchResultsModelBridge);
diff --git a/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.mm b/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.mm
index d56c5fd4296..69a3205ef06 100644
--- a/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.mm
+++ b/chromium/ui/app_list/cocoa/apps_search_results_model_bridge.mm
@@ -7,6 +7,8 @@
#import <Cocoa/Cocoa.h>
#include "base/strings/sys_string_conversions.h"
+#include "ui/app_list/app_list_model.h"
+#import "ui/app_list/cocoa/apps_search_results_controller.h"
#include "ui/app_list/search_result.h"
#include "ui/app_list/search_result_observer.h"
#import "ui/base/cocoa/menu_controller.h"
@@ -19,7 +21,7 @@ class AppsSearchResultsModelBridge::ItemObserver : public SearchResultObserver {
: bridge_(bridge), row_in_view_(index) {
// Cache the result, because the results array is updated before notifying
// observers (which happens before deleting the SearchResult).
- result_ = bridge_->results_->GetItemAt(index);
+ result_ = [bridge_->parent_ results]->GetItemAt(index);
result_->AddObserver(this);
}
@@ -29,8 +31,12 @@ class AppsSearchResultsModelBridge::ItemObserver : public SearchResultObserver {
NSMenu* GetContextMenu() {
if (!context_menu_controller_) {
+ ui::MenuModel* menu_model = result_->GetContextMenuModel();
+ if (!menu_model)
+ return nil;
+
context_menu_controller_.reset(
- [[MenuController alloc] initWithModel:result_->GetContextMenuModel()
+ [[MenuController alloc] initWithModel:menu_model
useWithPopUpButtonCell:NO]);
}
return [context_menu_controller_ menu];
@@ -44,7 +50,7 @@ class AppsSearchResultsModelBridge::ItemObserver : public SearchResultObserver {
virtual void OnIsInstallingChanged() OVERRIDE {}
virtual void OnPercentDownloadedChanged() OVERRIDE {}
virtual void OnItemInstalled() OVERRIDE {}
- virtual void OnItemUninstalled() OVERRIDE {}
+ virtual void OnItemUninstalled() OVERRIDE;
private:
AppsSearchResultsModelBridge* bridge_; // Weak. Owns us.
@@ -55,17 +61,24 @@ class AppsSearchResultsModelBridge::ItemObserver : public SearchResultObserver {
DISALLOW_COPY_AND_ASSIGN(ItemObserver);
};
+void AppsSearchResultsModelBridge::ItemObserver::OnItemUninstalled() {
+ // Performing the search again will destroy |this|, so post a task. This also
+ // ensures that the AppSearchProvider has observed the uninstall before
+ // performing the search again, otherwise it will provide a NULL result.
+ [[bridge_->parent_ delegate] performSelector:@selector(redoSearch)
+ withObject:nil
+ afterDelay:0];
+}
+
AppsSearchResultsModelBridge::AppsSearchResultsModelBridge(
- AppListModel::SearchResults* results_model,
- NSTableView* results_table_view)
- : results_(results_model),
- table_view_([results_table_view retain]) {
+ AppsSearchResultsController* results_controller)
+ : parent_(results_controller) {
UpdateItemObservers();
- results_->AddObserver(this);
+ [parent_ results]->AddObserver(this);
}
AppsSearchResultsModelBridge::~AppsSearchResultsModelBridge() {
- results_->RemoveObserver(this);
+ [parent_ results]->RemoveObserver(this);
}
NSMenu* AppsSearchResultsModelBridge::MenuForItem(size_t index) {
@@ -75,7 +88,7 @@ NSMenu* AppsSearchResultsModelBridge::MenuForItem(size_t index) {
void AppsSearchResultsModelBridge::UpdateItemObservers() {
DCHECK(item_observers_.empty());
- const size_t itemCount = results_->item_count();
+ const size_t itemCount = [parent_ results]->item_count();
for (size_t i = 0 ; i < itemCount; ++i)
item_observers_.push_back(new ItemObserver(this, i));
}
@@ -85,27 +98,27 @@ void AppsSearchResultsModelBridge::ReloadDataForItems(
NSIndexSet* column = [NSIndexSet indexSetWithIndex:0];
NSIndexSet* rows =
[NSIndexSet indexSetWithIndexesInRange:NSMakeRange(start, count)];
- [table_view_ reloadDataForRowIndexes:rows
- columnIndexes:column];
+ [[parent_ tableView] reloadDataForRowIndexes:rows
+ columnIndexes:column];
}
void AppsSearchResultsModelBridge::ListItemsAdded(
size_t start, size_t count) {
item_observers_.clear();
- if (start == static_cast<size_t>([table_view_ numberOfRows]))
- [table_view_ noteNumberOfRowsChanged];
+ if (start == static_cast<size_t>([[parent_ tableView] numberOfRows]))
+ [[parent_ tableView] noteNumberOfRowsChanged];
else
- [table_view_ reloadData];
+ [[parent_ tableView] reloadData];
UpdateItemObservers();
}
void AppsSearchResultsModelBridge::ListItemsRemoved(
size_t start, size_t count) {
item_observers_.clear();
- if (start == results_->item_count())
- [table_view_ noteNumberOfRowsChanged];
+ if (start == [parent_ results]->item_count())
+ [[parent_ tableView] noteNumberOfRowsChanged];
else
- [table_view_ reloadData];
+ [[parent_ tableView] reloadData];
UpdateItemObservers();
}
diff --git a/chromium/ui/app_list/cocoa/current_user_menu_item_view.h b/chromium/ui/app_list/cocoa/current_user_menu_item_view.h
deleted file mode 100644
index 84c240a4bec..00000000000
--- a/chromium/ui/app_list/cocoa/current_user_menu_item_view.h
+++ /dev/null
@@ -1,24 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_APP_LIST_COCOA_CURRENT_USER_MENU_ITEM_VIEW_H_
-#define UI_APP_LIST_COCOA_CURRENT_USER_MENU_ITEM_VIEW_H_
-
-#import <Cocoa/Cocoa.h>
-
-#include "ui/app_list/app_list_export.h"
-
-namespace app_list {
-class AppListViewDelegate;
-}
-
-// The custom in-menu view representing the currently signed-in user.
-APP_LIST_EXPORT
-@interface CurrentUserMenuItemView : NSView
-
-- (id)initWithDelegate:(app_list::AppListViewDelegate*)delegate;
-
-@end
-
-#endif // UI_APP_LIST_COCOA_CURRENT_USER_MENU_ITEM_VIEW_H_
diff --git a/chromium/ui/app_list/cocoa/current_user_menu_item_view.mm b/chromium/ui/app_list/cocoa/current_user_menu_item_view.mm
deleted file mode 100644
index 6aac34c6a99..00000000000
--- a/chromium/ui/app_list/cocoa/current_user_menu_item_view.mm
+++ /dev/null
@@ -1,85 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#import "ui/app_list/cocoa/current_user_menu_item_view.h"
-
-#include "base/logging.h"
-#include "base/mac/scoped_nsobject.h"
-#include "base/strings/sys_string_conversions.h"
-#include "grit/ui_resources.h"
-#include "ui/app_list/app_list_view_delegate.h"
-#include "ui/base/resource/resource_bundle.h"
-
-namespace {
-
-// Padding on the left of the indicator icon.
-const CGFloat kMenuLeftMargin = 3;
-
-}
-
-@interface CurrentUserMenuItemView ()
-
-// Adds a text label in the custom view in the menu showing the current user.
-- (NSTextField*)addLabelWithFrame:(NSPoint)origin
- labelText:(const string16&)labelText;
-
-@end
-
-@implementation CurrentUserMenuItemView
-
-- (id)initWithDelegate:(app_list::AppListViewDelegate*)delegate {
- DCHECK(delegate);
- if ((self = [super initWithFrame:NSZeroRect])) {
- NSImage* userImage = ui::ResourceBundle::GetSharedInstance().
- GetNativeImageNamed(IDR_APP_LIST_USER_INDICATOR).AsNSImage();
- NSRect imageRect = NSMakeRect(kMenuLeftMargin, 0, 0, 0);
- imageRect.size = [userImage size];
- base::scoped_nsobject<NSImageView> userImageView(
- [[NSImageView alloc] initWithFrame:imageRect]);
- [userImageView setImage:userImage];
- [self addSubview:userImageView];
-
- NSPoint labelOrigin = NSMakePoint(NSMaxX(imageRect), 0);
- NSTextField* userField =
- [self addLabelWithFrame:labelOrigin
- labelText:delegate->GetCurrentUserName()];
-
- labelOrigin.y = NSMaxY([userField frame]);
- NSTextField* emailField =
- [self addLabelWithFrame:labelOrigin
- labelText:delegate->GetCurrentUserEmail()];
- [emailField setTextColor:[NSColor disabledControlTextColor]];
-
- // Size the container view to fit the longest label.
- NSRect labelFrame = [emailField frame];
- if (NSWidth([userField frame]) > NSWidth(labelFrame))
- labelFrame.size.width = NSWidth([userField frame]);
- [self setFrameSize:NSMakeSize(
- NSMaxX(labelFrame) + NSMaxX(imageRect),
- NSMaxY(labelFrame))];
- }
- return self;
-}
-
-- (NSTextField*)addLabelWithFrame:(NSPoint)origin
- labelText:(const string16&)labelText {
- NSRect labelFrame = NSZeroRect;
- labelFrame.origin = origin;
- base::scoped_nsobject<NSTextField> label(
- [[NSTextField alloc] initWithFrame:labelFrame]);
- [label setStringValue:base::SysUTF16ToNSString(labelText)];
- [label setEditable:NO];
- [label setBordered:NO];
- [label setDrawsBackground:NO];
- [label setFont:[NSFont menuFontOfSize:0]];
- [label sizeToFit];
- [self addSubview:label];
- return label.autorelease();
-}
-
-- (BOOL)isFlipped {
- return YES;
-}
-
-@end
diff --git a/chromium/ui/app_list/pagination_model.cc b/chromium/ui/app_list/pagination_model.cc
index 2bf69020ab8..5e8d655a375 100644
--- a/chromium/ui/app_list/pagination_model.cc
+++ b/chromium/ui/app_list/pagination_model.cc
@@ -7,7 +7,7 @@
#include <algorithm>
#include "ui/app_list/pagination_model_observer.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
namespace app_list {
@@ -32,7 +32,7 @@ void PaginationModel::SetTotalPages(int total_pages) {
if (selected_page_ < 0)
SelectPage(0, false /* animate */);
if (selected_page_ >= total_pages_)
- SelectPage(total_pages_ - 1, false /* animate */);
+ SelectPage(std::max(total_pages_ - 1, 0), false /* animate */);
FOR_EACH_OBSERVER(PaginationModelObserver, observers_, TotalPagesChanged());
}
@@ -82,7 +82,7 @@ void PaginationModel::SelectPage(int page, bool animate) {
}
}
} else {
- DCHECK(page >= 0 && page < total_pages_);
+ DCHECK(total_pages_ == 0 || (page >= 0 && page < total_pages_));
if (page == selected_page_)
return;
@@ -221,8 +221,8 @@ void PaginationModel::StartTransitionAnimation(const Transition& transition) {
NotifyTransitionStarted();
SetTransition(transition);
- transition_animation_.reset(new ui::SlideAnimation(this));
- transition_animation_->SetTweenType(ui::Tween::LINEAR);
+ transition_animation_.reset(new gfx::SlideAnimation(this));
+ transition_animation_->SetTweenType(gfx::Tween::LINEAR);
transition_animation_->Reset(transition_.progress);
const int duration = is_valid_page(transition_.target_page) ?
@@ -240,12 +240,12 @@ void PaginationModel::ResetTransitionAnimation() {
pending_selected_page_ = -1;
}
-void PaginationModel::AnimationProgressed(const ui::Animation* animation) {
+void PaginationModel::AnimationProgressed(const gfx::Animation* animation) {
transition_.progress = transition_animation_->GetCurrentValue();
NotifyTransitionChanged();
}
-void PaginationModel::AnimationEnded(const ui::Animation* animation) {
+void PaginationModel::AnimationEnded(const gfx::Animation* animation) {
// Save |pending_selected_page_| because SelectPage resets it.
int next_target = pending_selected_page_;
diff --git a/chromium/ui/app_list/pagination_model.h b/chromium/ui/app_list/pagination_model.h
index 00ddd96e818..0546adc4bf8 100644
--- a/chromium/ui/app_list/pagination_model.h
+++ b/chromium/ui/app_list/pagination_model.h
@@ -11,9 +11,9 @@
#include "base/observer_list.h"
#include "base/time/time.h"
#include "ui/app_list/app_list_export.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
-namespace ui {
+namespace gfx {
class SlideAnimation;
}
@@ -24,7 +24,7 @@ class PaginationModelObserver;
// A simple pagination model that consists of two numbers: the total pages and
// the currently selected page. The model is a single selection model that at
// the most one page can become selected at any time.
-class APP_LIST_EXPORT PaginationModel : public ui::AnimationDelegate {
+class APP_LIST_EXPORT PaginationModel : public gfx::AnimationDelegate {
public:
// Holds info for transition animation and touch scroll.
struct Transition {
@@ -113,9 +113,9 @@ class APP_LIST_EXPORT PaginationModel : public ui::AnimationDelegate {
void StartTransitionAnimation(const Transition& transition);
void ResetTransitionAnimation();
- // ui::AnimationDelegate overrides:
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
+ // gfx::AnimationDelegate overrides:
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
int total_pages_;
int selected_page_;
@@ -127,7 +127,7 @@ class APP_LIST_EXPORT PaginationModel : public ui::AnimationDelegate {
// last target page is remembered here.
int pending_selected_page_;
- scoped_ptr<ui::SlideAnimation> transition_animation_;
+ scoped_ptr<gfx::SlideAnimation> transition_animation_;
int transition_duration_ms_; // Transition duration in millisecond.
int overscroll_transition_duration_ms_;
diff --git a/chromium/ui/app_list/search_result.h b/chromium/ui/app_list/search_result.h
index 5baa50f5579..e8e265fa70b 100644
--- a/chromium/ui/app_list/search_result.h
+++ b/chromium/ui/app_list/search_result.h
@@ -12,8 +12,8 @@
#include "base/strings/string16.h"
#include "ui/app_list/app_list_export.h"
#include "ui/base/models/list_model.h"
-#include "ui/base/range/range.h"
#include "ui/gfx/image/image_skia.h"
+#include "ui/gfx/range/range.h"
namespace ui {
class MenuModel;
@@ -45,7 +45,7 @@ class APP_LIST_EXPORT SearchResult {
}
int styles;
- ui::Range range;
+ gfx::Range range;
};
typedef std::vector<Tag> Tags;
@@ -106,7 +106,8 @@ class APP_LIST_EXPORT SearchResult {
void AddObserver(SearchResultObserver* observer);
void RemoveObserver(SearchResultObserver* observer);
- // Returns the context menu model for this item.
+ // Returns the context menu model for this item, or NULL if there is currently
+ // no menu for the item (e.g. during install).
// Note the returned menu model is owned by this item.
virtual ui::MenuModel* GetContextMenuModel();
diff --git a/chromium/ui/app_list/signin_delegate.cc b/chromium/ui/app_list/signin_delegate.cc
index 51eb8305019..b0dd7e67590 100644
--- a/chromium/ui/app_list/signin_delegate.cc
+++ b/chromium/ui/app_list/signin_delegate.cc
@@ -3,7 +3,6 @@
// found in the LICENSE file.
#include "ui/app_list/signin_delegate.h"
-#include "ui/app_list/signin_delegate_observer.h"
namespace app_list {
@@ -11,17 +10,4 @@ SigninDelegate::SigninDelegate() {}
SigninDelegate::~SigninDelegate() {}
-void SigninDelegate::AddObserver(SigninDelegateObserver* observer) {
- observers_.AddObserver(observer);
-}
-
-void SigninDelegate::RemoveObserver(SigninDelegateObserver* observer) {
- observers_.RemoveObserver(observer);
-}
-
-void SigninDelegate::NotifySigninSuccess() {
- FOR_EACH_OBSERVER(app_list::SigninDelegateObserver, observers_,
- OnSigninSuccess());
-}
-
} // namespace app_list
diff --git a/chromium/ui/app_list/signin_delegate.h b/chromium/ui/app_list/signin_delegate.h
index eda67f410e8..54f59179de9 100644
--- a/chromium/ui/app_list/signin_delegate.h
+++ b/chromium/ui/app_list/signin_delegate.h
@@ -6,14 +6,11 @@
#define UI_APP_LIST_SIGNIN_DELEGATE_H_
#include "base/basictypes.h"
-#include "base/observer_list.h"
#include "base/strings/string16.h"
#include "ui/app_list/app_list_export.h"
namespace app_list {
-class SigninDelegateObserver;
-
class APP_LIST_EXPORT SigninDelegate {
public:
SigninDelegate();
@@ -30,15 +27,7 @@ class APP_LIST_EXPORT SigninDelegate {
virtual base::string16 GetLearnMoreLinkText() = 0;
virtual base::string16 GetSettingsLinkText() = 0;
- void AddObserver(SigninDelegateObserver* observer);
- void RemoveObserver(SigninDelegateObserver* observer);
-
- protected:
- void NotifySigninSuccess();
-
private:
- ObserverList<SigninDelegateObserver, true> observers_;
-
DISALLOW_COPY_AND_ASSIGN(SigninDelegate);
};
diff --git a/chromium/ui/app_list/signin_delegate_observer.h b/chromium/ui/app_list/signin_delegate_observer.h
deleted file mode 100644
index 47c499260ef..00000000000
--- a/chromium/ui/app_list/signin_delegate_observer.h
+++ /dev/null
@@ -1,24 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_APP_LIST_SIGNIN_DELEGATE_OBSERVER_H_
-#define UI_APP_LIST_SIGNIN_DELEGATE_OBSERVER_H_
-
-#include "ui/app_list/app_list_export.h"
-
-namespace app_list {
-
-// Abstract interface to allow handling app list signin success.
-class APP_LIST_EXPORT SigninDelegateObserver {
- public:
- // Called by the SigninDelegate when signin has successfully completed.
- virtual void OnSigninSuccess() = 0;
-
- protected:
- virtual ~SigninDelegateObserver() {}
-};
-
-} // namespace app_list
-
-#endif // UI_APP_LIST_SIGNIN_DELEGATE_OBSERVER_H_
diff --git a/chromium/ui/app_list/views/app_list_item_view.cc b/chromium/ui/app_list/views/app_list_item_view.cc
index 1b9aaf701d1..2717f51a825 100644
--- a/chromium/ui/app_list/views/app_list_item_view.cc
+++ b/chromium/ui/app_list/views/app_list_item_view.cc
@@ -13,11 +13,11 @@
#include "ui/app_list/views/cached_label.h"
#include "ui/app_list/views/progress_bar_view.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/animation/throb_animation.h"
#include "ui/base/dragdrop/drag_utils.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/scoped_layer_animation_settings.h"
+#include "ui/gfx/animation/throb_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/gfx/image/image_skia_operations.h"
@@ -130,6 +130,11 @@ void AppListItemView::UpdateIcon() {
icon_->SetImage(resized);
}
+void AppListItemView::UpdateTooltip() {
+ title_->SetTooltipText(model_->title() == model_->full_name() ?
+ string16() : UTF8ToUTF16(model_->full_name()));
+}
+
void AppListItemView::SetUIState(UIState state) {
if (ui_state_ == state)
return;
@@ -193,6 +198,7 @@ void AppListItemView::ItemIconChanged() {
void AppListItemView::ItemTitleChanged() {
title_->SetText(UTF8ToUTF16(model_->title()));
title_->Invalidate();
+ UpdateTooltip();
Layout();
}
diff --git a/chromium/ui/app_list/views/app_list_item_view.h b/chromium/ui/app_list/views/app_list_item_view.h
index 0738d83c7e7..311d7219456 100644
--- a/chromium/ui/app_list/views/app_list_item_view.h
+++ b/chromium/ui/app_list/views/app_list_item_view.h
@@ -62,6 +62,9 @@ class APP_LIST_EXPORT AppListItemView : public views::CustomButton,
// Get icon from model and schedule background processing.
void UpdateIcon();
+ // Update the tooltip text from the model.
+ void UpdateTooltip();
+
void SetUIState(UIState state);
// Sets |touch_dragging_| flag and updates UI.
diff --git a/chromium/ui/app_list/views/app_list_main_view.cc b/chromium/ui/app_list/views/app_list_main_view.cc
index fa0de27ce0e..f08fef82d9b 100644
--- a/chromium/ui/app_list/views/app_list_main_view.cc
+++ b/chromium/ui/app_list/views/app_list_main_view.cc
@@ -6,8 +6,10 @@
#include <algorithm>
+#include "base/bind.h"
#include "base/callback.h"
#include "base/files/file_path.h"
+#include "base/message_loop/message_loop.h"
#include "base/strings/string_util.h"
#include "ui/app_list/app_list_constants.h"
#include "ui/app_list/app_list_item_model.h"
@@ -77,13 +79,14 @@ class AppListMainView::IconLoader : public AppListItemModelObserver {
AppListMainView::AppListMainView(AppListViewDelegate* delegate,
AppListModel* model,
PaginationModel* pagination_model,
- views::View* anchor)
+ gfx::NativeView parent)
: delegate_(delegate),
model_(model),
search_box_view_(NULL),
- contents_view_(NULL) {
+ contents_view_(NULL),
+ weak_ptr_factory_(this) {
// Starts icon loading early.
- PreloadIcons(pagination_model, anchor);
+ PreloadIcons(pagination_model, parent);
SetLayoutManager(new views::BoxLayout(views::BoxLayout::kVertical,
kInnerPadding,
@@ -127,6 +130,7 @@ void AppListMainView::ShowAppListWhenReady() {
void AppListMainView::Close() {
icon_loading_wait_timer_.Stop();
+ contents_view_->CancelDrag();
}
void AppListMainView::Prerender() {
@@ -134,17 +138,15 @@ void AppListMainView::Prerender() {
}
void AppListMainView::SetDragAndDropHostOfCurrentAppList(
- app_list::ApplicationDragAndDropHost* drag_and_drop_host) {
+ ApplicationDragAndDropHost* drag_and_drop_host) {
contents_view_->SetDragAndDropHostOfCurrentAppList(drag_and_drop_host);
}
void AppListMainView::PreloadIcons(PaginationModel* pagination_model,
- views::View* anchor) {
+ gfx::NativeView parent) {
ui::ScaleFactor scale_factor = ui::SCALE_FACTOR_100P;
- if (anchor && anchor->GetWidget()) {
- scale_factor = ui::GetScaleFactorForNativeView(
- anchor->GetWidget()->GetNativeView());
- }
+ if (parent)
+ scale_factor = ui::GetScaleFactorForNativeView(parent);
// |pagination_model| could have -1 as the initial selected page and
// assumes first page (i.e. index 0) will be used in this case.
@@ -230,7 +232,13 @@ void AppListMainView::OnResultInstalled(SearchResult* result) {
}
void AppListMainView::OnResultUninstalled(SearchResult* result) {
- QueryChanged(search_box_view_);
+ // Resubmit the query via a posted task so that all observers for the
+ // uninstall notification are notified.
+ base::MessageLoop::current()->PostTask(
+ FROM_HERE,
+ base::Bind(&AppListMainView::QueryChanged,
+ weak_ptr_factory_.GetWeakPtr(),
+ search_box_view_));
}
} // namespace app_list
diff --git a/chromium/ui/app_list/views/app_list_main_view.h b/chromium/ui/app_list/views/app_list_main_view.h
index 1909d97c1da..0c9a7383e12 100644
--- a/chromium/ui/app_list/views/app_list_main_view.h
+++ b/chromium/ui/app_list/views/app_list_main_view.h
@@ -8,10 +8,11 @@
#include <string>
#include "base/memory/scoped_vector.h"
+#include "base/memory/weak_ptr.h"
#include "base/timer/timer.h"
-#include "ui/app_list/apps_grid_view_delegate.h"
-#include "ui/app_list/search_box_view_delegate.h"
-#include "ui/app_list/search_result_list_view_delegate.h"
+#include "ui/app_list/views/apps_grid_view_delegate.h"
+#include "ui/app_list/views/search_box_view_delegate.h"
+#include "ui/app_list/views/search_result_list_view_delegate.h"
#include "ui/views/view.h"
namespace views {
@@ -39,7 +40,7 @@ class AppListMainView : public views::View,
explicit AppListMainView(AppListViewDelegate* delegate,
AppListModel* model,
PaginationModel* pagination_model,
- views::View* anchor);
+ gfx::NativeView parent);
virtual ~AppListMainView();
void ShowAppListWhenReady();
@@ -59,9 +60,9 @@ class AppListMainView : public views::View,
class IconLoader;
// Loads icon image for the apps in the selected page of |pagination_model|.
- // |anchor| is used to determine the image scale factor to use.
+ // |parent| is used to determine the image scale factor to use.
void PreloadIcons(PaginationModel* pagination_model,
- views::View* anchor);
+ gfx::NativeView parent);
// Invoked when |icon_loading_wait_timer_| fires.
void OnIconLoadingWaitTimer();
@@ -99,6 +100,8 @@ class AppListMainView : public views::View,
ScopedVector<IconLoader> pending_icon_loaders_;
+ base::WeakPtrFactory<AppListMainView> weak_ptr_factory_;
+
DISALLOW_COPY_AND_ASSIGN(AppListMainView);
};
diff --git a/chromium/ui/app_list/views/app_list_menu_views.cc b/chromium/ui/app_list/views/app_list_menu_views.cc
index 0eb853607f0..04c1f2155b4 100644
--- a/chromium/ui/app_list/views/app_list_menu_views.cc
+++ b/chromium/ui/app_list/views/app_list_menu_views.cc
@@ -5,6 +5,7 @@
#include "ui/app_list/views/app_list_menu_views.h"
#include "grit/ui_resources.h"
+#include "ui/app_list/app_list_model.h"
#include "ui/app_list/app_list_view_delegate.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/views/controls/button/menu_button.h"
@@ -19,114 +20,10 @@ using views::MenuItemView;
namespace app_list {
-namespace {
-
-class CurrentUserView : public views::View {
- public:
- CurrentUserView(const base::string16& user_name,
- const base::string16& user_email,
- const gfx::ImageSkia& icon) {
- const views::MenuConfig& menu_config = views::MenuConfig::instance(NULL);
- views::GridLayout* layout = new views::GridLayout(this);
- int item_right_padding = menu_config.label_to_arrow_padding +
- menu_config.arrow_width +
- menu_config.arrow_to_edge_padding;
-
- layout->SetInsets(0, 0, 0, item_right_padding);
- SetLayoutManager(layout);
-
- views::ColumnSet* columns = layout->AddColumnSet(0);
- columns->AddColumn(views::GridLayout::FILL,
- views::GridLayout::FILL,
- 0,
- views::GridLayout::USE_PREF,
- 0,
- menu_config.check_width + menu_config.item_left_margin);
- columns->AddColumn(views::GridLayout::FILL,
- views::GridLayout::FILL,
- 1,
- views::GridLayout::USE_PREF,
- 0,
- 0);
-
- layout->StartRow(0, 0);
- views::ImageView* image_view = new views::ImageView();
- image_view->SetImage(icon);
- layout->AddView(image_view);
-
- views::Label* user_name_view = new views::Label(user_name);
- user_name_view->SetHorizontalAlignment(gfx::ALIGN_LEFT);
- layout->AddView(user_name_view);
-
- layout->StartRow(0, 0);
- views::Label* user_email_view = new views::Label(user_email);
- user_email_view->SetHorizontalAlignment(gfx::ALIGN_LEFT);
- user_email_view->SetEnabled(false);
- layout->SkipColumns(1);
- layout->AddView(user_email_view);
- }
-
- private:
- DISALLOW_COPY_AND_ASSIGN(CurrentUserView);
-};
-
-class CurrentUserMenuItem : public MenuItemView {
- public:
- CurrentUserMenuItem(MenuItemView* parent,
- int id,
- const base::string16& user_name,
- const base::string16& user_email,
- const gfx::ImageSkia& icon)
- : MenuItemView(parent, id, MenuItemView::NORMAL) {
- AddChildView(new CurrentUserView(user_name, user_email, icon));
- }
-
- private:
- DISALLOW_COPY_AND_ASSIGN(CurrentUserMenuItem);
-};
-
-class AppListMenuModelAdapter : public views::MenuModelAdapter {
- public:
- AppListMenuModelAdapter(ui::MenuModel* menu_model,
- AppListViewDelegate* delegate)
- : views::MenuModelAdapter(menu_model),
- delegate_(delegate) {}
- virtual ~AppListMenuModelAdapter() {}
-
- // Overridden from views::MenuModelAdapter:
- virtual MenuItemView* AppendMenuItem(MenuItemView* menu,
- ui::MenuModel* model,
- int index) OVERRIDE {
- if (!delegate_)
- return NULL;
-
- int id = model->GetCommandIdAt(index);
- if (id != AppListMenu::CURRENT_USER)
- return MenuModelAdapter::AppendMenuItem(menu, model, index);
-
- ui::ResourceBundle& rb = ui::ResourceBundle::GetSharedInstance();
- MenuItemView* item = new CurrentUserMenuItem(
- menu,
- id,
- delegate_->GetCurrentUserName(),
- delegate_->GetCurrentUserEmail(),
- *rb.GetImageSkiaNamed(IDR_APP_LIST_USER_INDICATOR));
- menu->CreateSubmenu();
- menu->GetSubmenu()->AddChildViewAt(item, index);
- return item;
- }
-
- private:
- AppListViewDelegate* delegate_;
-
- DISALLOW_COPY_AND_ASSIGN(AppListMenuModelAdapter);
-};
-
-} // namespace
-
-AppListMenuViews::AppListMenuViews(AppListViewDelegate* delegate)
- : AppListMenu(delegate) {
- menu_delegate_.reset(new AppListMenuModelAdapter(menu_model(), delegate));
+AppListMenuViews::AppListMenuViews(AppListViewDelegate* delegate,
+ AppListModel* app_list_model)
+ : AppListMenu(delegate, app_list_model->users()) {
+ menu_delegate_.reset(new views::MenuModelAdapter(menu_model()));
menu_ = new MenuItemView(menu_delegate_.get());
menu_runner_.reset(new views::MenuRunner(menu_));
menu_delegate_->BuildMenu(menu_);
diff --git a/chromium/ui/app_list/views/app_list_menu_views.h b/chromium/ui/app_list/views/app_list_menu_views.h
index 15f3dbb1f85..2dc3d01f046 100644
--- a/chromium/ui/app_list/views/app_list_menu_views.h
+++ b/chromium/ui/app_list/views/app_list_menu_views.h
@@ -20,11 +20,14 @@ class MenuButton;
namespace app_list {
+class AppListModel;
+
// Views implementation of the app list menu.
// TODO(benwells): We should consider moving this into Chrome.
-class AppListMenuViews : public app_list::AppListMenu {
+class AppListMenuViews : public AppListMenu {
public:
- explicit AppListMenuViews(AppListViewDelegate* delegate);
+ AppListMenuViews(AppListViewDelegate* delegate,
+ AppListModel* model);
virtual ~AppListMenuViews();
void RunMenuAt(views::MenuButton* button, const gfx::Point& point);
diff --git a/chromium/ui/app_list/views/app_list_view.cc b/chromium/ui/app_list/views/app_list_view.cc
index 118ab2b3409..ae4647ff2c3 100644
--- a/chromium/ui/app_list/views/app_list_view.cc
+++ b/chromium/ui/app_list/views/app_list_view.cc
@@ -4,6 +4,7 @@
#include "ui/app_list/views/app_list_view.h"
+#include "base/callback.h"
#include "base/command_line.h"
#include "base/strings/string_util.h"
#include "ui/app_list/app_list_constants.h"
@@ -37,6 +38,8 @@ namespace app_list {
namespace {
+base::Closure g_next_paint_callback;
+
// The distance between the arrow tip and edge of the anchor view.
const int kArrowOffset = 10;
@@ -51,83 +54,38 @@ AppListView::AppListView(AppListViewDelegate* delegate)
app_list_main_view_(NULL),
signin_view_(NULL) {
if (delegate_)
- delegate_->SetModel(model_.get());
- if (GetSigninDelegate())
- GetSigninDelegate()->AddObserver(this);
+ delegate_->InitModel(model_.get());
+ model_->AddObserver(this);
}
AppListView::~AppListView() {
- if (GetSigninDelegate())
- GetSigninDelegate()->RemoveObserver(this);
-
+ model_->RemoveObserver(this);
// Models are going away, ensure their references are cleared.
RemoveAllChildViews(true);
}
-void AppListView::InitAsBubble(gfx::NativeView parent,
- PaginationModel* pagination_model,
- views::View* anchor,
- const gfx::Point& anchor_point,
- views::BubbleBorder::Arrow arrow,
- bool border_accepts_events) {
- app_list_main_view_ = new AppListMainView(delegate_.get(),
- model_.get(),
- pagination_model,
- anchor);
- AddChildView(app_list_main_view_);
-#if defined(USE_AURA)
- app_list_main_view_->SetPaintToLayer(true);
- app_list_main_view_->SetFillsBoundsOpaquely(false);
- app_list_main_view_->layer()->SetMasksToBounds(true);
-#endif
-
- signin_view_ = new SigninView(
- GetSigninDelegate(),
- app_list_main_view_->GetPreferredSize().width());
- AddChildView(signin_view_);
-
- OnSigninStatusChanged();
-
+void AppListView::InitAsBubbleAttachedToAnchor(
+ gfx::NativeView parent,
+ PaginationModel* pagination_model,
+ views::View* anchor,
+ const gfx::Vector2d& anchor_offset,
+ views::BubbleBorder::Arrow arrow,
+ bool border_accepts_events) {
set_anchor_view(anchor);
- set_anchor_rect(gfx::Rect(anchor_point, gfx::Size()));
- set_color(kContentsBackgroundColor);
- set_margins(gfx::Insets());
- set_move_with_anchor(true);
- set_parent_window(parent);
- set_close_on_deactivate(false);
- set_close_on_esc(false);
- set_anchor_view_insets(gfx::Insets(kArrowOffset, kArrowOffset,
- kArrowOffset, kArrowOffset));
- set_border_accepts_events(border_accepts_events);
- set_shadow(views::BubbleBorder::BIG_SHADOW);
-#if defined(USE_AURA) && defined(OS_WIN)
- if (!ui::win::IsAeroGlassEnabled() ||
- CommandLine::ForCurrentProcess()->HasSwitch(
- switches::kDisableDwmComposition)) {
- set_shadow(views::BubbleBorder::NO_SHADOW_OPAQUE_BORDER);
- }
-#endif
- views::BubbleDelegateView::CreateBubble(this);
- SetBubbleArrow(arrow);
-
-#if defined(USE_AURA)
- GetWidget()->GetNativeWindow()->layer()->SetMasksToBounds(true);
- GetBubbleFrameView()->set_background(new AppListBackground(
- GetBubbleFrameView()->bubble_border()->GetBorderCornerRadius(),
- app_list_main_view_));
- set_background(NULL);
-#else
- set_background(new AppListBackground(
- GetBubbleFrameView()->bubble_border()->GetBorderCornerRadius(),
- app_list_main_view_));
+ InitAsBubbleInternal(
+ parent, pagination_model, arrow, border_accepts_events, anchor_offset);
+}
- // On non-aura the bubble has two widgets, and it's possible for the border
- // to be shown independently in odd situations. Explicitly hide the bubble
- // widget to ensure that any WM_WINDOWPOSCHANGED messages triggered by the
- // window manager do not have the SWP_SHOWWINDOW flag set which would cause
- // the border to be shown. See http://crbug.com/231687 .
- GetWidget()->Hide();
-#endif
+void AppListView::InitAsBubbleAtFixedLocation(
+ gfx::NativeView parent,
+ PaginationModel* pagination_model,
+ const gfx::Point& anchor_point_in_screen,
+ views::BubbleBorder::Arrow arrow,
+ bool border_accepts_events) {
+ set_anchor_view(NULL);
+ set_anchor_rect(gfx::Rect(anchor_point_in_screen, gfx::Size()));
+ InitAsBubbleInternal(
+ parent, pagination_model, arrow, border_accepts_events, gfx::Vector2d());
}
void AppListView::SetBubbleArrow(views::BubbleBorder::Arrow arrow) {
@@ -142,7 +100,7 @@ void AppListView::SetAnchorPoint(const gfx::Point& anchor_point) {
}
void AppListView::SetDragAndDropHostOfCurrentAppList(
- app_list::ApplicationDragAndDropHost* drag_and_drop_host) {
+ ApplicationDragAndDropHost* drag_and_drop_host) {
app_list_main_view_->SetDragAndDropHostOfCurrentAppList(drag_and_drop_host);
}
@@ -166,6 +124,14 @@ gfx::Size AppListView::GetPreferredSize() {
return app_list_main_view_->GetPreferredSize();
}
+void AppListView::Paint(gfx::Canvas* canvas) {
+ views::BubbleDelegateView::Paint(canvas);
+ if (!g_next_paint_callback.is_null()) {
+ g_next_paint_callback.Run();
+ g_next_paint_callback.Reset();
+ }
+}
+
bool AppListView::ShouldHandleSystemCommands() const {
return true;
}
@@ -175,14 +141,28 @@ void AppListView::Prerender() {
}
void AppListView::OnSigninStatusChanged() {
- const bool needs_signin =
- GetSigninDelegate() && GetSigninDelegate()->NeedSignin();
-
- signin_view_->SetVisible(needs_signin);
- app_list_main_view_->SetVisible(!needs_signin);
+ signin_view_->SetVisible(!model_->signed_in());
+ app_list_main_view_->SetVisible(model_->signed_in());
app_list_main_view_->search_box_view()->InvalidateMenu();
}
+void AppListView::SetProfileByPath(const base::FilePath& profile_path) {
+ delegate_->SetProfileByPath(profile_path);
+}
+
+void AppListView::AddObserver(Observer* observer) {
+ observers_.AddObserver(observer);
+}
+
+void AppListView::RemoveObserver(Observer* observer) {
+ observers_.RemoveObserver(observer);
+}
+
+// static
+void AppListView::SetNextPaintCallback(const base::Closure& callback) {
+ g_next_paint_callback = callback;
+}
+
#if defined(OS_WIN)
HWND AppListView::GetHWND() const {
#if defined(USE_AURA)
@@ -195,6 +175,71 @@ HWND AppListView::GetHWND() const {
}
#endif
+void AppListView::InitAsBubbleInternal(gfx::NativeView parent,
+ PaginationModel* pagination_model,
+ views::BubbleBorder::Arrow arrow,
+ bool border_accepts_events,
+ const gfx::Vector2d& anchor_offset) {
+ app_list_main_view_ = new AppListMainView(delegate_.get(),
+ model_.get(),
+ pagination_model,
+ parent);
+ AddChildView(app_list_main_view_);
+#if defined(USE_AURA)
+ app_list_main_view_->SetPaintToLayer(true);
+ app_list_main_view_->SetFillsBoundsOpaquely(false);
+ app_list_main_view_->layer()->SetMasksToBounds(true);
+#endif
+
+ signin_view_ = new SigninView(
+ delegate_ ? delegate_->GetSigninDelegate()
+ : NULL,
+ app_list_main_view_->GetPreferredSize().width());
+ AddChildView(signin_view_);
+
+ OnSigninStatusChanged();
+ set_color(kContentsBackgroundColor);
+ set_margins(gfx::Insets());
+ set_move_with_anchor(true);
+ set_parent_window(parent);
+ set_close_on_deactivate(false);
+ set_close_on_esc(false);
+ set_anchor_view_insets(gfx::Insets(kArrowOffset + anchor_offset.y(),
+ kArrowOffset + anchor_offset.x(),
+ kArrowOffset - anchor_offset.y(),
+ kArrowOffset - anchor_offset.x()));
+ set_border_accepts_events(border_accepts_events);
+ set_shadow(views::BubbleBorder::BIG_SHADOW);
+#if defined(USE_AURA) && defined(OS_WIN)
+ if (!ui::win::IsAeroGlassEnabled() ||
+ CommandLine::ForCurrentProcess()->HasSwitch(
+ switches::kDisableDwmComposition)) {
+ set_shadow(views::BubbleBorder::NO_SHADOW_OPAQUE_BORDER);
+ }
+#endif
+ views::BubbleDelegateView::CreateBubble(this);
+ SetBubbleArrow(arrow);
+
+#if defined(USE_AURA)
+ GetWidget()->GetNativeWindow()->layer()->SetMasksToBounds(true);
+ GetBubbleFrameView()->set_background(new AppListBackground(
+ GetBubbleFrameView()->bubble_border()->GetBorderCornerRadius(),
+ app_list_main_view_));
+ set_background(NULL);
+#else
+ set_background(new AppListBackground(
+ GetBubbleFrameView()->bubble_border()->GetBorderCornerRadius(),
+ app_list_main_view_));
+
+ // On non-aura the bubble has two widgets, and it's possible for the border
+ // to be shown independently in odd situations. Explicitly hide the bubble
+ // widget to ensure that any WM_WINDOWPOSCHANGED messages triggered by the
+ // window manager do not have the SWP_SHOWWINDOW flag set which would cause
+ // the border to be shown. See http://crbug.com/231687 .
+ GetWidget()->Hide();
+#endif
+}
+
views::View* AppListView::GetInitiallyFocusedView() {
return app_list_main_view_->search_box_view()->search_box();
}
@@ -247,8 +292,9 @@ void AppListView::OnWidgetActivationChanged(views::Widget* widget,
bool active) {
// Do not called inherited function as the bubble delegate auto close
// functionality is not used.
- if (delegate_ && widget == GetWidget())
- delegate_->ViewActivationChanged(active);
+ if (widget == GetWidget())
+ FOR_EACH_OBSERVER(Observer, observers_,
+ OnActivationChanged(widget, active));
}
void AppListView::OnWidgetVisibilityChanged(views::Widget* widget,
@@ -268,12 +314,12 @@ void AppListView::OnWidgetVisibilityChanged(views::Widget* widget,
Layout();
}
-void AppListView::OnSigninSuccess() {
+void AppListView::OnAppListModelSigninStatusChanged() {
OnSigninStatusChanged();
}
-SigninDelegate* AppListView::GetSigninDelegate() {
- return delegate_ ? delegate_->GetSigninDelegate() : NULL;
+void AppListView::OnAppListModelUsersChanged() {
+ OnSigninStatusChanged();
}
} // namespace app_list
diff --git a/chromium/ui/app_list/views/app_list_view.h b/chromium/ui/app_list/views/app_list_view.h
index fff4815ba1b..38564949307 100644
--- a/chromium/ui/app_list/views/app_list_view.h
+++ b/chromium/ui/app_list/views/app_list_view.h
@@ -5,11 +5,17 @@
#ifndef UI_APP_LIST_VIEWS_APP_LIST_VIEW_H_
#define UI_APP_LIST_VIEWS_APP_LIST_VIEW_H_
+#include "base/callback_forward.h"
#include "base/memory/scoped_ptr.h"
+#include "base/observer_list.h"
#include "ui/app_list/app_list_export.h"
-#include "ui/app_list/signin_delegate_observer.h"
+#include "ui/app_list/app_list_model_observer.h"
#include "ui/views/bubble/bubble_delegate.h"
+namespace base {
+class FilePath;
+}
+
namespace views {
class Widget;
}
@@ -26,19 +32,33 @@ class SigninView;
// AppListView is the top-level view and controller of app list UI. It creates
// and hosts a AppsGridView and passes AppListModel to it for display.
class APP_LIST_EXPORT AppListView : public views::BubbleDelegateView,
- public SigninDelegateObserver {
+ public AppListModelObserver {
public:
+ class Observer {
+ public:
+ virtual void OnActivationChanged(views::Widget* widget, bool active) = 0;
+ };
+
// Takes ownership of |delegate|.
explicit AppListView(AppListViewDelegate* delegate);
virtual ~AppListView();
- // Initializes the widget.
- void InitAsBubble(gfx::NativeView parent,
- PaginationModel* pagination_model,
- views::View* anchor,
- const gfx::Point& anchor_point,
- views::BubbleBorder::Arrow arrow,
- bool border_accepts_events);
+ // Initializes the widget and use a given |anchor| plus an |anchor_offset| for
+ // positioning.
+ void InitAsBubbleAttachedToAnchor(gfx::NativeView parent,
+ PaginationModel* pagination_model,
+ views::View* anchor,
+ const gfx::Vector2d& anchor_offset,
+ views::BubbleBorder::Arrow arrow,
+ bool border_accepts_events);
+
+ // Initializes the widget and use a fixed |anchor_point_in_screen| for
+ // positioning.
+ void InitAsBubbleAtFixedLocation(gfx::NativeView parent,
+ PaginationModel* pagination_model,
+ const gfx::Point& anchor_point_in_screen,
+ views::BubbleBorder::Arrow arrow,
+ bool border_accepts_events);
void SetBubbleArrow(views::BubbleBorder::Arrow arrow);
@@ -49,7 +69,7 @@ class APP_LIST_EXPORT AppListView : public views::BubbleDelegateView,
// InitAsBubble was called since the app list object needs to exist so that
// it can set the host.
void SetDragAndDropHostOfCurrentAppList(
- app_list::ApplicationDragAndDropHost* drag_and_drop_host);
+ ApplicationDragAndDropHost* drag_and_drop_host);
// Shows the UI when there are no pending icon loads. Otherwise, starts a
// timer to show the UI when a maximum allowed wait time has expired.
@@ -61,6 +81,7 @@ class APP_LIST_EXPORT AppListView : public views::BubbleDelegateView,
// Overridden from views::View:
virtual gfx::Size GetPreferredSize() OVERRIDE;
+ virtual void Paint(gfx::Canvas* canvas) OVERRIDE;
// WidgetDelegate overrides:
virtual bool ShouldHandleSystemCommands() const OVERRIDE;
@@ -70,11 +91,27 @@ class APP_LIST_EXPORT AppListView : public views::BubbleDelegateView,
// Invoked when the sign-in status is changed to switch on/off sign-in view.
void OnSigninStatusChanged();
+ void SetProfileByPath(const base::FilePath& profile_path);
+
+ void AddObserver(Observer* observer);
+ void RemoveObserver(Observer* observer);
+
+ // Set a callback to be called the next time any app list paints.
+ static void SetNextPaintCallback(const base::Closure& callback);
+
#if defined(OS_WIN)
HWND GetHWND() const;
#endif
+ AppListModel* model() { return model_.get(); }
+
private:
+ void InitAsBubbleInternal(gfx::NativeView parent,
+ PaginationModel* pagination_model,
+ views::BubbleBorder::Arrow arrow,
+ bool border_accepts_events,
+ const gfx::Vector2d& anchor_offset);
+
// Overridden from views::WidgetDelegateView:
virtual views::View* GetInitiallyFocusedView() OVERRIDE;
virtual gfx::ImageSkia GetWindowIcon() OVERRIDE;
@@ -92,8 +129,9 @@ class APP_LIST_EXPORT AppListView : public views::BubbleDelegateView,
virtual void OnWidgetActivationChanged(
views::Widget* widget, bool active) OVERRIDE;
- // Overridden from SigninDelegateObserver:
- virtual void OnSigninSuccess() OVERRIDE;
+ // Overridden from AppListModelObserver:
+ virtual void OnAppListModelSigninStatusChanged() OVERRIDE;
+ virtual void OnAppListModelUsersChanged() OVERRIDE;
SigninDelegate* GetSigninDelegate();
@@ -103,6 +141,8 @@ class APP_LIST_EXPORT AppListView : public views::BubbleDelegateView,
AppListMainView* app_list_main_view_;
SigninView* signin_view_;
+ ObserverList<Observer> observers_;
+
DISALLOW_COPY_AND_ASSIGN(AppListView);
};
diff --git a/chromium/ui/app_list/views/apps_grid_view.cc b/chromium/ui/app_list/views/apps_grid_view.cc
index 1e9b2bfeda5..9135dda7344 100644
--- a/chromium/ui/app_list/views/apps_grid_view.cc
+++ b/chromium/ui/app_list/views/apps_grid_view.cc
@@ -7,15 +7,15 @@
#include <algorithm>
#include "ui/app_list/app_list_item_model.h"
-#include "ui/app_list/apps_grid_view_delegate.h"
#include "ui/app_list/pagination_model.h"
#include "ui/app_list/views/app_list_drag_and_drop_host.h"
#include "ui/app_list/views/app_list_item_view.h"
+#include "ui/app_list/views/apps_grid_view_delegate.h"
#include "ui/app_list/views/page_switcher.h"
#include "ui/app_list/views/pulsing_block_view.h"
-#include "ui/base/animation/animation.h"
-#include "ui/base/events/event.h"
#include "ui/compositor/scoped_layer_animation_settings.h"
+#include "ui/events/event.h"
+#include "ui/gfx/animation/animation.h"
#include "ui/views/border.h"
#include "ui/views/view_model_utils.h"
#include "ui/views/widget/widget.h"
@@ -34,6 +34,8 @@
#include "ui/base/dragdrop/os_exchange_data_provider_win.h"
#endif
+namespace app_list {
+
namespace {
// Distance a drag needs to be from the app grid to be considered 'outside', at
@@ -66,7 +68,7 @@ const int kPrerenderPages = 1;
const float kDragAndDropProxyScale = 1.5f;
// For testing we remember the last created grid view.
-app_list::AppsGridView* last_created_grid_view_for_test = NULL;
+AppsGridView* last_created_grid_view_for_test = NULL;
// RowMoveAnimationDelegate is used when moving an item into a different row.
// Before running the animation, the item's layer is re-created and kept in
@@ -86,8 +88,8 @@ class RowMoveAnimationDelegate
}
virtual ~RowMoveAnimationDelegate() {}
- // ui::AnimationDelegate overrides:
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE {
+ // gfx::AnimationDelegate overrides:
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE {
view_->layer()->SetOpacity(animation->GetCurrentValue());
view_->layer()->ScheduleDraw();
@@ -98,11 +100,11 @@ class RowMoveAnimationDelegate
layer_->ScheduleDraw();
}
}
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE {
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE {
view_->layer()->SetOpacity(1.0f);
view_->layer()->ScheduleDraw();
}
- virtual void AnimationCanceled(const ui::Animation* animation) OVERRIDE {
+ virtual void AnimationCanceled(const gfx::Animation* animation) OVERRIDE {
view_->layer()->SetOpacity(1.0f);
view_->layer()->ScheduleDraw();
}
@@ -120,8 +122,6 @@ class RowMoveAnimationDelegate
} // namespace
-namespace app_list {
-
#if defined(OS_WIN) && !defined(USE_AURA)
// Interprets drag events sent from Windows via the drag/drop API and forwards
// them to AppsGridView.
@@ -134,16 +134,15 @@ namespace app_list {
// Windows drag that never enters the synchronous drag phase.
class SynchronousDrag : public ui::DragSourceWin {
public:
- SynchronousDrag(app_list::AppsGridView* grid_view,
- app_list::AppListItemView* drag_view,
- const gfx::Point& drag_view_offset)
+ SynchronousDrag(AppsGridView* grid_view,
+ AppListItemView* drag_view,
+ const gfx::Point& drag_view_offset)
: grid_view_(grid_view),
drag_view_(drag_view),
drag_view_offset_(drag_view_offset),
has_shortcut_path_(false),
running_(false),
- canceled_(false) {
- }
+ canceled_(false) {}
void set_shortcut_path(const base::FilePath& shortcut_path) {
has_shortcut_path_ = true;
@@ -187,8 +186,7 @@ class SynchronousDrag : public ui::DragSourceWin {
}
virtual void OnDragSourceMove() OVERRIDE {
- grid_view_->UpdateDrag(app_list::AppsGridView::MOUSE,
- GetCursorInGridViewCoords());
+ grid_view_->UpdateDrag(AppsGridView::MOUSE, GetCursorInGridViewCoords());
}
void SetupExchangeData(ui::OSExchangeData* data) {
@@ -221,8 +219,8 @@ class SynchronousDrag : public ui::DragSourceWin {
return grid_view_pt;
}
- app_list::AppsGridView* grid_view_;
- app_list::AppListItemView* drag_view_;
+ AppsGridView* grid_view_;
+ AppListItemView* drag_view_;
gfx::Point drag_view_offset_;
bool has_shortcut_path_;
base::FilePath shortcut_path_;
@@ -256,6 +254,13 @@ AppsGridView::AppsGridView(AppsGridViewDelegate* delegate,
}
AppsGridView::~AppsGridView() {
+ // Coming here |drag_view_| should already be canceled since otherwise the
+ // drag would disappear after the app list got animated away and closed,
+ // which would look odd.
+ DCHECK(!drag_view_);
+ if (drag_view_)
+ EndDrag(true);
+
if (model_) {
model_->RemoveObserver(this);
model_->apps()->RemoveObserver(this);
@@ -347,9 +352,12 @@ void AppsGridView::OnGotShortcutPath(const base::FilePath& path) {
void AppsGridView::StartSettingUpSynchronousDrag() {
#if defined(OS_WIN) && !defined(USE_AURA)
+ if (!delegate_)
+ return;
+
delegate_->GetShortcutPathForApp(
- drag_view_->model()->app_id(),
- base::Bind(&AppsGridView::OnGotShortcutPath, base::Unretained(this)));
+ drag_view_->model()->app_id(),
+ base::Bind(&AppsGridView::OnGotShortcutPath, base::Unretained(this)));
synchronous_drag_ = new SynchronousDrag(this, drag_view_, drag_view_offset_);
#endif
}
@@ -431,7 +439,8 @@ void AppsGridView::EndDrag(bool cancel) {
// EndDrag was called before if |drag_view_| is NULL.
if (!drag_view_)
return;
-
+ // Coming here a drag and drop was in progress.
+ bool landed_in_drag_and_drop_host = forward_events_to_drag_and_drop_host_;
if (forward_events_to_drag_and_drop_host_) {
forward_events_to_drag_and_drop_host_ = false;
drag_and_drop_host_->EndDrag(cancel);
@@ -445,7 +454,17 @@ void AppsGridView::EndDrag(bool cancel) {
// If we had a drag and drop proxy icon, we delete it and make the real
// item visible again.
drag_and_drop_host_->DestroyDragIconProxy();
- HideView(drag_view_, false);
+ if (landed_in_drag_and_drop_host) {
+ // Move the item directly to the target location, avoiding the "zip back"
+ // animation if the user was pinning it to the shelf.
+ int i = drop_target_.slot;
+ gfx::Rect bounds = view_model_.ideal_bounds(i);
+ drag_view_->SetBoundsRect(bounds);
+ }
+ // Fade in slowly if it landed in the shelf.
+ SetViewHidden(drag_view_,
+ false /* hide */,
+ !landed_in_drag_and_drop_host /* animate */);
}
// The drag can be ended after the synchronous drag is created but before it
@@ -969,7 +988,9 @@ void AppsGridView::StartDragAndDropHostDrag(const gfx::Point& grid_location) {
drag_view_,
delta,
kDragAndDropProxyScale);
- HideView(drag_view_, true);
+ SetViewHidden(drag_view_,
+ true /* hide */,
+ true /* no animation */);
}
void AppsGridView::DispatchDragEventToDragAndDropHost(
@@ -1170,10 +1191,12 @@ void AppsGridView::OnAppListModelStatusChanged() {
SchedulePaint();
}
-void AppsGridView::HideView(views::View* view, bool hide) {
+void AppsGridView::SetViewHidden(views::View* view, bool hide, bool immediate) {
#if defined(USE_AURA)
ui::ScopedLayerAnimationSettings animator(view->layer()->GetAnimator());
- animator.SetPreemptionStrategy(ui::LayerAnimator::IMMEDIATELY_SET_NEW_TARGET);
+ animator.SetPreemptionStrategy(
+ immediate ? ui::LayerAnimator::IMMEDIATELY_SET_NEW_TARGET :
+ ui::LayerAnimator::BLEND_WITH_CURRENT_ANIMATION);
view->layer()->SetOpacity(hide ? 0 : 1);
#endif
}
diff --git a/chromium/ui/app_list/views/apps_grid_view.h b/chromium/ui/app_list/views/apps_grid_view.h
index 9c201641f15..2b7b51d0b88 100644
--- a/chromium/ui/app_list/views/apps_grid_view.h
+++ b/chromium/ui/app_list/views/apps_grid_view.h
@@ -135,7 +135,7 @@ class APP_LIST_EXPORT AppsGridView : public views::View,
}
private:
- friend class app_list::test::AppsGridViewTestApi;
+ friend class test::AppsGridViewTestApi;
// Represents the index to an item view in the grid.
struct Index {
@@ -246,8 +246,10 @@ class APP_LIST_EXPORT AppsGridView : public views::View,
virtual void OnAppListModelStatusChanged() OVERRIDE;
// Hide a given view temporarily without losing (mouse) events and / or
- // changing the size of it.
- void HideView(views::View* view, bool hide);
+ // changing the size of it. If |immediate| is set the change will be
+ // immediately applied - otherwise it will change gradually.
+ // If |hide| is set the view will get hidden, otherwise it gets shown.
+ void SetViewHidden(views::View* view, bool hide, bool immediate);
AppListModel* model_; // Owned by AppListView.
AppsGridViewDelegate* delegate_;
diff --git a/chromium/ui/app_list/apps_grid_view_delegate.h b/chromium/ui/app_list/views/apps_grid_view_delegate.h
index 59dc8f66fb2..83430b0fa40 100644
--- a/chromium/ui/app_list/apps_grid_view_delegate.h
+++ b/chromium/ui/app_list/views/apps_grid_view_delegate.h
@@ -1,9 +1,9 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_APP_LIST_APPS_GRID_VIEW_DELEGATE_H_
-#define UI_APP_LIST_APPS_GRID_VIEW_DELEGATE_H_
+#ifndef UI_APP_LIST_VIEWS_APPS_GRID_VIEW_DELEGATE_H_
+#define UI_APP_LIST_VIEWS_APPS_GRID_VIEW_DELEGATE_H_
#include "base/callback_forward.h"
#include "ui/app_list/app_list_export.h"
@@ -34,4 +34,4 @@ class APP_LIST_EXPORT AppsGridViewDelegate {
} // namespace app_list
-#endif // UI_APP_LIST_APPS_GRID_VIEW_DELEGATE_H_
+#endif // UI_APP_LIST_VIEWS_APPS_GRID_VIEW_DELEGATE_H_
diff --git a/chromium/ui/app_list/views/apps_grid_view_unittest.cc b/chromium/ui/app_list/views/apps_grid_view_unittest.cc
index 87d5f672c12..9e0cc5c0340 100644
--- a/chromium/ui/app_list/views/apps_grid_view_unittest.cc
+++ b/chromium/ui/app_list/views/apps_grid_view_unittest.cc
@@ -10,6 +10,7 @@
#include "base/compiler_specific.h"
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_loop.h"
+#include "base/strings/utf_string_conversions.h"
#include "base/timer/timer.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/app_list/app_list_item_model.h"
@@ -47,10 +48,14 @@ class PageFlipWaiter : public PaginationModelObserver {
DCHECK(!wait_);
wait_ = true;
page_changed_ = false;
- wait_timer_.Stop();
- wait_timer_.Start(FROM_HERE,
- base::TimeDelta::FromMilliseconds(time_out_ms),
- this, &PageFlipWaiter::OnWaitTimeOut);
+
+ if (time_out_ms) {
+ wait_timer_.Stop();
+ wait_timer_.Start(FROM_HERE,
+ base::TimeDelta::FromMilliseconds(time_out_ms),
+ this, &PageFlipWaiter::OnWaitTimeOut);
+ }
+
ui_loop_->Run();
wait_ = false;
return page_changed_;
@@ -260,15 +265,7 @@ TEST_F(AppsGridViewTest, MouseDrag) {
test_api_->LayoutToIdealBounds();
}
-// Test fails sometimes on chrome os.
-// http://crbug.com/242248
-#if defined(OS_CHROMEOS)
-#define MAYBE_MouseDragFlipPage DISABLED_MouseDragFlipPage
-#else
-#define MAYBE_MouseDragFlipPage MouseDragFlipPage
-#endif // defined(OS_CHROMEOS)
-
-TEST_F(AppsGridViewTest, MAYBE_MouseDragFlipPage) {
+TEST_F(AppsGridViewTest, MouseDragFlipPage) {
test_api_->SetPageFlipDelay(10);
pagination_model_->SetTransitionDurations(10, 10);
@@ -288,11 +285,11 @@ TEST_F(AppsGridViewTest, MAYBE_MouseDragFlipPage) {
SimulateDrag(AppsGridView::MOUSE, from, to);
// Page should be flipped after sometime.
- EXPECT_TRUE(page_flip_waiter.Wait(100));
+ EXPECT_TRUE(page_flip_waiter.Wait(0));
EXPECT_EQ(1, pagination_model_->selected_page());
// Stay there and page should be flipped again.
- EXPECT_TRUE(page_flip_waiter.Wait(100));
+ EXPECT_TRUE(page_flip_waiter.Wait(0));
EXPECT_EQ(2, pagination_model_->selected_page());
// Stay there longer and no page flip happen since we are at the last page.
@@ -306,10 +303,10 @@ TEST_F(AppsGridViewTest, MAYBE_MouseDragFlipPage) {
SimulateDrag(AppsGridView::MOUSE, from, to);
- EXPECT_TRUE(page_flip_waiter.Wait(100));
+ EXPECT_TRUE(page_flip_waiter.Wait(0));
EXPECT_EQ(1, pagination_model_->selected_page());
- EXPECT_TRUE(page_flip_waiter.Wait(100));
+ EXPECT_TRUE(page_flip_waiter.Wait(0));
EXPECT_EQ(0, pagination_model_->selected_page());
EXPECT_FALSE(page_flip_waiter.Wait(100));
@@ -428,5 +425,37 @@ TEST_F(AppsGridViewTest, HighlightWithKeyboard) {
first_index_on_page2)));
}
+TEST_F(AppsGridViewTest, ItemLabelShortNameOverride) {
+ // If the app's full name and short name differ, the title label's tooltip
+ // should always be the full name of the app.
+ std::string expected_text("xyz");
+ std::string expected_tooltip("tooltip");
+ model_->AddItem(expected_text, expected_tooltip);
+
+ string16 actual_tooltip;
+ AppListItemView* item_view = GetItemViewAt(0);
+ ASSERT_TRUE(item_view);
+ const views::Label* title_label = item_view->title();
+ EXPECT_TRUE(title_label->GetTooltipText(
+ title_label->bounds().CenterPoint(), &actual_tooltip));
+ EXPECT_EQ(expected_tooltip, UTF16ToUTF8(actual_tooltip));
+ EXPECT_EQ(expected_text, UTF16ToUTF8(title_label->text()));
+}
+
+TEST_F(AppsGridViewTest, ItemLabelNoShortName) {
+ // If the app's full name and short name are the same, use the default tooltip
+ // behavior of the label (only show a tooltip if the title is truncated).
+ std::string title("a");
+ model_->AddItem(title, title);
+
+ string16 actual_tooltip;
+ AppListItemView* item_view = GetItemViewAt(0);
+ ASSERT_TRUE(item_view);
+ const views::Label* title_label = item_view->title();
+ EXPECT_FALSE(title_label->GetTooltipText(
+ title_label->bounds().CenterPoint(), &actual_tooltip));
+ EXPECT_EQ(title, UTF16ToUTF8(title_label->text()));
+}
+
} // namespace test
} // namespace app_list
diff --git a/chromium/ui/app_list/views/contents_view.cc b/chromium/ui/app_list/views/contents_view.cc
index 5211eb1e6d7..3ecc276b75f 100644
--- a/chromium/ui/app_list/views/contents_view.cc
+++ b/chromium/ui/app_list/views/contents_view.cc
@@ -12,7 +12,7 @@
#include "ui/app_list/views/app_list_main_view.h"
#include "ui/app_list/views/apps_grid_view.h"
#include "ui/app_list/views/search_result_list_view.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/animation/bounds_animator.h"
#include "ui/views/view_model.h"
#include "ui/views/view_model_utils.h"
@@ -76,8 +76,13 @@ ContentsView::ContentsView(AppListMainView* app_list_main_view,
ContentsView::~ContentsView() {
}
+void ContentsView::CancelDrag() {
+ if (apps_grid_view_ && apps_grid_view_->has_dragged_view())
+ apps_grid_view_->EndDrag(true);
+}
+
void ContentsView::SetDragAndDropHostOfCurrentAppList(
- app_list::ApplicationDragAndDropHost* drag_and_drop_host) {
+ ApplicationDragAndDropHost* drag_and_drop_host) {
apps_grid_view_->SetDragAndDropHostOfCurrentAppList(drag_and_drop_host);
}
diff --git a/chromium/ui/app_list/views/contents_view.h b/chromium/ui/app_list/views/contents_view.h
index f0b974cf12b..b9447734b50 100644
--- a/chromium/ui/app_list/views/contents_view.h
+++ b/chromium/ui/app_list/views/contents_view.h
@@ -34,10 +34,13 @@ class ContentsView : public views::View {
AppListModel* model);
virtual ~ContentsView();
+ // The app list gets closed and drag and drop operations need to be cancelled.
+ void CancelDrag();
+
// If |drag_and_drop| is not NULL it will be called upon drag and drop
// operations outside the application list.
void SetDragAndDropHostOfCurrentAppList(
- app_list::ApplicationDragAndDropHost* drag_and_drop_host);
+ ApplicationDragAndDropHost* drag_and_drop_host);
void ShowSearchResults(bool show);
diff --git a/chromium/ui/app_list/views/page_switcher.cc b/chromium/ui/app_list/views/page_switcher.cc
index 665b0230713..99e9749d154 100644
--- a/chromium/ui/app_list/views/page_switcher.cc
+++ b/chromium/ui/app_list/views/page_switcher.cc
@@ -9,12 +9,14 @@
#include "third_party/skia/include/core/SkPath.h"
#include "ui/app_list/app_list_constants.h"
#include "ui/app_list/pagination_model.h"
-#include "ui/base/animation/throb_animation.h"
+#include "ui/gfx/animation/throb_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/skia_util.h"
#include "ui/views/controls/button/custom_button.h"
#include "ui/views/layout/box_layout.h"
+namespace app_list {
+
namespace {
const int kPreferredHeight = 57;
@@ -52,11 +54,10 @@ class PageSwitcherButton : public views::CustomButton {
}
virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE {
- if (state() == STATE_HOVERED) {
- PaintButton(canvas, app_list::kPagerHoverColor);
- } else {
- PaintButton(canvas, app_list::kPagerNormalColor);
- }
+ if (state() == STATE_HOVERED)
+ PaintButton(canvas, kPagerHoverColor);
+ else
+ PaintButton(canvas, kPagerNormalColor);
}
private:
@@ -94,7 +95,7 @@ class PageSwitcherButton : public views::CustomButton {
selected_path.addRoundRect(gfx::RectToSkRect(selected_rect),
SkIntToScalar(kButtonCornerRadius),
SkIntToScalar(kButtonCornerRadius));
- paint.setColor(app_list::kPagerSelectedColor);
+ paint.setColor(kPagerSelectedColor);
canvas->DrawPath(selected_path, paint);
}
}
@@ -116,8 +117,6 @@ PageSwitcherButton* GetButtonByIndex(views::View* buttons, int index) {
} // namespace
-namespace app_list {
-
PageSwitcher::PageSwitcher(PaginationModel* model)
: model_(model),
buttons_(new views::View) {
diff --git a/chromium/ui/app_list/views/search_box_view.cc b/chromium/ui/app_list/views/search_box_view.cc
index 1d997e5e7ef..9b96d3eec0a 100644
--- a/chromium/ui/app_list/views/search_box_view.cc
+++ b/chromium/ui/app_list/views/search_box_view.cc
@@ -9,10 +9,10 @@
#include "grit/ui_resources.h"
#include "ui/app_list/app_list_model.h"
#include "ui/app_list/search_box_model.h"
-#include "ui/app_list/search_box_view_delegate.h"
#include "ui/app_list/views/app_list_menu_views.h"
-#include "ui/base/events/event.h"
+#include "ui/app_list/views/search_box_view_delegate.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/events/event.h"
#include "ui/views/controls/button/menu_button.h"
#include "ui/views/controls/image_view.h"
#include "ui/views/controls/textfield/textfield.h"
@@ -40,7 +40,7 @@ SearchBoxView::SearchBoxView(SearchBoxViewDelegate* delegate,
AppListModel* model)
: delegate_(delegate),
view_delegate_(view_delegate),
- model_(model->search_box()),
+ model_(model),
icon_view_(new views::ImageView),
search_box_(new views::Textfield),
contents_view_(NULL) {
@@ -65,13 +65,13 @@ SearchBoxView::SearchBoxView(SearchBoxViewDelegate* delegate,
search_box_->SetController(this);
AddChildView(search_box_);
- model_->AddObserver(this);
+ model_->search_box()->AddObserver(this);
IconChanged();
HintTextChanged();
}
SearchBoxView::~SearchBoxView() {
- model_->RemoveObserver(this);
+ model_->search_box()->RemoveObserver(this);
}
bool SearchBoxView::HasSearch() const {
@@ -132,10 +132,10 @@ bool SearchBoxView::OnMouseWheel(const ui::MouseWheelEvent& event) {
void SearchBoxView::UpdateModel() {
// Temporarily remove from observer to ignore notifications caused by us.
- model_->RemoveObserver(this);
- model_->SetText(search_box_->text());
- model_->SetSelectionModel(search_box_->GetSelectionModel());
- model_->AddObserver(this);
+ model_->search_box()->RemoveObserver(this);
+ model_->search_box()->SetText(search_box_->text());
+ model_->search_box()->SetSelectionModel(search_box_->GetSelectionModel());
+ model_->search_box()->AddObserver(this);
}
void SearchBoxView::NotifyQueryChanged() {
@@ -160,7 +160,7 @@ bool SearchBoxView::HandleKeyEvent(views::Textfield* sender,
void SearchBoxView::OnMenuButtonClicked(View* source, const gfx::Point& point) {
if (!menu_)
- menu_.reset(new AppListMenuViews(view_delegate_));
+ menu_.reset(new AppListMenuViews(view_delegate_, model_));
const gfx::Point menu_location =
menu_button_->GetBoundsInScreen().bottom_right() +
@@ -169,19 +169,20 @@ void SearchBoxView::OnMenuButtonClicked(View* source, const gfx::Point& point) {
}
void SearchBoxView::IconChanged() {
- icon_view_->SetImage(model_->icon());
+ icon_view_->SetImage(model_->search_box()->icon());
}
void SearchBoxView::HintTextChanged() {
- search_box_->set_placeholder_text(model_->hint_text());
+ search_box_->set_placeholder_text(model_->search_box()->hint_text());
}
void SearchBoxView::SelectionModelChanged() {
- search_box_->SelectSelectionModel(model_->selection_model());
+ search_box_->SelectSelectionModel(model_->search_box()->selection_model());
}
void SearchBoxView::TextChanged() {
- search_box_->SetText(model_->text());
+ search_box_->SetText(model_->search_box()->text());
+ NotifyQueryChanged();
}
} // namespace app_list
diff --git a/chromium/ui/app_list/views/search_box_view.h b/chromium/ui/app_list/views/search_box_view.h
index 439a4cf291b..c06990262a5 100644
--- a/chromium/ui/app_list/views/search_box_view.h
+++ b/chromium/ui/app_list/views/search_box_view.h
@@ -21,8 +21,8 @@ class Textfield;
namespace app_list {
class AppListMenuViews;
-class AppListViewDelegate;
class AppListModel;
+class AppListViewDelegate;
class SearchBoxModel;
class SearchBoxViewDelegate;
@@ -80,7 +80,7 @@ class SearchBoxView : public views::View,
SearchBoxViewDelegate* delegate_; // Not owned.
AppListViewDelegate* view_delegate_; // Not owned.
- SearchBoxModel* model_; // Owned by AppListModel.
+ AppListModel* model_; // Owned by AppListView.
scoped_ptr<AppListMenuViews> menu_;
diff --git a/chromium/ui/app_list/search_box_view_delegate.h b/chromium/ui/app_list/views/search_box_view_delegate.h
index df5d2b41e09..cdbf23878bb 100644
--- a/chromium/ui/app_list/search_box_view_delegate.h
+++ b/chromium/ui/app_list/views/search_box_view_delegate.h
@@ -1,9 +1,9 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_APP_LIST_SEARCH_BOX_VIEW_DELEGATE_H_
-#define UI_APP_LIST_SEARCH_BOX_VIEW_DELEGATE_H_
+#ifndef UI_APP_LIST_VIEWS_SEARCH_BOX_VIEW_DELEGATE_H_
+#define UI_APP_LIST_VIEWS_SEARCH_BOX_VIEW_DELEGATE_H_
#include "ui/app_list/app_list_export.h"
@@ -22,4 +22,4 @@ class APP_LIST_EXPORT SearchBoxViewDelegate {
} // namespace app_list
-#endif // UI_APP_LIST_SEARCH_BOX_VIEW_DELEGATE_H_
+#endif // UI_APP_LIST_VIEWS_SEARCH_BOX_VIEW_DELEGATE_H_
diff --git a/chromium/ui/app_list/views/search_result_list_view.cc b/chromium/ui/app_list/views/search_result_list_view.cc
index 5eaad3c688f..3387cecad10 100644
--- a/chromium/ui/app_list/views/search_result_list_view.cc
+++ b/chromium/ui/app_list/views/search_result_list_view.cc
@@ -8,9 +8,9 @@
#include "base/bind.h"
#include "base/message_loop/message_loop.h"
-#include "ui/app_list/search_result_list_view_delegate.h"
+#include "ui/app_list/views/search_result_list_view_delegate.h"
#include "ui/app_list/views/search_result_view.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/layout/box_layout.h"
namespace {
diff --git a/chromium/ui/app_list/search_result_list_view_delegate.h b/chromium/ui/app_list/views/search_result_list_view_delegate.h
index e45ac4b3bc7..405094b31a5 100644
--- a/chromium/ui/app_list/search_result_list_view_delegate.h
+++ b/chromium/ui/app_list/views/search_result_list_view_delegate.h
@@ -1,9 +1,9 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_APP_LIST_SEARCH_RESULT_LIST_VIEW_DELEGATE_H_
-#define UI_APP_LIST_SEARCH_RESULT_LIST_VIEW_DELEGATE_H_
+#ifndef UI_APP_LIST_VIEWS_SEARCH_RESULT_LIST_VIEW_DELEGATE_H_
+#define UI_APP_LIST_VIEWS_SEARCH_RESULT_LIST_VIEW_DELEGATE_H_
#include "ui/app_list/app_list_export.h"
@@ -37,4 +37,4 @@ class APP_LIST_EXPORT SearchResultListViewDelegate {
} // namespace app_list
-#endif // UI_APP_LIST_SEARCH_RESULT_LIST_VIEW_DELEGATE_H_
+#endif // UI_APP_LIST_VIEWS_SEARCH_RESULT_LIST_VIEW_DELEGATE_H_
diff --git a/chromium/ui/app_list/views/search_result_view.cc b/chromium/ui/app_list/views/search_result_view.cc
index 55b9e0b653d..9e7fe51f648 100644
--- a/chromium/ui/app_list/views/search_result_view.cc
+++ b/chromium/ui/app_list/views/search_result_view.cc
@@ -20,6 +20,8 @@
#include "ui/views/controls/menu/menu_item_view.h"
#include "ui/views/controls/menu/menu_runner.h"
+namespace app_list {
+
namespace {
const int kPreferredWidth = 300;
@@ -36,24 +38,24 @@ const int kActionButtonRightMargin = 8;
// Creates a RenderText of given |text| and |styles|. Caller takes ownership
// of returned RenderText.
gfx::RenderText* CreateRenderText(const base::string16& text,
- const app_list::SearchResult::Tags& tags) {
+ const SearchResult::Tags& tags) {
gfx::RenderText* render_text = gfx::RenderText::CreateInstance();
render_text->SetText(text);
- render_text->SetColor(app_list::kResultDefaultTextColor);
+ render_text->SetColor(kResultDefaultTextColor);
- for (app_list::SearchResult::Tags::const_iterator it = tags.begin();
+ for (SearchResult::Tags::const_iterator it = tags.begin();
it != tags.end();
++it) {
// NONE means default style so do nothing.
- if (it->styles == app_list::SearchResult::Tag::NONE)
+ if (it->styles == SearchResult::Tag::NONE)
continue;
- if (it->styles & app_list::SearchResult::Tag::MATCH)
+ if (it->styles & SearchResult::Tag::MATCH)
render_text->ApplyStyle(gfx::BOLD, true, it->range);
- if (it->styles & app_list::SearchResult::Tag::DIM)
- render_text->ApplyColor(app_list::kResultDimmedTextColor, it->range);
- else if (it->styles & app_list::SearchResult::Tag::URL)
- render_text->ApplyColor(app_list::kResultURLTextColor, it->range);
+ if (it->styles & SearchResult::Tag::DIM)
+ render_text->ApplyColor(kResultDimmedTextColor, it->range);
+ else if (it->styles & SearchResult::Tag::URL)
+ render_text->ApplyColor(kResultURLTextColor, it->range);
}
return render_text;
@@ -61,8 +63,6 @@ gfx::RenderText* CreateRenderText(const base::string16& text,
} // namespace
-namespace app_list {
-
// static
const char SearchResultView::kViewClassName[] = "ui/app_list/SearchResultView";
diff --git a/chromium/ui/aura/aura.gyp b/chromium/ui/aura/aura.gyp
index a4fe8612de6..c2983e921a6 100644
--- a/chromium/ui/aura/aura.gyp
+++ b/chromium/ui/aura/aura.gyp
@@ -83,19 +83,13 @@
'remote_root_window_host_win.h',
'root_window_host.h',
'root_window_host_delegate.h',
- 'root_window_host_mac.h',
- 'root_window_host_mac.mm',
'root_window_host_ozone.cc',
'root_window_host_ozone.h',
'root_window_host_win.cc',
'root_window_host_win.h',
'root_window_host_x11.cc',
'root_window_host_x11.h',
- 'root_window_mac.h',
- 'root_window_mac.mm',
'root_window_transformer.h',
- 'root_window_view_mac.h',
- 'root_window_view_mac.mm',
'root_window.cc',
'root_window.h',
'window.cc',
@@ -106,12 +100,6 @@
'window_tracker.h',
],
'conditions': [
- ['OS=="mac"', {
- 'sources/': [
- ['exclude', 'client/dispatcher_client.cc'],
- ['exclude', 'client/dispatcher_client.h'],
- ],
- }],
['use_x11==1', {
'link_settings': {
'libraries': [
@@ -181,6 +169,7 @@
'target_name': 'aura_test_support_pak',
'type': 'none',
'dependencies': [
+ '<(DEPTH)/ui/base/strings/ui_strings.gyp:ui_strings',
'<(DEPTH)/ui/ui.gyp:ui_resources',
],
'variables': {
@@ -191,6 +180,7 @@
'action_name': 'repack_aura_test_support_pack',
'variables': {
'pak_inputs': [
+ '<(SHARED_INTERMEDIATE_DIR)/ui/app_locale_settings/app_locale_settings_en-US.pak',
'<(SHARED_INTERMEDIATE_DIR)/ui/ui_resources/ui_resources_100_percent.pak',
],
},
diff --git a/chromium/ui/aura/bench/DEPS b/chromium/ui/aura/bench/DEPS
index 69deb976808..1fda55436bc 100644
--- a/chromium/ui/aura/bench/DEPS
+++ b/chromium/ui/aura/bench/DEPS
@@ -1,4 +1,5 @@
include_rules = [
+ "+cc",
"+third_party/khronos",
"+third_party/WebKit/public/platform",
]
diff --git a/chromium/ui/aura/bench/bench_main.cc b/chromium/ui/aura/bench/bench_main.cc
index aee7e79c83a..f344854ea1a 100644
--- a/chromium/ui/aura/bench/bench_main.cc
+++ b/chromium/ui/aura/bench/bench_main.cc
@@ -10,6 +10,7 @@
#include "base/message_loop/message_loop.h"
#include "base/strings/string_split.h"
#include "base/time/time.h"
+#include "cc/output/context_provider.h"
#include "third_party/khronos/GLES2/gl2.h"
#include "third_party/skia/include/core/SkXfermode.h"
#include "ui/aura/client/default_capture_client.h"
@@ -35,7 +36,7 @@
#include "third_party/khronos/GLES2/gl2ext.h"
#if defined(USE_X11)
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#endif
using base::TimeTicks;
@@ -181,7 +182,7 @@ class WebGLBench : public BenchCompositorObserver {
parent_(parent),
webgl_(ui::LAYER_TEXTURED),
compositor_(compositor),
- context_(),
+ context_provider_(),
texture_(),
fbo_(0),
do_draw_(true) {
@@ -207,24 +208,26 @@ class WebGLBench : public BenchCompositorObserver {
webgl_.SetBounds(bounds);
parent_->Add(&webgl_);
- context_ = ui::ContextFactory::GetInstance()->CreateOffscreenContext();
- context_->makeContextCurrent();
- texture_ = new WebGLTexture(context_.get(), bounds.size());
- fbo_ = context_->createFramebuffer();
+ context_provider_ = ui::ContextFactory::GetInstance()
+ ->OffscreenContextProviderForMainThread();
+ WebKit::WebGraphicsContext3D* context = context_provider_->Context3d();
+ context->makeContextCurrent();
+ texture_ = new WebGLTexture(context, bounds.size());
+ fbo_ = context->createFramebuffer();
compositor->AddObserver(this);
webgl_.SetExternalTexture(texture_.get());
- context_->bindFramebuffer(GL_FRAMEBUFFER, fbo_);
- context_->framebufferTexture2D(
+ context->bindFramebuffer(GL_FRAMEBUFFER, fbo_);
+ context->framebufferTexture2D(
GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
GL_TEXTURE_2D, texture_->PrepareTexture(), 0);
- context_->clearColor(0.f, 1.f, 0.f, 1.f);
- context_->clear(GL_COLOR_BUFFER_BIT);
- context_->flush();
+ context->clearColor(0.f, 1.f, 0.f, 1.f);
+ context->clear(GL_COLOR_BUFFER_BIT);
+ context->flush();
}
virtual ~WebGLBench() {
- context_->makeContextCurrent();
- context_->deleteFramebuffer(fbo_);
+ context_provider_->Context3d()->makeContextCurrent();
+ context_provider_->Context3d()->deleteFramebuffer(fbo_);
webgl_.SetExternalTexture(NULL);
texture_ = NULL;
compositor_->RemoveObserver(this);
@@ -232,10 +235,11 @@ class WebGLBench : public BenchCompositorObserver {
virtual void Draw() OVERRIDE {
if (do_draw_) {
- context_->makeContextCurrent();
- context_->clearColor((frames() % kFrames)*1.0/kFrames, 1.f, 0.f, 1.f);
- context_->clear(GL_COLOR_BUFFER_BIT);
- context_->flush();
+ WebKit::WebGraphicsContext3D* context = context_provider_->Context3d();
+ context->makeContextCurrent();
+ context->clearColor((frames() % kFrames)*1.0/kFrames, 1.f, 0.f, 1.f);
+ context->clear(GL_COLOR_BUFFER_BIT);
+ context->flush();
}
webgl_.SetExternalTexture(texture_.get());
webgl_.SchedulePaint(gfx::Rect(webgl_.bounds().size()));
@@ -246,7 +250,7 @@ class WebGLBench : public BenchCompositorObserver {
Layer* parent_;
Layer webgl_;
Compositor* compositor_;
- scoped_ptr<WebGraphicsContext3D> context_;
+ scoped_refptr<cc::ContextProvider> context_provider_;
scoped_refptr<WebGLTexture> texture_;
// The FBO that is used to render to the texture.
@@ -296,8 +300,12 @@ int main(int argc, char** argv) {
base::AtExitManager exit_manager;
+ // The ContextFactory must exist before any Compositors are created.
+ bool allow_test_contexts = false;
+ ui::Compositor::InitializeContextFactoryForTests(allow_test_contexts);
+
ui::RegisterPathProvider();
- icu_util::Initialize();
+ base::i18n::InitializeICU();
ResourceBundle::InitSharedInstanceWithLocale("en-US", NULL);
base::MessageLoop message_loop(base::MessageLoop::TYPE_UI);
diff --git a/chromium/ui/aura/client/cursor_client.h b/chromium/ui/aura/client/cursor_client.h
index acdf255b850..e8740ac1704 100644
--- a/chromium/ui/aura/client/cursor_client.h
+++ b/chromium/ui/aura/client/cursor_client.h
@@ -7,6 +7,7 @@
#include "base/strings/string16.h"
#include "ui/aura/aura_export.h"
+#include "ui/base/cursor/cursor.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
@@ -34,6 +35,9 @@ class AURA_EXPORT CursorClient {
// Sets the scale of the mouse cursor icon.
virtual void SetScale(float scale) = 0;
+ // Sets the type of the mouse cursor icon.
+ virtual void SetCursorSet(ui::CursorSetType cursor_set) = 0;
+
// Gets whether the cursor is visible.
virtual bool IsCursorVisible() const = 0;
@@ -60,6 +64,9 @@ class AURA_EXPORT CursorClient {
// EnableMouseEvents/DisableMouseEvents.
virtual void UnlockCursor() = 0;
+ // Returns true if the cursor is locked.
+ virtual bool IsCursorLocked() const = 0;
+
// Used to add or remove a CursorClientObserver.
virtual void AddObserver(CursorClientObserver* observer) = 0;
virtual void RemoveObserver(CursorClientObserver* observer) = 0;
diff --git a/chromium/ui/aura/demo/demo_main.cc b/chromium/ui/aura/demo/demo_main.cc
index 06938d87419..dbf1c80b7a6 100644
--- a/chromium/ui/aura/demo/demo_main.cc
+++ b/chromium/ui/aura/demo/demo_main.cc
@@ -16,15 +16,16 @@
#include "ui/aura/test/test_screen.h"
#include "ui/aura/window.h"
#include "ui/aura/window_delegate.h"
-#include "ui/base/events/event.h"
#include "ui/base/hit_test.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/base/ui_base_paths.h"
+#include "ui/compositor/compositor.h"
+#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/rect.h"
#if defined(USE_X11)
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#endif
namespace {
@@ -67,9 +68,8 @@ class DemoWindowDelegate : public aura::WindowDelegate {
virtual void OnWindowTargetVisibilityChanged(bool visible) OVERRIDE {}
virtual bool HasHitTestMask() const OVERRIDE { return false; }
virtual void GetHitTestMask(gfx::Path* mask) const OVERRIDE {}
- virtual scoped_refptr<ui::Texture> CopyTexture() OVERRIDE {
- return scoped_refptr<ui::Texture>();
- }
+ virtual void DidRecreateLayer(ui::Layer* old_layer,
+ ui::Layer* new_layer) OVERRIDE {}
private:
SkColor color_;
@@ -110,6 +110,11 @@ class DemoStackingClient : public aura::client::StackingClient {
int DemoMain() {
// Create the message-loop here before creating the root window.
base::MessageLoop message_loop(base::MessageLoop::TYPE_UI);
+
+ // The ContextFactory must exist before any Compositors are created.
+ bool allow_test_contexts = false;
+ ui::Compositor::InitializeContextFactoryForTests(allow_test_contexts);
+
aura::Env::GetInstance();
scoped_ptr<aura::TestScreen> test_screen(aura::TestScreen::Create());
gfx::Screen::SetScreenInstance(gfx::SCREEN_TYPE_NATIVE, test_screen.get());
@@ -160,7 +165,7 @@ int main(int argc, char** argv) {
base::AtExitManager exit_manager;
ui::RegisterPathProvider();
- icu_util::Initialize();
+ base::i18n::InitializeICU();
ResourceBundle::InitSharedInstanceWithLocale("en-US", NULL);
return DemoMain();
diff --git a/chromium/ui/aura/device_list_updater_aurax11.cc b/chromium/ui/aura/device_list_updater_aurax11.cc
index 0671dfecbfd..8240cb495c3 100644
--- a/chromium/ui/aura/device_list_updater_aurax11.cc
+++ b/chromium/ui/aura/device_list_updater_aurax11.cc
@@ -6,7 +6,7 @@
#include <X11/extensions/XInput2.h>
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event_utils.h"
namespace aura {
diff --git a/chromium/ui/aura/env.cc b/chromium/ui/aura/env.cc
index 6b2b3e023a3..a4cf8151e24 100644
--- a/chromium/ui/aura/env.cc
+++ b/chromium/ui/aura/env.cc
@@ -12,7 +12,7 @@
#include "ui/compositor/compositor_switches.h"
#if defined(USE_X11)
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#endif
namespace aura {
@@ -30,7 +30,7 @@ Env::Env()
Env::~Env() {
#if defined(USE_X11)
- base::MessagePumpAuraX11::Current()->RemoveObserver(
+ base::MessagePumpX11::Current()->RemoveObserver(
&device_list_updater_aurax11_);
#endif
@@ -62,15 +62,13 @@ void Env::RemoveObserver(EnvObserver* observer) {
observers_.RemoveObserver(observer);
}
-#if !defined(OS_MACOSX)
base::MessageLoop::Dispatcher* Env::GetDispatcher() {
#if defined(USE_X11)
- return base::MessagePumpAuraX11::Current();
+ return base::MessagePumpX11::Current();
#else
return dispatcher_.get();
#endif
}
-#endif
void Env::RootWindowActivated(RootWindow* root_window) {
FOR_EACH_OBSERVER(EnvObserver, observers_,
@@ -87,7 +85,7 @@ void Env::Init() {
#if defined(USE_X11)
// We can't do this with a root window listener because XI_HierarchyChanged
// messages don't have a target window.
- base::MessagePumpAuraX11::Current()->AddObserver(
+ base::MessagePumpX11::Current()->AddObserver(
&device_list_updater_aurax11_);
#endif
ui::Compositor::Initialize();
diff --git a/chromium/ui/aura/env.h b/chromium/ui/aura/env.h
index ad31cd57ac5..c52b892d573 100644
--- a/chromium/ui/aura/env.h
+++ b/chromium/ui/aura/env.h
@@ -9,8 +9,8 @@
#include "base/message_loop/message_loop.h"
#include "base/observer_list.h"
#include "ui/aura/aura_export.h"
-#include "ui/base/events/event_handler.h"
-#include "ui/base/events/event_target.h"
+#include "ui/events/event_handler.h"
+#include "ui/events/event_target.h"
#include "ui/gfx/point.h"
#if defined(USE_X11)
@@ -60,9 +60,7 @@ class AURA_EXPORT Env : public ui::EventTarget {
// Returns the native event dispatcher. The result should only be passed to
// base::RunLoop(dispatcher), or used to dispatch an event by
// |Dispatch(const NativeEvent&)| on it. It must never be stored.
-#if !defined(OS_MACOSX)
base::MessageLoop::Dispatcher* GetDispatcher();
-#endif
// Invoked by RootWindow when its host is activated.
void RootWindowActivated(RootWindow* root_window);
diff --git a/chromium/ui/aura/gestures/gesture_recognizer_unittest.cc b/chromium/ui/aura/gestures/gesture_recognizer_unittest.cc
index d377ef458a3..f17a32045ec 100644
--- a/chromium/ui/aura/gestures/gesture_recognizer_unittest.cc
+++ b/chromium/ui/aura/gestures/gesture_recognizer_unittest.cc
@@ -14,14 +14,14 @@
#include "ui/aura/test/event_generator.h"
#include "ui/aura/test/test_window_delegate.h"
#include "ui/aura/test/test_windows.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/gestures/gesture_configuration.h"
#include "ui/base/gestures/gesture_recognizer_impl.h"
#include "ui/base/gestures/gesture_sequence.h"
#include "ui/base/gestures/gesture_types.h"
#include "ui/base/hit_test.h"
#include "ui/base/ui_base_switches.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
@@ -2908,9 +2908,7 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMoveConsumed) {
tes.SendScrollEvent(root_window(), 130, 230, kTouchId, delegate.get());
EXPECT_FALSE(delegate->tap());
EXPECT_FALSE(delegate->tap_down());
- // TODO(rbyers): Really we should get the TapCancel here instead of below,
- // but this is a symptom of a larger issue: crbug.com/146397.
- EXPECT_FALSE(delegate->tap_cancel());
+ EXPECT_TRUE(delegate->tap_cancel());
EXPECT_FALSE(delegate->begin());
EXPECT_FALSE(delegate->scroll_begin());
EXPECT_FALSE(delegate->scroll_update());
@@ -2924,7 +2922,7 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMoveConsumed) {
root_window()->AsRootWindowHostDelegate()->OnHostTouchEvent(&release);
EXPECT_FALSE(delegate->tap());
EXPECT_FALSE(delegate->tap_down());
- EXPECT_TRUE(delegate->tap_cancel());
+ EXPECT_FALSE(delegate->tap_cancel());
EXPECT_FALSE(delegate->begin());
EXPECT_TRUE(delegate->end());
EXPECT_FALSE(delegate->scroll_begin());
@@ -3059,9 +3057,7 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMovePartialConsumed) {
tes.SendScrollEvent(root_window(), 130, 230, kTouchId, delegate.get());
EXPECT_FALSE(delegate->tap());
EXPECT_FALSE(delegate->tap_down());
- // TODO(rbyers): Really we should get the TapCancel here instead of below,
- // but this is a symptom of a larger issue: crbug.com/146397.
- EXPECT_FALSE(delegate->tap_cancel());
+ EXPECT_TRUE(delegate->tap_cancel());
EXPECT_FALSE(delegate->begin());
EXPECT_FALSE(delegate->scroll_begin());
EXPECT_FALSE(delegate->scroll_update());
@@ -3072,21 +3068,18 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMovePartialConsumed) {
tes.SendScrollEvent(root_window(), 159, 259, kTouchId, delegate.get());
EXPECT_FALSE(delegate->tap());
EXPECT_FALSE(delegate->tap_down());
- EXPECT_TRUE(delegate->tap_cancel());
+ EXPECT_FALSE(delegate->tap_cancel());
EXPECT_FALSE(delegate->begin());
- EXPECT_TRUE(delegate->scroll_begin());
- EXPECT_TRUE(delegate->scroll_update());
+ EXPECT_FALSE(delegate->scroll_begin());
+ EXPECT_FALSE(delegate->scroll_update());
EXPECT_FALSE(delegate->scroll_end());
- // Consuming move events doesn't effect what the ultimate scroll position
- // will be if scrolling is later allowed to happen.
- EXPECT_EQ(58, delegate->scroll_x());
- EXPECT_EQ(58, delegate->scroll_y());
- EXPECT_EQ(gfx::Point(1, 1).ToString(),
+ // No scroll has occurred, because an early touch move was consumed.
+ EXPECT_EQ(0, delegate->scroll_x());
+ EXPECT_EQ(0, delegate->scroll_y());
+ EXPECT_EQ(gfx::Point(0, 0).ToString(),
delegate->scroll_begin_position().ToString());
- // Start consuming touch-move events again. However, since gesture-scroll has
- // already started, the touch-move events should still result in scroll-update
- // gestures.
+ // Start consuming touch-move events again.
delegate->set_consume_touch_move(true);
// Move some more to generate a few more scroll updates.
@@ -3096,10 +3089,10 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMovePartialConsumed) {
EXPECT_FALSE(delegate->tap_cancel());
EXPECT_FALSE(delegate->begin());
EXPECT_FALSE(delegate->scroll_begin());
- EXPECT_TRUE(delegate->scroll_update());
+ EXPECT_FALSE(delegate->scroll_update());
EXPECT_FALSE(delegate->scroll_end());
- EXPECT_EQ(-49, delegate->scroll_x());
- EXPECT_EQ(-48, delegate->scroll_y());
+ EXPECT_EQ(0, delegate->scroll_x());
+ EXPECT_EQ(0, delegate->scroll_y());
tes.SendScrollEvent(root_window(), 140, 215, kTouchId, delegate.get());
EXPECT_FALSE(delegate->tap());
@@ -3107,12 +3100,12 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMovePartialConsumed) {
EXPECT_FALSE(delegate->tap_cancel());
EXPECT_FALSE(delegate->begin());
EXPECT_FALSE(delegate->scroll_begin());
- EXPECT_TRUE(delegate->scroll_update());
+ EXPECT_FALSE(delegate->scroll_update());
EXPECT_FALSE(delegate->scroll_end());
- EXPECT_EQ(30, delegate->scroll_x());
- EXPECT_EQ(4, delegate->scroll_y());
+ EXPECT_EQ(0, delegate->scroll_x());
+ EXPECT_EQ(0, delegate->scroll_y());
- // Release the touch. This should end the scroll.
+ // Release the touch.
delegate->Reset();
ui::TouchEvent release(ui::ET_TOUCH_RELEASED, gfx::Point(101, 201),
kTouchId, tes.LeapForward(50));
@@ -3125,8 +3118,7 @@ TEST_F(GestureRecognizerTest, GestureEventScrollTouchMovePartialConsumed) {
EXPECT_FALSE(delegate->scroll_begin());
EXPECT_FALSE(delegate->scroll_update());
EXPECT_FALSE(delegate->scroll_end());
- // Moves arrive without delays and hence have high velocity.
- EXPECT_TRUE(delegate->fling());
+ EXPECT_FALSE(delegate->fling());
}
// Check that appropriate touch events generate double tap gesture events.
@@ -3418,5 +3410,38 @@ TEST_F(GestureRecognizerTest, NoDriftInScroll) {
delegate->Reset();
}
+// Ensure that move events which are preventDefaulted will cause a tap
+// cancel gesture event to be fired if the move would normally cause a
+// scroll. See bug http://crbug.com/146397.
+TEST_F(GestureRecognizerTest, GestureEventConsumedTouchMoveCanFireTapCancel) {
+ scoped_ptr<ConsumesTouchMovesDelegate> delegate(
+ new ConsumesTouchMovesDelegate());
+ const int kTouchId = 5;
+ gfx::Rect bounds(100, 200, 123, 45);
+ scoped_ptr<aura::Window> window(CreateTestWindowWithDelegate(
+ delegate.get(), -1234, bounds, root_window()));
+ TimedEvents tes;
+
+ delegate->Reset();
+ ui::TouchEvent press(ui::ET_TOUCH_PRESSED, gfx::Point(101, 201),
+ kTouchId, tes.Now());
+
+ delegate->set_consume_touch_move(false);
+ root_window()->AsRootWindowHostDelegate()->OnHostTouchEvent(&press);
+ delegate->set_consume_touch_move(true);
+ delegate->Reset();
+ // Move the touch-point enough so that it would normally be considered a
+ // scroll. But since the touch-moves will be consumed, the scroll should not
+ // start.
+ tes.SendScrollEvent(root_window(), 130, 230, kTouchId, delegate.get());
+ EXPECT_FALSE(delegate->tap());
+ EXPECT_FALSE(delegate->tap_down());
+ EXPECT_TRUE(delegate->tap_cancel());
+ EXPECT_FALSE(delegate->begin());
+ EXPECT_FALSE(delegate->scroll_begin());
+ EXPECT_FALSE(delegate->scroll_update());
+ EXPECT_FALSE(delegate->scroll_end());
+}
+
} // namespace test
} // namespace aura
diff --git a/chromium/ui/aura/remote_root_window_host_win.cc b/chromium/ui/aura/remote_root_window_host_win.cc
index f5dc26bff55..9d5cb8cf93a 100644
--- a/chromium/ui/aura/remote_root_window_host_win.cc
+++ b/chromium/ui/aura/remote_root_window_host_win.cc
@@ -15,8 +15,8 @@
#include "ui/aura/client/cursor_client.h"
#include "ui/aura/root_window.h"
#include "ui/base/cursor/cursor_loader_win.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
#include "ui/base/view_prop.h"
#include "ui/gfx/insets.h"
#include "ui/metro_viewer/metro_viewer_messages.h"
@@ -108,33 +108,39 @@ void HandleSelectFolder(const base::string16& title,
RemoteRootWindowHostWin* g_instance = NULL;
RemoteRootWindowHostWin* RemoteRootWindowHostWin::Instance() {
- return g_instance;
+ if (g_instance)
+ return g_instance;
+ return Create(gfx::Rect());
}
RemoteRootWindowHostWin* RemoteRootWindowHostWin::Create(
const gfx::Rect& bounds) {
- g_instance = new RemoteRootWindowHostWin(bounds);
+ g_instance = g_instance ? g_instance : new RemoteRootWindowHostWin(bounds);
return g_instance;
}
RemoteRootWindowHostWin::RemoteRootWindowHostWin(const gfx::Rect& bounds)
- : delegate_(NULL),
+ : remote_window_(NULL),
+ delegate_(NULL),
host_(NULL),
ignore_mouse_moves_until_set_cursor_ack_(false) {
prop_.reset(new ui::ViewProp(NULL, kRootWindowHostWinKey, this));
}
RemoteRootWindowHostWin::~RemoteRootWindowHostWin() {
+ g_instance = NULL;
}
-void RemoteRootWindowHostWin::Connected(IPC::Sender* host) {
+void RemoteRootWindowHostWin::Connected(IPC::Sender* host, HWND remote_window) {
CHECK(host_ == NULL);
host_ = host;
+ remote_window_ = remote_window;
}
void RemoteRootWindowHostWin::Disconnected() {
CHECK(host_ != NULL);
host_ = NULL;
+ remote_window_ = NULL;
}
bool RemoteRootWindowHostWin::OnMessageReceived(const IPC::Message& message) {
@@ -161,8 +167,6 @@ bool RemoteRootWindowHostWin::OnMessageReceived(const IPC::Message& message) {
OnMultiFileOpenDone)
IPC_MESSAGE_HANDLER(MetroViewerHostMsg_SelectFolderDone,
OnSelectFolderDone)
- IPC_MESSAGE_HANDLER(MetroViewerHostMsg_WindowActivated,
- OnWindowActivated)
IPC_MESSAGE_HANDLER(MetroViewerHostMsg_SetCursorPosAck,
OnSetCursorPosAck)
IPC_MESSAGE_HANDLER(MetroViewerHostMsg_WindowSizeChanged,
@@ -172,6 +176,14 @@ bool RemoteRootWindowHostWin::OnMessageReceived(const IPC::Message& message) {
return handled;
}
+void RemoteRootWindowHostWin::HandleOpenURLOnDesktop(
+ const base::FilePath& shortcut,
+ const base::string16& url) {
+ if (!host_)
+ return;
+ host_->Send(new MetroViewerHostMsg_OpenURLOnDesktop(shortcut, url));
+}
+
void RemoteRootWindowHostWin::HandleOpenFile(
const base::string16& title,
const base::FilePath& default_path,
@@ -271,10 +283,9 @@ RootWindow* RemoteRootWindowHostWin::GetRootWindow() {
}
gfx::AcceleratedWidget RemoteRootWindowHostWin::GetAcceleratedWidget() {
- // TODO(cpu): This is bad. Chrome's compositor needs a valid window
- // initially and then later on we swap it. Since the compositor never
- // uses this initial window we tell ourselves this hack is ok to get
- // thing off the ground.
+ if (remote_window_)
+ return remote_window_;
+ // Getting here should only happen for ash_unittests.exe and related code.
return ::GetDesktopWindow();
}
@@ -339,13 +350,6 @@ bool RemoteRootWindowHostWin::ConfineCursorToRootWindow() {
return true;
}
-bool RemoteRootWindowHostWin::CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- NOTIMPLEMENTED();
- return false;
-}
-
void RemoteRootWindowHostWin::UnConfineCursor() {
}
@@ -538,10 +542,6 @@ void RemoteRootWindowHostWin::OnSelectFolderDone(
failure_callback_.Reset();
}
-void RemoteRootWindowHostWin::OnWindowActivated(bool active) {
- active ? GetRootWindow()->Focus() : GetRootWindow()->Blur();
-}
-
void RemoteRootWindowHostWin::OnSetCursorPosAck() {
DCHECK(ignore_mouse_moves_until_set_cursor_ack_);
ignore_mouse_moves_until_set_cursor_ack_ = false;
diff --git a/chromium/ui/aura/remote_root_window_host_win.h b/chromium/ui/aura/remote_root_window_host_win.h
index 132f0f236f0..e92a5add625 100644
--- a/chromium/ui/aura/remote_root_window_host_win.h
+++ b/chromium/ui/aura/remote_root_window_host_win.h
@@ -11,8 +11,8 @@
#include "base/compiler_specific.h"
#include "base/strings/string16.h"
#include "ui/aura/root_window_host.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/native_widget_types.h"
namespace base {
@@ -86,18 +86,24 @@ AURA_EXPORT void HandleSelectFolder(const base::string16& title,
// frontend process, which forwards input events to this class.
class AURA_EXPORT RemoteRootWindowHostWin : public RootWindowHost {
public:
+ // Returns the only RemoteRootWindowHostWin, if this is the first time
+ // this function is called, it will call Create() wiht empty bounds.
static RemoteRootWindowHostWin* Instance();
static RemoteRootWindowHostWin* Create(const gfx::Rect& bounds);
// Called when the remote process has established its IPC connection.
- // The |host| can be used when we need to send a message to it.
- void Connected(IPC::Sender* host);
+ // The |host| can be used when we need to send a message to it and
+ // |remote_window| is the actual window owned by the viewer process.
+ void Connected(IPC::Sender* host, HWND remote_window);
// Called when the remote process has closed its IPC connection.
void Disconnected();
// Called when we have a message from the remote process.
bool OnMessageReceived(const IPC::Message& message);
+ void HandleOpenURLOnDesktop(const base::FilePath& shortcut,
+ const base::string16& url);
+
void HandleOpenFile(const base::string16& title,
const base::FilePath& default_path,
const base::string16& filter,
@@ -159,7 +165,6 @@ class AURA_EXPORT RemoteRootWindowHostWin : public RootWindowHost {
void OnMultiFileOpenDone(bool success,
const std::vector<base::FilePath>& files);
void OnSelectFolderDone(bool success, const base::FilePath& folder);
- void OnWindowActivated(bool active);
void OnSetCursorPosAck();
void OnWindowSizeChanged(uint32 width, uint32 height);
@@ -184,9 +189,6 @@ class AURA_EXPORT RemoteRootWindowHostWin : public RootWindowHost {
virtual void OnCursorVisibilityChanged(bool show) OVERRIDE;
virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
virtual void SetFocusWhenShown(bool focus_when_shown) OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
virtual void PostNativeEvent(const base::NativeEvent& native_event) OVERRIDE;
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
virtual void PrepareForShutdown() OVERRIDE;
@@ -203,6 +205,7 @@ class AURA_EXPORT RemoteRootWindowHostWin : public RootWindowHost {
uint32 flags,
bool is_character);
+ HWND remote_window_;
RootWindowHostDelegate* delegate_;
IPC::Sender* host_;
scoped_ptr<ui::ViewProp> prop_;
diff --git a/chromium/ui/aura/root_window.cc b/chromium/ui/aura/root_window.cc
index 43366f001aa..303ec90f18e 100644
--- a/chromium/ui/aura/root_window.cc
+++ b/chromium/ui/aura/root_window.cc
@@ -6,7 +6,6 @@
#include <vector>
-#include "base/auto_reset.h"
#include "base/bind.h"
#include "base/command_line.h"
#include "base/debug/trace_event.h"
@@ -25,7 +24,6 @@
#include "ui/aura/window.h"
#include "ui/aura/window_delegate.h"
#include "ui/aura/window_tracker.h"
-#include "ui/base/events/event.h"
#include "ui/base/gestures/gesture_recognizer.h"
#include "ui/base/gestures/gesture_types.h"
#include "ui/base/hit_test.h"
@@ -34,6 +32,7 @@
#include "ui/compositor/dip_util.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animator.h"
+#include "ui/events/event.h"
#include "ui/gfx/display.h"
#include "ui/gfx/point3_f.h"
#include "ui/gfx/point_conversions.h"
@@ -149,7 +148,6 @@ RootWindow::RootWindow(const CreateParams& params)
last_cursor_(ui::kCursorNull),
mouse_pressed_handler_(NULL),
mouse_moved_handler_(NULL),
- mouse_event_dispatch_target_(NULL),
event_dispatch_target_(NULL),
gesture_recognizer_(ui::GestureRecognizer::Create(this)),
synthesize_mouse_move_(false),
@@ -171,6 +169,8 @@ RootWindow::RootWindow(const CreateParams& params)
}
RootWindow::~RootWindow() {
+ TRACE_EVENT0("shutdown", "RootWindow::Destructor");
+
compositor_->RemoveObserver(this);
// Make sure to destroy the compositor before terminating so that state is
// cleared and we don't hit asserts.
@@ -216,6 +216,8 @@ void RootWindow::PrepareForShutdown() {
}
void RootWindow::RepostEvent(const ui::LocatedEvent& event) {
+ DCHECK(event.type() == ui::ET_MOUSE_PRESSED ||
+ event.type() == ui::ET_GESTURE_TAP_DOWN);
// We allow for only one outstanding repostable event. This is used
// in exiting context menus. A dropped repost request is allowed.
if (event.type() == ui::ET_MOUSE_PRESSED) {
@@ -231,7 +233,8 @@ void RootWindow::RepostEvent(const ui::LocatedEvent& event) {
} else {
DCHECK(event.type() == ui::ET_GESTURE_TAP_DOWN);
held_repostable_event_.reset();
- // TODO(sschmitz): add similar code for gesture events.
+ // TODO(rbyers): Reposing of gestures is tricky to get
+ // right, so it's not yet supported. crbug.com/170987.
}
}
@@ -276,6 +279,13 @@ void RootWindow::SetCursor(gfx::NativeCursor cursor) {
}
void RootWindow::OnCursorVisibilityChanged(bool show) {
+ // Clear any existing mouse hover effects when the cursor becomes invisible.
+ // Note we do not need to dispatch a mouse enter when the cursor becomes
+ // visible because that can only happen in response to a mouse event, which
+ // will trigger its own mouse enter.
+ if (!show)
+ DispatchMouseExitAtPoint(GetLastMouseLocationInRoot());
+
host_->OnCursorVisibilityChanged(show);
}
@@ -378,13 +388,13 @@ void RootWindow::DispatchMouseExitToHidingWindow(Window* window) {
// |window| is the capture window.
gfx::Point last_mouse_location = GetLastMouseLocationInRoot();
if (window->Contains(mouse_moved_handler_) &&
- window->ContainsPointInRoot(last_mouse_location)) {
- ui::MouseEvent event(ui::ET_MOUSE_EXITED,
- last_mouse_location,
- last_mouse_location,
- ui::EF_NONE);
- DispatchMouseEnterOrExit(event, ui::ET_MOUSE_EXITED);
- }
+ window->ContainsPointInRoot(last_mouse_location))
+ DispatchMouseExitAtPoint(last_mouse_location);
+}
+
+void RootWindow::DispatchMouseExitAtPoint(const gfx::Point& point) {
+ ui::MouseEvent event(ui::ET_MOUSE_EXITED, point, point, ui::EF_NONE);
+ DispatchMouseEnterOrExit(event, ui::ET_MOUSE_EXITED);
}
void RootWindow::OnWindowVisibilityChanged(Window* window, bool is_visible) {
@@ -422,9 +432,7 @@ void RootWindow::RemoveRootWindowObserver(RootWindowObserver* observer) {
}
void RootWindow::PostNativeEvent(const base::NativeEvent& native_event) {
-#if !defined(OS_MACOSX)
host_->PostNativeEvent(native_event);
-#endif
}
void RootWindow::ConvertPointToNativeScreen(gfx::Point* point) const {
@@ -441,13 +449,13 @@ void RootWindow::ConvertPointFromNativeScreen(gfx::Point* point) const {
void RootWindow::ConvertPointToHost(gfx::Point* point) const {
gfx::Point3F point_3f(*point);
- GetRootTransform().TransformPoint(point_3f);
+ GetRootTransform().TransformPoint(&point_3f);
*point = gfx::ToFlooredPoint(point_3f.AsPointF());
}
void RootWindow::ConvertPointFromHost(gfx::Point* point) const {
gfx::Point3F point_3f(*point);
- GetInverseRootTransform().TransformPoint(point_3f);
+ GetInverseRootTransform().TransformPoint(&point_3f);
*point = gfx::ToFlooredPoint(point_3f.AsPointF());
}
@@ -499,15 +507,6 @@ void RootWindow::SetFocusWhenShown(bool focused) {
host_->SetFocusWhenShown(focused);
}
-bool RootWindow::CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- DCHECK(canvas);
- DCHECK(bounds().Contains(source_bounds));
- gfx::Rect source_pixels = ui::ConvertRectToPixel(layer(), source_bounds);
- return host_->CopyAreaToSkCanvas(source_pixels, dest_offset, canvas);
-}
-
gfx::Point RootWindow::GetLastMouseLocationInRoot() const {
gfx::Point location = Env::GetInstance()->last_mouse_location();
client::ScreenPositionClient* client = client::GetScreenPositionClient(this);
@@ -654,6 +653,14 @@ bool RootWindow::CanReceiveEvents() const {
void RootWindow::UpdateCapture(Window* old_capture,
Window* new_capture) {
+ if (!new_capture && old_capture && old_capture->GetRootWindow() != this) {
+ // If we no longer contain the window that had capture make sure we clean
+ // state in the GestureRecognizer. Since we don't contain the window we'll
+ // never get notification of its destruction and clean up state.
+ // We do this early on as OnCaptureLost() may delete |old_capture|.
+ gesture_recognizer_->CleanupStateForConsumer(old_capture);
+ }
+
if (old_capture && old_capture->GetRootWindow() == this &&
old_capture->delegate()) {
// Send a capture changed event with bogus location data.
@@ -674,9 +681,8 @@ void RootWindow::UpdateCapture(Window* old_capture,
}
if (new_capture) {
- // Make all subsequent mouse events and touch go to the capture window. We
- // shouldn't need to send an event here as OnCaptureLost should take care of
- // that.
+ // Make all subsequent mouse events go to the capture window. We shouldn't
+ // need to send an event here as OnCaptureLost() should take care of that.
if (mouse_moved_handler_ || Env::GetInstance()->is_mouse_button_down())
mouse_moved_handler_ = new_capture;
} else {
@@ -698,12 +704,6 @@ bool RootWindow::QueryMouseLocationForTest(gfx::Point* point) const {
return host_->QueryMouseLocation(point);
}
-void RootWindow::ClearMouseHandlers() {
- mouse_pressed_handler_ = NULL;
- mouse_moved_handler_ = NULL;
- mouse_event_dispatch_target_ = NULL;
-}
-
////////////////////////////////////////////////////////////////////////////////
// RootWindow, private:
@@ -724,22 +724,6 @@ void RootWindow::MoveCursorToInternal(const gfx::Point& root_location,
synthesize_mouse_move_ = false;
}
-void RootWindow::HandleMouseMoved(const ui::MouseEvent& event, Window* target) {
- if (target == mouse_moved_handler_)
- return;
-
- DispatchMouseEnterOrExit(event, ui::ET_MOUSE_EXITED);
-
- if (mouse_event_dispatch_target_ != target) {
- mouse_moved_handler_ = NULL;
- return;
- }
-
- mouse_moved_handler_ = target;
-
- DispatchMouseEnterOrExit(event, ui::ET_MOUSE_ENTERED);
-}
-
void RootWindow::DispatchMouseEnterOrExit(const ui::MouseEvent& event,
ui::EventType type) {
if (!mouse_moved_handler_ || !mouse_moved_handler_->delegate())
@@ -825,15 +809,13 @@ void RootWindow::OnWindowHidden(Window* invisible, WindowHiddenReason reason) {
mouse_pressed_handler_ = NULL;
if (invisible->Contains(mouse_moved_handler_))
mouse_moved_handler_ = NULL;
- if (invisible->Contains(mouse_event_dispatch_target_))
- mouse_event_dispatch_target_ = NULL;
CleanupGestureRecognizerState(invisible);
}
void RootWindow::CleanupGestureRecognizerState(Window* window) {
gesture_recognizer_->CleanupStateForConsumer(window);
- Windows windows = window->children();
+ const Windows& windows = window->children();
for (Windows::const_iterator iter = windows.begin();
iter != windows.end();
++iter) {
@@ -973,7 +955,8 @@ void RootWindow::OnHostLostWindowCapture() {
}
void RootWindow::OnHostLostMouseGrab() {
- ClearMouseHandlers();
+ mouse_pressed_handler_ = NULL;
+ mouse_moved_handler_ = NULL;
}
void RootWindow::OnHostPaint(const gfx::Rect& damage_rect) {
@@ -1038,21 +1021,46 @@ bool RootWindow::DispatchMouseEventToTarget(ui::MouseEvent* event,
ui::EF_LEFT_MOUSE_BUTTON |
ui::EF_MIDDLE_MOUSE_BUTTON |
ui::EF_RIGHT_MOUSE_BUTTON;
- base::AutoReset<Window*> reset(&mouse_event_dispatch_target_, target);
+ // WARNING: because of nested message loops |this| may be deleted after
+ // dispatching any event. Do not use AutoReset or the like here.
+ WindowTracker destroyed_tracker;
+ destroyed_tracker.Add(this);
SetLastMouseLocation(this, event->location());
synthesize_mouse_move_ = false;
switch (event->type()) {
case ui::ET_MOUSE_EXITED:
if (!target) {
DispatchMouseEnterOrExit(*event, ui::ET_MOUSE_EXITED);
+ if (!destroyed_tracker.Contains(this))
+ return false;
mouse_moved_handler_ = NULL;
}
break;
case ui::ET_MOUSE_MOVED:
- mouse_event_dispatch_target_ = target;
- HandleMouseMoved(*event, target);
- if (mouse_event_dispatch_target_ != target)
- return false;
+ // Send an exit to the current |mouse_moved_handler_| and an enter to
+ // |target|. Take care that both us and |target| aren't destroyed during
+ // dispatch.
+ if (target != mouse_moved_handler_) {
+ aura::Window* old_mouse_moved_handler = mouse_moved_handler_;
+ if (target)
+ destroyed_tracker.Add(target);
+ DispatchMouseEnterOrExit(*event, ui::ET_MOUSE_EXITED);
+ if (!destroyed_tracker.Contains(this))
+ return false;
+ // If the |mouse_moved_handler_| changes out from under us, assume a
+ // nested message loop ran and we don't need to do anything.
+ if (mouse_moved_handler_ != old_mouse_moved_handler)
+ return false;
+ if (destroyed_tracker.Contains(target)) {
+ destroyed_tracker.Remove(target);
+ mouse_moved_handler_ = target;
+ DispatchMouseEnterOrExit(*event, ui::ET_MOUSE_ENTERED);
+ if (!destroyed_tracker.Contains(this))
+ return false;
+ } else {
+ mouse_moved_handler_ = NULL;
+ }
+ }
break;
case ui::ET_MOUSE_PRESSED:
// Don't set the mouse pressed handler for non client mouse down events.
@@ -1072,14 +1080,19 @@ bool RootWindow::DispatchMouseEventToTarget(ui::MouseEvent* event,
default:
break;
}
+ bool result;
if (target) {
event->ConvertLocationToTarget(static_cast<Window*>(this), target);
if (IsNonClientLocation(target, event->location()))
event->set_flags(event->flags() | ui::EF_IS_NON_CLIENT);
ProcessEvent(target, event);
- return event->handled();
+ if (!destroyed_tracker.Contains(this))
+ return false;
+ result = event->handled();
+ } else {
+ result = false;
}
- return false;
+ return result;
}
bool RootWindow::DispatchTouchEventImpl(ui::TouchEvent* event) {
@@ -1153,11 +1166,11 @@ void RootWindow::DispatchHeldEvents() {
if (held_repostable_event_->type() == ui::ET_MOUSE_PRESSED) {
ui::MouseEvent mouse_event(
static_cast<const ui::MouseEvent&>(*held_repostable_event_.get()));
- held_repostable_event_.reset(); // must be reset before dispatch
+ held_repostable_event_.reset(); // must be reset before dispatch
DispatchMouseEventRepost(&mouse_event);
} else {
- DCHECK(held_repostable_event_->type() == ui::ET_GESTURE_TAP_DOWN);
- // TODO(sschmitz): add similar code for gesture events
+ // TODO(rbyers): GESTURE_TAP_DOWN not yet supported: crbug.com/170987.
+ NOTREACHED();
}
held_repostable_event_.reset();
}
diff --git a/chromium/ui/aura/root_window.h b/chromium/ui/aura/root_window.h
index e8a6b260f85..10ce2d507bf 100644
--- a/chromium/ui/aura/root_window.h
+++ b/chromium/ui/aura/root_window.h
@@ -18,19 +18,17 @@
#include "ui/aura/root_window_host_delegate.h"
#include "ui/aura/window.h"
#include "ui/base/cursor/cursor.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_dispatcher.h"
#include "ui/base/gestures/gesture_recognizer.h"
#include "ui/base/gestures/gesture_types.h"
#include "ui/compositor/compositor.h"
#include "ui/compositor/compositor_observer.h"
#include "ui/compositor/layer_animation_observer.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_dispatcher.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/point.h"
#include "ui/gfx/transform.h"
-class SkCanvas;
-
namespace gfx {
class Size;
class Transform;
@@ -86,6 +84,7 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
ui::Compositor* compositor() { return compositor_.get(); }
gfx::NativeCursor last_cursor() const { return last_cursor_; }
Window* mouse_pressed_handler() { return mouse_pressed_handler_; }
+ Window* mouse_moved_handler() { return mouse_moved_handler_; }
// Initializes the root window.
void Init();
@@ -100,6 +99,8 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
void PrepareForShutdown();
// Repost event for re-processing. Used when exiting context menus.
+ // We only support the ET_MOUSE_PRESSED and ET_GESTURE_TAP_DOWN event
+ // types (although the latter is currently a no-op).
void RepostEvent(const ui::LocatedEvent& event);
RootWindowHostDelegate* AsRootWindowHostDelegate();
@@ -162,6 +163,9 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
// Dispatches OnMouseExited to the |window| which is hiding if nessessary.
void DispatchMouseExitToHidingWindow(Window* window);
+ // Dispatches a ui::ET_MOUSE_EXITED event at |point|.
+ void DispatchMouseExitAtPoint(const gfx::Point& point);
+
// Invoked when |window|'s visibility has changed.
void OnWindowVisibilityChanged(Window* window, bool is_visible);
@@ -239,12 +243,6 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
// Sets if the window should be focused when shown.
void SetFocusWhenShown(bool focus_when_shown);
- // Copies |source_bounds| from the root window (as displayed on the host
- // machine) to |canvas| at offset |dest_offset|.
- bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas);
-
// Gets the last location seen in a mouse event in this root window's
// coordinates. This may return a point outside the root window's bounds.
gfx::Point GetLastMouseLocationInRoot() const;
@@ -286,10 +284,6 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
// Exposes RootWindowHost::QueryMouseLocation() for test purposes.
bool QueryMouseLocationForTest(gfx::Point* point) const;
- // Clears internal mouse state (such as mouse ups should be sent to the same
- // window that ate mouse downs).
- void ClearMouseHandlers();
-
void SetRootWindowTransformer(scoped_ptr<RootWindowTransformer> transformer);
gfx::Transform GetRootTransform() const;
@@ -319,10 +313,6 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
void MoveCursorToInternal(const gfx::Point& root_location,
const gfx::Point& host_location);
- // Called whenever the mouse moves, tracks the current |mouse_moved_handler_|,
- // sending exited and entered events as its value changes.
- void HandleMouseMoved(const ui::MouseEvent& event, Window* target);
-
// Dispatches the specified event type (intended for enter/exit) to the
// |mouse_moved_handler_|.
void DispatchMouseEnterOrExit(const ui::MouseEvent& event,
@@ -426,7 +416,6 @@ class AURA_EXPORT RootWindow : public ui::CompositorDelegate,
Window* mouse_pressed_handler_;
Window* mouse_moved_handler_;
- Window* mouse_event_dispatch_target_;
Window* event_dispatch_target_;
// The gesture_recognizer_ for this.
diff --git a/chromium/ui/aura/root_window_host.h b/chromium/ui/aura/root_window_host.h
index 09e48fad817..0528ae179a1 100644
--- a/chromium/ui/aura/root_window_host.h
+++ b/chromium/ui/aura/root_window_host.h
@@ -12,8 +12,6 @@
#include "ui/base/cursor/cursor.h"
#include "ui/gfx/native_widget_types.h"
-class SkCanvas;
-
namespace gfx {
class Insets;
class Point;
@@ -99,17 +97,8 @@ class AURA_EXPORT RootWindowHost {
// Sets if the window should be focused when shown.
virtual void SetFocusWhenShown(bool focus_when_shown) = 0;
- // Copies |source_bounds| from the root window (as displayed on the host
- // machine) to |canvas| at offset |dest_offset|. The bounds need to be in
- // physical pixels.
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) = 0;
-
// Posts |native_event| to the platform's event queue.
-#if !defined(OS_MACOSX)
virtual void PostNativeEvent(const base::NativeEvent& native_event) = 0;
-#endif
// Called when the device scale factor of the root window has chagned.
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) = 0;
diff --git a/chromium/ui/aura/root_window_host_mac.h b/chromium/ui/aura/root_window_host_mac.h
deleted file mode 100644
index e7c26c35482..00000000000
--- a/chromium/ui/aura/root_window_host_mac.h
+++ /dev/null
@@ -1,29 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_AURA_ROOT_WINDOW_HOST_MAC_H_
-#define UI_AURA_ROOT_WINDOW_HOST_MAC_H_
-
-#include "base/basictypes.h"
-#include "base/event_types.h"
-
-namespace aura {
-
-// An interface establishing event dispatch from the Mac native window and the
-// Aura host.
-class RootWindowHostMacDelegate {
- public:
- RootWindowHostMacDelegate();
- virtual ~RootWindowHostMacDelegate();
-
- // Route events from platform code to the RootWindowHost.
- virtual void SendEvent(const base::NativeEvent& native_event) = 0;
-
- private:
- DISALLOW_COPY_AND_ASSIGN(RootWindowHostMacDelegate);
-};
-
-} // namespace aura
-
-#endif // UI_AURA_ROOT_WINDOW_HOST_MAC_H_
diff --git a/chromium/ui/aura/root_window_host_mac.mm b/chromium/ui/aura/root_window_host_mac.mm
deleted file mode 100644
index 28943a958f9..00000000000
--- a/chromium/ui/aura/root_window_host_mac.mm
+++ /dev/null
@@ -1,218 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/aura/root_window_host_mac.h"
-
-#import <Cocoa/Cocoa.h>
-
-#include "base/compiler_specific.h"
-#include "base/mac/bundle_locations.h"
-#include "base/mac/scoped_nsobject.h"
-#include "ui/aura/event.h"
-#include "ui/aura/root_window.h"
-#include "ui/aura/root_window_host.h"
-#include "ui/aura/root_window_mac.h"
-#include "ui/aura/root_window_view_mac.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/gfx/point.h"
-
-namespace aura {
-
-// The Mac-specific implementation of the RootWindowHost interface. This class
-// acts at an intermediary between the Aura shell and an NSWindow. The
-// association between the Aura compositor and the native window's view is
-// established with this class as is the association between the native window's
-// event dispatch and the Aura event processing.
-class RootWindowHostMac : public RootWindowHost,
- public RootWindowHostMacDelegate {
- public:
- explicit RootWindowHostMac(const gfx::Rect& bounds);
- virtual ~RootWindowHostMac();
-
- // RootWindowHost:
- virtual void SetRootWindow(RootWindow* root_window) OVERRIDE;
- virtual gfx::AcceleratedWidget GetAcceleratedWidget() OVERRIDE;
- virtual void Show() OVERRIDE;
- virtual void ToggleFullScreen() OVERRIDE;
- virtual gfx::Size GetSize() const OVERRIDE;
- virtual void SetSize(const gfx::Size& size) OVERRIDE;
- virtual gfx::Point GetLocationOnNativeScreen() const OVERRIDE;
- virtual void SetCapture() OVERRIDE;
- virtual void ReleaseCapture() OVERRIDE;
- virtual void SetCursor(gfx::NativeCursor cursor) OVERRIDE;
- virtual void ShowCursor(bool show) OVERRIDE;
- virtual bool QueryMouseLocation(gfx::Point* location_return) OVERRIDE;
- virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
- virtual bool ConfineCursorToRootWindow() OVERRIDE;
- virtual void UnConfineCursor() OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
- // RootWindowHostMacDelegate:
- virtual void SendEvent(const base::NativeEvent& native_event) OVERRIDE;
-
- // Set the initial location of the root window. The origin of |bounds| is
- // top-left. This gets converted to bottom-left to match Mac coordinates on
- // the main screen.
- void SetLocation(const gfx::Rect& bounds);
-
- private:
- // Weak reference.
- RootWindow* root_window_;
-
- // The bounds of the Aura desktop. Relative to Aura's coordinate system.
- // This is currently used only for size information, not location.
- gfx::Rect bounds_;
-
- // An NSWindowController for the root window. Controls the actual Cocoa
- // window on Mac.
- base::scoped_nsobject<NSWindowController> controller_;
-
- DISALLOW_COPY_AND_ASSIGN(RootWindowHostMac);
-};
-
-RootWindowHostMacDelegate::RootWindowHostMacDelegate() {
-}
-
-RootWindowHostMacDelegate::~RootWindowHostMacDelegate() {
-}
-
-RootWindowHostMac::RootWindowHostMac(const gfx::Rect& bounds)
- : root_window_(NULL), bounds_(bounds) {
- NSString* nibpath = [base::mac::FrameworkBundle()
- pathForResource:@"RootWindow"
- ofType:@"nib"];
- NSWindowController* controller = [NSWindowController alloc];
- controller_.reset([controller initWithWindowNibPath:nibpath
- owner:controller]);
- SetSize(bounds.size());
- SetLocation(bounds);
-}
-
-RootWindowHostMac::~RootWindowHostMac() {
- RootWindowView* view = [[controller_ window] contentView];
- [view setCompositor:NULL];
- [controller_ close];
-}
-
-// static
-RootWindowHost* RootWindowHost::Create(const gfx::Rect& bounds) {
- return new RootWindowHostMac(bounds);
-}
-
-// static
-gfx::Size RootWindowHost::GetNativeScreenSize() {
- NSRect screen = [[NSScreen mainScreen] visibleFrame];
- return gfx::Size(NSSizeToCGSize(screen.size));
-}
-
-void RootWindowHostMac::SetRootWindow(RootWindow* root_window) {
- root_window_ = root_window;
-
- RootWindowView* view = [[controller_ window] contentView];
- DCHECK([view respondsToSelector:@selector(setCompositor:)]);
- [view setCompositor:root_window->compositor()];
-
- RootWindowMac* window = static_cast<RootWindowMac*>([controller_ window]);
- DCHECK([window respondsToSelector:@selector(setHostDelegate:)]);
- [window setHostDelegate:this];
-}
-
-gfx::AcceleratedWidget RootWindowHostMac::GetAcceleratedWidget() {
- return [[controller_ window] contentView];
-}
-
-void RootWindowHostMac::Show() {
- [controller_ showWindow:controller_];
-}
-
-void RootWindowHostMac::ToggleFullScreen() {
-}
-
-gfx::Size RootWindowHostMac::GetSize() const {
- NSSize size = [[[controller_ window] contentView] bounds].size;
- return gfx::Size(NSSizeToCGSize(size));
-}
-
-void RootWindowHostMac::SetSize(const gfx::Size& size) {
- NSSize nssize = NSSizeFromCGSize(size.ToCGSize());
- [[controller_ window] setContentSize:nssize];
- [[controller_ window] setContentMaxSize:nssize];
- [[controller_ window] setContentMinSize:nssize];
-}
-
-gfx::Point RootWindowHostMac::GetLocationOnNativeScreen() const {
- return gfx::Point();
-}
-
-void RootWindowHostMac::SetCapture() {
-}
-
-void RootWindowHostMac::ReleaseCapture() {
-}
-
-void RootWindowHostMac::SetCursor(gfx::NativeCursor cursor) {
-}
-
-void RootWindowHostMac::ShowCursor(bool show) {
-}
-
-bool RootWindowHostMac::QueryMouseLocation(gfx::Point* location_return) {
- *location_return = gfx::Point();
- return true;
-}
-
-void RootWindowHostMac::MoveCursorTo(const gfx::Point& location) {
-}
-
-bool RootWindowHostMac::ConfineCursorToRootWindow() {
- return false;
-}
-
-void RootWindowHostMac::UnConfineCursor() {
-}
-
-void RootWindowHostMac::SendEvent(const base::NativeEvent& native_event) {
- ui::EventType type = ui::EventTypeFromNative(native_event);
- switch (type) {
- case ui::ET_MOUSE_PRESSED:
- case ui::ET_MOUSE_DRAGGED:
- case ui::ET_MOUSE_RELEASED:
- case ui::ET_MOUSE_MOVED:
- case ui::ET_MOUSE_ENTERED:
- case ui::ET_MOUSE_EXITED: {
- MouseEvent mouse_event(native_event);
- root_window_->DispatchMouseEvent(&mouse_event);
- break;
- }
- case ui::ET_KEY_PRESSED:
- case ui::ET_KEY_RELEASED: {
- KeyEvent key_event(native_event, false);
- root_window_->DispatchKeyEvent(&key_event);
- break;
- }
- case ui::ET_MOUSEWHEEL:
- case ui::ET_TOUCH_RELEASED:
- case ui::ET_TOUCH_PRESSED:
- case ui::ET_TOUCH_MOVED:
- case ui::ET_TOUCH_STATIONARY:
- case ui::ET_TOUCH_CANCELLED:
- case ui::ET_DROP_TARGET_EVENT:
- case ui::ET_FOCUS_CHANGE:
- case ui::ET_SCROLL:
- case ui::ET_UNKNOWN:
- default:
- break;
- }
-}
-
-void RootWindowHostMac::SetLocation(const gfx::Rect& bounds) {
- NSRect screen = [[NSScreen mainScreen] visibleFrame];
- NSPoint origin = NSMakePoint(screen.origin.x + bounds.x(),
- screen.origin.y + screen.size.height -
- bounds.y() - bounds.height());
- [[controller_ window] setFrameOrigin:origin];
-}
-
-} // namespace aura
diff --git a/chromium/ui/aura/root_window_host_ozone.cc b/chromium/ui/aura/root_window_host_ozone.cc
index 28c8d0c4807..3af82898e79 100644
--- a/chromium/ui/aura/root_window_host_ozone.cc
+++ b/chromium/ui/aura/root_window_host_ozone.cc
@@ -5,7 +5,7 @@
#include "ui/aura/root_window_host_ozone.h"
#include "ui/aura/root_window.h"
-#include "ui/base/ozone/surface_factory_ozone.h"
+#include "ui/gfx/ozone/surface_factory_ozone.h"
namespace aura {
@@ -15,8 +15,8 @@ RootWindowHostOzone::RootWindowHostOzone(const gfx::Rect& bounds)
bounds_(bounds),
factory_(new ui::EventFactoryOzone()) {
factory_->CreateStartupEventConverters();
- ui::SurfaceFactoryOzone* surface_factory =
- ui::SurfaceFactoryOzone::GetInstance();
+ gfx::SurfaceFactoryOzone* surface_factory =
+ gfx::SurfaceFactoryOzone::GetInstance();
widget_ = surface_factory->GetAcceleratedWidget();
surface_factory->AttemptToResizeAcceleratedWidget(widget_, bounds_);
@@ -106,13 +106,6 @@ void RootWindowHostOzone::SetFocusWhenShown(bool focus_when_shown) {
NOTIMPLEMENTED();
}
-bool RootWindowHostOzone::CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- NOTIMPLEMENTED();
- return false;
-}
-
void RootWindowHostOzone::PostNativeEvent(
const base::NativeEvent& native_event) {
NOTIMPLEMENTED();
diff --git a/chromium/ui/aura/root_window_host_ozone.h b/chromium/ui/aura/root_window_host_ozone.h
index 6acd1a2c0ce..8be9e484fc3 100644
--- a/chromium/ui/aura/root_window_host_ozone.h
+++ b/chromium/ui/aura/root_window_host_ozone.h
@@ -10,7 +10,7 @@
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_loop.h"
#include "ui/aura/root_window_host.h"
-#include "ui/base/ozone/event_factory_ozone.h"
+#include "ui/events/ozone/event_factory_ozone.h"
#include "ui/gfx/rect.h"
namespace aura {
@@ -46,9 +46,6 @@ class RootWindowHostOzone : public RootWindowHost,
virtual void OnCursorVisibilityChanged(bool show) OVERRIDE;
virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
virtual void SetFocusWhenShown(bool focus_when_shown) OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
virtual void PostNativeEvent(const base::NativeEvent& event) OVERRIDE;
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
virtual void PrepareForShutdown() OVERRIDE;
diff --git a/chromium/ui/aura/root_window_host_win.cc b/chromium/ui/aura/root_window_host_win.cc
index 5c67b776d07..e5658f76447 100644
--- a/chromium/ui/aura/root_window_host_win.cc
+++ b/chromium/ui/aura/root_window_host_win.cc
@@ -13,7 +13,7 @@
#include "ui/aura/client/cursor_client.h"
#include "ui/aura/root_window.h"
#include "ui/base/cursor/cursor_loader_win.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/base/view_prop.h"
#include "ui/gfx/display.h"
#include "ui/gfx/insets.h"
@@ -210,13 +210,6 @@ bool RootWindowHostWin::ConfineCursorToRootWindow() {
return ClipCursor(&window_rect) != 0;
}
-bool RootWindowHostWin::CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- NOTIMPLEMENTED();
- return false;
-}
-
void RootWindowHostWin::UnConfineCursor() {
ClipCursor(NULL);
}
diff --git a/chromium/ui/aura/root_window_host_win.h b/chromium/ui/aura/root_window_host_win.h
index 491ab903445..42c8ada89ca 100644
--- a/chromium/ui/aura/root_window_host_win.h
+++ b/chromium/ui/aura/root_window_host_win.h
@@ -8,11 +8,11 @@
#include "base/compiler_specific.h"
#include "ui/aura/root_window_host.h"
#include "ui/base/ui_export.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
namespace aura {
-class RootWindowHostWin : public RootWindowHost, public ui::WindowImpl {
+class RootWindowHostWin : public RootWindowHost, public gfx::WindowImpl {
public:
RootWindowHostWin(const gfx::Rect& bounds);
virtual ~RootWindowHostWin();
@@ -37,9 +37,6 @@ class RootWindowHostWin : public RootWindowHost, public ui::WindowImpl {
virtual void OnCursorVisibilityChanged(bool show) OVERRIDE;
virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
virtual void SetFocusWhenShown(bool focus_when_shown) OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
virtual void PostNativeEvent(const base::NativeEvent& native_event) OVERRIDE;
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
virtual void PrepareForShutdown() OVERRIDE;
diff --git a/chromium/ui/aura/root_window_host_x11.cc b/chromium/ui/aura/root_window_host_x11.cc
index f69a54a8898..abf1da06b9d 100644
--- a/chromium/ui/aura/root_window_host_x11.cc
+++ b/chromium/ui/aura/root_window_host_x11.cc
@@ -20,14 +20,11 @@
#include "base/command_line.h"
#include "base/debug/trace_event.h"
#include "base/message_loop/message_loop.h"
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/stl_util.h"
#include "base/strings/string_number_conversions.h"
#include "base/strings/string_util.h"
#include "base/strings/stringprintf.h"
-#include "third_party/skia/include/core/SkBitmap.h"
-#include "third_party/skia/include/core/SkCanvas.h"
-#include "third_party/skia/include/core/SkPostConfig.h"
#include "ui/aura/client/capture_client.h"
#include "ui/aura/client/cursor_client.h"
#include "ui/aura/client/screen_position_client.h"
@@ -35,9 +32,6 @@
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
#include "ui/base/cursor/cursor.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/touch/touch_factory_x11.h"
#include "ui/base/ui_base_switches.h"
#include "ui/base/view_prop.h"
@@ -45,7 +39,9 @@
#include "ui/base/x/x11_util.h"
#include "ui/compositor/dip_util.h"
#include "ui/compositor/layer.h"
-#include "ui/gfx/codec/png_codec.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/screen.h"
#if defined(OS_CHROMEOS)
@@ -91,7 +87,7 @@ bool IsSideBezelsEnabled() {
#endif
void SelectEventsForRootWindow() {
- Display* display = ui::GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
::Window root_window = ui::GetX11RootWindow();
// Receive resize events for the root-window so |x_root_bounds_| can be
@@ -367,7 +363,7 @@ class RootWindowHostX11::MouseMoveFilter {
RootWindowHostX11::RootWindowHostX11(const gfx::Rect& bounds)
: delegate_(NULL),
- xdisplay_(base::MessagePumpAuraX11::GetDefaultXDisplay()),
+ xdisplay_(gfx::GetXDisplay()),
xwindow_(0),
x_root_window_(DefaultRootWindow(xdisplay_)),
current_cursor_(ui::kCursorNull),
@@ -377,7 +373,8 @@ RootWindowHostX11::RootWindowHostX11(const gfx::Rect& bounds)
focus_when_shown_(false),
touch_calibrate_(new internal::TouchEventCalibrate),
mouse_move_filter_(new MouseMoveFilter),
- atom_cache_(xdisplay_, kAtomsToCache) {
+ atom_cache_(xdisplay_, kAtomsToCache),
+ bezel_tracking_ids_(0) {
XSetWindowAttributes swa;
memset(&swa, 0, sizeof(swa));
swa.background_pixmap = None;
@@ -391,8 +388,8 @@ RootWindowHostX11::RootWindowHostX11(const gfx::Rect& bounds)
CopyFromParent, // visual
CWBackPixmap | CWOverrideRedirect,
&swa);
- base::MessagePumpAuraX11::Current()->AddDispatcherForWindow(this, xwindow_);
- base::MessagePumpAuraX11::Current()->AddDispatcherForRootWindow(this);
+ base::MessagePumpX11::Current()->AddDispatcherForWindow(this, xwindow_);
+ base::MessagePumpX11::Current()->AddDispatcherForRootWindow(this);
long event_mask = ButtonPressMask | ButtonReleaseMask | FocusChangeMask |
KeyPressMask | KeyReleaseMask |
@@ -443,8 +440,8 @@ RootWindowHostX11::RootWindowHostX11(const gfx::Rect& bounds)
RootWindowHostX11::~RootWindowHostX11() {
Env::GetInstance()->RemoveObserver(this);
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForRootWindow(this);
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(xwindow_);
+ base::MessagePumpX11::Current()->RemoveDispatcherForRootWindow(this);
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(xwindow_);
UnConfineCursor();
@@ -633,7 +630,7 @@ void RootWindowHostX11::Show() {
// We now block until our window is mapped. Some X11 APIs will crash and
// burn if passed |xwindow_| before the window is mapped, and XMapWindow is
// asynchronous.
- base::MessagePumpAuraX11::Current()->BlockUntilWindowMapped(xwindow_);
+ base::MessagePumpX11::Current()->BlockUntilWindowMapped(xwindow_);
window_mapped_ = true;
}
}
@@ -819,51 +816,6 @@ void RootWindowHostX11::SetFocusWhenShown(bool focus_when_shown) {
}
}
-bool RootWindowHostX11::CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- ui::XScopedImage scoped_image(
- XGetImage(xdisplay_, xwindow_,
- source_bounds.x(), source_bounds.y(),
- source_bounds.width(), source_bounds.height(),
- AllPlanes, ZPixmap));
- XImage* image = scoped_image.get();
- if (!image) {
- LOG(ERROR) << "XGetImage failed";
- return false;
- }
-
- if (image->bits_per_pixel == 32) {
- if ((0xff << SK_R32_SHIFT) != image->red_mask ||
- (0xff << SK_G32_SHIFT) != image->green_mask ||
- (0xff << SK_B32_SHIFT) != image->blue_mask) {
- LOG(WARNING) << "XImage and Skia byte orders differ";
- return false;
- }
-
- // Set the alpha channel before copying to the canvas. Otherwise, areas of
- // the framebuffer that were cleared by ply-image rather than being obscured
- // by an image during boot may end up transparent.
- // TODO(derat|marcheu): Remove this if/when ply-image has been updated to
- // set the framebuffer's alpha channel regardless of whether the device
- // claims to support alpha or not.
- for (int i = 0; i < image->width * image->height * 4; i += 4)
- image->data[i + 3] = 0xff;
-
- SkBitmap bitmap;
- bitmap.setConfig(SkBitmap::kARGB_8888_Config,
- image->width, image->height,
- image->bytes_per_line);
- bitmap.setPixels(image->data);
- canvas->drawBitmap(bitmap, SkIntToScalar(0), SkIntToScalar(0), NULL);
- } else {
- NOTIMPLEMENTED() << "Unsupported bits-per-pixel " << image->bits_per_pixel;
- return false;
- }
-
- return true;
-}
-
void RootWindowHostX11::PostNativeEvent(
const base::NativeEvent& native_event) {
DCHECK(xwindow_);
@@ -902,7 +854,7 @@ void RootWindowHostX11::OnDeviceScaleFactorChanged(
}
void RootWindowHostX11::PrepareForShutdown() {
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(xwindow_);
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(xwindow_);
}
void RootWindowHostX11::OnWindowInitialized(Window* window) {
@@ -961,15 +913,22 @@ void RootWindowHostX11::DispatchXI2Event(const base::NativeEvent& event) {
case ui::ET_TOUCH_PRESSED:
case ui::ET_TOUCH_CANCELLED:
case ui::ET_TOUCH_RELEASED: {
+ ui::TouchEvent touchev(xev);
#if defined(USE_XI2_MT)
- // Ignore events from the bezel when the side bezel flag is not explicitly
- // enabled.
- if (!IsSideBezelsEnabled() &&
- touch_calibrate_->IsEventOnSideBezels(xev, bounds_)) {
- break;
+ // Ignore touch events with touch press happening on the side bezel.
+ if (!IsSideBezelsEnabled()) {
+ uint32 tracking_id = (1 << touchev.touch_id());
+ if (type == ui::ET_TOUCH_PRESSED &&
+ touch_calibrate_->IsEventOnSideBezels(xev, bounds_))
+ bezel_tracking_ids_ |= tracking_id;
+ if (bezel_tracking_ids_ & tracking_id) {
+ if (type == ui::ET_TOUCH_CANCELLED || type == ui::ET_TOUCH_RELEASED)
+ bezel_tracking_ids_ =
+ (bezel_tracking_ids_ | tracking_id) ^ tracking_id;
+ return;
+ }
}
#endif // defined(USE_XI2_MT)
- ui::TouchEvent touchev(xev);
#if defined(OS_CHROMEOS)
if (base::chromeos::IsRunningOnChromeOS()) {
if (!bounds_.Contains(touchev.location()))
@@ -1131,7 +1090,7 @@ RootWindowHost* RootWindowHost::Create(const gfx::Rect& bounds) {
// static
gfx::Size RootWindowHost::GetNativeScreenSize() {
- ::Display* xdisplay = base::MessagePumpAuraX11::GetDefaultXDisplay();
+ ::XDisplay* xdisplay = gfx::GetXDisplay();
return gfx::Size(DisplayWidth(xdisplay, 0), DisplayHeight(xdisplay, 0));
}
diff --git a/chromium/ui/aura/root_window_host_x11.h b/chromium/ui/aura/root_window_host_x11.h
index c38002dda07..77d97b90efa 100644
--- a/chromium/ui/aura/root_window_host_x11.h
+++ b/chromium/ui/aura/root_window_host_x11.h
@@ -63,9 +63,6 @@ class RootWindowHostX11 : public RootWindowHost,
virtual void OnCursorVisibilityChanged(bool show) OVERRIDE;
virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
virtual void SetFocusWhenShown(bool focus_when_shown) OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
virtual void PostNativeEvent(const base::NativeEvent& event) OVERRIDE;
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
virtual void PrepareForShutdown() OVERRIDE;
@@ -106,7 +103,7 @@ class RootWindowHostX11 : public RootWindowHost,
RootWindowHostDelegate* delegate_;
// The display and the native X window hosting the root window.
- Display* xdisplay_;
+ XDisplay* xdisplay_;
::Window xwindow_;
// The native root window.
@@ -141,6 +138,9 @@ class RootWindowHostX11 : public RootWindowHost,
ui::X11AtomCache atom_cache_;
+ // Touch ids of which the touch press happens at side bezel region.
+ uint32 bezel_tracking_ids_;
+
DISALLOW_COPY_AND_ASSIGN(RootWindowHostX11);
};
diff --git a/chromium/ui/aura/root_window_mac.h b/chromium/ui/aura/root_window_mac.h
deleted file mode 100644
index 13a044c21d2..00000000000
--- a/chromium/ui/aura/root_window_mac.h
+++ /dev/null
@@ -1,37 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_AURA_ROOT_WINDOW_MAC_H_
-#define UI_AURA_ROOT_WINDOW_MAC_H_
-
-#import <Cocoa/Cocoa.h>
-
-namespace aura {
-class RootWindowHostMacDelegate;
-} // aura
-
-// RootWindow routes NSWindow events back to the RootWindowHost for dispatch
-// to the Aura event handling system.
-@interface RootWindowMac : NSWindow {
- @private
- // Weak. May be NULL. The host delegate acts as a conduit for event routing
- // back to the host.
- aura::RootWindowHostMacDelegate* hostDelegate_;
-}
-
-// Designated initializer.
-- (id)initWithContentRect:(NSRect)contentRect
- styleMask:(NSUInteger)windowStyle
- backing:(NSBackingStoreType)bufferingType
- defer:(BOOL)deferCreation;
-
-// Sets the |hostDelegate_|
-- (void)setHostDelegate:(aura::RootWindowHostMacDelegate*)hostDelegate;
-
-// Overrides main event dispatch to route NSWindow events to host delegate.
-- (void)sendEvent:(NSEvent*)event;
-
-@end
-
-#endif // UI_AURA_ROOT_WINDOW_MAC_H_
diff --git a/chromium/ui/aura/root_window_mac.mm b/chromium/ui/aura/root_window_mac.mm
deleted file mode 100644
index 32e42b7ad9d..00000000000
--- a/chromium/ui/aura/root_window_mac.mm
+++ /dev/null
@@ -1,35 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#import "ui/aura/root_window_mac.h"
-
-#include "ui/aura/root_window_host_mac.h"
-
-@implementation RootWindowMac
-
-- (id)initWithContentRect:(NSRect)contentRect
- styleMask:(NSUInteger)windowStyle
- backing:(NSBackingStoreType)bufferingType
- defer:(BOOL)deferCreation {
- if ((self = [super initWithContentRect:contentRect
- styleMask:windowStyle
- backing:bufferingType
- defer:deferCreation])) {
- hostDelegate_ = NULL;
- }
- return self;
-}
-
-- (void)setHostDelegate:(aura::RootWindowHostMacDelegate*)hostDelegate {
- hostDelegate_ = hostDelegate;
-}
-
-- (void)sendEvent:(NSEvent*)event {
- // Allow both the Cocoa machinery and the Aura machinery to handle the event.
- [super sendEvent:event];
- if (hostDelegate_)
- hostDelegate_->SendEvent(event);
-}
-
-@end
diff --git a/chromium/ui/aura/root_window_unittest.cc b/chromium/ui/aura/root_window_unittest.cc
index 739de66811f..652562b2604 100644
--- a/chromium/ui/aura/root_window_unittest.cc
+++ b/chromium/ui/aura/root_window_unittest.cc
@@ -17,12 +17,12 @@
#include "ui/aura/test/test_window_delegate.h"
#include "ui/aura/test/test_windows.h"
#include "ui/aura/window_tracker.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_handler.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/gestures/gesture_configuration.h"
#include "ui/base/hit_test.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/event_handler.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/screen.h"
@@ -402,11 +402,15 @@ namespace {
class EventFilterRecorder : public ui::EventHandler {
public:
typedef std::vector<ui::EventType> Events;
+ typedef std::vector<gfx::Point> MouseEventLocations;
EventFilterRecorder() {}
Events& events() { return events_; }
+ MouseEventLocations& mouse_locations() { return mouse_locations_; }
+ gfx::Point mouse_location(int i) const { return mouse_locations_[i]; }
+
// ui::EventHandler overrides:
virtual void OnKeyEvent(ui::KeyEvent* event) OVERRIDE {
events_.push_back(event->type());
@@ -414,6 +418,7 @@ class EventFilterRecorder : public ui::EventHandler {
virtual void OnMouseEvent(ui::MouseEvent* event) OVERRIDE {
events_.push_back(event->type());
+ mouse_locations_.push_back(event->location());
}
virtual void OnScrollEvent(ui::ScrollEvent* event) OVERRIDE {
@@ -430,6 +435,7 @@ class EventFilterRecorder : public ui::EventHandler {
private:
Events events_;
+ MouseEventLocations mouse_locations_;
DISALLOW_COPY_AND_ASSIGN(EventFilterRecorder);
};
@@ -679,6 +685,41 @@ TEST_F(RootWindowTest, DispatchSyntheticMouseEvents) {
EXPECT_TRUE(filter->events().empty());
}
+// Tests that a mouse exit is dispatched to the last known cursor location
+// when the cursor becomes invisible.
+TEST_F(RootWindowTest, DispatchMouseExitWhenCursorHidden) {
+ EventFilterRecorder* filter = new EventFilterRecorder;
+ root_window()->SetEventFilter(filter); // passes ownership
+
+ test::TestWindowDelegate delegate;
+ gfx::Point window_origin(7, 18);
+ scoped_ptr<aura::Window> window(CreateTestWindowWithDelegate(
+ &delegate, 1234, gfx::Rect(window_origin,
+ gfx::Size(100, 100)), root_window()));
+ window->Show();
+
+ // Dispatch a mouse move event into the window.
+ gfx::Point mouse_location(gfx::Point(15, 25));
+ ui::MouseEvent mouse1(ui::ET_MOUSE_MOVED, mouse_location,
+ mouse_location, 0);
+ EXPECT_TRUE(filter->events().empty());
+ root_window()->AsRootWindowHostDelegate()->OnHostMouseEvent(&mouse1);
+ EXPECT_FALSE(filter->events().empty());
+ filter->events().clear();
+
+ // Hide the cursor and verify a mouse exit was dispatched.
+ root_window()->OnCursorVisibilityChanged(false);
+ EXPECT_FALSE(filter->events().empty());
+ EXPECT_EQ("MOUSE_EXITED", EventTypesToString(filter->events()));
+
+ // Verify the mouse exit was dispatched at the correct location
+ // (in the correct coordinate space).
+ int translated_x = mouse_location.x() - window_origin.x();
+ int translated_y = mouse_location.y() - window_origin.y();
+ gfx::Point translated_point(translated_x, translated_y);
+ EXPECT_EQ(filter->mouse_location(0).ToString(), translated_point.ToString());
+}
+
class DeletingEventFilter : public ui::EventHandler {
public:
DeletingEventFilter()
@@ -882,4 +923,132 @@ TEST_F(RootWindowTest, GestureEndDeliveredAfterNestedGestures) {
EXPECT_EQ(1, d2.gesture_end_count());
}
+// Tests whether we can repost the Tap down gesture event.
+TEST_F(RootWindowTest, RepostTapdownGestureTest) {
+ EventFilterRecorder* filter = new EventFilterRecorder;
+ root_window()->SetEventFilter(filter); // passes ownership
+
+ test::TestWindowDelegate delegate;
+ scoped_ptr<aura::Window> window(CreateTestWindowWithDelegate(
+ &delegate, 1, gfx::Rect(0, 0, 100, 100), root_window()));
+
+ ui::GestureEventDetails details(ui::ET_GESTURE_TAP_DOWN, 0.0f, 0.0f);
+ gfx::Point point(10, 10);
+ ui::GestureEvent event(
+ ui::ET_GESTURE_TAP_DOWN,
+ point.x(),
+ point.y(),
+ 0,
+ ui::EventTimeForNow(),
+ details,
+ 0);
+ root_window()->RepostEvent(event);
+ RunAllPendingInMessageLoop();
+ // TODO(rbyers): Currently disabled - crbug.com/170987
+ EXPECT_FALSE(EventTypesToString(filter->events()).find("GESTURE_TAP_DOWN") !=
+ std::string::npos);
+ filter->events().clear();
+}
+
+// This class inherits from the EventFilterRecorder class which provides a
+// facility to record events. This class additionally provides a facility to
+// repost the ET_GESTURE_TAP_DOWN gesture to the target window and records
+// events after that.
+class RepostGestureEventRecorder : public EventFilterRecorder {
+ public:
+ RepostGestureEventRecorder(aura::Window* repost_source,
+ aura::Window* repost_target)
+ : repost_source_(repost_source),
+ repost_target_(repost_target),
+ reposted_(false) {}
+
+ virtual ~RepostGestureEventRecorder() {}
+
+ virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE {
+ EXPECT_EQ(reposted_ ? repost_target_ : repost_source_, event->target());
+ if (event->type() == ui::ET_GESTURE_TAP_DOWN) {
+ if (!reposted_) {
+ EXPECT_NE(repost_target_, event->target());
+ reposted_ = true;
+ events().clear();
+ repost_target_->GetRootWindow()->RepostEvent(*event);
+ // Ensure that the reposted gesture event above goes to the
+ // repost_target_;
+ repost_source_->GetRootWindow()->RemoveChild(repost_source_);
+ return;
+ }
+ }
+ EventFilterRecorder::OnGestureEvent(event);
+ }
+
+ // Ignore mouse events as they don't fire at all times. This causes
+ // the GestureRepostEventOrder test to fail randomly.
+ virtual void OnMouseEvent(ui::MouseEvent* event) OVERRIDE {}
+
+ private:
+ aura::Window* repost_source_;
+ aura::Window* repost_target_;
+ // set to true if we reposted the ET_GESTURE_TAP_DOWN event.
+ bool reposted_;
+ DISALLOW_COPY_AND_ASSIGN(RepostGestureEventRecorder);
+};
+
+// Tests whether events which are generated after the reposted gesture event
+// are received after that. In this case the scroll sequence events should
+// be received after the reposted gesture event.
+TEST_F(RootWindowTest, GestureRepostEventOrder) {
+ // Expected events at the end for the repost_target window defined below.
+ const char kExpectedTargetEvents[] =
+ // TODO)(rbyers): Gesture event reposting is disabled - crbug.com/279039.
+ // "GESTURE_BEGIN GESTURE_TAP_DOWN "
+ "TOUCH_RELEASED TOUCH_PRESSED GESTURE_BEGIN GESTURE_TAP_DOWN TOUCH_MOVED "
+ " GESTURE_SCROLL_BEGIN GESTURE_SCROLL_UPDATE TOUCH_MOVED "
+ "GESTURE_SCROLL_UPDATE TOUCH_MOVED GESTURE_SCROLL_UPDATE TOUCH_RELEASED "
+ "GESTURE_SCROLL_END GESTURE_END";
+ // We create two windows.
+ // The first window (repost_source) is the one to which the initial tap
+ // gesture is sent. It reposts this event to the second window
+ // (repost_target).
+ // We then generate the scroll sequence for repost_target and look for two
+ // ET_GESTURE_TAP_DOWN events in the event list at the end.
+ test::TestWindowDelegate delegate;
+ scoped_ptr<aura::Window> repost_target(CreateTestWindowWithDelegate(
+ &delegate, 1, gfx::Rect(0, 0, 100, 100), root_window()));
+
+ scoped_ptr<aura::Window> repost_source(CreateTestWindowWithDelegate(
+ &delegate, 1, gfx::Rect(0, 0, 50, 50), root_window()));
+
+ RepostGestureEventRecorder* repost_event_recorder =
+ new RepostGestureEventRecorder(repost_source.get(), repost_target.get());
+ root_window()->SetEventFilter(repost_event_recorder); // passes ownership
+
+ // Generate a tap down gesture for the repost_source. This will be reposted
+ // to repost_target.
+ test::EventGenerator repost_generator(root_window(), repost_source.get());
+ repost_generator.GestureTapAt(gfx::Point(40, 40));
+ RunAllPendingInMessageLoop();
+
+ test::EventGenerator scroll_generator(root_window(), repost_target.get());
+ scroll_generator.GestureScrollSequence(
+ gfx::Point(80, 80),
+ gfx::Point(100, 100),
+ base::TimeDelta::FromMilliseconds(100),
+ 3);
+ RunAllPendingInMessageLoop();
+
+ int tap_down_count = 0;
+ for (size_t i = 0; i < repost_event_recorder->events().size(); ++i) {
+ if (repost_event_recorder->events()[i] == ui::ET_GESTURE_TAP_DOWN)
+ ++tap_down_count;
+ }
+
+ // We expect two tap down events. One from the repost and the other one from
+ // the scroll sequence posted above.
+ // TODO(rbyers): Currently disabled - crbug.com/170987
+ EXPECT_EQ(1, tap_down_count);
+
+ EXPECT_EQ(kExpectedTargetEvents,
+ EventTypesToString(repost_event_recorder->events()));
+}
+
} // namespace aura
diff --git a/chromium/ui/aura/root_window_view_mac.h b/chromium/ui/aura/root_window_view_mac.h
deleted file mode 100644
index 6617f36dad9..00000000000
--- a/chromium/ui/aura/root_window_view_mac.h
+++ /dev/null
@@ -1,21 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_AURA_ROOT_WINDOW_VIEW_MAC_H_
-#define UI_AURA_ROOT_WINDOW_VIEW_MAC_H_
-
-#import <Cocoa/Cocoa.h>
-
-#include "ui/compositor/compositor.h"
-
-// RootWindowView provides an NSView class that delegates drawing to a
-// ui::Compositor delegate, setting up the NSOpenGLContext as required.
-@interface RootWindowView : NSView {
- @private
- ui::Compositor* compositor_;
-}
--(void)setCompositor:(ui::Compositor*)compositor;
-@end
-
-#endif // UI_AURA_ROOT_WINDOW_VIEW_MAC_H_
diff --git a/chromium/ui/aura/root_window_view_mac.mm b/chromium/ui/aura/root_window_view_mac.mm
deleted file mode 100644
index a82100e8434..00000000000
--- a/chromium/ui/aura/root_window_view_mac.mm
+++ /dev/null
@@ -1,16 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#import "ui/aura/root_window_view_mac.h"
-
-@implementation RootWindowView
--(void)setCompositor:(ui::Compositor*)compositor {
- compositor_ = compositor;
-}
-
-- (void)drawRect:(NSRect)rect {
- if (compositor_)
- compositor_->Draw(false);
-}
-@end
diff --git a/chromium/ui/aura/window.cc b/chromium/ui/aura/window.cc
index e5289e46a29..b14048287c6 100644
--- a/chromium/ui/aura/window.cc
+++ b/chromium/ui/aura/window.cc
@@ -25,24 +25,15 @@
#include "ui/aura/window_delegate.h"
#include "ui/aura/window_observer.h"
#include "ui/aura/window_tracker.h"
-#include "ui/base/animation/multi_animation.h"
#include "ui/compositor/compositor.h"
#include "ui/compositor/layer.h"
+#include "ui/gfx/animation/multi_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/path.h"
#include "ui/gfx/screen.h"
namespace aura {
-namespace {
-
-void MailboxReleaseCallback(scoped_ptr<base::SharedMemory> shared_memory,
- unsigned sync_point, bool lost_resource) {
- // NOTE: shared_memory will get released when we go out of scope.
-}
-
-} // namespace
-
Window::Window(WindowDelegate* delegate)
: type_(client::WINDOW_TYPE_UNKNOWN),
owned_by_parent_(true),
@@ -154,12 +145,6 @@ ui::Layer* Window::RecreateLayer() {
return NULL;
old_layer->set_delegate(NULL);
- float mailbox_scale_factor;
- cc::TextureMailbox old_mailbox =
- old_layer->GetTextureMailbox(&mailbox_scale_factor);
- scoped_refptr<ui::Texture> old_texture = old_layer->external_texture();
- if (delegate_ && old_texture.get())
- old_layer->SetExternalTexture(delegate_->CopyTexture().get());
layer_ = new ui::Layer(old_layer->type());
layer_owner_.reset(layer_);
@@ -167,29 +152,9 @@ ui::Layer* Window::RecreateLayer() {
layer_->set_scale_content(old_layer->scale_content());
layer_->set_delegate(this);
layer_->SetMasksToBounds(old_layer->GetMasksToBounds());
- // Move the original texture to the new layer if the old layer has a
- // texture and we could copy it into the old layer,
- // crbug.com/175211.
- if (delegate_ && old_texture.get()) {
- layer_->SetExternalTexture(old_texture.get());
- } else if (old_mailbox.IsSharedMemory()) {
- base::SharedMemory* old_buffer = old_mailbox.shared_memory();
- const size_t size = old_mailbox.shared_memory_size_in_bytes();
-
- scoped_ptr<base::SharedMemory> new_buffer(new base::SharedMemory);
- new_buffer->CreateAndMapAnonymous(size);
-
- if (old_buffer->memory() && new_buffer->memory()) {
- memcpy(new_buffer->memory(), old_buffer->memory(), size);
- base::SharedMemory* new_buffer_raw_ptr = new_buffer.get();
- cc::TextureMailbox::ReleaseCallback callback =
- base::Bind(MailboxReleaseCallback, Passed(&new_buffer));
- cc::TextureMailbox new_mailbox(new_buffer_raw_ptr,
- old_mailbox.shared_memory_size(),
- callback);
- layer_->SetTextureMailbox(new_mailbox, mailbox_scale_factor);
- }
- }
+
+ if (delegate_)
+ delegate_->DidRecreateLayer(old_layer, layer_);
UpdateLayerName(name_);
layer_->SetFillsBoundsOpaquely(!transparent_);
@@ -224,9 +189,9 @@ void Window::SetName(const std::string& name) {
}
void Window::SetTransparent(bool transparent) {
- // Cannot change transparent flag after the window is initialized.
- DCHECK(!layer());
transparent_ = transparent;
+ if (layer())
+ layer_->SetFillsBoundsOpaquely(!transparent_);
}
RootWindow* Window::GetRootWindow() {
diff --git a/chromium/ui/aura/window.h b/chromium/ui/aura/window.h
index 92dfa90b9c4..3ed7ca5cdff 100644
--- a/chromium/ui/aura/window.h
+++ b/chromium/ui/aura/window.h
@@ -17,13 +17,13 @@
#include "ui/aura/aura_export.h"
#include "ui/aura/client/window_types.h"
#include "ui/aura/window_observer.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_target.h"
#include "ui/base/gestures/gesture_types.h"
#include "ui/compositor/layer_animator.h"
#include "ui/compositor/layer_delegate.h"
#include "ui/compositor/layer_owner.h"
#include "ui/compositor/layer_type.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_target.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/rect.h"
diff --git a/chromium/ui/aura/window_delegate.h b/chromium/ui/aura/window_delegate.h
index bcbd2a6984c..ff941ef95b3 100644
--- a/chromium/ui/aura/window_delegate.h
+++ b/chromium/ui/aura/window_delegate.h
@@ -8,8 +8,8 @@
#include "base/compiler_specific.h"
#include "base/memory/ref_counted.h"
#include "ui/aura/aura_export.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_handler.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_handler.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
@@ -23,6 +23,7 @@ class Size;
namespace ui {
class GestureEvent;
class KeyEvent;
+class Layer;
class MouseEvent;
class Texture;
class TouchEvent;
@@ -95,9 +96,12 @@ class AURA_EXPORT WindowDelegate : public ui::EventHandler {
// above returns true.
virtual void GetHitTestMask(gfx::Path* mask) const = 0;
- // Called from RecreateLayer() if the layer the window is associated with has
- // an external texture.
- virtual scoped_refptr<ui::Texture> CopyTexture() = 0;
+ // Called from RecreateLayer() after the new layer was created. old_layer is
+ // the layer that will be returned to the caller of RecreateLayer, new_layer
+ // will be the layer now used on the Window. The implementation only has to do
+ // anything if the layer has external content (SetExternalTexture /
+ // SetTextureMailbox / SetDelegatedFrame was called).
+ virtual void DidRecreateLayer(ui::Layer* old_layer, ui::Layer* new_layer) = 0;
protected:
virtual ~WindowDelegate() {}
diff --git a/chromium/ui/aura/window_unittest.cc b/chromium/ui/aura/window_unittest.cc
index 320d1a61f7b..c37eb833cc9 100644
--- a/chromium/ui/aura/window_unittest.cc
+++ b/chromium/ui/aura/window_unittest.cc
@@ -27,15 +27,15 @@
#include "ui/aura/window_delegate.h"
#include "ui/aura/window_observer.h"
#include "ui/aura/window_property.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/gestures/gesture_configuration.h"
#include "ui/base/hit_test.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/scoped_animation_duration_scale_mode.h"
#include "ui/compositor/scoped_layer_animation_settings.h"
#include "ui/compositor/test/test_layers.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/screen.h"
@@ -1780,7 +1780,7 @@ TEST_F(WindowTest, SetBoundsInternalShouldCheckTargetBounds) {
EXPECT_FALSE(!w1->layer());
w1->layer()->GetAnimator()->set_disable_timer_for_test(true);
- ui::AnimationContainerElement* element = w1->layer()->GetAnimator();
+ gfx::AnimationContainerElement* element = w1->layer()->GetAnimator();
EXPECT_EQ("0,0 100x100", w1->bounds().ToString());
EXPECT_EQ("0,0 100x100", w1->layer()->GetTargetBounds().ToString());
@@ -2740,7 +2740,7 @@ TEST_F(WindowTest, DelegateNotifiedAsBoundsChange) {
// Animate to the end, which should notify of the change.
base::TimeTicks start_time =
window->layer()->GetAnimator()->last_step_time();
- ui::AnimationContainerElement* element = window->layer()->GetAnimator();
+ gfx::AnimationContainerElement* element = window->layer()->GetAnimator();
element->Step(start_time + base::TimeDelta::FromMilliseconds(1000));
EXPECT_TRUE(delegate.bounds_changed());
EXPECT_NE("0,0 100x100", window->bounds().ToString());
@@ -2782,7 +2782,7 @@ TEST_F(WindowTest, DelegateNotifiedAsBoundsChangeInHiddenLayer) {
// Animate to the end: will *not* notify of the change since we are hidden.
base::TimeTicks start_time =
window->layer()->GetAnimator()->last_step_time();
- ui::AnimationContainerElement* element = window->layer()->GetAnimator();
+ gfx::AnimationContainerElement* element = window->layer()->GetAnimator();
element->Step(start_time + base::TimeDelta::FromMilliseconds(1000));
// No bounds changed notification at the end of animation since layer
diff --git a/chromium/ui/base/accelerators/accelerator.cc b/chromium/ui/base/accelerators/accelerator.cc
index fbb60a796b4..4439af51dbe 100644
--- a/chromium/ui/base/accelerators/accelerator.cc
+++ b/chromium/ui/base/accelerators/accelerator.cc
@@ -18,7 +18,7 @@
#include "ui/base/l10n/l10n_util.h"
#if !defined(OS_WIN) && (defined(USE_AURA) || defined(OS_MACOSX))
-#include "ui/base/keycodes/keyboard_code_conversion.h"
+#include "ui/events/keycodes/keyboard_code_conversion.h"
#endif
namespace ui {
@@ -155,6 +155,18 @@ base::string16 Accelerator::GetShortcutText() const {
case ui::VKEY_OEM_PERIOD:
string_id = IDS_APP_PERIOD_KEY;
break;
+ case ui::VKEY_MEDIA_NEXT_TRACK:
+ string_id = IDS_APP_MEDIA_NEXT_TRACK_KEY;
+ break;
+ case ui::VKEY_MEDIA_PLAY_PAUSE:
+ string_id = IDS_APP_MEDIA_PLAY_PAUSE_KEY;
+ break;
+ case ui::VKEY_MEDIA_PREV_TRACK:
+ string_id = IDS_APP_MEDIA_PREV_TRACK_KEY;
+ break;
+ case ui::VKEY_MEDIA_STOP:
+ string_id = IDS_APP_MEDIA_STOP_KEY;
+ break;
default:
break;
}
diff --git a/chromium/ui/base/accelerators/accelerator.h b/chromium/ui/base/accelerators/accelerator.h
index e86538c529f..020c7bea40c 100644
--- a/chromium/ui/base/accelerators/accelerator.h
+++ b/chromium/ui/base/accelerators/accelerator.h
@@ -14,9 +14,9 @@
#include "base/memory/scoped_ptr.h"
#include "base/strings/string16.h"
#include "ui/base/accelerators/platform_accelerator.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace ui {
diff --git a/chromium/ui/base/accelerators/accelerator_manager.h b/chromium/ui/base/accelerators/accelerator_manager.h
index 2e6645ee996..818dc3ea05a 100644
--- a/chromium/ui/base/accelerators/accelerator_manager.h
+++ b/chromium/ui/base/accelerators/accelerator_manager.h
@@ -11,8 +11,8 @@
#include "base/basictypes.h"
#include "ui/base/accelerators/accelerator.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
namespace ui {
diff --git a/chromium/ui/base/accelerators/accelerator_manager_unittest.cc b/chromium/ui/base/accelerators/accelerator_manager_unittest.cc
index 73d1a1d0719..b8672ec1462 100644
--- a/chromium/ui/base/accelerators/accelerator_manager_unittest.cc
+++ b/chromium/ui/base/accelerators/accelerator_manager_unittest.cc
@@ -6,8 +6,8 @@
#include "base/compiler_specific.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace ui {
namespace test {
diff --git a/chromium/ui/base/accelerators/platform_accelerator_gtk.cc b/chromium/ui/base/accelerators/platform_accelerator_gtk.cc
index cae259b6d65..5662452a530 100644
--- a/chromium/ui/base/accelerators/platform_accelerator_gtk.cc
+++ b/chromium/ui/base/accelerators/platform_accelerator_gtk.cc
@@ -4,11 +4,36 @@
#include "ui/base/accelerators/platform_accelerator_gtk.h"
-#include "ui/base/events/event_conversion_gtk.h"
-#include "ui/base/keycodes/keyboard_code_conversion_gtk.h"
+#include "ui/events/keycodes/keyboard_code_conversion_gtk.h"
namespace ui {
+namespace {
+
+int GdkModifierToEventFlag(GdkModifierType gdk_modifier) {
+ int event_flags = 0;
+ if (gdk_modifier & GDK_SHIFT_MASK)
+ event_flags |= EF_SHIFT_DOWN;
+ if (gdk_modifier & GDK_CONTROL_MASK)
+ event_flags |= EF_CONTROL_DOWN;
+ if (gdk_modifier & GDK_MOD1_MASK)
+ event_flags |= EF_ALT_DOWN;
+ return event_flags;
+}
+
+GdkModifierType EventFlagToGdkModifier(int event_flag) {
+ int modifier = 0;
+ if (event_flag & EF_SHIFT_DOWN)
+ modifier |= GDK_SHIFT_MASK;
+ if (event_flag & EF_CONTROL_DOWN)
+ modifier |= GDK_CONTROL_MASK;
+ if (event_flag & EF_ALT_DOWN)
+ modifier |= GDK_MOD1_MASK;
+ return static_cast<GdkModifierType>(modifier);
+}
+
+} // namespace
+
PlatformAcceleratorGtk::PlatformAcceleratorGtk()
: gdk_key_code_(0),
gdk_modifier_(static_cast<GdkModifierType>(0)) {
diff --git a/chromium/ui/base/accessibility/accessible_text_utils.cc b/chromium/ui/base/accessibility/accessible_text_utils.cc
index 72ab60e7b42..5fab22e120a 100644
--- a/chromium/ui/base/accessibility/accessible_text_utils.cc
+++ b/chromium/ui/base/accessibility/accessible_text_utils.cc
@@ -9,7 +9,7 @@
namespace ui {
-size_t FindAccessibleTextBoundary(const string16& text,
+size_t FindAccessibleTextBoundary(const base::string16& text,
const std::vector<int>& line_breaks,
TextBoundaryType boundary,
size_t start_offset,
diff --git a/chromium/ui/base/accessibility/accessible_text_utils.h b/chromium/ui/base/accessibility/accessible_text_utils.h
index 479e719087e..a64088c7f94 100644
--- a/chromium/ui/base/accessibility/accessible_text_utils.h
+++ b/chromium/ui/base/accessibility/accessible_text_utils.h
@@ -42,7 +42,7 @@ enum TextBoundaryDirection {
// (depending on |direction|) from the given |start_offset| until the
// given boundary is found, and return the offset of that boundary,
// using the vector of line break character offsets in |line_breaks|.
-size_t UI_EXPORT FindAccessibleTextBoundary(const string16& text,
+size_t UI_EXPORT FindAccessibleTextBoundary(const base::string16& text,
const std::vector<int>& line_breaks,
TextBoundaryType boundary,
size_t start_offset,
diff --git a/chromium/ui/base/accessibility/accessible_view_state.h b/chromium/ui/base/accessibility/accessible_view_state.h
index 8e835ec2c63..2f4b4bffaac 100644
--- a/chromium/ui/base/accessibility/accessible_view_state.h
+++ b/chromium/ui/base/accessibility/accessible_view_state.h
@@ -34,16 +34,16 @@ struct UI_EXPORT AccessibleViewState {
AccessibilityTypes::State state;
// The view's name / label.
- string16 name;
+ base::string16 name;
// The view's value, for example the text content.
- string16 value;
+ base::string16 value;
// The name of the default action if the user clicks on this view.
- string16 default_action;
+ base::string16 default_action;
// The keyboard shortcut to activate this view, if any.
- string16 keyboard_shortcut;
+ base::string16 keyboard_shortcut;
// The selection start and end. Only applies to views with text content,
// such as a text box or combo box; start and end should be -1 otherwise.
diff --git a/chromium/ui/base/base_window.cc b/chromium/ui/base/base_window.cc
new file mode 100644
index 00000000000..231a1771797
--- /dev/null
+++ b/chromium/ui/base/base_window.cc
@@ -0,0 +1,16 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/base_window.h"
+
+namespace ui {
+
+bool BaseWindow::IsRestored(const BaseWindow& window) {
+ return !window.IsMaximized() &&
+ !window.IsMinimized() &&
+ !window.IsFullscreen();
+}
+
+} // namespace ui
+
diff --git a/chromium/ui/base/base_window.h b/chromium/ui/base/base_window.h
index 4f847d1eebd..d5fd2fae1c4 100644
--- a/chromium/ui/base/base_window.h
+++ b/chromium/ui/base/base_window.h
@@ -19,7 +19,7 @@ namespace ui {
// Provides an interface to perform actions on windows, and query window
// state.
-class BaseWindow {
+class UI_EXPORT BaseWindow {
public:
// Returns true if the window is currently the active/focused window.
virtual bool IsActive() const = 0;
@@ -33,6 +33,10 @@ class BaseWindow {
// Returns true if the window is full screen.
virtual bool IsFullscreen() const = 0;
+ // Returns true if the window is fully restored (not Fullscreen, Maximized,
+ // Minimized).
+ static bool IsRestored(const BaseWindow& window);
+
// Return a platform dependent identifier for this window.
virtual gfx::NativeWindow GetNativeWindow() = 0;
diff --git a/chromium/ui/base/clipboard/clipboard_aurax11.cc b/chromium/ui/base/clipboard/clipboard_aurax11.cc
index 287941dbdab..5c6ebb8dfe3 100644
--- a/chromium/ui/base/clipboard/clipboard_aurax11.cc
+++ b/chromium/ui/base/clipboard/clipboard_aurax11.cc
@@ -12,10 +12,11 @@
#include "base/basictypes.h"
#include "base/files/file_path.h"
#include "base/logging.h"
+#include "base/memory/ref_counted_memory.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/singleton.h"
-#include "base/message_loop/message_pump_aurax11.h"
#include "base/message_loop/message_pump_observer.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/stl_util.h"
#include "base/strings/utf_string_conversions.h"
#include "third_party/skia/include/core/SkBitmap.h"
@@ -25,7 +26,7 @@
#include "ui/base/x/selection_utils.h"
#include "ui/base/x/x11_atom_cache.h"
#include "ui/base/x/x11_util.h"
-
+#include "ui/gfx/codec/png_codec.h"
#include "ui/gfx/size.h"
namespace ui {
@@ -33,7 +34,6 @@ namespace ui {
namespace {
const char kClipboard[] = "CLIPBOARD";
-const char kMimeTypeBitmap[] = "image/bmp";
const char kMimeTypeFilename[] = "chromium/filename";
const char kMimeTypePepperCustomData[] = "chromium/x-pepper-custom-data";
const char kMimeTypeWebkitSmartPaste[] = "chromium/x-webkit-paste";
@@ -41,7 +41,7 @@ const char kTargets[] = "TARGETS";
const char* kAtomsToCache[] = {
kClipboard,
- kMimeTypeBitmap,
+ Clipboard::kMimeTypePNG,
kMimeTypeFilename,
kMimeTypeMozillaURL,
kMimeTypeWebkitSmartPaste,
@@ -90,9 +90,9 @@ SelectionChangeObserver::SelectionChangeObserver()
clipboard_sequence_number_(0),
primary_sequence_number_(0) {
int ignored;
- if (XFixesQueryExtension(GetXDisplay(), &event_base_, &ignored)) {
- clipboard_atom_ = XInternAtom(GetXDisplay(), kClipboard, false);
- XFixesSelectSelectionInput(GetXDisplay(), GetX11RootWindow(),
+ if (XFixesQueryExtension(gfx::GetXDisplay(), &event_base_, &ignored)) {
+ clipboard_atom_ = XInternAtom(gfx::GetXDisplay(), kClipboard, false);
+ XFixesSelectSelectionInput(gfx::GetXDisplay(), GetX11RootWindow(),
clipboard_atom_,
XFixesSetSelectionOwnerNotifyMask |
XFixesSelectionWindowDestroyNotifyMask |
@@ -100,13 +100,13 @@ SelectionChangeObserver::SelectionChangeObserver()
// This seems to be semi-optional. For some reason, registering for any
// selection notify events seems to subscribe us to events for both the
// primary and the clipboard buffers. Register anyway just to be safe.
- XFixesSelectSelectionInput(GetXDisplay(), GetX11RootWindow(),
+ XFixesSelectSelectionInput(gfx::GetXDisplay(), GetX11RootWindow(),
XA_PRIMARY,
XFixesSetSelectionOwnerNotifyMask |
XFixesSelectionWindowDestroyNotifyMask |
XFixesSelectionClientCloseNotifyMask);
- base::MessagePumpAuraX11::Current()->AddObserver(this);
+ base::MessagePumpX11::Current()->AddObserver(this);
}
}
@@ -309,7 +309,7 @@ class Clipboard::AuraX11Details : public base::MessagePumpDispatcher {
};
Clipboard::AuraX11Details::AuraX11Details()
- : x_display_(GetXDisplay()),
+ : x_display_(gfx::GetXDisplay()),
x_root_window_(DefaultRootWindow(x_display_)),
x_window_(XCreateWindow(
x_display_, x_root_window_,
@@ -332,11 +332,11 @@ Clipboard::AuraX11Details::AuraX11Details()
XStoreName(x_display_, x_window_, "Chromium clipboard");
XSelectInput(x_display_, x_window_, PropertyChangeMask);
- base::MessagePumpAuraX11::Current()->AddDispatcherForWindow(this, x_window_);
+ base::MessagePumpX11::Current()->AddDispatcherForWindow(this, x_window_);
}
Clipboard::AuraX11Details::~AuraX11Details() {
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(x_window_);
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(x_window_);
XDestroyWindow(x_display_, x_window_);
}
@@ -653,7 +653,16 @@ void Clipboard::ReadRTF(Buffer buffer, std::string* result) const {
SkBitmap Clipboard::ReadImage(Buffer buffer) const {
DCHECK(CalledOnValidThread());
- NOTIMPLEMENTED();
+
+ SelectionData data(aurax11_details_->RequestAndWaitForTypes(
+ buffer,
+ aurax11_details_->GetAtomsForFormat(GetBitmapFormatType())));
+ if (data.IsValid()) {
+ SkBitmap bitmap;
+ if (gfx::PNGCodec::Decode(data.GetData(), data.GetSize(), &bitmap))
+ return SkBitmap(bitmap);
+ }
+
return SkBitmap();
}
@@ -749,10 +758,21 @@ void Clipboard::WriteWebSmartPaste() {
}
void Clipboard::WriteBitmap(const char* pixel_data, const char* size_data) {
- // TODO(erg): I'm not sure if we should be writting BMP data here or
- // not. It's what the GTK port does, but I'm not sure it's the right thing to
- // do.
- NOTIMPLEMENTED();
+ const gfx::Size* size = reinterpret_cast<const gfx::Size*>(size_data);
+
+ // Adopt the pixels into a SkBitmap. Note that the pixel order in memory is
+ // actually BGRA.
+ SkBitmap bitmap;
+ bitmap.setConfig(SkBitmap::kARGB_8888_Config, size->width(), size->height());
+ bitmap.setPixels(const_cast<char*>(pixel_data));
+
+ // Encode the bitmap as a PNG for transport.
+ std::vector<unsigned char> output;
+ if (gfx::PNGCodec::FastEncodeBGRASkBitmap(bitmap, false, &output)) {
+ aurax11_details_->InsertMapping(kMimeTypePNG,
+ base::RefCountedBytes::TakeVector(
+ &output));
+ }
}
void Clipboard::WriteData(const FormatType& format,
@@ -822,7 +842,7 @@ const Clipboard::FormatType& Clipboard::GetRtfFormatType() {
// static
const Clipboard::FormatType& Clipboard::GetBitmapFormatType() {
- CR_DEFINE_STATIC_LOCAL(FormatType, type, (kMimeTypeBitmap));
+ CR_DEFINE_STATIC_LOCAL(FormatType, type, (kMimeTypePNG));
return type;
}
diff --git a/chromium/ui/base/clipboard/clipboard_gtk.cc b/chromium/ui/base/clipboard/clipboard_gtk.cc
index 722242ae30d..86f4a3c3dc3 100644
--- a/chromium/ui/base/clipboard/clipboard_gtk.cc
+++ b/chromium/ui/base/clipboard/clipboard_gtk.cc
@@ -20,10 +20,10 @@
#include "third_party/skia/include/core/SkBitmap.h"
#include "ui/base/clipboard/custom_data_helper.h"
#include "ui/base/gtk/gtk_signal.h"
-#include "ui/base/gtk/scoped_gobject.h"
#include "ui/base/x/x11_util.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/gtk_util.h"
+#include "ui/gfx/scoped_gobject.h"
#include "ui/gfx/size.h"
namespace ui {
@@ -62,9 +62,9 @@ SelectionChangeObserver::SelectionChangeObserver()
clipboard_sequence_number_(0),
primary_sequence_number_(0) {
int ignored;
- if (XFixesQueryExtension(GetXDisplay(), &event_base_, &ignored)) {
- clipboard_atom_ = XInternAtom(GetXDisplay(), "CLIPBOARD", false);
- XFixesSelectSelectionInput(GetXDisplay(), GetX11RootWindow(),
+ if (XFixesQueryExtension(gfx::GetXDisplay(), &event_base_, &ignored)) {
+ clipboard_atom_ = XInternAtom(gfx::GetXDisplay(), "CLIPBOARD", false);
+ XFixesSelectSelectionInput(gfx::GetXDisplay(), GetX11RootWindow(),
clipboard_atom_,
XFixesSetSelectionOwnerNotifyMask |
XFixesSelectionWindowDestroyNotifyMask |
@@ -72,7 +72,7 @@ SelectionChangeObserver::SelectionChangeObserver()
// This seems to be semi-optional. For some reason, registering for any
// selection notify events seems to subscribe us to events for both the
// primary and the clipboard buffers. Register anyway just to be safe.
- XFixesSelectSelectionInput(GetXDisplay(), GetX11RootWindow(),
+ XFixesSelectSelectionInput(gfx::GetXDisplay(), GetX11RootWindow(),
XA_PRIMARY,
XFixesSetSelectionOwnerNotifyMask |
XFixesSelectionWindowDestroyNotifyMask |
diff --git a/chromium/ui/base/clipboard/clipboard_unittest.cc b/chromium/ui/base/clipboard/clipboard_unittest.cc
index 6e7ad4cafb8..8217a601063 100644
--- a/chromium/ui/base/clipboard/clipboard_unittest.cc
+++ b/chromium/ui/base/clipboard/clipboard_unittest.cc
@@ -319,8 +319,6 @@ TEST_F(ClipboardTest, URLTest) {
#endif
}
-// TODO(erg): Reenable this everywhere once linux_aura learns what bitmaps are.
-#if !(defined(USE_AURA) && !defined(OS_CHROMEOS))
TEST_F(ClipboardTest, SharedBitmapTest) {
unsigned int fake_bitmap[] = {
0x46155189, 0xF6A55C8D, 0x79845674, 0xFA57BD89,
@@ -363,14 +361,11 @@ TEST_F(ClipboardTest, SharedBitmapTest) {
EXPECT_TRUE(clipboard().IsFormatAvailable(Clipboard::GetBitmapFormatType(),
Clipboard::BUFFER_STANDARD));
}
-#endif
-// The following test somehow fails on GTK. The image when read back from the
-// clipboard has the alpha channel set to 0xFF for some reason. The other
-// channels stay intact. So I am turning this on only for aura.
-//
-// TODO(erg): This also crashes in linux_aura. Investigate once bitmap writing
-// is implemented.
+// The following test somehow fails on GTK and linux_aura. The image when read
+// back from the clipboard has the alpha channel set to 0xFF for some
+// reason. The other channels stay intact. So I am turning this on only for
+// aura.
#if (defined(USE_AURA) && !(defined(OS_WIN) || !defined(OS_CHROMEOS))) || \
defined(OS_ANDROID)
TEST_F(ClipboardTest, MultipleBitmapReadWriteTest) {
diff --git a/chromium/ui/base/cocoa/appkit_utils.h b/chromium/ui/base/cocoa/appkit_utils.h
new file mode 100644
index 00000000000..159921bd136
--- /dev/null
+++ b/chromium/ui/base/cocoa/appkit_utils.h
@@ -0,0 +1,35 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_BASE_COCOA_APPKIT_UTILS_H
+#define UI_BASE_COCOA_APPKIT_UTILS_H
+
+#import <Cocoa/Cocoa.h>
+
+#include "ui/base/ui_export.h"
+
+namespace ui {
+
+struct NinePartImageIds {
+ int top_left;
+ int top;
+ int top_right;
+ int left;
+ int center;
+ int right;
+ int bottom_left;
+ int bottom;
+ int bottom_right;
+};
+
+// Utility method to draw a nine part image using image ids.
+UI_EXPORT void DrawNinePartImage(NSRect frame,
+ const NinePartImageIds& image_ids,
+ NSCompositingOperation operation,
+ CGFloat alpha,
+ BOOL flipped);
+
+} // namespace ui
+
+#endif // UI_BASE_COCOA_APPKIT_UTILS_H
diff --git a/chromium/ui/base/cocoa/appkit_utils.mm b/chromium/ui/base/cocoa/appkit_utils.mm
new file mode 100644
index 00000000000..824a6ac9256
--- /dev/null
+++ b/chromium/ui/base/cocoa/appkit_utils.mm
@@ -0,0 +1,41 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#import "ui/base/cocoa/appkit_utils.h"
+
+#include "ui/base/resource/resource_bundle.h"
+
+namespace {
+
+// Gets an NSImage given an image id.
+NSImage* GetImage(int image_id) {
+ return ui::ResourceBundle::GetSharedInstance().GetNativeImageNamed(image_id)
+ .ToNSImage();
+}
+
+} // namespace
+
+namespace ui {
+
+void DrawNinePartImage(NSRect frame,
+ const NinePartImageIds& image_ids,
+ NSCompositingOperation operation,
+ CGFloat alpha,
+ BOOL flipped) {
+ NSDrawNinePartImage(frame,
+ GetImage(image_ids.top_left),
+ GetImage(image_ids.top),
+ GetImage(image_ids.top_right),
+ GetImage(image_ids.left),
+ GetImage(image_ids.center),
+ GetImage(image_ids.right),
+ GetImage(image_ids.bottom_left),
+ GetImage(image_ids.bottom),
+ GetImage(image_ids.bottom_right),
+ operation,
+ alpha,
+ flipped);
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/cocoa/cocoa_event_utils.mm b/chromium/ui/base/cocoa/cocoa_event_utils.mm
index 19206992364..a8fd8c38a1c 100644
--- a/chromium/ui/base/cocoa/cocoa_event_utils.mm
+++ b/chromium/ui/base/cocoa/cocoa_event_utils.mm
@@ -4,7 +4,7 @@
#import "ui/base/cocoa/cocoa_event_utils.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "ui/base/window_open_disposition.h"
namespace {
diff --git a/chromium/ui/base/cocoa/cocoa_event_utils_unittest.mm b/chromium/ui/base/cocoa/cocoa_event_utils_unittest.mm
index cb5f68a407e..5ec3936fdcb 100644
--- a/chromium/ui/base/cocoa/cocoa_event_utils_unittest.mm
+++ b/chromium/ui/base/cocoa/cocoa_event_utils_unittest.mm
@@ -7,7 +7,7 @@
#include "testing/gtest/include/gtest/gtest.h"
#include "testing/platform_test.h"
#include "ui/base/cocoa/cocoa_event_utils.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#import "ui/base/test/cocoa_test_event_utils.h"
#import "ui/base/test/ui_cocoa_test_helper.h"
diff --git a/chromium/ui/base/cocoa/controls/hyperlink_button_cell.mm b/chromium/ui/base/cocoa/controls/hyperlink_button_cell.mm
index c723b03a7c3..57b70779cf3 100644
--- a/chromium/ui/base/cocoa/controls/hyperlink_button_cell.mm
+++ b/chromium/ui/base/cocoa/controls/hyperlink_button_cell.mm
@@ -52,6 +52,14 @@
return self;
}
+- (id)copyWithZone:(NSZone*)zone {
+ NSColor* color = textColor_.release();
+ HyperlinkButtonCell* cell = [super copyWithZone:zone];
+ cell->textColor_.reset([color copy]);
+ textColor_.reset(color);
+ return cell;
+}
+
// Because an NSButtonCell has multiple initializers, this method performs the
// common cell customization code.
- (void)customizeButtonCell {
diff --git a/chromium/ui/base/cocoa/controls/hyperlink_button_cell_unittest.mm b/chromium/ui/base/cocoa/controls/hyperlink_button_cell_unittest.mm
index 479141b7234..3d24f01fa90 100644
--- a/chromium/ui/base/cocoa/controls/hyperlink_button_cell_unittest.mm
+++ b/chromium/ui/base/cocoa/controls/hyperlink_button_cell_unittest.mm
@@ -8,6 +8,7 @@
#include "base/mac/foundation_util.h"
#include "base/mac/scoped_nsobject.h"
+#import "testing/gtest_mac.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "testing/platform_test.h"
#import "ui/base/test/ui_cocoa_test_helper.h"
@@ -115,6 +116,17 @@ TEST_F(HyperlinkButtonCellTest, UnderlineOnHover) {
EXPECT_FALSE(HasUnderlineAttribute([cell_ linkAttributes]));
}
+TEST_F(HyperlinkButtonCellTest, Copy) {
+ base::scoped_nsobject<HyperlinkButtonCell> cell1([[HyperlinkButtonCell alloc]
+ initTextCell:@"Cell"]);
+ [cell1 setTextColor:[NSColor redColor]];
+
+ base::scoped_nsobject<HyperlinkButtonCell> cell2([cell1 copy]);
+ EXPECT_NSEQ([cell1 textColor], [cell2 textColor]);
+ [cell1 setTextColor:[NSColor purpleColor]];
+ [cell2 setTextColor:[NSColor greenColor]];
+}
+
} // namespace
} // namespace ui
diff --git a/chromium/ui/base/cocoa/events_mac.mm b/chromium/ui/base/cocoa/events_mac.mm
index eacfb964bee..da08510a922 100644
--- a/chromium/ui/base/cocoa/events_mac.mm
+++ b/chromium/ui/base/cocoa/events_mac.mm
@@ -4,13 +4,13 @@
#include <Cocoa/Cocoa.h>
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "base/event_types.h"
#include "base/logging.h"
#include "base/time/time.h"
-#include "ui/base/events/event_utils.h"
-#import "ui/base/keycodes/keyboard_code_conversion_mac.h"
+#include "ui/events/event_utils.h"
+#import "ui/events/keycodes/keyboard_code_conversion_mac.h"
#include "ui/gfx/point.h"
namespace ui {
diff --git a/chromium/ui/base/cocoa/events_mac_unittest.mm b/chromium/ui/base/cocoa/events_mac_unittest.mm
index cf641c8dc7d..63f5319067e 100644
--- a/chromium/ui/base/cocoa/events_mac_unittest.mm
+++ b/chromium/ui/base/cocoa/events_mac_unittest.mm
@@ -5,8 +5,8 @@
#import <Cocoa/Cocoa.h>
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
#include "ui/base/test/cocoa_test_event_utils.h"
#import "ui/base/test/ui_cocoa_test_helper.h"
#include "ui/gfx/point.h"
diff --git a/chromium/ui/base/cocoa/focus_window_set.h b/chromium/ui/base/cocoa/focus_window_set.h
index af9c25386b2..d43ff2acf97 100644
--- a/chromium/ui/base/cocoa/focus_window_set.h
+++ b/chromium/ui/base/cocoa/focus_window_set.h
@@ -15,7 +15,8 @@ namespace ui {
// Brings a group of windows to the front without changing their order, and
// makes the frontmost one key and main. If none are visible, the frontmost
// miniaturized window is deminiaturized.
-UI_EXPORT void FocusWindowSet(const std::set<gfx::NativeWindow>& windows);
+UI_EXPORT void FocusWindowSet(const std::set<gfx::NativeWindow>& windows,
+ bool allow_workspace_switch);
} // namespace ui
diff --git a/chromium/ui/base/cocoa/focus_window_set.mm b/chromium/ui/base/cocoa/focus_window_set.mm
index 553db6fe3be..e260627d3ca 100644
--- a/chromium/ui/base/cocoa/focus_window_set.mm
+++ b/chromium/ui/base/cocoa/focus_window_set.mm
@@ -8,25 +8,56 @@
namespace ui {
-void FocusWindowSet(const std::set<NSWindow*>& windows) {
+// This attempts to match OS X's native behavior, namely that a window
+// is only ever deminiaturized if ALL windows on ALL workspaces are
+// miniaturized. (This callback runs before AppKit picks its own
+// window to deminiaturize, so we get to pick one from the right set.)
+//
+// In addition, limit to the windows on the current
+// workspace. Otherwise we jump spaces haphazardly.
+//
+// NOTE: This is not perfect. If clicking the dock icon resulted in
+// switching spaces, isOnActiveSpace gives the answer for the PREVIOUS
+// space. This means that we actually raise the wrong space's
+// windows. This seems to still work okay.
+//
+// However, if we decide to deminiaturize a window instead, that
+// results in switching spaces and switching back. Fortunately, this
+// only happens if, say, space 1 contains an app, space 2 contains a
+// miniaturized browser. We click the icon, OS X switches to space 1,
+// we deminiaturize the browser, and that triggers switching back.
+void FocusWindowSet(const std::set<NSWindow*>& windows,
+ bool allow_workspace_switch) {
NSArray* ordered_windows = [NSApp orderedWindows];
NSWindow* frontmost_window = nil;
+ NSWindow* frontmost_window_all_spaces = nil;
NSWindow* frontmost_miniaturized_window = nil;
+ bool all_miniaturized = true;
for (int i = [ordered_windows count] - 1; i >= 0; i--) {
NSWindow* win = [ordered_windows objectAtIndex:i];
if (windows.find(win) != windows.end()) {
- if ([win isVisible]) {
- [win orderFront:nil];
- frontmost_window = win;
- } else if ([win isMiniaturized]) {
+ if ([win isMiniaturized]) {
frontmost_miniaturized_window = win;
+ } else if ([win isVisible]) {
+ all_miniaturized = false;
+ frontmost_window_all_spaces = win;
+ if ([win isOnActiveSpace]) {
+ [win orderFront:nil];
+ frontmost_window = win;
+ }
}
}
}
- if (!frontmost_window && frontmost_miniaturized_window) {
+ if (all_miniaturized && frontmost_miniaturized_window) {
[frontmost_miniaturized_window deminiaturize:nil];
frontmost_window = frontmost_miniaturized_window;
}
+ // If we couldn't find one on this window, consider all spaces.
+ if (allow_workspace_switch &&
+ !frontmost_window && frontmost_window_all_spaces) {
+ frontmost_window = frontmost_window_all_spaces;
+ [frontmost_window orderFront:nil];
+ }
if (frontmost_window) {
[NSApp activateIgnoringOtherApps:YES];
[frontmost_window makeMainWindow];
diff --git a/chromium/ui/base/cocoa/menu_controller.mm b/chromium/ui/base/cocoa/menu_controller.mm
index 1179284924b..c7b8dff2fa3 100644
--- a/chromium/ui/base/cocoa/menu_controller.mm
+++ b/chromium/ui/base/cocoa/menu_controller.mm
@@ -11,8 +11,9 @@
#import "ui/base/cocoa/cocoa_event_utils.h"
#include "ui/base/l10n/l10n_util_mac.h"
#include "ui/base/models/simple_menu_model.h"
-#include "ui/base/text/text_elider.h"
+#include "ui/gfx/font.h"
#include "ui/gfx/image/image.h"
+#include "ui/gfx/text_elider.h"
@interface MenuController (Private)
- (void)addSeparatorToMenu:(NSMenu*)menu
@@ -29,7 +30,7 @@
NSFont* nsfont = [NSFont menuBarFontOfSize:0]; // 0 means "default"
gfx::Font font(base::SysNSStringToUTF8([nsfont fontName]),
static_cast<int>([nsfont pointSize]));
- return ui::ElideText(title, font, width, ui::ELIDE_AT_END);
+ return gfx::ElideText(title, font, width, gfx::ELIDE_AT_END);
}
- (id)init {
diff --git a/chromium/ui/base/cursor/cursor.h b/chromium/ui/base/cursor/cursor.h
index 43c201db37b..bb832fa9631 100644
--- a/chromium/ui/base/cursor/cursor.h
+++ b/chromium/ui/base/cursor/cursor.h
@@ -82,6 +82,11 @@ const int kCursorGrab = 42;
const int kCursorGrabbing = 43;
const int kCursorCustom = 44;
+enum CursorSetType {
+ CURSOR_SET_NORMAL,
+ CURSOR_SET_LARGE
+};
+
// Ref-counted cursor that supports both default and custom cursors.
class UI_EXPORT Cursor {
public:
diff --git a/chromium/ui/base/cursor/cursor_loader_win.cc b/chromium/ui/base/cursor/cursor_loader_win.cc
index 9d633f1cec8..6d35e554574 100644
--- a/chromium/ui/base/cursor/cursor_loader_win.cc
+++ b/chromium/ui/base/cursor/cursor_loader_win.cc
@@ -2,11 +2,16 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "ui/base/cursor/cursor_loader_win.h"
+
#include "base/lazy_instance.h"
#include "base/strings/string16.h"
-#include "ui/base/cursor/cursor_loader_win.h"
#include "grit/ui_unscaled_resources.h"
+#if defined(USE_AURA)
+#include "ui/base/cursor/cursor.h"
+#endif
+
namespace ui {
#if defined(USE_AURA)
diff --git a/chromium/ui/base/cursor/cursor_loader_x11.cc b/chromium/ui/base/cursor/cursor_loader_x11.cc
index e30b24cfb33..aa84173ff48 100644
--- a/chromium/ui/base/cursor/cursor_loader_x11.cc
+++ b/chromium/ui/base/cursor/cursor_loader_x11.cc
@@ -146,7 +146,7 @@ CursorLoader* CursorLoader::Create() {
}
CursorLoaderX11::CursorLoaderX11()
- : invisible_cursor_(CreateInvisibleCursor(), GetXDisplay()) {
+ : invisible_cursor_(CreateInvisibleCursor(), gfx::GetXDisplay()) {
}
CursorLoaderX11::~CursorLoaderX11() {
@@ -205,7 +205,7 @@ void CursorLoaderX11::LoadAnimatedCursor(int id,
}
animated_cursors_[id] = std::make_pair(
- XcursorImagesLoadCursor(GetXDisplay(), x_images), x_images);
+ XcursorImagesLoadCursor(gfx::GetXDisplay(), x_images), x_images);
// |bitmap| is owned by the resource bundle. So we do not need to free it.
}
@@ -218,7 +218,7 @@ void CursorLoaderX11::UnloadAll() {
for (AnimatedCursorMap::iterator it = animated_cursors_.begin();
it != animated_cursors_.end(); ++it) {
XcursorImagesDestroy(it->second.second); // also frees individual frames.
- XFreeCursor(GetXDisplay(), it->second.first);
+ XFreeCursor(gfx::GetXDisplay(), it->second.first);
}
}
diff --git a/chromium/ui/base/cursor/cursors_aura.cc b/chromium/ui/base/cursor/cursors_aura.cc
index 17349a7c458..bb5947a57e6 100644
--- a/chromium/ui/base/cursor/cursors_aura.cc
+++ b/chromium/ui/base/cursor/cursors_aura.cc
@@ -5,7 +5,6 @@
#include "ui/base/cursor/cursors_aura.h"
#include "grit/ui_resources.h"
-#include "ui/base/cursor/cursor.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/gfx/point.h"
@@ -24,7 +23,15 @@ struct CursorData {
HotPoint hot_2x;
};
-const CursorData kImageCursors[] = {
+struct CursorSet {
+ const CursorSetType id;
+ const CursorData* cursors;
+ const int length;
+ const CursorData* animated_cursors;
+ const int animated_length;
+};
+
+const CursorData kNormalCursors[] = {
{ui::kCursorNull, IDR_AURA_CURSOR_PTR, {4, 4}, {8, 9}},
{ui::kCursorPointer, IDR_AURA_CURSOR_PTR, {4, 4}, {8, 9}},
{ui::kCursorNoDrop, IDR_AURA_CURSOR_NO_DROP, {9, 9}, {18, 18}},
@@ -67,11 +74,80 @@ const CursorData kImageCursors[] = {
{ui::kCursorGrabbing, IDR_AURA_CURSOR_GRABBING, {9, 9}, {18, 18}},
};
+const CursorData kLargeCursors[] = {
+ {ui::kCursorNull, IDR_AURA_CURSOR_BIG_PTR, {10, 10}, {10, 10}},
+ {ui::kCursorPointer, IDR_AURA_CURSOR_BIG_PTR, {10, 10}, {10, 10}},
+ {ui::kCursorNoDrop, IDR_AURA_CURSOR_BIG_NO_DROP, {23, 23}, {23, 23}},
+ {ui::kCursorNotAllowed, IDR_AURA_CURSOR_BIG_NO_DROP, {23, 23}, {23, 23}},
+ {ui::kCursorCopy, IDR_AURA_CURSOR_BIG_COPY, {23, 23}, {23, 23}},
+ {ui::kCursorHand, IDR_AURA_CURSOR_BIG_HAND, {23, 10}, {23, 10}},
+ {ui::kCursorMove, IDR_AURA_CURSOR_BIG_MOVE, {28, 28}, {28, 28}},
+ {ui::kCursorNorthEastResize, IDR_AURA_CURSOR_BIG_NORTH_EAST_RESIZE,
+ {31, 28}, {31, 28}},
+ {ui::kCursorSouthWestResize, IDR_AURA_CURSOR_BIG_SOUTH_WEST_RESIZE,
+ {31, 28}, {31, 28}},
+ {ui::kCursorSouthEastResize, IDR_AURA_CURSOR_BIG_SOUTH_EAST_RESIZE,
+ {28, 28}, {28, 28}},
+ {ui::kCursorNorthWestResize, IDR_AURA_CURSOR_BIG_NORTH_WEST_RESIZE,
+ {28, 28}, {28, 28}},
+ {ui::kCursorNorthResize, IDR_AURA_CURSOR_BIG_NORTH_RESIZE,
+ {28, 31}, {28, 31}},
+ {ui::kCursorSouthResize, IDR_AURA_CURSOR_BIG_SOUTH_RESIZE,
+ {28, 31}, {28, 31}},
+ {ui::kCursorEastResize, IDR_AURA_CURSOR_BIG_EAST_RESIZE, {31, 28}, {31, 28}},
+ {ui::kCursorWestResize, IDR_AURA_CURSOR_BIG_WEST_RESIZE, {31, 28}, {31, 28}},
+ {ui::kCursorIBeam, IDR_AURA_CURSOR_BIG_IBEAM, {31, 31}, {31, 31}},
+ {ui::kCursorAlias, IDR_AURA_CURSOR_BIG_ALIAS, {51, 15}, {51, 11}},
+ {ui::kCursorCell, IDR_AURA_CURSOR_BIG_CELL, {28, 28}, {24, 23}},
+ {ui::kCursorContextMenu, IDR_AURA_CURSOR_BIG_CONTEXT_MENU, {4, 4}, {8, 9}},
+ {ui::kCursorCross, IDR_AURA_CURSOR_BIG_CROSSHAIR, {31, 31}, {31, 31}},
+ {ui::kCursorHelp, IDR_AURA_CURSOR_BIG_HELP, {10, 10}, {8, 9}},
+ {ui::kCursorVerticalText, IDR_AURA_CURSOR_BIG_XTERM_HORIZ,
+ {31, 28}, {31, 28}},
+ {ui::kCursorZoomIn, IDR_AURA_CURSOR_BIG_ZOOM_IN, {26, 26}, {26, 26}},
+ {ui::kCursorZoomOut, IDR_AURA_CURSOR_BIG_ZOOM_OUT, {26, 26}, {26, 26}},
+ {ui::kCursorRowResize, IDR_AURA_CURSOR_BIG_ROW_RESIZE, {28, 31}, {28, 31}},
+ {ui::kCursorColumnResize, IDR_AURA_CURSOR_BIG_COL_RESIZE, {31, 28}, {31, 28}},
+ {ui::kCursorEastWestResize, IDR_AURA_CURSOR_BIG_EAST_WEST_RESIZE,
+ {31, 28}, {31, 28}},
+ {ui::kCursorNorthSouthResize, IDR_AURA_CURSOR_BIG_NORTH_SOUTH_RESIZE,
+ {28, 31}, {28, 31}},
+ {ui::kCursorNorthEastSouthWestResize,
+ IDR_AURA_CURSOR_BIG_NORTH_EAST_SOUTH_WEST_RESIZE, {31, 28}, {31, 28}},
+ {ui::kCursorNorthWestSouthEastResize,
+ IDR_AURA_CURSOR_BIG_NORTH_WEST_SOUTH_EAST_RESIZE, {28, 28}, {28, 28}},
+ {ui::kCursorGrab, IDR_AURA_CURSOR_BIG_GRAB, {20, 13}, {20, 13}},
+ {ui::kCursorGrabbing, IDR_AURA_CURSOR_BIG_GRABBING, {23, 23}, {23, 23}},
+};
+
const CursorData kAnimatedCursors[] = {
{ui::kCursorWait, IDR_THROBBER, {7, 7}, {14, 14}},
{ui::kCursorProgress, IDR_THROBBER, {7, 7}, {14, 14}},
};
+const CursorSet kCursorSets[] = {
+ {
+ CURSOR_SET_NORMAL,
+ kNormalCursors, arraysize(kNormalCursors),
+ kAnimatedCursors, arraysize(kAnimatedCursors)
+ },
+ {
+ CURSOR_SET_LARGE,
+ kLargeCursors, arraysize(kLargeCursors),
+ // TODO(yoshiki): Replace animated cursors with big assets. crbug.com/247254
+ kAnimatedCursors, arraysize(kAnimatedCursors)
+ },
+};
+
+const CursorSet* GetCursorSetByType(CursorSetType cursor_set_id) {
+ for (size_t i = 0; i < arraysize(kCursorSets); ++i) {
+ if (kCursorSets[i].id == cursor_set_id)
+ return &kCursorSets[i];
+ }
+
+ return NULL;
+}
+
bool SearchTable(const CursorData* table,
size_t table_length,
int id,
@@ -96,19 +172,45 @@ bool SearchTable(const CursorData* table,
} // namespace
-bool GetCursorDataFor(int id,
+bool GetCursorDataFor(CursorSetType cursor_set_id,
+ int id,
float scale_factor,
int* resource_id,
gfx::Point* point) {
- return SearchTable(kImageCursors, arraysize(kImageCursors),
+ const CursorSet* cursor_set = GetCursorSetByType(cursor_set_id);
+ if (cursor_set &&
+ SearchTable(cursor_set->cursors,
+ cursor_set->length,
+ id, scale_factor, resource_id, point)) {
+ return true;
+ }
+
+ // Falls back to the default cursor set.
+ cursor_set = GetCursorSetByType(ui::CURSOR_SET_NORMAL);
+ DCHECK(cursor_set);
+ return SearchTable(cursor_set->cursors,
+ cursor_set->length,
id, scale_factor, resource_id, point);
}
-bool GetAnimatedCursorDataFor(int id,
+bool GetAnimatedCursorDataFor(CursorSetType cursor_set_id,
+ int id,
float scale_factor,
int* resource_id,
gfx::Point* point) {
- return SearchTable(kAnimatedCursors, arraysize(kAnimatedCursors),
+ const CursorSet* cursor_set = GetCursorSetByType(cursor_set_id);
+ if (cursor_set &&
+ SearchTable(cursor_set->animated_cursors,
+ cursor_set->animated_length,
+ id, scale_factor, resource_id, point)) {
+ return true;
+ }
+
+ // Falls back to the default cursor set.
+ cursor_set = GetCursorSetByType(ui::CURSOR_SET_NORMAL);
+ DCHECK(cursor_set);
+ return SearchTable(cursor_set->animated_cursors,
+ cursor_set->animated_length,
id, scale_factor, resource_id, point);
}
diff --git a/chromium/ui/base/cursor/cursors_aura.h b/chromium/ui/base/cursor/cursors_aura.h
index 4565a704e76..e916c28575e 100644
--- a/chromium/ui/base/cursor/cursors_aura.h
+++ b/chromium/ui/base/cursor/cursors_aura.h
@@ -5,6 +5,7 @@
#ifndef UI_BASE_CURSOR_CURSORS_AURA_H_
#define UI_BASE_CURSOR_CURSORS_AURA_H_
+#include "ui/base/cursor/cursor.h"
#include "ui/base/ui_export.h"
namespace gfx {
@@ -19,13 +20,15 @@ const int kAnimatedCursorFrameDelayMs = 25;
// ui::kCursorHelp. The IDR will be placed in |resource_id| and the hotspots
// for the different DPIs will be placed in |hot_1x| and |hot_2x|. Returns
// false if |id| is invalid.
-bool UI_EXPORT GetCursorDataFor(int id,
+bool UI_EXPORT GetCursorDataFor(CursorSetType cursor_set_id,
+ int id,
float scale_factor,
int* resource_id,
gfx::Point* point);
// Like above, but for animated cursors.
-bool UI_EXPORT GetAnimatedCursorDataFor(int id,
+bool UI_EXPORT GetAnimatedCursorDataFor(CursorSetType cursor_set_id,
+ int id,
float scale_factor,
int* resource_id,
gfx::Point* point);
diff --git a/chromium/ui/base/default_theme_provider.cc b/chromium/ui/base/default_theme_provider.cc
index e60c90029ce..9777b390729 100644
--- a/chromium/ui/base/default_theme_provider.cc
+++ b/chromium/ui/base/default_theme_provider.cc
@@ -26,8 +26,8 @@ SkColor DefaultThemeProvider::GetColor(int id) const {
return 0xff0000ff;
}
-bool DefaultThemeProvider::GetDisplayProperty(int id, int* result) const {
- return false;
+int DefaultThemeProvider::GetDisplayProperty(int id) const {
+ return -1;
}
bool DefaultThemeProvider::ShouldUseNativeFrame() const {
diff --git a/chromium/ui/base/default_theme_provider.h b/chromium/ui/base/default_theme_provider.h
index 2594dfbf66a..15fa4a9f487 100644
--- a/chromium/ui/base/default_theme_provider.h
+++ b/chromium/ui/base/default_theme_provider.h
@@ -26,7 +26,7 @@ class UI_EXPORT DefaultThemeProvider : public ThemeProvider {
// Overridden from ui::ThemeProvider:
virtual gfx::ImageSkia* GetImageSkiaNamed(int id) const OVERRIDE;
virtual SkColor GetColor(int id) const OVERRIDE;
- virtual bool GetDisplayProperty(int id, int* result) const OVERRIDE;
+ virtual int GetDisplayProperty(int id) const OVERRIDE;
virtual bool ShouldUseNativeFrame() const OVERRIDE;
virtual bool HasCustomImage(int id) const OVERRIDE;
virtual base::RefCountedMemory* GetRawData(
diff --git a/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11.cc b/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11.cc
index 52aa7c6dce2..ffd0a3c4b04 100644
--- a/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11.cc
+++ b/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11.cc
@@ -6,7 +6,7 @@
#include "base/logging.h"
#include "base/memory/ref_counted_memory.h"
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "net/base/net_util.h"
@@ -42,7 +42,7 @@ const char* kAtomsToCache[] = {
OSExchangeDataProviderAuraX11::OSExchangeDataProviderAuraX11(
::Window x_window,
const SelectionFormatMap& selection)
- : x_display_(GetXDisplay()),
+ : x_display_(gfx::GetXDisplay()),
x_root_window_(DefaultRootWindow(x_display_)),
own_window_(false),
x_window_(x_window),
@@ -55,7 +55,7 @@ OSExchangeDataProviderAuraX11::OSExchangeDataProviderAuraX11(
}
OSExchangeDataProviderAuraX11::OSExchangeDataProviderAuraX11()
- : x_display_(GetXDisplay()),
+ : x_display_(gfx::GetXDisplay()),
x_root_window_(DefaultRootWindow(x_display_)),
own_window_(true),
x_window_(XCreateWindow(
@@ -77,12 +77,12 @@ OSExchangeDataProviderAuraX11::OSExchangeDataProviderAuraX11()
XStoreName(x_display_, x_window_, "Chromium Drag & Drop Window");
- base::MessagePumpAuraX11::Current()->AddDispatcherForWindow(this, x_window_);
+ base::MessagePumpX11::Current()->AddDispatcherForWindow(this, x_window_);
}
OSExchangeDataProviderAuraX11::~OSExchangeDataProviderAuraX11() {
if (own_window_) {
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(x_window_);
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(x_window_);
XDestroyWindow(x_display_, x_window_);
}
}
@@ -196,13 +196,14 @@ bool OSExchangeDataProviderAuraX11::GetURLAndTitle(
std::vector<base::string16> tokens;
size_t num_tokens = Tokenize(unparsed, ASCIIToUTF16("\n"), &tokens);
- if (num_tokens >= 2) {
+ if (num_tokens > 0) {
+ if (num_tokens > 1)
+ *title = tokens[1];
+ else
+ *title = string16();
+
*url = GURL(tokens[0]);
- *title = tokens[1];
return true;
- } else {
- NOTREACHED() << "Data that claimed to be a Mozilla URL has "
- << num_tokens << " tokens instead of 2.";
}
} else if (data.GetType() == atom_cache_.GetAtom(
Clipboard::kMimeTypeURIList)) {
diff --git a/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11_unittest.cc b/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11_unittest.cc
new file mode 100644
index 00000000000..c3a944aa9e5
--- /dev/null
+++ b/chromium/ui/base/dragdrop/os_exchange_data_provider_aurax11_unittest.cc
@@ -0,0 +1,43 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/dragdrop/os_exchange_data_provider_aurax11.h"
+
+// Clean up X11 header polution
+#undef None
+#undef Bool
+
+#include "base/message_loop/message_loop.h"
+#include "base/strings/string16.h"
+#include "base/strings/utf_string_conversions.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "url/gurl.h"
+
+const char kGoogleTitle[] = "Google";
+const char kGoogleURL[] = "http://www.google.com/";
+
+TEST(OSExchangeDataProviderAuraX11Test, MozillaURL) {
+ base::MessageLoopForUI message_loop;
+ ui::OSExchangeDataProviderAuraX11 provider;
+
+ // Check that we can get titled entries.
+ provider.SetURL(GURL(kGoogleURL), ASCIIToUTF16(kGoogleTitle));
+ {
+ GURL out_gurl;
+ base::string16 out_str;
+ EXPECT_TRUE(provider.GetURLAndTitle(&out_gurl, &out_str));
+ EXPECT_EQ(ASCIIToUTF16(kGoogleTitle), out_str);
+ EXPECT_EQ(kGoogleURL, out_gurl.spec());
+ }
+
+ // Check that we can get non-titled entries.
+ provider.SetURL(GURL(kGoogleURL), string16());
+ {
+ GURL out_gurl;
+ base::string16 out_str;
+ EXPECT_TRUE(provider.GetURLAndTitle(&out_gurl, &out_str));
+ EXPECT_EQ(string16(), out_str);
+ EXPECT_EQ(kGoogleURL, out_gurl.spec());
+ }
+}
diff --git a/chromium/ui/base/events/event_conversion_gtk.cc b/chromium/ui/base/events/event_conversion_gtk.cc
deleted file mode 100644
index bc15dac260b..00000000000
--- a/chromium/ui/base/events/event_conversion_gtk.cc
+++ /dev/null
@@ -1,33 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/base/events/event_conversion_gtk.h"
-
-#include "ui/base/events/event_constants.h"
-
-namespace ui {
-
-int GdkModifierToEventFlag(GdkModifierType gdk_modifier) {
- int event_flags = 0;
- if (gdk_modifier & GDK_SHIFT_MASK)
- event_flags |= EF_SHIFT_DOWN;
- if (gdk_modifier & GDK_CONTROL_MASK)
- event_flags |= EF_CONTROL_DOWN;
- if (gdk_modifier & GDK_MOD1_MASK)
- event_flags |= EF_ALT_DOWN;
- return event_flags;
-}
-
-GdkModifierType EventFlagToGdkModifier(int event_flag) {
- int modifier = 0;
- if (event_flag & EF_SHIFT_DOWN)
- modifier |= GDK_SHIFT_MASK;
- if (event_flag & EF_CONTROL_DOWN)
- modifier |= GDK_CONTROL_MASK;
- if (event_flag & EF_ALT_DOWN)
- modifier |= GDK_MOD1_MASK;
- return static_cast<GdkModifierType>(modifier);
-}
-
-} // namespace ui
diff --git a/chromium/ui/base/events/event_conversion_gtk.h b/chromium/ui/base/events/event_conversion_gtk.h
deleted file mode 100644
index a78d09230af..00000000000
--- a/chromium/ui/base/events/event_conversion_gtk.h
+++ /dev/null
@@ -1,20 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_BASE_EVENTS_EVENT_CONVERSION_GTK_H_
-#define UI_BASE_EVENTS_EVENT_CONVERSION_GTK_H_
-
-#include <gtk/gtk.h>
-
-#include "ui/base/ui_export.h"
-
-namespace ui {
-
-UI_EXPORT int GdkModifierToEventFlag(GdkModifierType gdk_modifier);
-
-UI_EXPORT GdkModifierType EventFlagToGdkModifier(int event_flag);
-
-} // namespace ui
-
-#endif // UI_BASE_EVENTS_EVENT_CONVERSION_GTK_H_
diff --git a/chromium/ui/base/gestures/gesture_configuration.cc b/chromium/ui/base/gestures/gesture_configuration.cc
index 89d09b0954f..1d1cb73c37a 100644
--- a/chromium/ui/base/gestures/gesture_configuration.cc
+++ b/chromium/ui/base/gestures/gesture_configuration.cc
@@ -21,14 +21,14 @@ double
double GestureConfiguration::max_swipe_deviation_ratio_ = 3;
double
GestureConfiguration::max_touch_down_duration_in_seconds_for_click_ = 0.8;
-double GestureConfiguration::max_touch_move_in_pixels_for_click_ = 10;
+double GestureConfiguration::max_touch_move_in_pixels_for_click_ = 25;
double GestureConfiguration::max_distance_between_taps_for_double_tap_ = 20;
double GestureConfiguration::min_distance_for_pinch_scroll_in_pixels_ = 20;
double GestureConfiguration::min_flick_speed_squared_ = 550.f * 550.f;
double GestureConfiguration::min_pinch_update_distance_in_pixels_ = 5;
double GestureConfiguration::min_rail_break_velocity_ = 200;
double GestureConfiguration::min_scroll_delta_squared_ = 4 * 4;
-int GestureConfiguration::min_scroll_successive_velocity_events_ = 3;
+int GestureConfiguration::min_scroll_successive_velocity_events_ = 4;
float GestureConfiguration::min_scroll_velocity_ = 30.0f;
double GestureConfiguration::min_swipe_speed_ = 20;
double GestureConfiguration::scroll_prediction_seconds_ = 0.03;
diff --git a/chromium/ui/base/gestures/gesture_configuration.h b/chromium/ui/base/gestures/gesture_configuration.h
index 68d2573d5b2..3b4df56fdf4 100644
--- a/chromium/ui/base/gestures/gesture_configuration.h
+++ b/chromium/ui/base/gestures/gesture_configuration.h
@@ -232,7 +232,6 @@ class UI_EXPORT GestureConfiguration {
static double min_pinch_update_distance_in_pixels_;
static double min_rail_break_velocity_;
static double min_scroll_delta_squared_;
- // TODO(rjkroege): Expose these in chrome://gesture
static int min_scroll_successive_velocity_events_;
static float min_scroll_velocity_;
static double min_swipe_speed_;
diff --git a/chromium/ui/base/gestures/gesture_point.cc b/chromium/ui/base/gestures/gesture_point.cc
index 105779b17c2..2233bf11dc1 100644
--- a/chromium/ui/base/gestures/gesture_point.cc
+++ b/chromium/ui/base/gestures/gesture_point.cc
@@ -7,11 +7,11 @@
#include <cmath>
#include "base/basictypes.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/gestures/gesture_configuration.h"
#include "ui/base/gestures/gesture_types.h"
#include "ui/base/gestures/gesture_util.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
namespace ui {
@@ -107,6 +107,8 @@ bool GesturePoint::IsInTripleClickWindow(const TouchEvent& event) const {
}
bool GesturePoint::IsInScrollWindow(const TouchEvent& event) const {
+ if (IsConsistentScrollingActionUnderway())
+ return true;
return event.type() == ui::ET_TOUCH_MOVED &&
!IsInsideManhattanSquare(event);
}
@@ -130,7 +132,7 @@ bool GesturePoint::DidScroll(const TouchEvent& event, int dist) const {
return abs(d.x()) > dist || abs(d.y()) > dist;
}
-bool GesturePoint::IsConsistentScrollingActionUnderway() {
+bool GesturePoint::IsConsistentScrollingActionUnderway() const {
int me = GestureConfiguration::min_scroll_successive_velocity_events();
if (abs(same_direction_count_.x()) >= me ||
abs(same_direction_count_.y()) >= me)
diff --git a/chromium/ui/base/gestures/gesture_point.h b/chromium/ui/base/gestures/gesture_point.h
index b84c3bd7a3f..60dad3207fb 100644
--- a/chromium/ui/base/gestures/gesture_point.h
+++ b/chromium/ui/base/gestures/gesture_point.h
@@ -40,11 +40,11 @@ class GesturePoint {
bool IsInClickWindow(const TouchEvent& event) const;
bool IsInDoubleClickWindow(const TouchEvent& event) const;
bool IsInTripleClickWindow(const TouchEvent& event) const;
- bool IsInScrollWindow(const TouchEvent& event) const;
bool IsInFlickWindow(const TouchEvent& event);
bool IsInHorizontalRailWindow() const;
bool IsInVerticalRailWindow() const;
bool IsInsideManhattanSquare(const TouchEvent& event) const;
+ bool IsInScrollWindow(const TouchEvent& event) const;
bool BreaksHorizontalRail();
bool BreaksVerticalRail();
bool DidScroll(const TouchEvent& event, int distance) const;
@@ -79,12 +79,12 @@ class GesturePoint {
const gfx::Rect& enclosing_rectangle() const { return enclosing_rect_; }
- // Tests if the point has a consistent scroll vector across a window of touch
- // move events.
- bool IsConsistentScrollingActionUnderway();
-
private:
// Various statistical functions to manipulate gestures.
+
+ // Tests if the point has a consistent scroll vector across a window of touch
+ // move events.
+ bool IsConsistentScrollingActionUnderway() const;
bool IsInClickTimeWindow() const;
bool IsInClickAggregateTimeWindow(double before, double after) const;
bool IsPointInsideManhattanSquare(gfx::Point p1, gfx::Point p2) const;
diff --git a/chromium/ui/base/gestures/gesture_recognizer.h b/chromium/ui/base/gestures/gesture_recognizer.h
index b32bade8289..dbb139bc7d8 100644
--- a/chromium/ui/base/gestures/gesture_recognizer.h
+++ b/chromium/ui/base/gestures/gesture_recognizer.h
@@ -8,9 +8,9 @@
#include <vector>
#include "base/memory/scoped_vector.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/gestures/gesture_types.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
namespace ui {
// A GestureRecognizer is an abstract base class for conversion of touch events
@@ -25,7 +25,7 @@ class UI_EXPORT GestureRecognizer {
virtual ~GestureRecognizer() {}
// Invoked for each touch event that could contribute to the current gesture.
- // Returns list of zero or more GestureEvents identified after processing
+ // Returns list of zero or more GestureEvents identified after processing
// TouchEvent.
// Caller would be responsible for freeing up Gestures.
virtual Gestures* ProcessTouchEventForGesture(const TouchEvent& event,
diff --git a/chromium/ui/base/gestures/gesture_recognizer_impl.cc b/chromium/ui/base/gestures/gesture_recognizer_impl.cc
index 0e315a16cca..51aaa3033bd 100644
--- a/chromium/ui/base/gestures/gesture_recognizer_impl.cc
+++ b/chromium/ui/base/gestures/gesture_recognizer_impl.cc
@@ -7,12 +7,12 @@
#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
#include "base/time/time.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/gestures/gesture_configuration.h"
#include "ui/base/gestures/gesture_sequence.h"
#include "ui/base/gestures/gesture_types.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
namespace ui {
diff --git a/chromium/ui/base/gestures/gesture_recognizer_impl.h b/chromium/ui/base/gestures/gesture_recognizer_impl.h
index 812bc057578..5f9caf25c02 100644
--- a/chromium/ui/base/gestures/gesture_recognizer_impl.h
+++ b/chromium/ui/base/gestures/gesture_recognizer_impl.h
@@ -10,9 +10,9 @@
#include "base/memory/linked_ptr.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/gestures/gesture_recognizer.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/point.h"
namespace ui {
diff --git a/chromium/ui/base/gestures/gesture_sequence.cc b/chromium/ui/base/gestures/gesture_sequence.cc
index b4f32e4b50d..5d3619daa0b 100644
--- a/chromium/ui/base/gestures/gesture_sequence.cc
+++ b/chromium/ui/base/gestures/gesture_sequence.cc
@@ -12,11 +12,11 @@
#include "base/memory/scoped_ptr.h"
#include "base/strings/string_number_conversions.h"
#include "base/time/time.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/gestures/gesture_configuration.h"
#include "ui/base/gestures/gesture_util.h"
#include "ui/base/ui_base_switches.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/rect.h"
namespace ui {
@@ -108,6 +108,27 @@ enum EdgeStateSignatureType {
GST_PENDING_SYNTHETIC_CLICK_SECOND_PRESSED =
G(GS_PENDING_SYNTHETIC_CLICK, 1, TS_PRESSED, TSI_NOT_PROCESSED),
+ GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_RELEASED =
+ G(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL,
+ 0,
+ TS_RELEASED,
+ TSI_NOT_PROCESSED),
+
+ GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_RELEASED_HANDLED =
+ G(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL, 0, TS_RELEASED, TSI_PROCESSED),
+
+ GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_MOVED =
+ G(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL, 0, TS_MOVED, TSI_ALWAYS),
+
+ GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_STATIONARY =
+ G(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL, 0, TS_STATIONARY, TSI_ALWAYS),
+
+ GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_CANCELLED =
+ G(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL, 0, TS_CANCELLED, TSI_ALWAYS),
+
+ GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_SECOND_PRESSED =
+ G(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL, 1, TS_PRESSED, TSI_NOT_PROCESSED),
+
GST_SCROLL_FIRST_RELEASED =
G(GS_SCROLL, 0, TS_RELEASED, TSI_ALWAYS),
@@ -243,6 +264,12 @@ EdgeStateSignatureType Signature(GestureState gesture_state,
case GST_PENDING_SYNTHETIC_CLICK_FIRST_STATIONARY:
case GST_PENDING_SYNTHETIC_CLICK_FIRST_CANCELLED:
case GST_PENDING_SYNTHETIC_CLICK_SECOND_PRESSED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_RELEASED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_RELEASED_HANDLED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_MOVED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_STATIONARY:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_CANCELLED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_SECOND_PRESSED:
case GST_SCROLL_FIRST_RELEASED:
case GST_SCROLL_FIRST_MOVED:
case GST_SCROLL_FIRST_CANCELLED:
@@ -419,15 +446,26 @@ GestureSequence::Gestures* GestureSequence::ProcessTouchEventForGesture(
point.UpdateForScroll();
}
break;
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_MOVED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_STATIONARY:
+ // No scrolling allowed, so nothing happens.
+ break;
case GST_PENDING_SYNTHETIC_CLICK_FIRST_MOVED_PROCESSED:
- // TODO(rbyers): This should be able to trigger a TapCancel
- // if we moved far enough. crbug.com/146397
+ if (point.IsInScrollWindow(event)) {
+ PrependTapCancelGestureEvent(point, gestures.get());
+ set_state(GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL);
+ }
break;
case GST_PENDING_SYNTHETIC_CLICK_FIRST_RELEASED_HANDLED:
case GST_PENDING_SYNTHETIC_CLICK_FIRST_CANCELLED:
PrependTapCancelGestureEvent(point, gestures.get());
set_state(GS_NO_GESTURE);
break;
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_RELEASED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_RELEASED_HANDLED:
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_FIRST_CANCELLED:
+ set_state(GS_NO_GESTURE);
+ break;
case GST_SCROLL_FIRST_MOVED:
if (scroll_type_ == ST_VERTICAL ||
scroll_type_ == ST_HORIZONTAL)
@@ -442,12 +480,11 @@ GestureSequence::Gestures* GestureSequence::ProcessTouchEventForGesture(
break;
case GST_PENDING_SYNTHETIC_CLICK_SECOND_PRESSED:
PrependTapCancelGestureEvent(point, gestures.get());
- if (IsSecondTouchDownCloseEnoughForTwoFingerTap()) {
- TwoFingerTouchDown(event, point, gestures.get());
- set_state(GS_PENDING_TWO_FINGER_TAP);
- break;
- }
- // fall through
+ TwoFingerTapOrPinch(event, point, gestures.get());
+ break;
+ case GST_PENDING_SYNTHETIC_CLICK_NO_SCROLL_SECOND_PRESSED:
+ TwoFingerTapOrPinch(event, point, gestures.get());
+ break;
case GST_SCROLL_SECOND_PRESSED:
PinchStart(event, point, gestures.get());
set_state(GS_PINCH);
@@ -901,8 +938,7 @@ bool GestureSequence::ScrollStart(const TouchEvent& event,
GesturePoint& point,
Gestures* gestures) {
DCHECK(state_ == GS_PENDING_SYNTHETIC_CLICK);
- if (!point.IsConsistentScrollingActionUnderway() &&
- !point.IsInScrollWindow(event))
+ if (!point.IsInScrollWindow(event))
return false;
AppendScrollGestureBegin(point, point.first_touch_position(), gestures);
if (point.IsInHorizontalRailWindow())
@@ -953,7 +989,10 @@ bool GestureSequence::TouchDown(const TouchEvent& event,
bool GestureSequence::TwoFingerTouchDown(const TouchEvent& event,
const GesturePoint& point,
Gestures* gestures) {
- DCHECK(state_ == GS_PENDING_SYNTHETIC_CLICK || state_ == GS_SCROLL);
+ DCHECK(state_ == GS_PENDING_SYNTHETIC_CLICK ||
+ state_ == GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL ||
+ state_ == GS_SCROLL);
+
if (state_ == GS_SCROLL) {
AppendScrollGestureEnd(point, point.last_touch_position(), gestures,
0.f, 0.f);
@@ -1171,6 +1210,19 @@ bool GestureSequence::MaybeSwipe(const TouchEvent& event,
return true;
}
+void GestureSequence::TwoFingerTapOrPinch(const TouchEvent& event,
+ const GesturePoint& point,
+ Gestures* gestures) {
+ if (IsSecondTouchDownCloseEnoughForTwoFingerTap()) {
+ TwoFingerTouchDown(event, point, gestures);
+ set_state(GS_PENDING_TWO_FINGER_TAP);
+ } else {
+ PinchStart(event, point, gestures);
+ set_state(GS_PINCH);
+ }
+}
+
+
void GestureSequence::StopLongPressTimerIfRequired(const TouchEvent& event) {
if (!GetLongPressTimer()->IsRunning() ||
event.type() != ui::ET_TOUCH_MOVED)
diff --git a/chromium/ui/base/gestures/gesture_sequence.h b/chromium/ui/base/gestures/gesture_sequence.h
index 9aff570dd93..ddb90834338 100644
--- a/chromium/ui/base/gestures/gesture_sequence.h
+++ b/chromium/ui/base/gestures/gesture_sequence.h
@@ -6,9 +6,9 @@
#define UI_BASE_GESTURES_GESTURE_SEQUENCE_H_
#include "base/timer/timer.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/gestures/gesture_point.h"
#include "ui/base/gestures/gesture_recognizer.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/rect.h"
namespace ui {
@@ -19,6 +19,7 @@ class GestureEvent;
enum GestureState {
GS_NO_GESTURE,
GS_PENDING_SYNTHETIC_CLICK,
+ GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL,
GS_SCROLL,
GS_PINCH,
GS_PENDING_TWO_FINGER_TAP,
@@ -171,6 +172,10 @@ class UI_EXPORT GestureSequence {
const GesturePoint& point,
Gestures* gestures);
+ void TwoFingerTapOrPinch(const TouchEvent& event,
+ const GesturePoint& point,
+ Gestures* gestures);
+
void StopLongPressTimerIfRequired(const TouchEvent& event);
// Current state of gesture recognizer.
diff --git a/chromium/ui/base/gestures/gesture_types.h b/chromium/ui/base/gestures/gesture_types.h
index 584ea171338..bea1553fe38 100644
--- a/chromium/ui/base/gestures/gesture_types.h
+++ b/chromium/ui/base/gestures/gesture_types.h
@@ -6,7 +6,7 @@
#define UI_BASE_GESTURES_GESTURE_TYPES_H_
#include "base/logging.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/rect.h"
namespace ui {
diff --git a/chromium/ui/base/gestures/gestures.dot b/chromium/ui/base/gestures/gestures.dot
index 868c5421eb6..8524930d8db 100644
--- a/chromium/ui/base/gestures/gestures.dot
+++ b/chromium/ui/base/gestures/gestures.dot
@@ -1,6 +1,6 @@
// A diagram of the state machine found in gesture_sequence.cc
// To generate a pdf:
-// dot -Tpdf -ooutput.pdf gestures.dot
+// dot -Tpdf -ooutput.pdf gestures.dot
//
// If you alter this diagram, please update:
// sites.google.com/a/chromium.org/dev/developers/design-documents/aura/gesture-recognizer
@@ -17,25 +17,31 @@ R : Release \l\
M_Delay : Move after a certain delay}"
shape = record]
-subgraph none_pending {
GS_NO_GESTURE -> GS_PENDING_SYNTHETIC_CLICK [label= "D0"];
+
GS_PENDING_SYNTHETIC_CLICK -> GS_SCROLL [label= "M0\n S0"];
GS_PENDING_SYNTHETIC_CLICK -> GS_PENDING_SYNTHETIC_CLICK [label= "M0\n S0"];
GS_PENDING_SYNTHETIC_CLICK -> GS_NO_GESTURE [label= "C0\n R0"];
-}
+GS_PENDING_SYNTHETIC_CLICK -> GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL [label= "M0"];
+GS_PENDING_SYNTHETIC_CLICK -> GS_PENDING_TWO_FINGER_TAP [label= "D1"];
+
+GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL -> GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL [label= "M0\n S0"];
+GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL -> GS_NO_GESTURE [label= "C0\n R0"];
+GS_PENDING_SYNTHETIC_CLICK_NO_SCROLL -> GS_PENDING_TWO_FINGER_TAP [label= "D1"];
GS_SCROLL -> GS_SCROLL [label= "M0"];
GS_SCROLL -> GS_NO_GESTURE [label= "C0\n R0\n"];
-GS_PENDING_SYNTHETIC_CLICK -> GS_PENDING_TWO_FINGER_TAP [label= "D1"];
GS_SCROLL -> GS_PENDING_TWO_FINGER_TAP [label= "D1"];
+
GS_PENDING_TWO_FINGER_TAP -> GS_PINCH [label= "M0\n M1"];
GS_PENDING_TWO_FINGER_TAP -> GS_PINCH [label= "M_Delay0\n M_Delay1"];
GS_PENDING_TWO_FINGER_TAP -> GS_PINCH [label= "D2"];
GS_PENDING_TWO_FINGER_TAP -> GS_SCROLL [label= "R0\n R1\n C0\n C1"];
+
GS_PINCH -> GS_PINCH [label= "M0\n M1"];
GS_PINCH -> GS_SCROLL [label= "C0\n R0\n C1\n R1"];
-
GS_PINCH -> GS_PENDING_THREE_FINGER_SWIPE [label= "D2"];
+
GS_PENDING_THREE_FINGER_SWIPE -> GS_PINCH [label= "C0\n R0\n C1\n R1\n C2\n R2"];
GS_PENDING_THREE_FINGER_SWIPE -> GS_PENDING_THREE_FINGER_SWIPE [label= "M0\n M1\n M2"];
-}
+} \ No newline at end of file
diff --git a/chromium/ui/base/gtk/event_synthesis_gtk.cc b/chromium/ui/base/gtk/event_synthesis_gtk.cc
index bd3cb8aa220..ea56162dd22 100644
--- a/chromium/ui/base/gtk/event_synthesis_gtk.cc
+++ b/chromium/ui/base/gtk/event_synthesis_gtk.cc
@@ -4,7 +4,7 @@
#include "ui/base/gtk/event_synthesis_gtk.h"
-#include "ui/base/keycodes/keyboard_code_conversion_gtk.h"
+#include "ui/events/keycodes/keyboard_code_conversion_gtk.h"
namespace ui {
diff --git a/chromium/ui/base/gtk/event_synthesis_gtk.h b/chromium/ui/base/gtk/event_synthesis_gtk.h
index 50dde0f08c5..1839e29949a 100644
--- a/chromium/ui/base/gtk/event_synthesis_gtk.h
+++ b/chromium/ui/base/gtk/event_synthesis_gtk.h
@@ -13,8 +13,8 @@
#include <gdk/gdkkeysyms.h>
#include <vector>
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/ui_export.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace ui {
diff --git a/chromium/ui/base/gtk/gtk_expanded_container.cc b/chromium/ui/base/gtk/gtk_expanded_container.cc
index 30fc3db58b6..6b39821d806 100644
--- a/chromium/ui/base/gtk/gtk_expanded_container.cc
+++ b/chromium/ui/base/gtk/gtk_expanded_container.cc
@@ -8,7 +8,7 @@
#include <algorithm>
-#include "ui/base/gtk/gtk_compat.h"
+#include "ui/gfx/gtk_compat.h"
namespace {
diff --git a/chromium/ui/base/gtk/gtk_floating_container.cc b/chromium/ui/base/gtk/gtk_floating_container.cc
index 929216eab22..dd1ac26b0a2 100644
--- a/chromium/ui/base/gtk/gtk_floating_container.cc
+++ b/chromium/ui/base/gtk/gtk_floating_container.cc
@@ -8,7 +8,7 @@
#include <algorithm>
-#include "ui/base/gtk/gtk_compat.h"
+#include "ui/gfx/gtk_compat.h"
namespace {
diff --git a/chromium/ui/base/gtk/gtk_im_context_util.cc b/chromium/ui/base/gtk/gtk_im_context_util.cc
index b60856bf3f1..dfd5f3f9e8d 100644
--- a/chromium/ui/base/gtk/gtk_im_context_util.cc
+++ b/chromium/ui/base/gtk/gtk_im_context_util.cc
@@ -40,7 +40,7 @@ void ExtractCompositionTextFromGtkPreedit(const gchar* utf8_text,
size_t cursor_offset =
char16_offsets[std::max(0, std::min(char_length, cursor_position))];
- composition->selection = ui::Range(cursor_offset);
+ composition->selection = gfx::Range(cursor_offset);
if (attrs) {
int utf8_length = strlen(utf8_text);
diff --git a/chromium/ui/base/gtk/gtk_windowing.cc b/chromium/ui/base/gtk/gtk_windowing.cc
index 4ca4a1d2786..e378c8463ad 100644
--- a/chromium/ui/base/gtk/gtk_windowing.cc
+++ b/chromium/ui/base/gtk/gtk_windowing.cc
@@ -7,8 +7,8 @@
#include <gdk/gdkx.h>
#include "base/logging.h"
-#include "ui/base/gtk/gtk_compat.h"
#include "ui/base/x/x11_util.h"
+#include "ui/gfx/gtk_compat.h"
namespace ui {
diff --git a/chromium/ui/base/ime/character_composer.cc b/chromium/ui/base/ime/character_composer.cc
index 0402be2ba97..6fff429a2ac 100644
--- a/chromium/ui/base/ime/character_composer.cc
+++ b/chromium/ui/base/ime/character_composer.cc
@@ -14,9 +14,9 @@
// Note for Gtk removal: gdkkeysyms.h only contains a set of
// '#define GDK_KeyName 0xNNNN' macros and does not #include any Gtk headers.
#include "third_party/gtk+/gdk/gdkkeysyms.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/glib/glib_integers.h"
-#include "ui/base/x/x11_util.h"
+#include "ui/events/event_constants.h"
+#include "ui/gfx/x/x11_types.h"
// Note for Gtk removal: gtkimcontextsimpleseqs.h does not #include any Gtk
// headers and only contains one big guint16 array |gtk_compose_seqs_compact|
@@ -371,7 +371,7 @@ bool UTF32CharacterToUTF16(uint32 character, string16* output) {
// Converts a X keycode to a X keysym with no modifiers.
KeySym XKeyCodeToXKeySym(unsigned int keycode) {
- Display* display = ui::GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
if (!display)
return NoSymbol;
diff --git a/chromium/ui/base/ime/character_composer_unittest.cc b/chromium/ui/base/ime/character_composer_unittest.cc
index 9a7921931a9..0710204997e 100644
--- a/chromium/ui/base/ime/character_composer_unittest.cc
+++ b/chromium/ui/base/ime/character_composer_unittest.cc
@@ -7,8 +7,8 @@
#include "base/strings/utf_string_conversions.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/gtk+/gdk/gdkkeysyms.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/glib/glib_integers.h"
+#include "ui/events/event_constants.h"
namespace ui {
diff --git a/chromium/ui/base/ime/composition_text.cc b/chromium/ui/base/ime/composition_text.cc
index 660b3ef7ca4..f85bc748758 100644
--- a/chromium/ui/base/ime/composition_text.cc
+++ b/chromium/ui/base/ime/composition_text.cc
@@ -15,7 +15,7 @@ CompositionText::~CompositionText() {
void CompositionText::Clear() {
text.clear();
underlines.clear();
- selection = Range();
+ selection = gfx::Range();
}
} // namespace ui
diff --git a/chromium/ui/base/ime/composition_text.h b/chromium/ui/base/ime/composition_text.h
index b97712a6322..5beaffc0eb7 100644
--- a/chromium/ui/base/ime/composition_text.h
+++ b/chromium/ui/base/ime/composition_text.h
@@ -7,8 +7,8 @@
#include "base/strings/string16.h"
#include "ui/base/ime/composition_underline.h"
-#include "ui/base/range/range.h"
#include "ui/base/ui_export.h"
+#include "ui/gfx/range/range.h"
namespace ui {
@@ -47,7 +47,7 @@ struct UI_EXPORT CompositionText {
// if the range length is zero. Usually it's used for representing the target
// clause (on Windows). Gtk doesn't have such concept, so background color is
// usually used instead.
- Range selection;
+ gfx::Range selection;
};
} // namespace ui
diff --git a/chromium/ui/base/ime/dummy_input_method.cc b/chromium/ui/base/ime/dummy_input_method.cc
index f762e3b0b94..2fc206dee5d 100644
--- a/chromium/ui/base/ime/dummy_input_method.cc
+++ b/chromium/ui/base/ime/dummy_input_method.cc
@@ -32,6 +32,13 @@ bool DummyInputMethod::OnUntranslatedIMEMessage(const base::NativeEvent& event,
void DummyInputMethod::SetFocusedTextInputClient(TextInputClient* client) {
}
+void DummyInputMethod::SetStickyFocusedTextInputClient(
+ TextInputClient* client) {
+}
+
+void DummyInputMethod::DetachTextInputClient(TextInputClient* client) {
+}
+
TextInputClient* DummyInputMethod::GetTextInputClient() const {
return NULL;
}
@@ -72,6 +79,10 @@ TextInputType DummyInputMethod::GetTextInputType() const {
return TEXT_INPUT_TYPE_NONE;
}
+TextInputMode DummyInputMethod::GetTextInputMode() const {
+ return TEXT_INPUT_MODE_DEFAULT;
+}
+
bool DummyInputMethod::CanComposeInline() const {
return true;
}
diff --git a/chromium/ui/base/ime/dummy_input_method.h b/chromium/ui/base/ime/dummy_input_method.h
index 2276ae5d9a6..edceb0eac8e 100644
--- a/chromium/ui/base/ime/dummy_input_method.h
+++ b/chromium/ui/base/ime/dummy_input_method.h
@@ -25,6 +25,9 @@ class DummyInputMethod : public InputMethod {
virtual bool OnUntranslatedIMEMessage(
const base::NativeEvent& event, NativeEventResult* result) OVERRIDE;
virtual void SetFocusedTextInputClient(TextInputClient* client) OVERRIDE;
+ virtual void SetStickyFocusedTextInputClient(
+ TextInputClient* client) OVERRIDE;
+ virtual void DetachTextInputClient(TextInputClient* client) OVERRIDE;
virtual TextInputClient* GetTextInputClient() const OVERRIDE;
virtual bool DispatchKeyEvent(const base::NativeEvent& event) OVERRIDE;
virtual bool DispatchFabricatedKeyEvent(const ui::KeyEvent& event) OVERRIDE;
@@ -36,6 +39,7 @@ class DummyInputMethod : public InputMethod {
virtual base::i18n::TextDirection GetInputTextDirection() OVERRIDE;
virtual bool IsActive() OVERRIDE;
virtual TextInputType GetTextInputType() const OVERRIDE;
+ virtual TextInputMode GetTextInputMode() const OVERRIDE;
virtual bool CanComposeInline() const OVERRIDE;
virtual bool IsCandidatePopupOpen() const OVERRIDE;
virtual void AddObserver(InputMethodObserver* observer) OVERRIDE;
diff --git a/chromium/ui/base/ime/dummy_input_method_delegate.cc b/chromium/ui/base/ime/dummy_input_method_delegate.cc
new file mode 100644
index 00000000000..e7bb7dae2bd
--- /dev/null
+++ b/chromium/ui/base/ime/dummy_input_method_delegate.cc
@@ -0,0 +1,26 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/ime/dummy_input_method_delegate.h"
+
+namespace ui {
+namespace internal {
+
+DummyInputMethodDelegate::DummyInputMethodDelegate() {}
+DummyInputMethodDelegate::~DummyInputMethodDelegate() {}
+
+bool DummyInputMethodDelegate::DispatchKeyEventPostIME(
+ const base::NativeEvent& native_key_event) {
+ return true;
+}
+
+bool DummyInputMethodDelegate::DispatchFabricatedKeyEventPostIME(
+ ui::EventType type,
+ ui::KeyboardCode key_code,
+ int flags) {
+ return true;
+}
+
+} // namespace internal
+} // namespace ui
diff --git a/chromium/ui/base/ime/dummy_input_method_delegate.h b/chromium/ui/base/ime/dummy_input_method_delegate.h
new file mode 100644
index 00000000000..360d0b42b38
--- /dev/null
+++ b/chromium/ui/base/ime/dummy_input_method_delegate.h
@@ -0,0 +1,36 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_BASE_IME_DUMMY_INPUT_METHOD_DELEGATE_H_
+#define UI_BASE_IME_DUMMY_INPUT_METHOD_DELEGATE_H_
+
+#include "base/basictypes.h"
+#include "base/compiler_specific.h"
+#include "ui/base/ime/input_method_delegate.h"
+#include "ui/base/ui_export.h"
+
+namespace ui {
+namespace internal {
+
+class UI_EXPORT DummyInputMethodDelegate
+ : NON_EXPORTED_BASE(public InputMethodDelegate) {
+ public:
+ DummyInputMethodDelegate();
+ virtual ~DummyInputMethodDelegate();
+
+ // InputMethodDelegate overrides:
+ virtual bool DispatchKeyEventPostIME(
+ const base::NativeEvent& native_key_event) OVERRIDE;
+ virtual bool DispatchFabricatedKeyEventPostIME(ui::EventType type,
+ ui::KeyboardCode key_code,
+ int flags) OVERRIDE;
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(DummyInputMethodDelegate);
+};
+
+} // namespace internal
+} // namespace ui
+
+#endif // UI_BASE_IME_DUMMY_INPUT_METHOD_DELEGATE_H_
diff --git a/chromium/ui/base/ime/dummy_text_input_client.cc b/chromium/ui/base/ime/dummy_text_input_client.cc
new file mode 100644
index 00000000000..c12daef897a
--- /dev/null
+++ b/chromium/ui/base/ime/dummy_text_input_client.cc
@@ -0,0 +1,101 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/ime/dummy_text_input_client.h"
+#include "ui/gfx/rect.h"
+
+namespace ui {
+
+DummyTextInputClient::DummyTextInputClient() {
+}
+
+DummyTextInputClient::~DummyTextInputClient() {
+}
+
+void DummyTextInputClient::SetCompositionText(
+ const ui::CompositionText& composition) {
+}
+
+void DummyTextInputClient::ConfirmCompositionText() {
+}
+
+void DummyTextInputClient::ClearCompositionText() {
+}
+
+void DummyTextInputClient::InsertText(const string16& text) {
+}
+
+void DummyTextInputClient::InsertChar(char16 ch, int flags) {
+}
+
+gfx::NativeWindow DummyTextInputClient::GetAttachedWindow() const {
+ return NULL;
+}
+
+ui::TextInputType DummyTextInputClient::GetTextInputType() const {
+ return TEXT_INPUT_TYPE_NONE;
+}
+
+ui::TextInputMode DummyTextInputClient::GetTextInputMode() const {
+ return TEXT_INPUT_MODE_DEFAULT;
+}
+
+bool DummyTextInputClient::CanComposeInline() const {
+ return false;
+}
+
+gfx::Rect DummyTextInputClient::GetCaretBounds() {
+ return gfx::Rect();
+}
+
+bool DummyTextInputClient::GetCompositionCharacterBounds(uint32 index,
+ gfx::Rect* rect) {
+ return false;
+}
+
+bool DummyTextInputClient::HasCompositionText() {
+ return false;
+}
+
+bool DummyTextInputClient::GetTextRange(gfx::Range* range) {
+ return false;
+}
+
+bool DummyTextInputClient::GetCompositionTextRange(gfx::Range* range) {
+ return false;
+}
+
+bool DummyTextInputClient::GetSelectionRange(gfx::Range* range) {
+ return false;
+}
+
+bool DummyTextInputClient::SetSelectionRange(const gfx::Range& range) {
+ return false;
+}
+
+bool DummyTextInputClient::DeleteRange(const gfx::Range& range) {
+ return false;
+}
+
+bool DummyTextInputClient::GetTextFromRange(const gfx::Range& range,
+ string16* text) {
+ return false;
+}
+
+void DummyTextInputClient::OnInputMethodChanged() {
+}
+
+bool DummyTextInputClient::ChangeTextDirectionAndLayoutAlignment(
+ base::i18n::TextDirection direction) {
+ return false;
+}
+
+void DummyTextInputClient::ExtendSelectionAndDelete(size_t before,
+ size_t after) {
+}
+
+void DummyTextInputClient::EnsureCaretInRect(const gfx::Rect& rect) {
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/ime/dummy_text_input_client.h b/chromium/ui/base/ime/dummy_text_input_client.h
new file mode 100644
index 00000000000..966502faa92
--- /dev/null
+++ b/chromium/ui/base/ime/dummy_text_input_client.h
@@ -0,0 +1,49 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_BASE_IME_DUMMY_TEXT_INPUT_CLIENT_H_
+#define UI_BASE_IME_DUMMY_TEXT_INPUT_CLIENT_H_
+
+#include "ui/base/ime/text_input_client.h"
+
+namespace ui {
+
+// Dummy implementation of TextInputClient. All functions do nothing.
+class DummyTextInputClient : public TextInputClient {
+ public:
+ DummyTextInputClient();
+ virtual ~DummyTextInputClient();
+
+ // Overriden from TextInputClient.
+ virtual void SetCompositionText(
+ const ui::CompositionText& composition) OVERRIDE;
+ virtual void ConfirmCompositionText() OVERRIDE;
+ virtual void ClearCompositionText() OVERRIDE;
+ virtual void InsertText(const string16& text) OVERRIDE;
+ virtual void InsertChar(char16 ch, int flags) OVERRIDE;
+ virtual gfx::NativeWindow GetAttachedWindow() const OVERRIDE;
+ virtual ui::TextInputType GetTextInputType() const OVERRIDE;
+ virtual ui::TextInputMode GetTextInputMode() const OVERRIDE;
+ virtual bool CanComposeInline() const OVERRIDE;
+ virtual gfx::Rect GetCaretBounds() OVERRIDE;
+ virtual bool GetCompositionCharacterBounds(uint32 index,
+ gfx::Rect* rect) OVERRIDE;
+ virtual bool HasCompositionText() OVERRIDE;
+ virtual bool GetTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetCompositionTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetSelectionRange(gfx::Range* range) OVERRIDE;
+ virtual bool SetSelectionRange(const gfx::Range& range) OVERRIDE;
+ virtual bool DeleteRange(const gfx::Range& range) OVERRIDE;
+ virtual bool GetTextFromRange(const gfx::Range& range,
+ string16* text) OVERRIDE;
+ virtual void OnInputMethodChanged() OVERRIDE;
+ virtual bool ChangeTextDirectionAndLayoutAlignment(
+ base::i18n::TextDirection direction) OVERRIDE;
+ virtual void ExtendSelectionAndDelete(size_t before, size_t after) OVERRIDE;
+ virtual void EnsureCaretInRect(const gfx::Rect& rect) OVERRIDE;
+};
+
+} // namespace ui
+
+#endif // UI_BASE_IME_DUMMY_TEXT_INPUT_CLIENT_H_
diff --git a/chromium/ui/base/ime/fake_input_method.cc b/chromium/ui/base/ime/fake_input_method.cc
index 1cf236de56b..21736168392 100644
--- a/chromium/ui/base/ime/fake_input_method.cc
+++ b/chromium/ui/base/ime/fake_input_method.cc
@@ -6,19 +6,19 @@
#include "base/logging.h"
#include "base/strings/string16.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/glib/glib_integers.h"
#include "ui/base/ime/input_method_delegate.h"
#include "ui/base/ime/text_input_client.h"
-#include "ui/base/keycodes/keyboard_code_conversion.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion.h"
#if defined(USE_X11)
#include <X11/X.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
#endif
namespace {
@@ -38,7 +38,8 @@ namespace ui {
FakeInputMethod::FakeInputMethod(internal::InputMethodDelegate* delegate)
: delegate_(NULL),
- text_input_client_(NULL) {
+ text_input_client_(NULL),
+ is_sticky_text_input_client_(false) {
SetDelegate(delegate);
}
@@ -50,11 +51,29 @@ void FakeInputMethod::SetDelegate(internal::InputMethodDelegate* delegate) {
}
void FakeInputMethod::SetFocusedTextInputClient(TextInputClient* client) {
+ if (is_sticky_text_input_client_)
+ return;
text_input_client_ = client;
FOR_EACH_OBSERVER(InputMethodObserver, observers_,
OnTextInputStateChanged(client));
}
+void FakeInputMethod::SetStickyFocusedTextInputClient(TextInputClient* client) {
+ text_input_client_ = client;
+ is_sticky_text_input_client_ = (client != NULL);
+ FOR_EACH_OBSERVER(InputMethodObserver, observers_,
+ OnTextInputStateChanged(client));
+}
+
+void FakeInputMethod::DetachTextInputClient(TextInputClient* client) {
+ if (text_input_client_ == client) {
+ text_input_client_ = NULL;
+ is_sticky_text_input_client_ = false;
+ FOR_EACH_OBSERVER(InputMethodObserver, observers_,
+ OnTextInputStateChanged(client));
+ }
+}
+
TextInputClient* FakeInputMethod::GetTextInputClient() const {
return text_input_client_;
}
@@ -92,6 +111,27 @@ bool FakeInputMethod::DispatchKeyEvent(const base::NativeEvent& native_event) {
text_input_client_->InsertChar(ch, state);
}
}
+#elif defined(USE_OZONE)
+ DCHECK(native_event);
+ if (EventTypeFromNative(native_event) == ET_KEY_RELEASED) {
+ // On key release, just dispatch it.
+ handled = delegate_->DispatchKeyEventPostIME(native_event);
+ } else {
+ const uint32 state = EventFlagsFromNative(native_event);
+ // Send a RawKeyDown event first,
+ handled = delegate_->DispatchKeyEventPostIME(native_event);
+ if (text_input_client_) {
+ // then send a Char event via ui::TextInputClient.
+ const KeyboardCode key_code = ui::KeyboardCodeFromNative(native_event);
+ uint16 ch = 0;
+
+ // TODO(vignatti): Support EF_CONTROL_DOWN state
+
+ ch = ui::GetCharacterFromKeyCode(key_code, state);
+ if (ch)
+ text_input_client_->InsertChar(ch, state);
+ }
+ }
#else
// TODO(yusukes): Support other platforms. Call InsertChar() when necessary.
handled = delegate_->DispatchKeyEventPostIME(native_event);
@@ -141,8 +181,12 @@ bool FakeInputMethod::IsCandidatePopupOpen() const {
return false;
}
-ui::TextInputType FakeInputMethod::GetTextInputType() const {
- return ui::TEXT_INPUT_TYPE_NONE;
+TextInputType FakeInputMethod::GetTextInputType() const {
+ return TEXT_INPUT_TYPE_NONE;
+}
+
+TextInputMode FakeInputMethod::GetTextInputMode() const {
+ return TEXT_INPUT_MODE_DEFAULT;
}
bool FakeInputMethod::CanComposeInline() const {
diff --git a/chromium/ui/base/ime/fake_input_method.h b/chromium/ui/base/ime/fake_input_method.h
index 12f9aac0180..42b8b024978 100644
--- a/chromium/ui/base/ime/fake_input_method.h
+++ b/chromium/ui/base/ime/fake_input_method.h
@@ -34,6 +34,9 @@ class UI_EXPORT FakeInputMethod : NON_EXPORTED_BASE(public InputMethod) {
virtual bool OnUntranslatedIMEMessage(const base::NativeEvent& event,
NativeEventResult* result) OVERRIDE;
virtual void SetFocusedTextInputClient(TextInputClient* client) OVERRIDE;
+ virtual void SetStickyFocusedTextInputClient(
+ TextInputClient* client) OVERRIDE;
+ virtual void DetachTextInputClient(TextInputClient* client) OVERRIDE;
virtual TextInputClient* GetTextInputClient() const OVERRIDE;
virtual bool DispatchKeyEvent(const base::NativeEvent& native_event) OVERRIDE;
virtual bool DispatchFabricatedKeyEvent(const ui::KeyEvent& event) OVERRIDE;
@@ -44,7 +47,8 @@ class UI_EXPORT FakeInputMethod : NON_EXPORTED_BASE(public InputMethod) {
virtual std::string GetInputLocale() OVERRIDE;
virtual base::i18n::TextDirection GetInputTextDirection() OVERRIDE;
virtual bool IsActive() OVERRIDE;
- virtual ui::TextInputType GetTextInputType() const OVERRIDE;
+ virtual TextInputType GetTextInputType() const OVERRIDE;
+ virtual TextInputMode GetTextInputMode() const OVERRIDE;
virtual bool CanComposeInline() const OVERRIDE;
virtual bool IsCandidatePopupOpen() const OVERRIDE;
virtual void AddObserver(InputMethodObserver* observer) OVERRIDE;
@@ -53,6 +57,7 @@ class UI_EXPORT FakeInputMethod : NON_EXPORTED_BASE(public InputMethod) {
private:
internal::InputMethodDelegate* delegate_;
TextInputClient* text_input_client_;
+ bool is_sticky_text_input_client_;
ObserverList<InputMethodObserver> observers_;
DISALLOW_COPY_AND_ASSIGN(FakeInputMethod);
diff --git a/chromium/ui/base/ime/ime.gypi b/chromium/ui/base/ime/ime.gypi
index b8a18963588..70c5cd0f306 100644
--- a/chromium/ui/base/ime/ime.gypi
+++ b/chromium/ui/base/ime/ime.gypi
@@ -10,6 +10,8 @@
'composition_text.cc',
'composition_text.h',
'composition_underline.h',
+ 'dummy_input_method_delegate.cc',
+ 'dummy_input_method_delegate.h',
'input_method.h',
'input_method_base.cc',
'input_method_base.h',
diff --git a/chromium/ui/base/ime/ime_test_support.gypi b/chromium/ui/base/ime/ime_test_support.gypi
index a6ac3615261..02fa6eb1191 100644
--- a/chromium/ui/base/ime/ime_test_support.gypi
+++ b/chromium/ui/base/ime/ime_test_support.gypi
@@ -6,6 +6,8 @@
'sources': [
'dummy_input_method.cc',
'dummy_input_method.h',
+ 'dummy_text_input_client.cc',
+ 'dummy_text_input_client.h',
'win/mock_tsf_bridge.cc',
'win/mock_tsf_bridge.h',
],
diff --git a/chromium/ui/base/ime/ime_unittests.gypi b/chromium/ui/base/ime/ime_unittests.gypi
index 173e74c9063..3dabb50eda3 100644
--- a/chromium/ui/base/ime/ime_unittests.gypi
+++ b/chromium/ui/base/ime/ime_unittests.gypi
@@ -3,27 +3,29 @@
# found in the LICENSE file.
{
- 'variables': {
- 'ime_test_files': [
- 'character_composer_unittest.cc',
- 'input_method_ibus_unittest.cc',
- ],
- },
'sources': [
- '<@(ime_test_files)',
+ 'character_composer_unittest.cc',
+ 'input_method_base_unittest.cc',
+ 'input_method_ibus_unittest.cc',
'win/imm32_manager_unittest.cc',
+ 'win/tsf_input_scope_unittest.cc',
'win/tsf_text_store_unittest.cc',
],
'conditions': [
['use_aura==0 or use_x11==0 or chromeos==0', {
'sources!': [
- '<@(ime_test_files)',
+ 'character_composer_unittest.cc',
+ 'input_method_ibus_unittest.cc',
],
}],
- ['OS!="win"', {
+ ['use_aura==0 and OS!="win"', {
'sources!': [
- 'win/imm32_manager_unittest.cc',
- 'win/tsf_text_store_unittest.cc',
+ 'input_method_base_unittest.cc',
+ ],
+ }],
+ ['OS!="win"', {
+ 'sources/': [
+ ['exclude', '^win'],
],
}],
],
diff --git a/chromium/ui/base/ime/input_method.h b/chromium/ui/base/ime/input_method.h
index 575cbcdb305..ac24f77af16 100644
--- a/chromium/ui/base/ime/input_method.h
+++ b/chromium/ui/base/ime/input_method.h
@@ -10,9 +10,10 @@
#include "base/basictypes.h"
#include "base/event_types.h"
#include "base/i18n/rtl.h"
+#include "ui/base/ime/text_input_mode.h"
#include "ui/base/ime/text_input_type.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/ui_export.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace ui {
@@ -82,9 +83,22 @@ class InputMethod {
// SetCompositionText(). |client| can be NULL. A gfx::NativeWindow which
// implementes TextInputClient interface, e.g. NWA and RWHVA, should register
// itself by calling the method when it is focused, and unregister itself by
- // calling the metho with NULL when it is unfocused.
+ // calling the method with NULL when it is unfocused.
virtual void SetFocusedTextInputClient(TextInputClient* client) = 0;
+ // A variant of SetFocusedTextInputClient. Unlike SetFocusedTextInputClient,
+ // all the subsequent calls of SetFocusedTextInputClient will be ignored
+ // until |client| is detached. This method is introduced as a workaround
+ // against crbug.com/287620.
+ // NOTE: You can pass NULL to |client| to detach the sticky client.
+ // NOTE: You can also use DetachTextInputClient to remove the sticky client.
+ virtual void SetStickyFocusedTextInputClient(TextInputClient* client) = 0;
+
+ // Detaches and forgets the |client| regardless of whether it has the focus or
+ // not. This method is meant to be called when the |client| is going to be
+ // destroyed.
+ virtual void DetachTextInputClient(TextInputClient* client) = 0;
+
// Gets the current text input client. Returns NULL when no client is set.
virtual TextInputClient* GetTextInputClient() const = 0;
@@ -140,10 +154,18 @@ class InputMethod {
// is not active.
virtual bool IsActive() = 0;
+ // TODO(yoichio): Following 3 methods(GetTextInputType, GetTextInputMode and
+ // CanComposeInline) calls client's same method and returns its value. It is
+ // not InputMethod itself's infomation. So rename these to
+ // GetClientTextInputType and so on.
// Gets the text input type of the focused text input client. Returns
// ui::TEXT_INPUT_TYPE_NONE if there is no focused client.
virtual TextInputType GetTextInputType() const = 0;
+ // Gets the text input mode of the focused text input client. Returns
+ // ui::TEXT_INPUT_TYPE_DEFAULT if there is no focused client.
+ virtual TextInputMode GetTextInputMode() const = 0;
+
// Checks if the focused text input client supports inline composition.
virtual bool CanComposeInline() const = 0;
diff --git a/chromium/ui/base/ime/input_method_base.cc b/chromium/ui/base/ime/input_method_base.cc
index 6972eed9258..d3770765340 100644
--- a/chromium/ui/base/ime/input_method_base.cc
+++ b/chromium/ui/base/ime/input_method_base.cc
@@ -14,6 +14,7 @@ namespace ui {
InputMethodBase::InputMethodBase()
: delegate_(NULL),
text_input_client_(NULL),
+ is_sticky_text_input_client_(false),
system_toplevel_window_focused_(false) {
}
@@ -43,13 +44,24 @@ void InputMethodBase::OnBlur() {
}
void InputMethodBase::SetFocusedTextInputClient(TextInputClient* client) {
- TextInputClient* old = text_input_client_;
- OnWillChangeFocusedClient(old, client);
- text_input_client_ = client; // NULL allowed.
- OnDidChangeFocusedClient(old, client);
+ if (is_sticky_text_input_client_)
+ return;
+ SetFocusedTextInputClientInternal(client);
+}
+
+void InputMethodBase::SetStickyFocusedTextInputClient(TextInputClient* client) {
+ is_sticky_text_input_client_ = (client != NULL);
+ SetFocusedTextInputClientInternal(client);
+}
- if (old != text_input_client_)
+void InputMethodBase::DetachTextInputClient(TextInputClient* client) {
+ if (text_input_client_ == client) {
+ OnWillChangeFocusedClient(client, NULL);
+ text_input_client_ = NULL;
+ is_sticky_text_input_client_ = false;
+ OnDidChangeFocusedClient(client, NULL);
NotifyTextInputStateChanged(text_input_client_);
+ }
}
TextInputClient* InputMethodBase::GetTextInputClient() const {
@@ -67,6 +79,11 @@ TextInputType InputMethodBase::GetTextInputType() const {
return client ? client->GetTextInputType() : TEXT_INPUT_TYPE_NONE;
}
+TextInputMode InputMethodBase::GetTextInputMode() const {
+ TextInputClient* client = GetTextInputClient();
+ return client ? client->GetTextInputMode() : TEXT_INPUT_MODE_DEFAULT;
+}
+
bool InputMethodBase::CanComposeInline() const {
TextInputClient* client = GetTextInputClient();
return client ? client->CanComposeInline() : true;
@@ -113,4 +130,15 @@ void InputMethodBase::NotifyTextInputStateChanged(
OnTextInputStateChanged(client));
}
+void InputMethodBase::SetFocusedTextInputClientInternal(
+ TextInputClient* client) {
+ TextInputClient* old = text_input_client_;
+ if (old == client)
+ return;
+ OnWillChangeFocusedClient(old, client);
+ text_input_client_ = client; // NULL allowed.
+ OnDidChangeFocusedClient(old, client);
+ NotifyTextInputStateChanged(text_input_client_);
+}
+
} // namespace ui
diff --git a/chromium/ui/base/ime/input_method_base.h b/chromium/ui/base/ime/input_method_base.h
index e467e0bec8e..665070a9c78 100644
--- a/chromium/ui/base/ime/input_method_base.h
+++ b/chromium/ui/base/ime/input_method_base.h
@@ -8,9 +8,9 @@
#include "base/basictypes.h"
#include "base/compiler_specific.h"
#include "base/observer_list.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/ime/input_method.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
namespace gfx {
class Rect;
@@ -37,6 +37,9 @@ class UI_EXPORT InputMethodBase : NON_EXPORTED_BASE(public InputMethod) {
virtual void OnFocus() OVERRIDE;
virtual void OnBlur() OVERRIDE;
virtual void SetFocusedTextInputClient(TextInputClient* client) OVERRIDE;
+ virtual void SetStickyFocusedTextInputClient(
+ TextInputClient* client) OVERRIDE;
+ virtual void DetachTextInputClient(TextInputClient* client) OVERRIDE;
virtual TextInputClient* GetTextInputClient() const OVERRIDE;
// If a derived class overrides this method, it should call parent's
@@ -44,6 +47,7 @@ class UI_EXPORT InputMethodBase : NON_EXPORTED_BASE(public InputMethod) {
virtual void OnTextInputTypeChanged(const TextInputClient* client) OVERRIDE;
virtual TextInputType GetTextInputType() const OVERRIDE;
+ virtual TextInputMode GetTextInputMode() const OVERRIDE;
virtual bool CanComposeInline() const OVERRIDE;
virtual void AddObserver(InputMethodObserver* observer) OVERRIDE;
@@ -86,8 +90,11 @@ class UI_EXPORT InputMethodBase : NON_EXPORTED_BASE(public InputMethod) {
}
private:
+ void SetFocusedTextInputClientInternal(TextInputClient* client);
+
internal::InputMethodDelegate* delegate_;
TextInputClient* text_input_client_;
+ bool is_sticky_text_input_client_;
ObserverList<InputMethodObserver> observer_list_;
diff --git a/chromium/ui/base/ime/input_method_base_unittest.cc b/chromium/ui/base/ime/input_method_base_unittest.cc
new file mode 100644
index 00000000000..cc7304cefcc
--- /dev/null
+++ b/chromium/ui/base/ime/input_method_base_unittest.cc
@@ -0,0 +1,383 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/ime/input_method_base.h"
+
+#include "base/scoped_observer.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "ui/base/ime/dummy_text_input_client.h"
+#include "ui/base/ime/input_method_observer.h"
+#include "ui/events/event.h"
+
+namespace ui {
+namespace {
+
+class ClientChangeVerifier {
+ public:
+ ClientChangeVerifier()
+ : previous_client_(NULL),
+ next_client_(NULL),
+ call_expected_(false),
+ on_will_change_focused_client_called_(false),
+ on_did_change_focused_client_called_(false),
+ on_text_input_state_changed_(false) {
+ }
+
+ // Expects that focused text input client will not be changed.
+ void ExpectClientDoesNotChange() {
+ previous_client_ = NULL;
+ next_client_ = NULL;
+ call_expected_ = false;
+ on_will_change_focused_client_called_ = false;
+ on_did_change_focused_client_called_ = false;
+ on_text_input_state_changed_ = false;
+ }
+
+ // Expects that focused text input client will be changed from
+ // |previous_client| to |next_client|.
+ void ExpectClientChange(TextInputClient* previous_client,
+ TextInputClient* next_client) {
+ previous_client_ = previous_client;
+ next_client_ = next_client;
+ call_expected_ = true;
+ on_will_change_focused_client_called_ = false;
+ on_did_change_focused_client_called_ = false;
+ on_text_input_state_changed_ = false;
+ }
+
+ // Verifies the result satisfies the expectation or not.
+ void Verify() {
+ EXPECT_EQ(call_expected_, on_will_change_focused_client_called_);
+ EXPECT_EQ(call_expected_, on_did_change_focused_client_called_);
+ EXPECT_EQ(call_expected_, on_text_input_state_changed_);
+ }
+
+ void OnWillChangeFocusedClient(TextInputClient* focused_before,
+ TextInputClient* focused) {
+ EXPECT_TRUE(call_expected_);
+
+ // Check arguments
+ EXPECT_EQ(previous_client_, focused_before);
+ EXPECT_EQ(next_client_, focused);
+
+ // Check call order
+ EXPECT_FALSE(on_will_change_focused_client_called_);
+ EXPECT_FALSE(on_did_change_focused_client_called_);
+ EXPECT_FALSE(on_text_input_state_changed_);
+
+ on_will_change_focused_client_called_ = true;
+ }
+
+ void OnDidChangeFocusedClient(TextInputClient* focused_before,
+ TextInputClient* focused) {
+ EXPECT_TRUE(call_expected_);
+
+ // Check arguments
+ EXPECT_EQ(previous_client_, focused_before);
+ EXPECT_EQ(next_client_, focused);
+
+ // Check call order
+ EXPECT_TRUE(on_will_change_focused_client_called_);
+ EXPECT_FALSE(on_did_change_focused_client_called_);
+ EXPECT_FALSE(on_text_input_state_changed_);
+
+ on_did_change_focused_client_called_ = true;
+ }
+
+ void OnTextInputStateChanged(const TextInputClient* client) {
+ EXPECT_TRUE(call_expected_);
+
+ // Check arguments
+ EXPECT_EQ(next_client_, client);
+
+ // Check call order
+ EXPECT_TRUE(on_will_change_focused_client_called_);
+ EXPECT_TRUE(on_did_change_focused_client_called_);
+ EXPECT_FALSE(on_text_input_state_changed_);
+
+ on_text_input_state_changed_ = true;
+ }
+
+ private:
+ TextInputClient* previous_client_;
+ TextInputClient* next_client_;
+ bool call_expected_;
+ bool on_will_change_focused_client_called_;
+ bool on_did_change_focused_client_called_;
+ bool on_text_input_state_changed_;
+
+ DISALLOW_COPY_AND_ASSIGN(ClientChangeVerifier);
+};
+
+class MockInputMethodBase : public InputMethodBase {
+ public:
+ // Note: this class does not take the ownership of |verifier|.
+ explicit MockInputMethodBase(ClientChangeVerifier* verifier)
+ : verifier_(verifier) {
+ }
+ virtual ~MockInputMethodBase() {
+ }
+
+ private:
+ // Overriden from InputMethod.
+ virtual bool OnUntranslatedIMEMessage(
+ const base::NativeEvent& event,
+ InputMethod::NativeEventResult* result) OVERRIDE {
+ return false;
+ }
+ virtual bool DispatchKeyEvent(const base::NativeEvent&) OVERRIDE {
+ return false;
+ }
+ virtual bool DispatchFabricatedKeyEvent(const ui::KeyEvent&) OVERRIDE {
+ return false;
+ }
+ virtual void OnCaretBoundsChanged(const TextInputClient* clien) OVERRIDE {
+ }
+ virtual void CancelComposition(const TextInputClient* clien) OVERRIDE {
+ }
+ virtual void OnInputLocaleChanged() OVERRIDE {
+ }
+ virtual std::string GetInputLocale() OVERRIDE {
+ return "";
+ }
+ virtual base::i18n::TextDirection GetInputTextDirection() OVERRIDE {
+ return base::i18n::UNKNOWN_DIRECTION;
+ }
+ virtual bool IsActive() OVERRIDE {
+ return false;
+ }
+ virtual bool IsCandidatePopupOpen() const OVERRIDE {
+ return false;
+ }
+
+ // Overriden from InputMethodBase.
+ virtual void OnWillChangeFocusedClient(TextInputClient* focused_before,
+ TextInputClient* focused) OVERRIDE {
+ verifier_->OnWillChangeFocusedClient(focused_before, focused);
+ }
+
+ virtual void OnDidChangeFocusedClient(TextInputClient* focused_before,
+ TextInputClient* focused) OVERRIDE {
+ verifier_->OnDidChangeFocusedClient(focused_before, focused);
+ }
+
+ ClientChangeVerifier* verifier_;
+ DISALLOW_COPY_AND_ASSIGN(MockInputMethodBase);
+};
+
+class MockInputMethodObserver : public InputMethodObserver {
+ public:
+ // Note: this class does not take the ownership of |verifier|.
+ explicit MockInputMethodObserver(ClientChangeVerifier* verifier)
+ : verifier_(verifier) {
+ }
+ virtual ~MockInputMethodObserver() {
+ }
+
+ private:
+ virtual void OnTextInputStateChanged(const TextInputClient* client) OVERRIDE {
+ verifier_->OnTextInputStateChanged(client);
+ }
+ virtual void OnInputMethodDestroyed(const InputMethod* client) OVERRIDE {
+ }
+
+ ClientChangeVerifier* verifier_;
+ DISALLOW_COPY_AND_ASSIGN(MockInputMethodObserver);
+};
+
+typedef ScopedObserver<InputMethod, InputMethodObserver>
+ InputMethodScopedObserver;
+
+TEST(InputMethodBaseTest, SetFocusedTextInputClient) {
+ DummyTextInputClient text_input_client_1st;
+ DummyTextInputClient text_input_client_2nd;
+
+ ClientChangeVerifier verifier;
+ MockInputMethodBase input_method(&verifier);
+ MockInputMethodObserver input_method_observer(&verifier);
+ InputMethodScopedObserver scoped_observer(&input_method_observer);
+ scoped_observer.Add(&input_method);
+
+ // Assume that the top-level-widget gains focus.
+ input_method.OnFocus();
+
+ {
+ SCOPED_TRACE("Focus from NULL to 1st TextInputClient");
+
+ ASSERT_EQ(NULL, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(NULL, &text_input_client_1st);
+ input_method.SetFocusedTextInputClient(&text_input_client_1st);
+ EXPECT_EQ(&text_input_client_1st, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Redundant focus events must be ignored");
+ verifier.ExpectClientDoesNotChange();
+ input_method.SetFocusedTextInputClient(&text_input_client_1st);
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Focus from 1st to 2nd TextInputClient");
+
+ ASSERT_EQ(&text_input_client_1st, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(&text_input_client_1st,
+ &text_input_client_2nd);
+ input_method.SetFocusedTextInputClient(&text_input_client_2nd);
+ EXPECT_EQ(&text_input_client_2nd, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Focus from 2nd TextInputClient to NULL");
+
+ ASSERT_EQ(&text_input_client_2nd, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(&text_input_client_2nd, NULL);
+ input_method.SetFocusedTextInputClient(NULL);
+ EXPECT_EQ(NULL, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Redundant focus events must be ignored");
+ verifier.ExpectClientDoesNotChange();
+ input_method.SetFocusedTextInputClient(NULL);
+ verifier.Verify();
+ }
+}
+
+TEST(InputMethodBaseTest, DetachTextInputClient) {
+ DummyTextInputClient text_input_client;
+ DummyTextInputClient text_input_client_the_other;
+
+ ClientChangeVerifier verifier;
+ MockInputMethodBase input_method(&verifier);
+ MockInputMethodObserver input_method_observer(&verifier);
+ InputMethodScopedObserver scoped_observer(&input_method_observer);
+ scoped_observer.Add(&input_method);
+
+ // Assume that the top-level-widget gains focus.
+ input_method.OnFocus();
+
+ // Initialize for the next test.
+ {
+ verifier.ExpectClientChange(NULL, &text_input_client);
+ input_method.SetFocusedTextInputClient(&text_input_client);
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("DetachTextInputClient must be ignored for other clients");
+ ASSERT_EQ(&text_input_client, input_method.GetTextInputClient());
+ verifier.ExpectClientDoesNotChange();
+ input_method.DetachTextInputClient(&text_input_client_the_other);
+ EXPECT_EQ(&text_input_client, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("DetachTextInputClient must succeed even after the "
+ "top-level loses the focus");
+
+ ASSERT_EQ(&text_input_client, input_method.GetTextInputClient());
+ input_method.OnBlur();
+ input_method.OnFocus();
+ verifier.ExpectClientChange(&text_input_client, NULL);
+ input_method.DetachTextInputClient(&text_input_client);
+ EXPECT_EQ(NULL, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+}
+
+TEST(InputMethodBaseTest, SetStickyFocusedTextInputClient) {
+ DummyTextInputClient sticky_client;
+ DummyTextInputClient non_sticky_client;
+
+ ClientChangeVerifier verifier;
+ MockInputMethodBase input_method(&verifier);
+ MockInputMethodObserver input_method_observer(&verifier);
+ InputMethodScopedObserver scoped_observer(&input_method_observer);
+ scoped_observer.Add(&input_method);
+
+ // Assume that the top-level-widget gains focus.
+ input_method.OnFocus();
+
+ {
+ SCOPED_TRACE("Focus from NULL to non-sticky client");
+
+ ASSERT_EQ(NULL, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(NULL, &non_sticky_client);
+ input_method.SetFocusedTextInputClient(&non_sticky_client);
+ EXPECT_EQ(&non_sticky_client, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Focus from non-sticky to sticky client");
+
+ ASSERT_EQ(&non_sticky_client, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(&non_sticky_client, &sticky_client);
+ input_method.SetStickyFocusedTextInputClient(&sticky_client);
+ EXPECT_EQ(&sticky_client, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Focus from sticky to non-sticky client -> must fail");
+
+ ASSERT_EQ(&sticky_client, input_method.GetTextInputClient());
+ verifier.ExpectClientDoesNotChange();
+ input_method.SetFocusedTextInputClient(&non_sticky_client);
+ EXPECT_EQ(&sticky_client, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Focus from sticky to NULL -> must fail");
+
+ verifier.ExpectClientDoesNotChange();
+ input_method.SetFocusedTextInputClient(NULL);
+ EXPECT_EQ(&sticky_client, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("SetStickyFocusedTextInputClient(NULL) must be supported");
+
+ ASSERT_EQ(&sticky_client, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(&sticky_client, NULL);
+ input_method.SetStickyFocusedTextInputClient(NULL);
+ EXPECT_EQ(NULL, input_method.GetTextInputClient());
+ verifier.Verify();
+
+ // |SetStickyFocusedTextInputClient(NULL)| must be equivalent to
+ // |SetFocusedTextInputClient(NULL)|. We should be able to use
+ // |SetFocusedTextInputClient(&non_sticky_client)| here.
+ verifier.ExpectClientChange(NULL, &non_sticky_client);
+ input_method.SetFocusedTextInputClient(&non_sticky_client);
+ EXPECT_EQ(&non_sticky_client, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("Set stick client again for the next test");
+ verifier.ExpectClientChange(&non_sticky_client, &sticky_client);
+ input_method.SetStickyFocusedTextInputClient(&sticky_client);
+ verifier.Verify();
+ }
+
+ {
+ SCOPED_TRACE("DetachTextInputClient must be supported for sticky client");
+
+ ASSERT_EQ(&sticky_client, input_method.GetTextInputClient());
+ verifier.ExpectClientChange(&sticky_client, NULL);
+ input_method.DetachTextInputClient(&sticky_client);
+ EXPECT_EQ(NULL, input_method.GetTextInputClient());
+ verifier.Verify();
+ }
+}
+
+} // namespace
+} // namespace ui
diff --git a/chromium/ui/base/ime/input_method_delegate.h b/chromium/ui/base/ime/input_method_delegate.h
index c0846b1c039..21319437d65 100644
--- a/chromium/ui/base/ime/input_method_delegate.h
+++ b/chromium/ui/base/ime/input_method_delegate.h
@@ -6,9 +6,9 @@
#define UI_BASE_IME_INPUT_METHOD_DELEGATE_H_
#include "base/event_types.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace ui {
namespace internal {
diff --git a/chromium/ui/base/ime/input_method_ibus.cc b/chromium/ui/base/ime/input_method_ibus.cc
index 7c4f803d445..8ff645a2130 100644
--- a/chromium/ui/base/ime/input_method_ibus.cc
+++ b/chromium/ui/base/ime/input_method_ibus.cc
@@ -23,30 +23,21 @@
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "base/third_party/icu/icu_utf.h"
-#include "chromeos/dbus/dbus_thread_manager.h"
-#include "chromeos/dbus/ibus/ibus_client.h"
-#include "chromeos/dbus/ibus/ibus_input_context_client.h"
#include "chromeos/dbus/ibus/ibus_text.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
+#include "chromeos/ime/input_method_descriptor.h"
+#include "chromeos/ime/input_method_manager.h"
#include "ui/base/ime/text_input_client.h"
-#include "ui/base/keycodes/keyboard_code_conversion.h"
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/rect.h"
namespace {
const int kIBusReleaseMask = 1 << 30;
-const char kClientName[] = "chrome";
-const int kMaxRetryCount = 10;
-
-// Following capability mask is introduced from
-// http://ibus.googlecode.com/svn/docs/ibus-1.4/ibus-ibustypes.html#IBusCapabilite
-const uint32 kIBusCapabilityPreeditText = 1U;
-const uint32 kIBusCapabilityFocus = 8U;
-const uint32 kIBusCapabilitySurroundingText = 32U;
XKeyEvent* GetKeyEvent(XEvent* event) {
DCHECK(event && (event->type == KeyPress || event->type == KeyRelease));
@@ -70,15 +61,15 @@ uint32 IBusStateFromXState(unsigned int state) {
Button1Mask | Button2Mask | Button3Mask));
}
-chromeos::IBusInputContextClient* GetInputContextClient() {
- return chromeos::DBusThreadManager::Get()->GetIBusInputContextClient();
-}
-
// Converts gfx::Rect to ibus::Rect.
chromeos::ibus::Rect GfxRectToIBusRect(const gfx::Rect& rect) {
return chromeos::ibus::Rect(rect.x(), rect.y(), rect.width(), rect.height());
}
+chromeos::IBusEngineHandlerInterface* GetEngine() {
+ return chromeos::IBusBridge::Get()->GetEngineHandler();
+}
+
} // namespace
namespace ui {
@@ -86,33 +77,28 @@ namespace ui {
// InputMethodIBus implementation -----------------------------------------
InputMethodIBus::InputMethodIBus(
internal::InputMethodDelegate* delegate)
- : input_context_state_(INPUT_CONTEXT_STOP),
- create_input_context_fail_count_(0),
- context_focused_(false),
+ : context_focused_(false),
composing_text_(false),
composition_changed_(false),
suppress_next_result_(false),
current_keyevent_id_(0),
+ previous_textinput_type_(TEXT_INPUT_TYPE_NONE),
weak_ptr_factory_(this) {
SetDelegate(delegate);
+ chromeos::IBusBridge::Get()->SetInputContextHandler(this);
- // chromeos::IBusDaemonController is not available in case of some testing,
- // e.g. content_browser test can't initialize IBusDaemonController.
- DCHECK(!base::chromeos::IsRunningOnChromeOS() ||
- chromeos::IBusDaemonController::GetInstance());
-
- if (chromeos::IBusDaemonController::GetInstance())
- chromeos::IBusDaemonController::GetInstance()->AddObserver(this);
+ UpdateContextFocusState();
+ OnInputMethodChanged();
}
InputMethodIBus::~InputMethodIBus() {
AbandonAllPendingKeyEvents();
- if (IsContextReady())
- DestroyContext();
- if (GetInputContextClient())
- GetInputContextClient()->SetInputContextHandler(NULL);
- if (chromeos::IBusDaemonController::GetInstance())
- chromeos::IBusDaemonController::GetInstance()->RemoveObserver(this);
+ context_focused_ = false;
+ ConfirmCompositionText();
+ // We are dead, so we need to ask the client to stop relying on us.
+ OnInputMethodChanged();
+
+ chromeos::IBusBridge::Get()->SetInputContextHandler(NULL);
}
void InputMethodIBus::OnFocus() {
@@ -131,18 +117,6 @@ bool InputMethodIBus::OnUntranslatedIMEMessage(const base::NativeEvent& event,
return false;
}
-void InputMethodIBus::Init(bool focused) {
- // Initializes the connection to ibus daemon. It may happen asynchronously,
- // and as soon as the connection is established, the |context_| will be
- // created automatically.
-
- // Create the input context if the connection is already established.
- if (IsConnected())
- CreateContext();
-
- InputMethodBase::Init(focused);
-}
-
void InputMethodIBus::ProcessKeyEventDone(uint32 id,
XEvent* event,
uint32 ibus_keyval,
@@ -193,10 +167,8 @@ bool InputMethodIBus::DispatchKeyEvent(const base::NativeEvent& native_event) {
// TEXT_INPUT_TYPE_PASSWORD, to bypass the input method.
// Note: We need to send the key event to ibus even if the |context_| is not
// enabled, so that ibus can have a chance to enable the |context_|.
- if (!context_focused_ ||
- GetTextInputType() == TEXT_INPUT_TYPE_PASSWORD ||
- !GetInputContextClient() ||
- GetInputContextClient()->IsXKBLayout()) {
+ if (!context_focused_ || !GetEngine() ||
+ GetTextInputType() == TEXT_INPUT_TYPE_PASSWORD ) {
if (native_event->type == KeyPress) {
if (ExecuteCharacterComposer(ibus_keyval, ibus_keycode, ibus_state)) {
// Treating as PostIME event if character composer handles key event and
@@ -214,24 +186,22 @@ bool InputMethodIBus::DispatchKeyEvent(const base::NativeEvent& native_event) {
pending_key_events_.insert(current_keyevent_id_);
// Since |native_event| might be treated as XEvent whose size is bigger than
- // XKeyEvent e.g. in CopyNativeEvent() in ui/base/events/event.cc, allocating
+ // XKeyEvent e.g. in CopyNativeEvent() in ui/events/event.cc, allocating
// |event| as XKeyEvent and casting it to XEvent is unsafe. crbug.com/151884
XEvent* event = new XEvent;
*event = *native_event;
- const chromeos::IBusInputContextClient::ProcessKeyEventCallback callback =
+ GetEngine()->ProcessKeyEvent(
+ ibus_keyval,
+ ibus_keycode,
+ ibus_state,
base::Bind(&InputMethodIBus::ProcessKeyEventDone,
weak_ptr_factory_.GetWeakPtr(),
current_keyevent_id_,
base::Owned(event), // Pass the ownership of |event|.
ibus_keyval,
ibus_keycode,
- ibus_state);
+ ibus_state));
- GetInputContextClient()->ProcessKeyEvent(ibus_keyval,
- ibus_keycode,
- ibus_state,
- callback,
- base::Bind(callback, false));
++current_keyevent_id_;
// We don't want to suppress the result generated by this key event, but it
@@ -255,9 +225,11 @@ bool InputMethodIBus::DispatchFabricatedKeyEvent(const ui::KeyEvent& event) {
}
void InputMethodIBus::OnTextInputTypeChanged(const TextInputClient* client) {
- if (IsContextReady() && IsTextInputClientFocused(client)) {
+ if (IsTextInputClientFocused(client)) {
ResetContext();
UpdateContextFocusState();
+ if (previous_textinput_type_ != client->GetTextInputType())
+ OnInputMethodChanged();
}
InputMethodBase::OnTextInputTypeChanged(client);
}
@@ -276,18 +248,22 @@ void InputMethodIBus::OnCaretBoundsChanged(const TextInputClient* client) {
composition_head = rect;
}
- GetInputContextClient()->SetCursorLocation(
+ chromeos::IBusPanelCandidateWindowHandlerInterface* candidate_window =
+ chromeos::IBusBridge::Get()->GetCandidateWindowHandler();
+ if (!candidate_window)
+ return;
+ candidate_window->SetCursorLocation(
GfxRectToIBusRect(rect),
GfxRectToIBusRect(composition_head));
- ui::Range text_range;
- ui::Range selection_range;
+ gfx::Range text_range;
+ gfx::Range selection_range;
string16 surrounding_text;
if (!GetTextInputClient()->GetTextRange(&text_range) ||
!GetTextInputClient()->GetTextFromRange(text_range, &surrounding_text) ||
!GetTextInputClient()->GetSelectionRange(&selection_range)) {
previous_surrounding_text_.clear();
- previous_selection_range_ = ui::Range::InvalidRange();
+ previous_selection_range_ = gfx::Range::InvalidRange();
return;
}
@@ -308,7 +284,9 @@ void InputMethodIBus::OnCaretBoundsChanged(const TextInputClient* client) {
// Here SetSurroundingText accepts relative position of |surrounding_text|, so
// we have to convert |selection_range| from node coordinates to
// |surrounding_text| coordinates.
- GetInputContextClient()->SetSurroundingText(
+ if (!GetEngine())
+ return;
+ GetEngine()->SetSurroundingText(
UTF16ToUTF8(surrounding_text),
selection_range.start() - text_range.start(),
selection_range.end() - text_range.start());
@@ -360,61 +338,6 @@ void InputMethodIBus::OnDidChangeFocusedClient(TextInputClient* focused_before,
OnCaretBoundsChanged(focused);
}
-void InputMethodIBus::CreateContext() {
- DCHECK(IsConnected());
-
- if (input_context_state_ != INPUT_CONTEXT_STOP) {
- DVLOG(1) << "Input context is already created or waiting ibus-daemon"
- " response.";
- return;
- }
-
- input_context_state_ = INPUT_CONTEXT_WAIT_CREATE_INPUT_CONTEXT_RESPONSE;
-
- // Creates the input context asynchronously.
- DCHECK(!IsContextReady());
- chromeos::DBusThreadManager::Get()->GetIBusClient()->CreateInputContext(
- kClientName,
- base::Bind(&InputMethodIBus::CreateInputContextDone,
- weak_ptr_factory_.GetWeakPtr()),
- base::Bind(&InputMethodIBus::CreateInputContextFail,
- weak_ptr_factory_.GetWeakPtr()));
-}
-
-void InputMethodIBus::SetUpSignalHandlers() {
- DCHECK(IsContextReady());
-
- // We should reset the handler to NULL before |this| is deleted so handler
- // functions are not called after |this| is deleted.
- GetInputContextClient()->SetInputContextHandler(this);
-
- GetInputContextClient()->SetCapabilities(
- kIBusCapabilityPreeditText | kIBusCapabilityFocus |
- kIBusCapabilitySurroundingText);
-
- UpdateContextFocusState();
- // Since ibus-daemon is launched in an on-demand basis on Chrome OS, RWHVA (or
- // equivalents) might call OnCaretBoundsChanged() before the daemon starts. To
- // save the case, call OnCaretBoundsChanged() here.
- OnCaretBoundsChanged(GetTextInputClient());
- OnInputMethodChanged();
-}
-
-void InputMethodIBus::DestroyContext() {
- if (input_context_state_ == INPUT_CONTEXT_STOP)
- return;
- input_context_state_ = INPUT_CONTEXT_STOP;
- chromeos::IBusInputContextClient* input_context = GetInputContextClient();
- if (!input_context)
- return;
- if (input_context->IsObjectProxyReady()) {
- // We can't use IsContextReady here because we want to destroy object proxy
- // regardless of connection. The IsContextReady contains connection check.
- ResetInputContext();
- DCHECK(!IsContextReady());
- }
-}
-
void InputMethodIBus::ConfirmCompositionText() {
TextInputClient* client = GetTextInputClient();
if (client && client->HasCompositionText())
@@ -453,17 +376,13 @@ void InputMethodIBus::ResetContext() {
// Note: some input method engines may not support reset method, such as
// ibus-anthy. But as we control all input method engines by ourselves, we can
// make sure that all of the engines we are using support it correctly.
- GetInputContextClient()->Reset();
+ if (GetEngine())
+ GetEngine()->Reset();
character_composer_.Reset();
}
void InputMethodIBus::UpdateContextFocusState() {
- if (!IsContextReady()) {
- context_focused_ = false;
- return;
- }
-
const bool old_context_focused = context_focused_;
// Use switch here in case we are going to add more text input types.
switch (GetTextInputType()) {
@@ -475,19 +394,16 @@ void InputMethodIBus::UpdateContextFocusState() {
context_focused_ = true;
break;
}
+ if (!GetEngine())
+ return;
// We only focus in |context_| when the focus is in a normal textfield.
// ibus_input_context_focus_{in|out}() run asynchronously.
- if (old_context_focused && !context_focused_)
- GetInputContextClient()->FocusOut();
- else if (!old_context_focused && context_focused_)
- GetInputContextClient()->FocusIn();
-
- if (context_focused_) {
- uint32 capability = kIBusCapabilityFocus | kIBusCapabilitySurroundingText;
- if (CanComposeInline())
- capability |= kIBusCapabilityPreeditText;
- GetInputContextClient()->SetCapabilities(capability);
+ if (old_context_focused && !context_focused_) {
+ GetEngine()->FocusOut();
+ } else if (!old_context_focused && context_focused_) {
+ GetEngine()->FocusIn();
+ OnCaretBoundsChanged(GetTextInputClient());
}
}
@@ -723,6 +639,13 @@ void InputMethodIBus::UpdatePreeditText(const chromeos::IBusText& text,
if (suppress_next_result_ || IsTextInputTypeNone())
return;
+ if (!CanComposeInline()) {
+ chromeos::IBusPanelCandidateWindowHandlerInterface* candidate_window =
+ chromeos::IBusBridge::Get()->GetCandidateWindowHandler();
+ if (candidate_window)
+ candidate_window->UpdatePreeditText(text.text(), cursor_pos, visible);
+ }
+
// |visible| argument is very confusing. For example, what's the correct
// behavior when:
// 1. OnUpdatePreeditText() is called with a text and visible == false, then
@@ -777,71 +700,6 @@ void InputMethodIBus::DeleteSurroundingText(int32 offset, uint32 length) {
GetTextInputClient()->ExtendSelectionAndDelete(length, 0U);
}
-void InputMethodIBus::ResetInputContext() {
- context_focused_ = false;
-
- ConfirmCompositionText();
-
- // We are dead, so we need to ask the client to stop relying on us.
- OnInputMethodChanged();
- GetInputContextClient()->ResetObjectProxy();
-}
-
-void InputMethodIBus::CreateInputContextDone(
- const dbus::ObjectPath& object_path) {
- DCHECK_NE(INPUT_CONTEXT_RUNNING, input_context_state_);
-
- if (input_context_state_ == INPUT_CONTEXT_STOP) {
- // DestroyContext has already been called.
- return;
- }
-
- chromeos::DBusThreadManager::Get()->GetIBusInputContextClient()
- ->Initialize(chromeos::DBusThreadManager::Get()->GetIBusBus(),
- object_path);
-
- input_context_state_ = INPUT_CONTEXT_RUNNING;
- DCHECK(IsContextReady());
- SetUpSignalHandlers();
-}
-
-void InputMethodIBus::CreateInputContextFail() {
- DCHECK_NE(INPUT_CONTEXT_RUNNING, input_context_state_);
- if (input_context_state_ == INPUT_CONTEXT_STOP) {
- // CreateInputContext failed but the input context is no longer
- // necessary, thus do nothing.
- return;
- }
-
- if (++create_input_context_fail_count_ >= kMaxRetryCount) {
- DVLOG(1) << "CreateInputContext failed even tried "
- << kMaxRetryCount << " times, give up.";
- create_input_context_fail_count_ = 0;
- input_context_state_ = INPUT_CONTEXT_STOP;
- return;
- }
-
- // Try CreateInputContext again.
- chromeos::DBusThreadManager::Get()->GetIBusClient()->CreateInputContext(
- kClientName,
- base::Bind(&InputMethodIBus::CreateInputContextDone,
- weak_ptr_factory_.GetWeakPtr()),
- base::Bind(&InputMethodIBus::CreateInputContextFail,
- weak_ptr_factory_.GetWeakPtr()));
-}
-
-bool InputMethodIBus::IsConnected() {
- return chromeos::DBusThreadManager::Get()->GetIBusBus() != NULL;
-}
-
-bool InputMethodIBus::IsContextReady() {
- if (!IsConnected())
- return false;
- if (!GetInputContextClient())
- return false;
- return GetInputContextClient()->IsObjectProxyReady();
-}
-
bool InputMethodIBus::ExecuteCharacterComposer(uint32 ibus_keyval,
uint32 ibus_keycode,
uint32 ibus_state) {
@@ -866,20 +724,6 @@ bool InputMethodIBus::ExecuteCharacterComposer(uint32 ibus_keyval,
return consumed;
}
-void InputMethodIBus::OnConnected() {
- DCHECK(IsConnected());
- // If already input context is initialized, do nothing.
- if (IsContextReady())
- return;
-
- DestroyContext();
- CreateContext();
-}
-
-void InputMethodIBus::OnDisconnected() {
- DestroyContext();
-}
-
void InputMethodIBus::ExtractCompositionText(
const chromeos::IBusText& text,
uint32 cursor_position,
@@ -907,7 +751,7 @@ void InputMethodIBus::ExtractCompositionText(
size_t cursor_offset =
char16_offsets[std::min(char_length, cursor_position)];
- out_composition->selection = Range(cursor_offset);
+ out_composition->selection = gfx::Range(cursor_offset);
const std::vector<chromeos::IBusText::UnderlineAttribute>&
underline_attributes = text.underline_attributes();
diff --git a/chromium/ui/base/ime/input_method_ibus.h b/chromium/ui/base/ime/input_method_ibus.h
index bc6aa6ec83c..3be172fdad5 100644
--- a/chromium/ui/base/ime/input_method_ibus.h
+++ b/chromium/ui/base/ime/input_method_ibus.h
@@ -12,8 +12,7 @@
#include "base/compiler_specific.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/weak_ptr.h"
-#include "chromeos/dbus/ibus/ibus_input_context_client.h"
-#include "chromeos/ime/ibus_daemon_controller.h"
+#include "chromeos/ime/ibus_bridge.h"
#include "ui/base/ime/character_composer.h"
#include "ui/base/ime/composition_text.h"
#include "ui/base/ime/input_method_base.h"
@@ -32,8 +31,7 @@ namespace ui {
// A ui::InputMethod implementation based on IBus.
class UI_EXPORT InputMethodIBus
: public InputMethodBase,
- public chromeos::IBusInputContextHandlerInterface,
- public chromeos::IBusDaemonController::Observer {
+ public chromeos::IBusInputContextHandlerInterface {
public:
explicit InputMethodIBus(internal::InputMethodDelegate* delegate);
virtual ~InputMethodIBus();
@@ -43,7 +41,6 @@ class UI_EXPORT InputMethodIBus
virtual void OnBlur() OVERRIDE;
virtual bool OnUntranslatedIMEMessage(const base::NativeEvent& event,
NativeEventResult* result) OVERRIDE;
- virtual void Init(bool focused) OVERRIDE;
virtual bool DispatchKeyEvent(
const base::NativeEvent& native_key_event) OVERRIDE;
virtual bool DispatchFabricatedKeyEvent(const ui::KeyEvent& event) OVERRIDE;
@@ -57,10 +54,6 @@ class UI_EXPORT InputMethodIBus
virtual bool IsCandidatePopupOpen() const OVERRIDE;
protected:
- // chromeos::IBusDaemonController::Observer overrides.
- virtual void OnConnected() OVERRIDE;
- virtual void OnDisconnected() OVERRIDE;
-
// Converts |text| into CompositionText.
void ExtractCompositionText(const chromeos::IBusText& text,
uint32 cursor_position,
@@ -82,15 +75,6 @@ class UI_EXPORT InputMethodIBus
void ResetContext();
private:
- enum InputContextState {
- // The input context is not working.
- INPUT_CONTEXT_STOP,
- // The input context is waiting for CreateInputContext reply from
- // ibus-daemon.
- INPUT_CONTEXT_WAIT_CREATE_INPUT_CONTEXT_RESPONSE,
- // The input context is working and ready to communicate with ibus-daemon.
- INPUT_CONTEXT_RUNNING,
- };
class PendingKeyEvent;
// Overridden from InputMethodBase:
@@ -99,15 +83,6 @@ class UI_EXPORT InputMethodIBus
virtual void OnDidChangeFocusedClient(TextInputClient* focused_before,
TextInputClient* focused) OVERRIDE;
- // Creates context asynchronously.
- void CreateContext();
-
- // Sets necessary signal handlers.
- void SetUpSignalHandlers();
-
- // Destroys context.
- void DestroyContext();
-
// Asks the client to confirm current composition text.
void ConfirmCompositionText();
@@ -142,16 +117,6 @@ class UI_EXPORT InputMethodIBus
// focus, the text input type is changed or we are destroyed.
void AbandonAllPendingKeyEvents();
- // Releases context focus and confirms the composition text. Then destroy
- // object proxy.
- void ResetInputContext();
-
- // Returns true if the connection to ibus-daemon is established.
- bool IsConnected();
-
- // Returns true if the input context is ready to use.
- bool IsContextReady();
-
// Passes keyevent and executes character composition if necessary. Returns
// true if character composer comsumes key event.
bool ExecuteCharacterComposer(uint32 ibus_keyval,
@@ -170,8 +135,6 @@ class UI_EXPORT InputMethodIBus
bool visible) OVERRIDE;
virtual void DeleteSurroundingText(int32 offset, uint32 length) OVERRIDE;
- void CreateInputContextDone(const dbus::ObjectPath& object_path);
- void CreateInputContextFail();
void ProcessKeyEventDone(uint32 id, XEvent* xevent,
uint32 ibus_keyval, uint32 ibus_keycode,
uint32 ibus_state, bool is_handled);
@@ -181,12 +144,6 @@ class UI_EXPORT InputMethodIBus
// They will be deleted in ProcessKeyEventDone().
std::set<uint32> pending_key_events_;
- // Represents input context's state.
- InputContextState input_context_state_;
-
- // The count of CreateInputContext message failure.
- int create_input_context_fail_count_;
-
// Pending composition text generated by the current pending key event.
// It'll be sent to the focused text input client as soon as we receive the
// processing result of the pending key event.
@@ -198,7 +155,7 @@ class UI_EXPORT InputMethodIBus
string16 result_text_;
string16 previous_surrounding_text_;
- ui::Range previous_selection_range_;
+ gfx::Range previous_selection_range_;
// Indicates if input context is focused or not.
bool context_focused_;
@@ -220,6 +177,8 @@ class UI_EXPORT InputMethodIBus
// including dead key etc.
CharacterComposer character_composer_;
+ TextInputType previous_textinput_type_;
+
// Used for making callbacks.
base::WeakPtrFactory<InputMethodIBus> weak_ptr_factory_;
diff --git a/chromium/ui/base/ime/input_method_ibus_unittest.cc b/chromium/ui/base/ime/input_method_ibus_unittest.cc
index 99accfa42c6..b88894c9418 100644
--- a/chromium/ui/base/ime/input_method_ibus_unittest.cc
+++ b/chromium/ui/base/ime/input_method_ibus_unittest.cc
@@ -16,9 +16,10 @@
#include "chromeos/dbus/dbus_thread_manager.h"
#include "chromeos/dbus/ibus/ibus_text.h"
#include "chromeos/dbus/ibus/mock_ibus_client.h"
-#include "chromeos/dbus/ibus/mock_ibus_input_context_client.h"
#include "chromeos/dbus/mock_dbus_thread_manager_without_gmock.h"
-#include "chromeos/ime/mock_ibus_daemon_controller.h"
+#include "chromeos/ime/ibus_bridge.h"
+#include "chromeos/ime/mock_ime_candidate_window_handler.h"
+#include "chromeos/ime/mock_ime_engine_handler.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/base/ime/input_method_delegate.h"
#include "ui/base/ime/input_method_ibus.h"
@@ -38,6 +39,9 @@ const uint32 kTestIBusState1 = 99;
const uint32 kTestIBusState2 = 46;
const uint32 kTestIBusState3 = 8;
+typedef chromeos::IBusEngineHandlerInterface::KeyEventDoneCallback
+ KeyEventCallback;
+
uint32 GetOffsetInUTF16(const std::string& utf8_string, uint32 utf8_offset) {
string16 utf16_string = UTF8ToUTF16(utf8_string);
DCHECK_LT(utf8_offset, utf16_string.size());
@@ -58,7 +62,6 @@ bool IsEqualXKeyEvent(const XEvent& e1, const XEvent& e2) {
enum KeyEventHandlerBehavior {
KEYEVENT_CONSUME,
KEYEVENT_NOT_CONSUME,
- KEYEVENT_ERROR,
};
} // namespace
@@ -149,8 +152,7 @@ class CreateInputContextSuccessHandler {
}
void Run(const std::string& client_name,
- const chromeos::IBusClient::CreateInputContextCallback& callback,
- const chromeos::IBusClient::ErrorCallback& error_callback) {
+ const chromeos::IBusClient::CreateInputContextCallback& callback) {
EXPECT_EQ("chrome", client_name);
callback.Run(object_path_);
}
@@ -161,25 +163,11 @@ class CreateInputContextSuccessHandler {
DISALLOW_COPY_AND_ASSIGN(CreateInputContextSuccessHandler);
};
-class CreateInputContextFailHandler {
- public:
- CreateInputContextFailHandler() {}
- void Run(const std::string& client_name,
- const chromeos::IBusClient::CreateInputContextCallback& callback,
- const chromeos::IBusClient::ErrorCallback& error_callback) {
- error_callback.Run();
- }
-
- private:
- DISALLOW_COPY_AND_ASSIGN(CreateInputContextFailHandler);
-};
-
class CreateInputContextNoResponseHandler {
public:
CreateInputContextNoResponseHandler() {}
void Run(const std::string& client_name,
- const chromeos::IBusClient::CreateInputContextCallback& callback,
- const chromeos::IBusClient::ErrorCallback& error_callback) {
+ const chromeos::IBusClient::CreateInputContextCallback& callback) {
}
private:
@@ -193,23 +181,17 @@ class CreateInputContextDelayHandler {
}
void Run(const std::string& client_name,
- const chromeos::IBusClient::CreateInputContextCallback& callback,
- const chromeos::IBusClient::ErrorCallback& error_callback) {
+ const chromeos::IBusClient::CreateInputContextCallback& callback) {
callback_ = callback;
- error_callback_ = error_callback;
}
- void RunCallback(bool success) {
- if (success)
- callback_.Run(object_path_);
- else
- error_callback_.Run();
+ void RunCallback() {
+ callback_.Run(object_path_);
}
private:
dbus::ObjectPath object_path_;
chromeos::IBusClient::CreateInputContextCallback callback_;
- chromeos::IBusClient::ErrorCallback error_callback_;
DISALLOW_COPY_AND_ASSIGN(CreateInputContextDelayHandler);
};
@@ -230,15 +212,11 @@ class SynchronousKeyEventHandler {
void Run(uint32 keyval,
uint32 keycode,
uint32 state,
- const IBusInputContextClient::ProcessKeyEventCallback& callback,
- const IBusInputContextClient::ErrorCallback& error_callback) {
+ const KeyEventCallback& callback) {
EXPECT_EQ(expected_keyval_, keyval);
EXPECT_EQ(expected_keycode_, keycode);
EXPECT_EQ(expected_state_, state);
- if (behavior_ == KEYEVENT_ERROR)
- error_callback.Run();
- else
- callback.Run(behavior_ == KEYEVENT_CONSUME);
+ callback.Run(behavior_ == KEYEVENT_CONSUME);
}
private:
@@ -264,28 +242,22 @@ class AsynchronousKeyEventHandler {
void Run(uint32 keyval,
uint32 keycode,
uint32 state,
- const IBusInputContextClient::ProcessKeyEventCallback& callback,
- const IBusInputContextClient::ErrorCallback& error_callback) {
+ const KeyEventCallback& callback) {
EXPECT_EQ(expected_keyval_, keyval);
EXPECT_EQ(expected_keycode_, keycode);
EXPECT_EQ(expected_state_, state);
callback_ = callback;
- error_callback_ = error_callback;
}
void RunCallback(KeyEventHandlerBehavior behavior) {
- if (behavior == KEYEVENT_ERROR)
- error_callback_.Run();
- else
- callback_.Run(behavior == KEYEVENT_CONSUME);
+ callback_.Run(behavior == KEYEVENT_CONSUME);
}
private:
const uint32 expected_keyval_;
const uint32 expected_keycode_;
const uint32 expected_state_;
- IBusInputContextClient::ProcessKeyEventCallback callback_;
- IBusInputContextClient::ErrorCallback error_callback_;
+ KeyEventCallback callback_;
DISALLOW_COPY_AND_ASSIGN(AsynchronousKeyEventHandler);
};
@@ -328,17 +300,17 @@ class InputMethodIBusTest : public internal::InputMethodDelegate,
// testing::Test overrides:
virtual void SetUp() OVERRIDE {
- // |thread_manager_| will be released by DBusThreadManager::Shutdown
- // function in TearDown function.
- // Current MockIBusInputContext is strongly depend on gmock, but gmock is
- // banned in ui/*. So just use stab implementation for testing.
- mock_dbus_thread_manager_ =
- new chromeos::MockDBusThreadManagerWithoutGMock();
- chromeos::DBusThreadManager::InitializeForTesting(
- mock_dbus_thread_manager_);
- mock_ibus_daemon_controller_ = new chromeos::MockIBusDaemonController();
- chromeos::IBusDaemonController::InitializeForTesting(
- mock_ibus_daemon_controller_);
+ chromeos::IBusBridge::Initialize();
+
+ mock_ime_engine_handler_.reset(
+ new chromeos::MockIMEEngineHandler());
+ chromeos::IBusBridge::Get()->SetEngineHandler(
+ mock_ime_engine_handler_.get());
+
+ mock_ime_candidate_window_handler_.reset(
+ new chromeos::MockIMECandidateWindowHandler());
+ chromeos::IBusBridge::Get()->SetCandidateWindowHandler(
+ mock_ime_candidate_window_handler_.get());
ime_.reset(new TestableInputMethodIBus(this));
ime_->SetFocusedTextInputClient(this);
@@ -348,18 +320,11 @@ class InputMethodIBusTest : public internal::InputMethodDelegate,
if (ime_.get())
ime_->SetFocusedTextInputClient(NULL);
ime_.reset();
- chromeos::DBusThreadManager::Shutdown();
- chromeos::IBusDaemonController::Shutdown();
- }
-
- // Helper function to initialize IBus connection for testing.
- void InitIBusBus() {
- mock_dbus_thread_manager_->InitIBusBus("dummy address",
- base::Bind(&base::DoNothing));
- mock_ibus_client_ = mock_dbus_thread_manager_->mock_ibus_client();
- mock_ibus_input_context_client_ =
- mock_dbus_thread_manager_->mock_ibus_input_context_client();
-
+ chromeos::IBusBridge::Get()->SetEngineHandler(NULL);
+ chromeos::IBusBridge::Get()->SetCandidateWindowHandler(NULL);
+ mock_ime_engine_handler_.reset();
+ mock_ime_candidate_window_handler_.reset();
+ chromeos::IBusBridge::Shutdown();
}
// ui::internal::InputMethodDelegate overrides:
@@ -419,19 +384,19 @@ class InputMethodIBusTest : public internal::InputMethodDelegate,
CompositionText empty;
return composition_text_ != empty;
}
- virtual bool GetTextRange(Range* range) OVERRIDE {
+ virtual bool GetTextRange(gfx::Range* range) OVERRIDE {
*range = text_range_;
return true;
}
- virtual bool GetCompositionTextRange(Range* range) OVERRIDE { return false; }
- virtual bool GetSelectionRange(Range* range) OVERRIDE {
+ virtual bool GetCompositionTextRange(gfx::Range* range) OVERRIDE { return false; }
+ virtual bool GetSelectionRange(gfx::Range* range) OVERRIDE {
*range = selection_range_;
return true;
}
- virtual bool SetSelectionRange(const Range& range) OVERRIDE { return false; }
- virtual bool DeleteRange(const Range& range) OVERRIDE { return false; }
- virtual bool GetTextFromRange(const Range& range, string16* text) OVERRIDE {
+ virtual bool SetSelectionRange(const gfx::Range& range) OVERRIDE { return false; }
+ virtual bool DeleteRange(const gfx::Range& range) OVERRIDE { return false; }
+ virtual bool GetTextFromRange(const gfx::Range& range, string16* text) OVERRIDE {
*text = surrounding_text_.substr(range.GetMin(), range.length());
return true;
}
@@ -471,14 +436,6 @@ class InputMethodIBusTest : public internal::InputMethodDelegate,
caret_bounds_ = gfx::Rect();
}
- void SetCreateContextSuccessHandler() {
- CreateInputContextSuccessHandler create_input_context_handler(
- dbus::ObjectPath("InputContext_1"));
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextSuccessHandler::Run,
- base::Unretained(&create_input_context_handler)));
- }
-
scoped_ptr<TestableInputMethodIBus> ime_;
// Variables for remembering the parameters that are passed to
@@ -501,15 +458,13 @@ class InputMethodIBusTest : public internal::InputMethodDelegate,
TextInputType input_type_;
bool can_compose_inline_;
gfx::Rect caret_bounds_;
- ui::Range text_range_;
- ui::Range selection_range_;
+ gfx::Range text_range_;
+ gfx::Range selection_range_;
string16 surrounding_text_;
- // Variables for mock dbus connections.
- chromeos::MockDBusThreadManagerWithoutGMock* mock_dbus_thread_manager_;
- chromeos::MockIBusClient* mock_ibus_client_;
- chromeos::MockIBusInputContextClient* mock_ibus_input_context_client_;
- chromeos::MockIBusDaemonController* mock_ibus_daemon_controller_;
+ scoped_ptr<chromeos::MockIMEEngineHandler> mock_ime_engine_handler_;
+ scoped_ptr<chromeos::MockIMECandidateWindowHandler>
+ mock_ime_candidate_window_handler_;
DISALLOW_COPY_AND_ASSIGN(InputMethodIBusTest);
};
@@ -602,209 +557,6 @@ TEST_F(InputMethodIBusTest, GetInputTextType_WithoutFocusedWindow2) {
EXPECT_EQ(TEXT_INPUT_TYPE_PASSWORD, ime_->GetTextInputType());
}
-// Then, tests internal behavior of ui::InputMethodIBus, especially if the input
-// method implementation calls ui::internal::IBusClient APIs as expected.
-
-// Start ibus-daemon first, then create ui::InputMethodIBus. Check if a new
-// input context is created.
-TEST_F(InputMethodIBusTest, InitiallyConnected) {
- InitIBusBus();
- SetCreateContextSuccessHandler();
- ime_->Init(true);
- // An input context should be created immediately since is_connected_ is true.
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->set_capabilities_call_count());
- // However, since the current text input type is 'NONE' (the default), FocusIn
- // shouldn't be called.
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_TRUE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Create ui::InputMethodIBus, then start ibus-daemon.
-TEST_F(InputMethodIBusTest, InitiallyDisconnected) {
- ime_->Init(true);
- // Start the daemon.
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
- // A context should be created upon the signal delivery.
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_TRUE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash on "disconnected" signal
-// delivery.
-TEST_F(InputMethodIBusTest, Disconnect) {
- InitIBusBus();
- SetCreateContextSuccessHandler();
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- // Currently we can't shutdown IBusBus connection except in
- // DBusThreadManager's shutting down. So set ibus_bus_ as NULL to emulate
- // dynamical shutting down.
- mock_dbus_thread_manager_->set_ibus_bus(NULL);
- mock_ibus_daemon_controller_->EmulateDisconnect();
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus re-creates an input context when ibus-daemon
-// restarts.
-TEST_F(InputMethodIBusTest, DisconnectThenReconnect) {
- InitIBusBus();
- SetCreateContextSuccessHandler();
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_EQ(0,
- mock_ibus_input_context_client_->reset_object_proxy_call_caount());
- mock_dbus_thread_manager_->set_ibus_bus(NULL);
- mock_ibus_daemon_controller_->EmulateDisconnect();
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
- mock_ibus_daemon_controller_->EmulateDisconnect();
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
- // Check if the old context is deleted.
- EXPECT_EQ(0,
- mock_ibus_input_context_client_->reset_object_proxy_call_caount());
- // Check if a new context is created.
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_TRUE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash even if NULL context is
-// passed.
-// TODO(yusukes): Currently, ui::InputMethodIBus does not try to create ic once
-// it fails (unless ibus sends the "connected" signal to Chrome again). It might
-// be better to add some retry logic. Will revisit later.
-TEST_F(InputMethodIBusTest, CreateContextFail) {
- InitIBusBus();
- CreateInputContextFailHandler create_input_context_handler;
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextFailHandler::Run,
- base::Unretained(&create_input_context_handler)));
- ime_->Init(true);
- // InputMethodIBus tries several times if the CreateInputContext method call
- // is failed.
- EXPECT_EQ(kCreateInputContextMaxTrialCount,
- mock_ibus_client_->create_input_context_call_count());
- // |set_capabilities_call_count()| should be zero since a context is not
- // created yet.
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash even if ibus-daemon does not
-// respond.
-TEST_F(InputMethodIBusTest, CreateContextNoResp) {
- InitIBusBus();
- CreateInputContextNoResponseHandler create_input_context_handler;
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextNoResponseHandler::Run,
- base::Unretained(&create_input_context_handler)));
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash even if ibus-daemon responds
-// after ui::InputMethodIBus is deleted.
-TEST_F(InputMethodIBusTest, CreateContextFailDelayed) {
- InitIBusBus();
- CreateInputContextDelayHandler create_input_context_handler(
- dbus::ObjectPath("Sample object path"));
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextDelayHandler::Run,
- base::Unretained(&create_input_context_handler)));
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- ime_->SetFocusedTextInputClient(NULL);
- ime_.reset();
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- create_input_context_handler.RunCallback(false);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash even if ibus-daemon responds
-// after ui::InputMethodIBus is deleted.
-TEST_F(InputMethodIBusTest, CreateContextSuccessDelayed) {
- InitIBusBus();
- CreateInputContextDelayHandler create_input_context_handler(
- dbus::ObjectPath("Sample object path"));
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextDelayHandler::Run,
- base::Unretained(&create_input_context_handler)));
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- ime_->SetFocusedTextInputClient(NULL);
- ime_.reset();
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- create_input_context_handler.RunCallback(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash even if ibus-daemon responds
-// after disconnected from ibus-daemon.
-TEST_F(InputMethodIBusTest, CreateContextSuccessDelayedAfterDisconnection) {
- InitIBusBus();
- CreateInputContextDelayHandler create_input_context_handler(
- dbus::ObjectPath("Sample object path"));
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextDelayHandler::Run,
- base::Unretained(&create_input_context_handler)));
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- mock_ibus_daemon_controller_->EmulateDisconnect();
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- create_input_context_handler.RunCallback(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
-// Confirm that ui::InputMethodIBus does not crash even if ibus-daemon responds
-// after disconnected from ibus-daemon.
-TEST_F(InputMethodIBusTest, CreateContextFailDelayedAfterDisconnection) {
- InitIBusBus();
- CreateInputContextDelayHandler create_input_context_handler(
- dbus::ObjectPath("Sample object path"));
- mock_ibus_client_->set_create_input_context_handler(base::Bind(
- &CreateInputContextDelayHandler::Run,
- base::Unretained(&create_input_context_handler)));
- ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- mock_ibus_daemon_controller_->EmulateDisconnect();
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-
- create_input_context_handler.RunCallback(false);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->set_capabilities_call_count());
- EXPECT_FALSE(mock_ibus_input_context_client_->IsObjectProxyReady());
-}
-
// Confirm that IBusClient::FocusIn is called on "connected" if input_type_ is
// TEXT.
TEST_F(InputMethodIBusTest, FocusIn_Text) {
@@ -814,16 +566,11 @@ TEST_F(InputMethodIBusTest, FocusIn_Text) {
// Click a text input form.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
- // Start the daemon.
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
- // A context should be created upon the signal delivery.
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
// Since a form has focus, IBusClient::FocusIn() should be called.
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(1,
- mock_ibus_input_context_client_->set_cursor_location_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(
+ 1,
+ mock_ime_candidate_window_handler_->set_cursor_location_call_count());
// ui::TextInputClient::OnInputMethodChanged() should be called when
// ui::InputMethodIBus connects/disconnects to/from ibus-daemon and the
// current text input type is not NONE.
@@ -837,82 +584,71 @@ TEST_F(InputMethodIBusTest, FocusIn_Password) {
EXPECT_EQ(0U, on_input_method_changed_call_count_);
input_type_ = TEXT_INPUT_TYPE_PASSWORD;
ime_->OnTextInputTypeChanged(this);
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
// Since a form has focus, IBusClient::FocusIn() should NOT be called.
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_in_call_count());
+ EXPECT_EQ(0, mock_ime_engine_handler_->focus_in_call_count());
EXPECT_EQ(1U, on_input_method_changed_call_count_);
}
// Confirm that IBusClient::FocusOut is called as expected.
TEST_F(InputMethodIBusTest, FocusOut_None) {
input_type_ = TEXT_INPUT_TYPE_TEXT;
- InitIBusBus();
- SetCreateContextSuccessHandler();
ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_out_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(0, mock_ime_engine_handler_->focus_out_call_count());
input_type_ = TEXT_INPUT_TYPE_NONE;
ime_->OnTextInputTypeChanged(this);
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_out_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_out_call_count());
}
// Confirm that IBusClient::FocusOut is called as expected.
TEST_F(InputMethodIBusTest, FocusOut_Password) {
input_type_ = TEXT_INPUT_TYPE_TEXT;
- InitIBusBus();
- SetCreateContextSuccessHandler();
ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_out_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(0, mock_ime_engine_handler_->focus_out_call_count());
input_type_ = TEXT_INPUT_TYPE_PASSWORD;
ime_->OnTextInputTypeChanged(this);
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_out_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_out_call_count());
}
// Confirm that IBusClient::FocusOut is NOT called.
TEST_F(InputMethodIBusTest, FocusOut_Url) {
input_type_ = TEXT_INPUT_TYPE_TEXT;
- InitIBusBus();
- SetCreateContextSuccessHandler();
ime_->Init(true);
- EXPECT_EQ(1, mock_ibus_client_->create_input_context_call_count());
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_out_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(0, mock_ime_engine_handler_->focus_out_call_count());
input_type_ = TEXT_INPUT_TYPE_URL;
ime_->OnTextInputTypeChanged(this);
- EXPECT_EQ(1, mock_ibus_input_context_client_->focus_in_call_count());
- EXPECT_EQ(0, mock_ibus_input_context_client_->focus_out_call_count());
+ EXPECT_EQ(1, mock_ime_engine_handler_->focus_in_call_count());
+ EXPECT_EQ(0, mock_ime_engine_handler_->focus_out_call_count());
}
// Test if the new |caret_bounds_| is correctly sent to ibus-daemon.
TEST_F(InputMethodIBusTest, OnCaretBoundsChanged) {
- InitIBusBus();
- SetCreateContextSuccessHandler();
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->Init(true);
- EXPECT_EQ(0,
- mock_ibus_input_context_client_->set_cursor_location_call_count());
+ EXPECT_EQ(
+ 1,
+ mock_ime_candidate_window_handler_->set_cursor_location_call_count());
caret_bounds_ = gfx::Rect(1, 2, 3, 4);
ime_->OnCaretBoundsChanged(this);
- EXPECT_EQ(1,
- mock_ibus_input_context_client_->set_cursor_location_call_count());
+ EXPECT_EQ(
+ 2,
+ mock_ime_candidate_window_handler_->set_cursor_location_call_count());
caret_bounds_ = gfx::Rect(0, 2, 3, 4);
ime_->OnCaretBoundsChanged(this);
- EXPECT_EQ(2,
- mock_ibus_input_context_client_->set_cursor_location_call_count());
+ EXPECT_EQ(
+ 3,
+ mock_ime_candidate_window_handler_->set_cursor_location_call_count());
caret_bounds_ = gfx::Rect(0, 2, 3, 4); // unchanged
ime_->OnCaretBoundsChanged(this);
// Current InputMethodIBus implementation performs the IPC regardless of the
// bounds are changed or not.
- EXPECT_EQ(3,
- mock_ibus_input_context_client_->set_cursor_location_call_count());
+ EXPECT_EQ(
+ 4,
+ mock_ime_candidate_window_handler_->set_cursor_location_call_count());
}
TEST_F(InputMethodIBusTest, ExtractCompositionTextTest_NoAttribute) {
@@ -1121,28 +857,27 @@ TEST_F(InputMethodIBusTest, SurroundingText_NoSelectionTest) {
// Click a text input form.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
- // Start the daemon.
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
// Set the TextInputClient behaviors.
surrounding_text_ = UTF8ToUTF16("abcdef");
- text_range_ = ui::Range(0, 6);
- selection_range_ = ui::Range(3, 3);
+ text_range_ = gfx::Range(0, 6);
+ selection_range_ = gfx::Range(3, 3);
// Set the verifier for SetSurroundingText mock call.
SetSurroundingTextVerifier verifier(UTF16ToUTF8(surrounding_text_), 3, 3);
- mock_ibus_input_context_client_->set_set_surrounding_text_handler(
- base::Bind(&SetSurroundingTextVerifier::Verify,
- base::Unretained(&verifier)));
ime_->OnCaretBoundsChanged(this);
// Check the call count.
EXPECT_EQ(1,
- mock_ibus_input_context_client_->set_surrounding_text_call_count());
+ mock_ime_engine_handler_->set_surrounding_text_call_count());
+ EXPECT_EQ(UTF16ToUTF8(surrounding_text_),
+ mock_ime_engine_handler_->last_set_surrounding_text());
+ EXPECT_EQ(3U,
+ mock_ime_engine_handler_->last_set_surrounding_cursor_pos());
+ EXPECT_EQ(3U,
+ mock_ime_engine_handler_->last_set_surrounding_anchor_pos());
}
TEST_F(InputMethodIBusTest, SurroundingText_SelectionTest) {
@@ -1150,27 +885,26 @@ TEST_F(InputMethodIBusTest, SurroundingText_SelectionTest) {
// Click a text input form.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
- // Start the daemon.
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
// Set the TextInputClient behaviors.
surrounding_text_ = UTF8ToUTF16("abcdef");
- text_range_ = ui::Range(0, 6);
- selection_range_ = ui::Range(2, 5);
+ text_range_ = gfx::Range(0, 6);
+ selection_range_ = gfx::Range(2, 5);
// Set the verifier for SetSurroundingText mock call.
SetSurroundingTextVerifier verifier(UTF16ToUTF8(surrounding_text_), 2, 5);
- mock_ibus_input_context_client_->set_set_surrounding_text_handler(
- base::Bind(&SetSurroundingTextVerifier::Verify,
- base::Unretained(&verifier)));
ime_->OnCaretBoundsChanged(this);
// Check the call count.
EXPECT_EQ(1,
- mock_ibus_input_context_client_->set_surrounding_text_call_count());
+ mock_ime_engine_handler_->set_surrounding_text_call_count());
+ EXPECT_EQ(UTF16ToUTF8(surrounding_text_),
+ mock_ime_engine_handler_->last_set_surrounding_text());
+ EXPECT_EQ(2U,
+ mock_ime_engine_handler_->last_set_surrounding_cursor_pos());
+ EXPECT_EQ(5U,
+ mock_ime_engine_handler_->last_set_surrounding_anchor_pos());
}
TEST_F(InputMethodIBusTest, SurroundingText_PartialText) {
@@ -1178,28 +912,25 @@ TEST_F(InputMethodIBusTest, SurroundingText_PartialText) {
// Click a text input form.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
- // Start the daemon.
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
// Set the TextInputClient behaviors.
surrounding_text_ = UTF8ToUTF16("abcdefghij");
- text_range_ = ui::Range(5, 10);
- selection_range_ = ui::Range(7, 9);
-
- // Set the verifier for SetSurroundingText mock call.
- // Here (2, 4) is selection range in expected surrounding text coordinates.
- SetSurroundingTextVerifier verifier("fghij", 2, 4);
+ text_range_ = gfx::Range(5, 10);
+ selection_range_ = gfx::Range(7, 9);
- mock_ibus_input_context_client_->set_set_surrounding_text_handler(
- base::Bind(&SetSurroundingTextVerifier::Verify,
- base::Unretained(&verifier)));
ime_->OnCaretBoundsChanged(this);
// Check the call count.
EXPECT_EQ(1,
- mock_ibus_input_context_client_->set_surrounding_text_call_count());
+ mock_ime_engine_handler_->set_surrounding_text_call_count());
+ // Set the verifier for SetSurroundingText mock call.
+ // Here (2, 4) is selection range in expected surrounding text coordinates.
+ EXPECT_EQ("fghij",
+ mock_ime_engine_handler_->last_set_surrounding_text());
+ EXPECT_EQ(2U,
+ mock_ime_engine_handler_->last_set_surrounding_cursor_pos());
+ EXPECT_EQ(4U,
+ mock_ime_engine_handler_->last_set_surrounding_anchor_pos());
}
TEST_F(InputMethodIBusTest, SurroundingText_BecomeEmptyText) {
@@ -1207,34 +938,24 @@ TEST_F(InputMethodIBusTest, SurroundingText_BecomeEmptyText) {
// Click a text input form.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
- // Start the daemon.
- InitIBusBus();
- SetCreateContextSuccessHandler();
- mock_ibus_daemon_controller_->EmulateConnect();
// Set the TextInputClient behaviors.
// If the surrounding text becomes empty, text_range become (0, 0) and
// selection range become invalid.
surrounding_text_ = UTF8ToUTF16("");
- text_range_ = ui::Range(0, 0);
- selection_range_ = ui::Range::InvalidRange();
-
- // Set the verifier for SetSurroundingText mock call.
- SetSurroundingTextVerifier verifier("", 0, 0);
+ text_range_ = gfx::Range(0, 0);
+ selection_range_ = gfx::Range::InvalidRange();
- mock_ibus_input_context_client_->set_set_surrounding_text_handler(
- base::Bind(&SetSurroundingTextVerifier::Verify,
- base::Unretained(&verifier)));
ime_->OnCaretBoundsChanged(this);
// Check the call count.
EXPECT_EQ(0,
- mock_ibus_input_context_client_->set_surrounding_text_call_count());
+ mock_ime_engine_handler_->set_surrounding_text_call_count());
// Should not be called twice with same condition.
ime_->OnCaretBoundsChanged(this);
EXPECT_EQ(0,
- mock_ibus_input_context_client_->set_surrounding_text_call_count());
+ mock_ime_engine_handler_->set_surrounding_text_call_count());
}
class InputMethodIBusKeyEventTest : public InputMethodIBusTest {
@@ -1244,52 +965,13 @@ class InputMethodIBusKeyEventTest : public InputMethodIBusTest {
virtual void SetUp() OVERRIDE {
InputMethodIBusTest::SetUp();
- InitIBusBus();
- SetCreateContextSuccessHandler();
ime_->Init(true);
- mock_ibus_daemon_controller_->EmulateConnect();
- mock_ibus_input_context_client_->SetIsXKBLayout(false);
}
DISALLOW_COPY_AND_ASSIGN(InputMethodIBusKeyEventTest);
};
-TEST_F(InputMethodIBusKeyEventTest, KeyEventConsumeTest) {
- XEvent event = {};
- event.xkey.type = KeyPress;
-
- // Set up IBusKeyEventFromNativeKeyEvent result.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState1;
-
- // Set up ProcessKeyEvent handler.
- SynchronousKeyEventHandler success_consume_handler(kTestIBusKeyVal1,
- kTestIBusKeyCode1,
- kTestIBusState1,
- KEYEVENT_CONSUME);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&SynchronousKeyEventHandler::Run,
- base::Unretained(&success_consume_handler)));
-
- // Do key event.
- input_type_ = TEXT_INPUT_TYPE_TEXT;
- ime_->OnTextInputTypeChanged(this);
- ime_->DispatchKeyEvent(&event);
-
- // Check result
- EXPECT_EQ(1,
- mock_ibus_input_context_client_->process_key_event_call_count());
- EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_TRUE(ime_->process_key_event_post_ime_args().handled);
-}
-
-TEST_F(InputMethodIBusKeyEventTest, KeyEventNotConsumeTest) {
+TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseTest) {
XEvent event = {};
event.xkey.type = KeyPress;
@@ -1301,82 +983,6 @@ TEST_F(InputMethodIBusKeyEventTest, KeyEventNotConsumeTest) {
ime_->mutable_ibus_key_event_from_native_key_event_result()->state
= kTestIBusState1;
- // Set up ProcessKeyEvent handler.
- SynchronousKeyEventHandler success_nonconsume_handler(kTestIBusKeyVal1,
- kTestIBusKeyCode1,
- kTestIBusState1,
- KEYEVENT_NOT_CONSUME);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&SynchronousKeyEventHandler::Run,
- base::Unretained(&success_nonconsume_handler)));
-
- // Do key event.
- input_type_ = TEXT_INPUT_TYPE_TEXT;
- ime_->OnTextInputTypeChanged(this);
- ime_->DispatchKeyEvent(&event);
-
- EXPECT_EQ(1,
- mock_ibus_input_context_client_->process_key_event_call_count());
- EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-}
-
-TEST_F(InputMethodIBusKeyEventTest, KeyEventFailTest) {
- XEvent event = {};
- event.xkey.type = KeyPress;
-
- // Set up IBusKeyEventFromNativeKeyEvent result.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState1;
-
- // Set up ProcessKeyEvent handler.
- SynchronousKeyEventHandler fail_handler(kTestIBusKeyVal1,
- kTestIBusKeyCode1,
- kTestIBusState1,
- KEYEVENT_ERROR);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&SynchronousKeyEventHandler::Run,
- base::Unretained(&fail_handler)));
-
- // Do key event.
- input_type_ = TEXT_INPUT_TYPE_TEXT;
- ime_->OnTextInputTypeChanged(this);
- ime_->DispatchKeyEvent(&event);
-
- // Check result
- EXPECT_EQ(1,
- mock_ibus_input_context_client_->process_key_event_call_count());
- EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
- // If some error is happend, key should not be consumed.
- EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-}
-
-TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseSuccessTest) {
- XEvent event = {};
- event.xkey.type = KeyPress;
-
- // Set up IBusKeyEventFromNativeKeyEvent result.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState1;
-
- // Set up ProcessKeyEvent handler.
- AsynchronousKeyEventHandler success_consume_handler(kTestIBusKeyVal1,
- kTestIBusKeyCode1,
- kTestIBusState1);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&success_consume_handler)));
-
// Do key event.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
@@ -1384,11 +990,17 @@ TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseSuccessTest) {
// Check before state.
EXPECT_EQ(1,
- mock_ibus_input_context_client_->process_key_event_call_count());
+ mock_ime_engine_handler_->process_key_event_call_count());
+ EXPECT_EQ(kTestIBusKeyVal1,
+ mock_ime_engine_handler_->last_processed_keysym());
+ EXPECT_EQ(kTestIBusKeyCode1,
+ mock_ime_engine_handler_->last_processed_keycode());
+ EXPECT_EQ(kTestIBusState1,
+ mock_ime_engine_handler_->last_processed_state());
EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
// Do callback.
- success_consume_handler.RunCallback(KEYEVENT_CONSUME);
+ mock_ime_engine_handler_->last_passed_callback().Run(true);
// Check the results
EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
@@ -1397,46 +1009,7 @@ TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseSuccessTest) {
EXPECT_TRUE(ime_->process_key_event_post_ime_args().handled);
}
-TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseFailTest) {
- XEvent event = {};
- event.xkey.type = KeyPress;
-
- // Set up IBusKeyEventFromNativeKeyEvent result.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState1;
-
- // Set up ProcessKeyEvent handler.
- AsynchronousKeyEventHandler fail_handler(kTestIBusKeyVal1, kTestIBusKeyCode1,
- kTestIBusState1);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&fail_handler)));
-
- // Do key event.
- input_type_ = TEXT_INPUT_TYPE_TEXT;
- ime_->OnTextInputTypeChanged(this);
- ime_->DispatchKeyEvent(&event);
-
- // Check before state.
- EXPECT_EQ(1,
- mock_ibus_input_context_client_->process_key_event_call_count());
- EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
-
- // Do callback.
- fail_handler.RunCallback(KEYEVENT_ERROR);
-
- // Check the results
- EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-}
-
-TEST_F(InputMethodIBusKeyEventTest, MultiKeyEventDelayResponseSuccessTest) {
+TEST_F(InputMethodIBusKeyEventTest, MultiKeyEventDelayResponseTest) {
// Preparation
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
@@ -1452,83 +1025,17 @@ TEST_F(InputMethodIBusKeyEventTest, MultiKeyEventDelayResponseSuccessTest) {
ime_->mutable_ibus_key_event_from_native_key_event_result()->state
= kTestIBusState1;
- // Set up ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler1(kTestIBusKeyVal1, kTestIBusKeyCode1,
- kTestIBusState1);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler1)));
-
// Do key event.
ime_->DispatchKeyEvent(&event);
+ EXPECT_EQ(kTestIBusKeyVal1,
+ mock_ime_engine_handler_->last_processed_keysym());
+ EXPECT_EQ(kTestIBusKeyCode1,
+ mock_ime_engine_handler_->last_processed_keycode());
+ EXPECT_EQ(kTestIBusState1,
+ mock_ime_engine_handler_->last_processed_state());
- // Set up IBusKeyEventFromNativeKeyEvent result for second key event.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal2;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode2;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState2;
-
- // Set up yet another ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler2(kTestIBusKeyVal2, kTestIBusKeyCode2,
- kTestIBusState2);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler2)));
-
- // Do key event again.
- ime_->DispatchKeyEvent(&event);
-
- // Check before state.
- EXPECT_EQ(2,
- mock_ibus_input_context_client_->process_key_event_call_count());
- EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
-
- // Do callback for first key event.
- handler1.RunCallback(KEYEVENT_CONSUME);
-
- // Check the results for first key event.
- EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_TRUE(ime_->process_key_event_post_ime_args().handled);
-
- // Do callback for second key event.
- handler2.RunCallback(KEYEVENT_NOT_CONSUME);
-
- // Check the results for second key event.
- EXPECT_EQ(2, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-}
-
-TEST_F(InputMethodIBusKeyEventTest, MultiKeyEventDelayResponseFailTest) {
- // Preparation
- input_type_ = TEXT_INPUT_TYPE_TEXT;
- ime_->OnTextInputTypeChanged(this);
-
- XEvent event = {};
- event.xkey.type = KeyPress;
-
- // Set up IBusKeyEventFromNativeKeyEvent result for first key event.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState1;
-
- // Set up ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler1(kTestIBusKeyVal1, kTestIBusKeyCode1,
- kTestIBusState1);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler1)));
-
- // Do key event.
- ime_->DispatchKeyEvent(&event);
+ KeyEventCallback first_callback =
+ mock_ime_engine_handler_->last_passed_callback();
// Set up IBusKeyEventFromNativeKeyEvent result for second key event.
ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
@@ -1538,110 +1045,22 @@ TEST_F(InputMethodIBusKeyEventTest, MultiKeyEventDelayResponseFailTest) {
ime_->mutable_ibus_key_event_from_native_key_event_result()->state
= kTestIBusState2;
- // Set up yet another ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler2(kTestIBusKeyVal2, kTestIBusKeyCode2,
- kTestIBusState2);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler2)));
-
// Do key event again.
ime_->DispatchKeyEvent(&event);
+ EXPECT_EQ(kTestIBusKeyVal2,
+ mock_ime_engine_handler_->last_processed_keysym());
+ EXPECT_EQ(kTestIBusKeyCode2,
+ mock_ime_engine_handler_->last_processed_keycode());
+ EXPECT_EQ(kTestIBusState2,
+ mock_ime_engine_handler_->last_processed_state());
// Check before state.
EXPECT_EQ(2,
- mock_ibus_input_context_client_->process_key_event_call_count());
- EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
-
- // Do callback for first key event.
- handler1.RunCallback(KEYEVENT_ERROR);
-
- // Check the results for first key event.
- EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-
- // Do callback for second key event.
- handler2.RunCallback(KEYEVENT_ERROR);
-
- // Check the results for second key event.
- EXPECT_EQ(2, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-}
-
-TEST_F(InputMethodIBusKeyEventTest,
- MultiKeyEventDelayResponseSuccessFailMixTest) {
- // Preparation
- input_type_ = TEXT_INPUT_TYPE_TEXT;
- ime_->OnTextInputTypeChanged(this);
-
- XEvent event = {};
- event.xkey.type = KeyPress;
-
- // Set up IBusKeyEventFromNativeKeyEvent result for first key event.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode1;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState1;
-
- // Set up ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler1(kTestIBusKeyVal1, kTestIBusKeyCode1,
- kTestIBusState1);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler1)));
-
- // Do key event.
- ime_->DispatchKeyEvent(&event);
-
- // Set up IBusKeyEventFromNativeKeyEvent result for second key event.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal2;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode2;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState2;
-
- // Set up yet another ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler2(kTestIBusKeyVal2, kTestIBusKeyCode2,
- kTestIBusState2);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler2)));
-
- // Do key event again.
- ime_->DispatchKeyEvent(&event);
-
- // Set up IBusKeyEventFromNativeKeyEvent result for second key event.
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keyval
- = kTestIBusKeyVal3;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->keycode
- = kTestIBusKeyCode3;
- ime_->mutable_ibus_key_event_from_native_key_event_result()->state
- = kTestIBusState3;
-
- // Set up yet another ProcessKeyEvent handler.
- AsynchronousKeyEventHandler handler3(kTestIBusKeyVal3, kTestIBusKeyCode3,
- kTestIBusState3);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&handler3)));
-
- // Do key event again.
- ime_->DispatchKeyEvent(&event);
-
- // Check before state.
- EXPECT_EQ(3,
- mock_ibus_input_context_client_->process_key_event_call_count());
+ mock_ime_engine_handler_->process_key_event_call_count());
EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
// Do callback for first key event.
- handler1.RunCallback(KEYEVENT_CONSUME);
+ first_callback.Run(true);
// Check the results for first key event.
EXPECT_EQ(1, ime_->process_key_event_post_ime_call_count());
@@ -1650,22 +1069,13 @@ TEST_F(InputMethodIBusKeyEventTest,
EXPECT_TRUE(ime_->process_key_event_post_ime_args().handled);
// Do callback for second key event.
- handler2.RunCallback(KEYEVENT_ERROR);
+ mock_ime_engine_handler_->last_passed_callback().Run(false);
// Check the results for second key event.
EXPECT_EQ(2, ime_->process_key_event_post_ime_call_count());
EXPECT_TRUE(IsEqualXKeyEvent(event,
ime_->process_key_event_post_ime_args().event));
EXPECT_FALSE(ime_->process_key_event_post_ime_args().handled);
-
- // Do callback for first key event.
- handler3.RunCallback(KEYEVENT_CONSUME);
-
- // Check the results for first key event.
- EXPECT_EQ(3, ime_->process_key_event_post_ime_call_count());
- EXPECT_TRUE(IsEqualXKeyEvent(event,
- ime_->process_key_event_post_ime_args().event));
- EXPECT_TRUE(ime_->process_key_event_post_ime_args().handled);
}
TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseResetTest) {
@@ -1680,14 +1090,6 @@ TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseResetTest) {
ime_->mutable_ibus_key_event_from_native_key_event_result()->state
= kTestIBusState1;
- // Set up ProcessKeyEvent handler.
- AsynchronousKeyEventHandler success_consume_handler(kTestIBusKeyVal1,
- kTestIBusKeyCode1,
- kTestIBusState1);
- mock_ibus_input_context_client_->set_process_key_event_handler(
- base::Bind(&AsynchronousKeyEventHandler::Run,
- base::Unretained(&success_consume_handler)));
-
// Do key event.
input_type_ = TEXT_INPUT_TYPE_TEXT;
ime_->OnTextInputTypeChanged(this);
@@ -1695,13 +1097,13 @@ TEST_F(InputMethodIBusKeyEventTest, KeyEventDelayResponseResetTest) {
// Check before state.
EXPECT_EQ(1,
- mock_ibus_input_context_client_->process_key_event_call_count());
+ mock_ime_engine_handler_->process_key_event_call_count());
EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
ime_->ResetContext();
// Do callback.
- success_consume_handler.RunCallback(KEYEVENT_CONSUME);
+ mock_ime_engine_handler_->last_passed_callback().Run(true);
EXPECT_EQ(0, ime_->process_key_event_post_ime_call_count());
}
diff --git a/chromium/ui/base/ime/input_method_imm32.cc b/chromium/ui/base/ime/input_method_imm32.cc
index 1a3cf266afe..41f65dfb37d 100644
--- a/chromium/ui/base/ime/input_method_imm32.cc
+++ b/chromium/ui/base/ime/input_method_imm32.cc
@@ -120,11 +120,6 @@ void InputMethodIMM32::CancelComposition(const TextInputClient* client) {
imm32_manager_.CancelIME(GetAttachedWindowHandle(client));
}
-void InputMethodIMM32::SetFocusedTextInputClient(TextInputClient* client) {
- ConfirmCompositionText();
- InputMethodWin::SetFocusedTextInputClient(client);
-}
-
bool InputMethodIMM32::IsCandidatePopupOpen() const {
return is_candidate_popup_open_;
}
@@ -158,8 +153,7 @@ LRESULT InputMethodIMM32::OnImeSetContext(HWND window_handle,
WPARAM wparam,
LPARAM lparam,
BOOL* handled) {
- active_ = (wparam == TRUE);
- if (active_)
+ if (!!wparam)
imm32_manager_.CreateImeWindow(window_handle);
OnInputMethodChanged();
@@ -270,24 +264,20 @@ void InputMethodIMM32::ConfirmCompositionText() {
void InputMethodIMM32::UpdateIMEState() {
// Use switch here in case we are going to add more text input types.
// We disable input method in password field.
+ const HWND window_handle = GetAttachedWindowHandle(GetTextInputClient());
switch (GetTextInputType()) {
case ui::TEXT_INPUT_TYPE_NONE:
case ui::TEXT_INPUT_TYPE_PASSWORD:
- imm32_manager_.DisableIME(GetAttachedWindowHandle(GetTextInputClient()));
+ imm32_manager_.DisableIME(window_handle);
enabled_ = false;
break;
default:
- imm32_manager_.EnableIME(GetAttachedWindowHandle(GetTextInputClient()));
+ imm32_manager_.EnableIME(window_handle);
enabled_ = true;
break;
}
-}
-bool InputMethodIMM32::IsWindowFocused(const TextInputClient* client) const {
- if (!client)
- return false;
- HWND attached_window_handle = GetAttachedWindowHandle(client);
- return attached_window_handle && GetFocus() == attached_window_handle;
+ imm32_manager_.SetTextInputMode(window_handle, GetTextInputMode());
}
} // namespace ui
diff --git a/chromium/ui/base/ime/input_method_imm32.h b/chromium/ui/base/ime/input_method_imm32.h
index a67d79681ce..dc0a4dc8ea6 100644
--- a/chromium/ui/base/ime/input_method_imm32.h
+++ b/chromium/ui/base/ime/input_method_imm32.h
@@ -29,7 +29,6 @@ class UI_EXPORT InputMethodIMM32 : public InputMethodWin {
virtual void OnTextInputTypeChanged(const TextInputClient* client) OVERRIDE;
virtual void OnCaretBoundsChanged(const TextInputClient* client) OVERRIDE;
virtual void CancelComposition(const TextInputClient* client) OVERRIDE;
- virtual void SetFocusedTextInputClient(TextInputClient* client) OVERRIDE;
virtual bool IsCandidatePopupOpen() const OVERRIDE;
protected:
@@ -71,10 +70,6 @@ class UI_EXPORT InputMethodIMM32 : public InputMethodWin {
// Enables or disables the IME according to the current text input type.
void UpdateIMEState();
- // Returns true if the Win32 native window bound to |client| has Win32 input
- // focus.
- bool IsWindowFocused(const TextInputClient* client) const;
-
bool enabled_;
// True if we know for sure that a candidate window is open.
diff --git a/chromium/ui/base/ime/input_method_initializer.cc b/chromium/ui/base/ime/input_method_initializer.cc
index 69b76d6e067..8c4d34fee91 100644
--- a/chromium/ui/base/ime/input_method_initializer.cc
+++ b/chromium/ui/base/ime/input_method_initializer.cc
@@ -10,7 +10,7 @@
#include "base/chromeos/chromeos_version.h"
#include "base/logging.h"
#include "chromeos/dbus/dbus_thread_manager.h"
-#include "chromeos/ime/ibus_daemon_controller.h"
+#include "chromeos/ime/ibus_bridge.h"
#elif defined(OS_WIN)
#include "base/win/metro.h"
#include "ui/base/ime/win/tsf_bridge.h"
@@ -25,14 +25,18 @@ bool dbus_thread_manager_was_initialized = false;
namespace ui {
void InitializeInputMethod() {
-#if defined(OS_WIN)
+#if defined(OS_CHROMEOS)
+ chromeos::IBusBridge::Initialize();
+#elif defined(OS_WIN)
if (base::win::IsTSFAwareRequired())
ui::TSFBridge::Initialize();
#endif
}
void ShutdownInputMethod() {
-#if defined(OS_WIN)
+#if defined(OS_CHROMEOS)
+ chromeos::IBusBridge::Shutdown();
+#elif defined(OS_WIN)
ui::internal::DestroySharedInputMethod();
if (base::win::IsTSFAwareRequired())
ui::TSFBridge::Shutdown();
@@ -41,16 +45,12 @@ void ShutdownInputMethod() {
void InitializeInputMethodForTesting() {
#if defined(OS_CHROMEOS)
+ chromeos::IBusBridge::Initialize();
+ // TODO(nona): Remove DBusThreadManager initialize.
if (!chromeos::DBusThreadManager::IsInitialized()) {
chromeos::DBusThreadManager::InitializeWithStub();
dbus_thread_manager_was_initialized = true;
}
- if (!chromeos::IBusDaemonController::GetInstance()) {
- // Passing NULL is okay because IBusDaemonController will be initialized
- // with stub implementation on non-ChromeOS device.
- DCHECK(!base::chromeos::IsRunningOnChromeOS());
- chromeos::IBusDaemonController::Initialize(NULL, NULL);
- }
#elif defined(OS_WIN)
if (base::win::IsTSFAwareRequired()) {
// Make sure COM is initialized because TSF depends on COM.
@@ -62,12 +62,12 @@ void InitializeInputMethodForTesting() {
void ShutdownInputMethodForTesting() {
#if defined(OS_CHROMEOS)
+ chromeos::IBusBridge::Shutdown();
+ // TODO(nona): Remove DBusThreadManager finalize.
if (dbus_thread_manager_was_initialized) {
chromeos::DBusThreadManager::Shutdown();
dbus_thread_manager_was_initialized = false;
}
- if (chromeos::IBusDaemonController::GetInstance())
- chromeos::IBusDaemonController::Shutdown();
#elif defined(OS_WIN)
ui::internal::DestroySharedInputMethod();
if (base::win::IsTSFAwareRequired()) {
diff --git a/chromium/ui/base/ime/input_method_tsf.cc b/chromium/ui/base/ime/input_method_tsf.cc
index 21a57a86e17..aaec2e01f83 100644
--- a/chromium/ui/base/ime/input_method_tsf.cc
+++ b/chromium/ui/base/ime/input_method_tsf.cc
@@ -115,17 +115,9 @@ void InputMethodTSF::CancelComposition(const TextInputClient* client) {
ui::TSFBridge::GetInstance()->CancelComposition();
}
-void InputMethodTSF::SetFocusedTextInputClient(TextInputClient* client) {
- if (IsWindowFocused(client)) {
- ui::TSFBridge::GetInstance()->SetFocusedClient(
- GetAttachedWindowHandle(client), client);
- } else if (!client) {
- // SetFocusedTextInputClient(NULL) must be interpreted as
- // "Remove the attached client".
- ui::TSFBridge::GetInstance()->RemoveFocusedClient(
- ui::TSFBridge::GetInstance()->GetFocusedTextInputClient());
- }
- InputMethodWin::SetFocusedTextInputClient(client);
+void InputMethodTSF::DetachTextInputClient(TextInputClient* client) {
+ InputMethodWin::DetachTextInputClient(client);
+ ui::TSFBridge::GetInstance()->RemoveFocusedClient(client);
}
bool InputMethodTSF::IsCandidatePopupOpen() const {
@@ -142,9 +134,10 @@ void InputMethodTSF::OnWillChangeFocusedClient(TextInputClient* focused_before,
void InputMethodTSF::OnDidChangeFocusedClient(TextInputClient* focused_before,
TextInputClient* focused) {
- if (IsWindowFocused(focused)) {
+ if (IsWindowFocused(focused) && IsTextInputClientFocused(focused)) {
ui::TSFBridge::GetInstance()->SetFocusedClient(
GetAttachedWindowHandle(focused), focused);
+
// Force to update the input type since client's TextInputStateChanged()
// function might not be called if text input types before the client loses
// focus and after it acquires focus again are the same.
@@ -161,11 +154,4 @@ void InputMethodTSF::ConfirmCompositionText() {
ui::TSFBridge::GetInstance()->ConfirmComposition();
}
-bool InputMethodTSF::IsWindowFocused(const TextInputClient* client) const {
- if (!client)
- return false;
- HWND attached_window_handle = GetAttachedWindowHandle(client);
- return attached_window_handle && GetFocus() == attached_window_handle;
-}
-
} // namespace ui
diff --git a/chromium/ui/base/ime/input_method_tsf.h b/chromium/ui/base/ime/input_method_tsf.h
index 98fa1f738c8..2b4a9bde10c 100644
--- a/chromium/ui/base/ime/input_method_tsf.h
+++ b/chromium/ui/base/ime/input_method_tsf.h
@@ -31,7 +31,7 @@ class UI_EXPORT InputMethodTSF : public InputMethodWin {
virtual void OnTextInputTypeChanged(const TextInputClient* client) OVERRIDE;
virtual void OnCaretBoundsChanged(const TextInputClient* client) OVERRIDE;
virtual void CancelComposition(const TextInputClient* client) OVERRIDE;
- virtual void SetFocusedTextInputClient(TextInputClient* client) OVERRIDE;
+ virtual void DetachTextInputClient(TextInputClient* client) OVERRIDE;
virtual bool IsCandidatePopupOpen() const OVERRIDE;
// Overridden from InputMethodBase:
@@ -46,10 +46,6 @@ class UI_EXPORT InputMethodTSF : public InputMethodWin {
// Asks the client to confirm current composition text.
void ConfirmCompositionText();
- // Returns true if the Win32 native window bound to |client| has Win32 input
- // focus.
- bool IsWindowFocused(const TextInputClient* client) const;
-
// TSF event router and observer.
scoped_ptr<TSFEventObserver> tsf_event_observer_;
scoped_ptr<TSFEventRouter> tsf_event_router_;
diff --git a/chromium/ui/base/ime/input_method_win.cc b/chromium/ui/base/ime/input_method_win.cc
index 4e3df395de4..bf679ed928b 100644
--- a/chromium/ui/base/ime/input_method_win.cc
+++ b/chromium/ui/base/ime/input_method_win.cc
@@ -5,12 +5,12 @@
#include "ui/base/ime/input_method_win.h"
#include "base/basictypes.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/ime/text_input_client.h"
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/gfx/win/hwnd_util.h"
namespace ui {
namespace {
@@ -148,13 +148,17 @@ LRESULT InputMethodWin::OnChar(HWND window_handle,
if (GetTextInputClient()) {
GetTextInputClient()->InsertChar(static_cast<char16>(wparam),
ui::GetModifiersFromKeyState());
+
+ // If Windows sends a WM_CHAR, then any previously sent WM_DEADCHARs (which
+ // are displayed as the composition text) should be cleared.
+ GetTextInputClient()->ClearCompositionText();
}
// Explicitly show the system menu at a good location on [Alt]+[Space].
// Note: Setting |handled| to FALSE for DefWindowProc triggering of the system
// menu causes undesirable titlebar artifacts in the classic theme.
if (message == WM_SYSCHAR && wparam == VK_SPACE)
- ui::ShowSystemMenu(window_handle);
+ gfx::ShowSystemMenu(window_handle);
return 0;
}
@@ -175,7 +179,7 @@ LRESULT InputMethodWin::OnDeadChar(UINT message,
// what dead key was pressed.
ui::CompositionText composition;
composition.text.assign(1, static_cast<char16>(wparam));
- composition.selection = ui::Range(0, 1);
+ composition.selection = gfx::Range(0, 1);
composition.underlines.push_back(
ui::CompositionUnderline(0, 1, SK_ColorBLACK, false));
GetTextInputClient()->SetCompositionText(composition);
@@ -187,12 +191,12 @@ LRESULT InputMethodWin::OnDocumentFeed(RECONVERTSTRING* reconv) {
if (!client)
return 0;
- ui::Range text_range;
+ gfx::Range text_range;
if (!client->GetTextRange(&text_range) || text_range.is_empty())
return 0;
bool result = false;
- ui::Range target_range;
+ gfx::Range target_range;
if (client->HasCompositionText())
result = client->GetCompositionTextRange(&target_range);
@@ -254,11 +258,11 @@ LRESULT InputMethodWin::OnReconvertString(RECONVERTSTRING* reconv) {
if (client->HasCompositionText())
return 0;
- ui::Range text_range;
+ gfx::Range text_range;
if (!client->GetTextRange(&text_range) || text_range.is_empty())
return 0;
- ui::Range selection_range;
+ gfx::Range selection_range;
if (!client->GetSelectionRange(&selection_range) ||
selection_range.is_empty()) {
return 0;
@@ -347,4 +351,20 @@ HWND InputMethodWin::GetAttachedWindowHandle(
#endif
}
+bool InputMethodWin::IsWindowFocused(const TextInputClient* client) const {
+ if (!client)
+ return false;
+ HWND attached_window_handle = GetAttachedWindowHandle(client);
+#if defined(USE_AURA)
+ // When Aura is enabled, |attached_window_handle| should always be a top-level
+ // window. So we can safely assume that |attached_window_handle| is ready for
+ // receiving keyboard input as long as it is an active window. This works well
+ // even when the |attached_window_handle| becomes active but has not received
+ // WM_FOCUS yet.
+ return attached_window_handle && GetActiveWindow() == attached_window_handle;
+#else
+ return attached_window_handle && GetFocus() == attached_window_handle;
+#endif
+}
+
} // namespace ui
diff --git a/chromium/ui/base/ime/input_method_win.h b/chromium/ui/base/ime/input_method_win.h
index 4d627e422f2..c69f2db6025 100644
--- a/chromium/ui/base/ime/input_method_win.h
+++ b/chromium/ui/base/ime/input_method_win.h
@@ -57,6 +57,10 @@ class UI_EXPORT InputMethodWin : public InputMethodBase {
// On Aura environment, |toplevel_window_handle_| is always returned.
HWND GetAttachedWindowHandle(const TextInputClient* text_input_client) const;
+ // Returns true if the Win32 native window bound to |client| is considered
+ // to be ready for receiving keyboard input.
+ bool IsWindowFocused(const TextInputClient* client) const;
+
// Indicates if the current input locale has an IME.
bool active_;
diff --git a/chromium/ui/base/ime/mock_input_method.cc b/chromium/ui/base/ime/mock_input_method.cc
index 7701b5c8f01..b6323ef1821 100644
--- a/chromium/ui/base/ime/mock_input_method.cc
+++ b/chromium/ui/base/ime/mock_input_method.cc
@@ -7,7 +7,8 @@
namespace ui {
MockInputMethod::MockInputMethod(internal::InputMethodDelegate* delegate)
- : text_input_client_(NULL) {
+ : text_input_client_(NULL),
+ is_sticky_text_input_client_(false) {
}
MockInputMethod::~MockInputMethod() {
@@ -17,6 +18,17 @@ void MockInputMethod::SetDelegate(internal::InputMethodDelegate* delegate) {
}
void MockInputMethod::SetFocusedTextInputClient(TextInputClient* client) {
+ if (is_sticky_text_input_client_)
+ return;
+ if (text_input_client_ == client)
+ return;
+ text_input_client_ = client;
+ if (client)
+ OnTextInputTypeChanged(client);
+}
+
+void MockInputMethod::SetStickyFocusedTextInputClient(TextInputClient* client) {
+ is_sticky_text_input_client_ = (client != NULL);
if (text_input_client_ == client)
return;
text_input_client_ = client;
@@ -24,6 +36,13 @@ void MockInputMethod::SetFocusedTextInputClient(TextInputClient* client) {
OnTextInputTypeChanged(client);
}
+void MockInputMethod::DetachTextInputClient(TextInputClient* client) {
+ if (text_input_client_ == client) {
+ text_input_client_ = NULL;
+ is_sticky_text_input_client_ = false;
+ }
+}
+
TextInputClient* MockInputMethod::GetTextInputClient() const {
return text_input_client_;
}
@@ -83,8 +102,12 @@ bool MockInputMethod::IsActive() {
return true;
}
-ui::TextInputType MockInputMethod::GetTextInputType() const {
- return ui::TEXT_INPUT_TYPE_NONE;
+TextInputType MockInputMethod::GetTextInputType() const {
+ return TEXT_INPUT_TYPE_NONE;
+}
+
+TextInputMode MockInputMethod::GetTextInputMode() const {
+ return TEXT_INPUT_MODE_DEFAULT;
}
bool MockInputMethod::CanComposeInline() const {
diff --git a/chromium/ui/base/ime/mock_input_method.h b/chromium/ui/base/ime/mock_input_method.h
index f318ca40ff4..8e14988ef5b 100644
--- a/chromium/ui/base/ime/mock_input_method.h
+++ b/chromium/ui/base/ime/mock_input_method.h
@@ -49,6 +49,9 @@ class UI_EXPORT MockInputMethod : NON_EXPORTED_BASE(public InputMethod) {
virtual bool OnUntranslatedIMEMessage(const base::NativeEvent& event,
NativeEventResult* result) OVERRIDE;
virtual void SetFocusedTextInputClient(TextInputClient* client) OVERRIDE;
+ virtual void SetStickyFocusedTextInputClient(
+ TextInputClient* client) OVERRIDE;
+ virtual void DetachTextInputClient(TextInputClient* client) OVERRIDE;
virtual TextInputClient* GetTextInputClient() const OVERRIDE;
virtual bool DispatchKeyEvent(const base::NativeEvent& native_event) OVERRIDE;
virtual bool DispatchFabricatedKeyEvent(const ui::KeyEvent& event) OVERRIDE;
@@ -60,6 +63,7 @@ class UI_EXPORT MockInputMethod : NON_EXPORTED_BASE(public InputMethod) {
virtual base::i18n::TextDirection GetInputTextDirection() OVERRIDE;
virtual bool IsActive() OVERRIDE;
virtual TextInputType GetTextInputType() const OVERRIDE;
+ virtual TextInputMode GetTextInputMode() const OVERRIDE;
virtual bool CanComposeInline() const OVERRIDE;
virtual bool IsCandidatePopupOpen() const OVERRIDE;
virtual void AddObserver(InputMethodObserver* observer) OVERRIDE;
@@ -67,6 +71,7 @@ class UI_EXPORT MockInputMethod : NON_EXPORTED_BASE(public InputMethod) {
private:
TextInputClient* text_input_client_;
+ bool is_sticky_text_input_client_;
ObserverList<Observer> observer_list_;
DISALLOW_COPY_AND_ASSIGN(MockInputMethod);
diff --git a/chromium/ui/base/ime/text_input_client.h b/chromium/ui/base/ime/text_input_client.h
index 2fd14a2cd4e..5eb4b5e7e44 100644
--- a/chromium/ui/base/ime/text_input_client.h
+++ b/chromium/ui/base/ime/text_input_client.h
@@ -11,9 +11,9 @@
#include "ui/base/ime/composition_text.h"
#include "ui/base/ime/text_input_mode.h"
#include "ui/base/ime/text_input_type.h"
-#include "ui/base/range/range.h"
#include "ui/base/ui_export.h"
#include "ui/gfx/native_widget_types.h"
+#include "ui/gfx/range/range.h"
namespace gfx {
class Rect;
@@ -91,20 +91,20 @@ class UI_EXPORT TextInputClient {
// Retrieves the UTF-16 based character range containing accessibled text in
// the View. It must cover the composition and selection range.
// Returns false if the information cannot be retrieved right now.
- virtual bool GetTextRange(ui::Range* range) = 0;
+ virtual bool GetTextRange(gfx::Range* range) = 0;
// Retrieves the UTF-16 based character range of current composition text.
// Returns false if the information cannot be retrieved right now.
- virtual bool GetCompositionTextRange(ui::Range* range) = 0;
+ virtual bool GetCompositionTextRange(gfx::Range* range) = 0;
// Retrieves the UTF-16 based character range of current selection.
// Returns false if the information cannot be retrieved right now.
- virtual bool GetSelectionRange(ui::Range* range) = 0;
+ virtual bool GetSelectionRange(gfx::Range* range) = 0;
// Selects the given UTF-16 based character range. Current composition text
// will be confirmed before selecting the range.
// Returns false if the operation is not supported.
- virtual bool SetSelectionRange(const ui::Range& range) = 0;
+ virtual bool SetSelectionRange(const gfx::Range& range) = 0;
// Deletes contents in the given UTF-16 based character range. Current
// composition text will be confirmed before deleting the range.
@@ -114,13 +114,13 @@ class UI_EXPORT TextInputClient {
// GetSelectionRange has a race condition due to asynchronous IPCs between
// browser and renderer.
// Returns false if the operation is not supported.
- virtual bool DeleteRange(const ui::Range& range) = 0;
+ virtual bool DeleteRange(const gfx::Range& range) = 0;
// Retrieves the text content in a given UTF-16 based character range.
// The result will be stored into |*text|.
// Returns false if the operation is not supported or the specified range
// is out of the text range returned by GetTextRange().
- virtual bool GetTextFromRange(const ui::Range& range, string16* text) = 0;
+ virtual bool GetTextFromRange(const gfx::Range& range, string16* text) = 0;
// Miscellaneous ------------------------------------------------------------
diff --git a/chromium/ui/base/ime/win/imm32_manager.cc b/chromium/ui/base/ime/win/imm32_manager.cc
index 7e595917a72..d418f6181b0 100644
--- a/chromium/ui/base/ime/win/imm32_manager.cc
+++ b/chromium/ui/base/ime/win/imm32_manager.cc
@@ -329,9 +329,9 @@ void IMM32Manager::GetCompositionInfo(HIMC imm_context, LPARAM lparam,
// IMM32 does not support non-zero-width selection in a composition. So
// always use the caret position as selection range.
int cursor = ::ImmGetCompositionString(imm_context, GCS_CURSORPOS, NULL, 0);
- composition->selection = ui::Range(cursor);
+ composition->selection = gfx::Range(cursor);
} else {
- composition->selection = ui::Range(0);
+ composition->selection = gfx::Range(0);
}
// Retrieve the clause segmentations and convert them to underlines.
diff --git a/chromium/ui/base/ime/win/tsf_bridge.cc b/chromium/ui/base/ime/win/tsf_bridge.cc
index 4186bc7883e..bf2820323ef 100644
--- a/chromium/ui/base/ime/win/tsf_bridge.cc
+++ b/chromium/ui/base/ime/win/tsf_bridge.cc
@@ -72,6 +72,24 @@ class TSFBridgeDelegate : public TSFBridge {
// Returns true if already initialized.
bool IsInitialized();
+ // Updates or clears the association maintained in the TSF runtime between
+ // |attached_window_handle_| and the current document manager. Keeping this
+ // association updated solves some tricky event ordering issues between
+ // logical text input focus managed by Chrome and native text input focus
+ // managed by the OS.
+ // Background:
+ // TSF runtime monitors some Win32 messages such as WM_ACTIVATE to
+ // change the focused document manager. This is problematic when
+ // TSFBridge::SetFocusedClient is called first then the target window
+ // receives WM_ACTIVATE. This actually occurs in Aura environment where
+ // WM_NCACTIVATE is used as a trigger to restore text input focus.
+ // Caveats:
+ // TSF runtime does not increment the reference count of the attached
+ // document manager. See the comment inside the method body for
+ // details.
+ void UpdateAssociateFocus();
+ void ClearAssociateFocus();
+
// A triple of document manager, text store and binding cookie between
// a context owned by the document manager and the text store. This is a
// minimum working set of an editable document in TSF.
@@ -110,12 +128,16 @@ class TSFBridgeDelegate : public TSFBridge {
// Current focused text input client. Do not free |client_|.
TextInputClient* client_;
+ // Represents the window that is currently owns text input focus.
+ HWND attached_window_handle_;
+
DISALLOW_COPY_AND_ASSIGN(TSFBridgeDelegate);
};
TSFBridgeDelegate::TSFBridgeDelegate()
: client_id_(TF_CLIENTID_NULL),
- client_(NULL) {
+ client_(NULL),
+ attached_window_handle_(NULL) {
}
TSFBridgeDelegate::~TSFBridgeDelegate() {
@@ -194,6 +216,8 @@ void TSFBridgeDelegate::OnTextInputTypeChanged(const TextInputClient* client) {
return;
}
+ UpdateAssociateFocus();
+
TSFDocument* document = GetAssociatedDocument();
if (!document)
return;
@@ -241,7 +265,10 @@ void TSFBridgeDelegate::SetFocusedClient(HWND focused_window,
DCHECK_EQ(base::MessageLoop::TYPE_UI, base::MessageLoop::current()->type());
DCHECK(client);
DCHECK(IsInitialized());
+ if (attached_window_handle_ != focused_window)
+ ClearAssociateFocus();
client_ = client;
+ attached_window_handle_ = focused_window;
for (TSFDocumentMap::iterator it = tsf_document_map_.begin();
it != tsf_document_map_.end(); ++it) {
@@ -260,9 +287,11 @@ void TSFBridgeDelegate::RemoveFocusedClient(TextInputClient* client) {
DCHECK(IsInitialized());
if (client_ != client)
return;
+ ClearAssociateFocus();
client_ = NULL;
+ attached_window_handle_ = NULL;
for (TSFDocumentMap::iterator it = tsf_document_map_.begin();
- it != tsf_document_map_.end(); ++it) {
+ it != tsf_document_map_.end(); ++it) {
if (it->second.text_store.get() == NULL)
continue;
it->second.text_store->SetFocusedTextInputClient(NULL, NULL);
@@ -413,13 +442,45 @@ bool TSFBridgeDelegate::IsInitialized() {
return client_id_ != TF_CLIENTID_NULL;
}
+void TSFBridgeDelegate::UpdateAssociateFocus() {
+ if (attached_window_handle_ == NULL)
+ return;
+ TSFDocument* document = GetAssociatedDocument();
+ if (document == NULL) {
+ ClearAssociateFocus();
+ return;
+ }
+ // NOTE: ITfThreadMgr::AssociateFocus does not increment the ref count of
+ // the document manager to be attached. It is our responsibility to make sure
+ // the attached document manager will not be destroyed while it is attached.
+ // This should be true as long as TSFBridge::Shutdown() is called late phase
+ // of UI thread shutdown.
+ base::win::ScopedComPtr<ITfDocumentMgr> previous_focus;
+ thread_manager_->AssociateFocus(
+ attached_window_handle_, document->document_manager.get(),
+ previous_focus.Receive());
+}
+
+void TSFBridgeDelegate::ClearAssociateFocus() {
+ if (attached_window_handle_ == NULL)
+ return;
+ base::win::ScopedComPtr<ITfDocumentMgr> previous_focus;
+ thread_manager_->AssociateFocus(
+ attached_window_handle_, NULL, previous_focus.Receive());
+}
+
TSFBridgeDelegate::TSFDocument* TSFBridgeDelegate::GetAssociatedDocument() {
if (!client_)
return NULL;
TSFDocumentMap::iterator it =
tsf_document_map_.find(client_->GetTextInputType());
- if (it == tsf_document_map_.end())
- return &tsf_document_map_[TEXT_INPUT_TYPE_TEXT];
+ if (it == tsf_document_map_.end()) {
+ it = tsf_document_map_.find(TEXT_INPUT_TYPE_TEXT);
+ // This check is necessary because it's possible that we failed to
+ // initialize |tsf_document_map_| and it has no TEXT_INPUT_TYPE_TEXT.
+ if (it == tsf_document_map_.end())
+ return NULL;
+ }
return &it->second;
}
diff --git a/chromium/ui/base/ime/win/tsf_event_router.cc b/chromium/ui/base/ime/win/tsf_event_router.cc
index 51f66a267ac..4f34a048eec 100644
--- a/chromium/ui/base/ime/win/tsf_event_router.cc
+++ b/chromium/ui/base/ime/win/tsf_event_router.cc
@@ -11,8 +11,8 @@
#include "base/bind.h"
#include "base/win/scoped_comptr.h"
#include "base/win/metro.h"
-#include "ui/base/range/range.h"
#include "ui/base/win/atl_module.h"
+#include "ui/gfx/range/range.h"
namespace ui {
@@ -56,9 +56,9 @@ class ATL_NO_VTABLE TSFEventRouter::Delegate
void SetRouter(TSFEventRouter* router);
private:
- // Returns current composition range. Returns ui::Range::InvalidRange if there
- // is no composition.
- static ui::Range GetCompositionRange(ITfContext* context);
+ // Returns current composition range. Returns gfx::Range::InvalidRange if
+ // there is no composition.
+ static gfx::Range GetCompositionRange(ITfContext* context);
// Returns true if the given |element_id| represents the candidate window.
bool IsCandidateWindowInternal(DWORD element_id);
@@ -85,7 +85,7 @@ class ATL_NO_VTABLE TSFEventRouter::Delegate
DWORD ui_source_cookie_;
TSFEventRouter* router_;
- ui::Range previous_composition_range_;
+ gfx::Range previous_composition_range_;
DISALLOW_COPY_AND_ASSIGN(Delegate);
};
@@ -94,7 +94,7 @@ TSFEventRouter::Delegate::Delegate()
: context_source_cookie_(TF_INVALID_COOKIE),
ui_source_cookie_(TF_INVALID_COOKIE),
router_(NULL),
- previous_composition_range_(ui::Range::InvalidRange()) {
+ previous_composition_range_(gfx::Range::InvalidRange()) {
}
TSFEventRouter::Delegate::~Delegate() {}
@@ -125,7 +125,7 @@ STDMETHODIMP TSFEventRouter::Delegate::OnEndEdit(ITfContext* context,
if (FAILED(ranges->Next(1, range.Receive(), &fetched_count)))
return S_OK; // Don't care about failures.
- const ui::Range composition_range = GetCompositionRange(context);
+ const gfx::Range composition_range = GetCompositionRange(context);
if (!previous_composition_range_.IsValid() && composition_range.IsValid())
router_->OnTSFStartComposition();
@@ -214,35 +214,35 @@ bool TSFEventRouter::Delegate::IsImeComposing() {
}
// static
-ui::Range TSFEventRouter::Delegate::GetCompositionRange(
+gfx::Range TSFEventRouter::Delegate::GetCompositionRange(
ITfContext* context) {
DCHECK(context);
base::win::ScopedComPtr<ITfContextComposition> context_composition;
if (FAILED(context_composition.QueryFrom(context)))
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
base::win::ScopedComPtr<IEnumITfCompositionView> enum_composition_view;
if (FAILED(context_composition->EnumCompositions(
enum_composition_view.Receive())))
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
base::win::ScopedComPtr<ITfCompositionView> composition_view;
if (enum_composition_view->Next(1, composition_view.Receive(),
NULL) != S_OK)
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
base::win::ScopedComPtr<ITfRange> range;
if (FAILED(composition_view->GetRange(range.Receive())))
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
base::win::ScopedComPtr<ITfRangeACP> range_acp;
if (FAILED(range_acp.QueryFrom(range)))
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
LONG start = 0;
LONG length = 0;
if (FAILED(range_acp->GetExtent(&start, &length)))
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
- return ui::Range(start, start + length);
+ return gfx::Range(start, start + length);
}
bool TSFEventRouter::Delegate::IsCandidateWindowInternal(DWORD element_id) {
@@ -292,7 +292,7 @@ void TSFEventRouter::OnTSFStartComposition() {
observer_->OnTSFStartComposition();
}
-void TSFEventRouter::OnTextUpdated(const ui::Range& composition_range) {
+void TSFEventRouter::OnTextUpdated(const gfx::Range& composition_range) {
observer_->OnTextUpdated(composition_range);
}
diff --git a/chromium/ui/base/ime/win/tsf_event_router.h b/chromium/ui/base/ime/win/tsf_event_router.h
index be2311c9fce..04a2a1e9eb0 100644
--- a/chromium/ui/base/ime/win/tsf_event_router.h
+++ b/chromium/ui/base/ime/win/tsf_event_router.h
@@ -15,8 +15,8 @@
#include "base/callback.h"
#include "base/compiler_specific.h"
#include "ui/base/ime/text_input_type.h"
-#include "ui/base/range/range.h"
#include "ui/base/ui_export.h"
+#include "ui/gfx/range/range.h"
struct ITfDocumentMgr;
@@ -33,8 +33,8 @@ class TSFEventRouterObserver {
virtual void OnTSFStartComposition() {}
// Called when the text contents are updated. If there is no composition,
- // ui::Range::InvalidRange is passed to |composition_range|.
- virtual void OnTextUpdated(const ui::Range& composition_range) {}
+ // gfx::Range::InvalidRange is passed to |composition_range|.
+ virtual void OnTextUpdated(const gfx::Range& composition_range) {}
// Called when a composition is terminated.
virtual void OnTSFEndComposition() {}
@@ -60,7 +60,7 @@ class UI_EXPORT TSFEventRouter {
// Callbacks from the TSFEventRouterDelegate:
void OnCandidateWindowCountChanged(size_t window_count);
void OnTSFStartComposition();
- void OnTextUpdated(const ui::Range& composition_range);
+ void OnTextUpdated(const gfx::Range& composition_range);
void OnTSFEndComposition();
// Sets |thread_manager| to be monitored. |thread_manager| can be NULL.
diff --git a/chromium/ui/base/ime/win/tsf_input_scope.cc b/chromium/ui/base/ime/win/tsf_input_scope.cc
index cb6792e9bd2..06481e9d8f0 100644
--- a/chromium/ui/base/ime/win/tsf_input_scope.cc
+++ b/chromium/ui/base/ime/win/tsf_input_scope.cc
@@ -4,8 +4,7 @@
#include "ui/base/ime/win/tsf_input_scope.h"
-#include <InputScope.h>
-#include <vector>
+#include <algorithm>
#include "base/compiler_specific.h"
#include "base/logging.h"
@@ -16,6 +15,20 @@ namespace ui {
namespace tsf_inputscope {
namespace {
+void AppendNonTrivialInputScope(std::vector<InputScope>* input_scopes,
+ InputScope input_scope) {
+ DCHECK(input_scopes);
+
+ if (input_scope == IS_DEFAULT)
+ return;
+
+ if (std::find(input_scopes->begin(), input_scopes->end(), input_scope) !=
+ input_scopes->end())
+ return;
+
+ input_scopes->push_back(input_scope);
+}
+
class TSFInputScope : public ITfInputScope {
public:
explicit TSFInputScope(const std::vector<InputScope>& input_scopes)
@@ -145,11 +158,6 @@ InputScope ConvertTextInputTypeToInputScope(TextInputType text_input_type) {
InputScope ConvertTextInputModeToInputScope(TextInputMode text_input_mode) {
switch (text_input_mode) {
- case TEXT_INPUT_MODE_VERBATIM:
- case TEXT_INPUT_MODE_LATIN:
- case TEXT_INPUT_MODE_LATIN_NAME:
- case TEXT_INPUT_MODE_LATIN_PROSE:
- return IS_ALPHANUMERIC_HALFWIDTH;
case TEXT_INPUT_MODE_FULL_WIDTH_LATIN:
return IS_ALPHANUMERIC_FULLWIDTH;
case TEXT_INPUT_MODE_KANA:
@@ -171,10 +179,24 @@ InputScope ConvertTextInputModeToInputScope(TextInputMode text_input_mode) {
} // namespace
-ITfInputScope* CreateInputScope(TextInputType text_input_type) {
- std::vector<InputScope> input_scopes(1);
- input_scopes.push_back(ConvertTextInputTypeToInputScope(text_input_type));
- return new TSFInputScope(input_scopes);
+std::vector<InputScope> GetInputScopes(TextInputType text_input_type,
+ TextInputMode text_input_mode) {
+ std::vector<InputScope> input_scopes;
+
+ AppendNonTrivialInputScope(&input_scopes,
+ ConvertTextInputTypeToInputScope(text_input_type));
+ AppendNonTrivialInputScope(&input_scopes,
+ ConvertTextInputModeToInputScope(text_input_mode));
+
+ if (input_scopes.empty())
+ input_scopes.push_back(IS_DEFAULT);
+
+ return input_scopes;
+}
+
+ITfInputScope* CreateInputScope(TextInputType text_input_type,
+ TextInputMode text_input_mode) {
+ return new TSFInputScope(GetInputScopes(text_input_type, text_input_mode));
}
void SetInputScopeForTsfUnawareWindow(
@@ -185,14 +207,10 @@ void SetInputScopeForTsfUnawareWindow(
if (!set_input_scopes)
return;
- InputScope input_scopes[] = {
- ConvertTextInputTypeToInputScope(text_input_type),
- ConvertTextInputModeToInputScope(text_input_mode),
- };
-
- set_input_scopes(window_handle, input_scopes,
- (input_scopes[0] == input_scopes[1] ? 1 : 2), NULL, 0, NULL,
- NULL);
+ std::vector<InputScope> input_scopes = GetInputScopes(text_input_type,
+ text_input_mode);
+ set_input_scopes(window_handle, &input_scopes[0], input_scopes.size(), NULL,
+ 0, NULL, NULL);
}
} // namespace tsf_inputscope
diff --git a/chromium/ui/base/ime/win/tsf_input_scope.h b/chromium/ui/base/ime/win/tsf_input_scope.h
index 24ac94ce2fe..2e5856c60d8 100644
--- a/chromium/ui/base/ime/win/tsf_input_scope.h
+++ b/chromium/ui/base/ime/win/tsf_input_scope.h
@@ -5,24 +5,32 @@
#ifndef UI_BASE_IME_WIN_TSF_INPUT_SCOPE_H_
#define UI_BASE_IME_WIN_TSF_INPUT_SCOPE_H_
+#include <InputScope.h>
#include <Windows.h>
+#include <vector>
#include "base/basictypes.h"
#include "ui/base/ime/text_input_mode.h"
#include "ui/base/ime/text_input_type.h"
#include "ui/base/ui_export.h"
-struct ITfInputScope;
-
namespace ui {
namespace tsf_inputscope {
+// Returns InputScope list corresoponding to ui::TextInputType and
+// ui::TextInputMode.
+// This function is only used from following functions but declared for test.
+UI_EXPORT std::vector<InputScope> GetInputScopes(TextInputType text_input_type,
+ TextInputMode text_input_mode);
+
// Returns an instance of ITfInputScope, which is the Windows-specific
-// category representation corresponding to ui::TextInputType that we are
-// using to specify the expected text type in the target field.
+// category representation corresponding to ui::TextInputType and
+// ui::TextInputMode that we are using to specify the expected text type
+// in the target field.
// The returned instance has 0 reference count. The caller must maintain its
// reference count.
-UI_EXPORT ITfInputScope* CreateInputScope(TextInputType text_input_type);
+UI_EXPORT ITfInputScope* CreateInputScope(TextInputType text_input_type,
+ TextInputMode text_input_mode);
// A wrapper of the SetInputScopes API exported by msctf.dll.
// http://msdn.microsoft.com/en-us/library/windows/desktop/ms629026.aspx
diff --git a/chromium/ui/base/ime/win/tsf_input_scope_unittest.cc b/chromium/ui/base/ime/win/tsf_input_scope_unittest.cc
new file mode 100644
index 00000000000..de6ede17ffd
--- /dev/null
+++ b/chromium/ui/base/ime/win/tsf_input_scope_unittest.cc
@@ -0,0 +1,121 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/ime/win/tsf_input_scope.h"
+
+#include <InputScope.h>
+
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace ui {
+namespace {
+
+struct GetInputScopesTestCase {
+ TextInputType input_type;
+ TextInputMode input_mode;
+ size_t expected_size;
+ InputScope expected_input_scopes[2];
+};
+
+// Google Test pretty-printer.
+void PrintTo(const GetInputScopesTestCase& data, std::ostream* os) {
+ *os << " input_type: " << testing::PrintToString(data.input_type)
+ << "; input_mode: " << testing::PrintToString(data.input_mode);
+}
+
+class TSFInputScopeTest
+ : public testing::TestWithParam<GetInputScopesTestCase> {
+};
+
+const GetInputScopesTestCase kGetInputScopesTestCases[] = {
+ // Test cases of TextInputType.
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_TEXT, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_PASSWORD, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_PASSWORD}},
+ {TEXT_INPUT_TYPE_SEARCH, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_SEARCH}},
+ {TEXT_INPUT_TYPE_EMAIL, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_EMAIL_SMTPEMAILADDRESS}},
+ {TEXT_INPUT_TYPE_NUMBER, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_NUMBER}},
+ {TEXT_INPUT_TYPE_TELEPHONE, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_TELEPHONE_FULLTELEPHONENUMBER}},
+ {TEXT_INPUT_TYPE_URL, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_URL}},
+ {TEXT_INPUT_TYPE_DATE, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_DATE_TIME, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_DATE_TIME_LOCAL, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_MONTH, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_TIME, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_WEEK, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_TEXT_AREA, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_CONTENT_EDITABLE, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_DATE_TIME_FIELD, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ // Test cases of TextInputMode.
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_DEFAULT,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_VERBATIM,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_LATIN,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_LATIN_NAME,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_LATIN_PROSE,
+ 1, {IS_DEFAULT}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_FULL_WIDTH_LATIN,
+ 1, {IS_ALPHANUMERIC_FULLWIDTH}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_KANA,
+ 1, {IS_HIRAGANA}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_KATAKANA,
+ 1, {IS_KATAKANA_FULLWIDTH}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_NUMERIC,
+ 1, {IS_NUMBER}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_TEL,
+ 1, {IS_TELEPHONE_FULLTELEPHONENUMBER}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_EMAIL,
+ 1, {IS_EMAIL_SMTPEMAILADDRESS}},
+ {TEXT_INPUT_TYPE_NONE, TEXT_INPUT_MODE_URL,
+ 1, {IS_URL}},
+ // Mixed test cases.
+ {TEXT_INPUT_TYPE_SEARCH, TEXT_INPUT_MODE_KANA,
+ 2, {IS_SEARCH, IS_HIRAGANA}},
+ {TEXT_INPUT_TYPE_EMAIL, TEXT_INPUT_MODE_EMAIL,
+ 1, {IS_EMAIL_SMTPEMAILADDRESS}},
+ {TEXT_INPUT_TYPE_NUMBER, TEXT_INPUT_MODE_NUMERIC,
+ 1, {IS_NUMBER}},
+ {TEXT_INPUT_TYPE_TELEPHONE, TEXT_INPUT_MODE_TEL,
+ 1, {IS_TELEPHONE_FULLTELEPHONENUMBER}},
+ {TEXT_INPUT_TYPE_URL, TEXT_INPUT_MODE_URL,
+ 1, {IS_URL}},
+};
+
+TEST_P(TSFInputScopeTest, GetInputScopes) {
+ const GetInputScopesTestCase& test_case = GetParam();
+
+ std::vector<InputScope> input_scopes = tsf_inputscope::GetInputScopes(
+ test_case.input_type, test_case.input_mode);
+
+ EXPECT_EQ(test_case.expected_size, input_scopes.size());
+ for (size_t i = 0; i < test_case.expected_size; ++i)
+ EXPECT_EQ(test_case.expected_input_scopes[i], input_scopes[i]);
+}
+
+INSTANTIATE_TEST_CASE_P(,
+ TSFInputScopeTest,
+ ::testing::ValuesIn(kGetInputScopesTestCases));
+
+} // namespace
+} // namespace ui
diff --git a/chromium/ui/base/ime/win/tsf_text_store.cc b/chromium/ui/base/ime/win/tsf_text_store.cc
index 40f02bf4ea1..abd19ae8a90 100644
--- a/chromium/ui/base/ime/win/tsf_text_store.cc
+++ b/chromium/ui/base/ime/win/tsf_text_store.cc
@@ -8,6 +8,10 @@
#include <InputScope.h>
#include <OleCtl.h>
+#include <algorithm>
+
+#include <algorithm>
+
#include "base/win/scoped_variant.h"
#include "ui/base/ime/text_input_client.h"
#include "ui/base/ime/win/tsf_input_scope.h"
@@ -585,6 +589,8 @@ STDMETHODIMP TSFTextStore::RequestSupportedAttrs(
const TS_ATTRID* attribute_buffer) {
if (!attribute_buffer)
return E_INVALIDARG;
+ if (!text_input_client_)
+ return E_FAIL;
// We support only input scope attribute.
for (size_t i = 0; i < attribute_buffer_size; ++i) {
if (IsEqualGUID(GUID_PROP_INPUTSCOPE, attribute_buffer[i]))
@@ -601,6 +607,8 @@ STDMETHODIMP TSFTextStore::RetrieveRequestedAttrs(
return E_INVALIDARG;
if (!attribute_buffer)
return E_INVALIDARG;
+ if (!text_input_client_)
+ return E_UNEXPECTED;
// We support only input scope attribute.
*attribute_buffer_copied = 0;
if (attribute_buffer_size == 0)
@@ -610,7 +618,8 @@ STDMETHODIMP TSFTextStore::RetrieveRequestedAttrs(
attribute_buffer[0].idAttr = GUID_PROP_INPUTSCOPE;
attribute_buffer[0].varValue.vt = VT_UNKNOWN;
attribute_buffer[0].varValue.punkVal = tsf_inputscope::CreateInputScope(
- text_input_client_->GetTextInputType());
+ text_input_client_->GetTextInputType(),
+ text_input_client_->GetTextInputMode());
attribute_buffer[0].varValue.punkVal->AddRef();
*attribute_buffer_copied = 1;
return S_OK;
diff --git a/chromium/ui/base/ime/win/tsf_text_store.h b/chromium/ui/base/ime/win/tsf_text_store.h
index 86ceeba4804..87cd6b42991 100644
--- a/chromium/ui/base/ime/win/tsf_text_store.h
+++ b/chromium/ui/base/ime/win/tsf_text_store.h
@@ -13,8 +13,8 @@
#include "base/strings/string16.h"
#include "base/win/scoped_comptr.h"
#include "ui/base/ime/composition_underline.h"
-#include "ui/base/range/range.h"
#include "ui/base/ui_export.h"
+#include "ui/gfx/range/range.h"
namespace ui {
class TextInputClient;
@@ -258,7 +258,7 @@ class UI_EXPORT TSFTextStore : public ITextStoreACP,
// |string_buffer_|: "aiueo"
// |selection_.start()|: 1
// |selection_.end()|: 4
- Range selection_;
+ gfx::Range selection_;
// |start_offset| and |end_offset| of |composition_undelines_| indicates
// the offsets in |string_buffer_|.
diff --git a/chromium/ui/base/ime/win/tsf_text_store_unittest.cc b/chromium/ui/base/ime/win/tsf_text_store_unittest.cc
index 62772f246c7..82268c9e584 100644
--- a/chromium/ui/base/ime/win/tsf_text_store_unittest.cc
+++ b/chromium/ui/base/ime/win/tsf_text_store_unittest.cc
@@ -4,7 +4,13 @@
#include "ui/base/ime/win/tsf_text_store.h"
+#include <initguid.h> // for GUID_NULL and GUID_PROP_INPUTSCOPE
+#include <InputScope.h>
+#include <OleCtl.h>
+
+#include "base/memory/ref_counted.h"
#include "base/win/scoped_com_initializer.h"
+#include "base/win/scoped_variant.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "ui/base/ime/text_input_client.h"
@@ -15,7 +21,6 @@ using testing::Invoke;
using testing::Return;
namespace ui {
-
namespace {
class MockTextInputClient : public TextInputClient {
@@ -33,12 +38,12 @@ class MockTextInputClient : public TextInputClient {
MOCK_METHOD0(GetCaretBounds, gfx::Rect());
MOCK_METHOD2(GetCompositionCharacterBounds, bool(uint32, gfx::Rect*));
MOCK_METHOD0(HasCompositionText, bool());
- MOCK_METHOD1(GetTextRange, bool(ui::Range*));
- MOCK_METHOD1(GetCompositionTextRange, bool(ui::Range*));
- MOCK_METHOD1(GetSelectionRange, bool(ui::Range*));
- MOCK_METHOD1(SetSelectionRange, bool(const ui::Range&));
- MOCK_METHOD1(DeleteRange, bool(const ui::Range&));
- MOCK_METHOD2(GetTextFromRange, bool(const ui::Range&, string16*));
+ MOCK_METHOD1(GetTextRange, bool(gfx::Range*));
+ MOCK_METHOD1(GetCompositionTextRange, bool(gfx::Range*));
+ MOCK_METHOD1(GetSelectionRange, bool(gfx::Range*));
+ MOCK_METHOD1(SetSelectionRange, bool(const gfx::Range&));
+ MOCK_METHOD1(DeleteRange, bool(const gfx::Range&));
+ MOCK_METHOD2(GetTextFromRange, bool(const gfx::Range&, string16*));
MOCK_METHOD0(OnInputMethodChanged, void());
MOCK_METHOD1(ChangeTextDirectionAndLayoutAlignment,
bool(base::i18n::TextDirection));
@@ -48,8 +53,7 @@ class MockTextInputClient : public TextInputClient {
class MockStoreACPSink : public ITextStoreACPSink {
public:
- MockStoreACPSink() : ref_count_(0) {
- }
+ MockStoreACPSink() : ref_count_(0) {}
// IUnknown
virtual ULONG STDMETHODCALLTYPE AddRef() OVERRIDE {
@@ -94,36 +98,36 @@ class MockStoreACPSink : public ITextStoreACPSink {
HRESULT());
private:
- ~MockStoreACPSink() {
- }
+ virtual ~MockStoreACPSink() {}
volatile LONG ref_count_;
};
+const HWND kWindowHandle = reinterpret_cast<HWND>(1);
+
} // namespace
class TSFTextStoreTest : public testing::Test {
protected:
virtual void SetUp() OVERRIDE {
text_store_ = new TSFTextStore();
- text_store_->AddRef();
sink_ = new MockStoreACPSink();
- sink_->AddRef();
EXPECT_EQ(S_OK, text_store_->AdviseSink(IID_ITextStoreACPSink,
sink_, TS_AS_ALL_SINKS));
- text_store_->SetFocusedTextInputClient(0, &text_input_client_);
+ text_store_->SetFocusedTextInputClient(kWindowHandle,
+ &text_input_client_);
}
virtual void TearDown() OVERRIDE {
EXPECT_EQ(S_OK, text_store_->UnadviseSink(sink_));
- sink_->Release();
- text_store_->Release();
+ sink_ = NULL;
+ text_store_ = NULL;
}
base::win::ScopedCOMInitializer com_initializer_;
MockTextInputClient text_input_client_;
- TSFTextStore* text_store_;
- MockStoreACPSink* sink_;
+ scoped_refptr<TSFTextStore> text_store_;
+ scoped_refptr<MockStoreACPSink> sink_;
};
class TSFTextStoreTestCallback {
@@ -139,7 +143,7 @@ class TSFTextStoreTestCallback {
bool* edit_flag() { return &text_store_->edit_flag_; }
string16* string_buffer() { return &text_store_->string_buffer_; }
size_t* committed_size() { return &text_store_->committed_size_; }
- Range* selection() { return &text_store_->selection_; }
+ gfx::Range* selection() { return &text_store_->selection_; }
CompositionUnderlines* composition_undelines() {
return &text_store_->composition_undelines_;
}
@@ -161,8 +165,8 @@ class TSFTextStoreTestCallback {
bool HasReadWriteLock() const { return text_store_->HasReadWriteLock(); }
void GetSelectionTest(LONG expected_acp_start, LONG expected_acp_end) {
- TS_SELECTION_ACP selection;
- ULONG fetched;
+ TS_SELECTION_ACP selection = {};
+ ULONG fetched = 0;
EXPECT_EQ(S_OK, text_store_->GetSelection(0, 1, &selection, &fetched));
EXPECT_EQ(1, fetched);
EXPECT_EQ(expected_acp_start, selection.acpStart);
@@ -170,7 +174,7 @@ class TSFTextStoreTestCallback {
}
void SetSelectionTest(LONG acp_start, LONG acp_end, HRESULT expected_result) {
- TS_SELECTION_ACP selection;
+ TS_SELECTION_ACP selection = {};
selection.acpStart = acp_start;
selection.acpEnd = acp_end;
selection.style.ase = TS_AE_NONE;
@@ -183,7 +187,7 @@ class TSFTextStoreTestCallback {
void SetTextTest(LONG acp_start, LONG acp_end,
const string16& text, HRESULT error_code) {
- TS_TEXTCHANGE change;
+ TS_TEXTCHANGE change = {};
ASSERT_EQ(error_code,
text_store_->SetText(0, acp_start, acp_end,
text.c_str(), text.size(), &change));
@@ -197,11 +201,11 @@ class TSFTextStoreTestCallback {
void GetTextTest(LONG acp_start, LONG acp_end,
const string16& expected_string,
LONG expected_next_acp) {
- wchar_t buffer[1024];
- ULONG text_buffer_copied;
- TS_RUNINFO run_info;
- ULONG run_info_buffer_copied;
- LONG next_acp;
+ wchar_t buffer[1024] = {};
+ ULONG text_buffer_copied = 0;
+ TS_RUNINFO run_info = {};
+ ULONG run_info_buffer_copied = 0;
+ LONG next_acp = 0;
ASSERT_EQ(S_OK,
text_store_->GetText(acp_start, acp_end, buffer, 1024,
&text_buffer_copied,
@@ -216,11 +220,11 @@ class TSFTextStoreTestCallback {
}
void GetTextErrorTest(LONG acp_start, LONG acp_end, HRESULT error_code) {
- wchar_t buffer[1024];
- ULONG text_buffer_copied;
- TS_RUNINFO run_info;
- ULONG run_info_buffer_copied;
- LONG next_acp;
+ wchar_t buffer[1024] = {};
+ ULONG text_buffer_copied = 0;
+ TS_RUNINFO run_info = {};
+ ULONG run_info_buffer_copied = 0;
+ LONG next_acp = 0;
EXPECT_EQ(error_code,
text_store_->GetText(acp_start, acp_end, buffer, 1024,
&text_buffer_copied,
@@ -233,8 +237,9 @@ class TSFTextStoreTestCallback {
LONG expected_change_start,
LONG expected_change_old_end,
LONG expected_change_new_end) {
- LONG start, end;
- TS_TEXTCHANGE change;
+ LONG start = 0;
+ LONG end = 0;
+ TS_TEXTCHANGE change = {};
EXPECT_EQ(S_OK,
text_store_->InsertTextAtSelection(0, buffer, buffer_size,
&start, &end, &change));
@@ -249,7 +254,8 @@ class TSFTextStoreTestCallback {
ULONG buffer_size,
LONG expected_start,
LONG expected_end) {
- LONG start, end;
+ LONG start = 0;
+ LONG end = 0;
EXPECT_EQ(S_OK,
text_store_->InsertTextAtSelection(TS_IAS_QUERYONLY, buffer,
buffer_size, &start, &end,
@@ -261,8 +267,8 @@ class TSFTextStoreTestCallback {
void GetTextExtTest(TsViewCookie view_cookie, LONG acp_start, LONG acp_end,
LONG expected_left, LONG expected_top,
LONG expected_right, LONG expected_bottom) {
- RECT rect;
- BOOL clipped;
+ RECT rect = {};
+ BOOL clipped = FALSE;
EXPECT_EQ(S_OK, text_store_->GetTextExt(view_cookie, acp_start, acp_end,
&rect, &clipped));
EXPECT_EQ(expected_left, rect.left);
@@ -274,29 +280,34 @@ class TSFTextStoreTestCallback {
void GetTextExtNoLayoutTest(TsViewCookie view_cookie, LONG acp_start,
LONG acp_end) {
- RECT rect;
- BOOL clipped;
+ RECT rect = {};
+ BOOL clipped = FALSE;
EXPECT_EQ(TS_E_NOLAYOUT,
text_store_->GetTextExt(view_cookie, acp_start, acp_end,
&rect, &clipped));
}
- TSFTextStore* text_store_;
+ scoped_refptr<TSFTextStore> text_store_;
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(TSFTextStoreTestCallback);
};
+namespace {
+
+const HRESULT kInvalidResult = 0x12345678;
+
TEST_F(TSFTextStoreTest, GetStatusTest) {
- TS_STATUS status;
+ TS_STATUS status = {};
EXPECT_EQ(S_OK, text_store_->GetStatus(&status));
EXPECT_EQ(0, status.dwDynamicFlags);
EXPECT_EQ(TS_SS_TRANSITORY | TS_SS_NOHIDDENTEXT, status.dwStaticFlags);
}
-
class SyncRequestLockTestCallback : public TSFTextStoreTestCallback {
public:
explicit SyncRequestLockTestCallback(TSFTextStore* text_store)
- : TSFTextStoreTestCallback(text_store) {
- }
+ : TSFTextStoreTestCallback(text_store) {}
HRESULT LockGranted1(DWORD flags) {
EXPECT_TRUE(HasReadLock());
@@ -313,7 +324,7 @@ class SyncRequestLockTestCallback : public TSFTextStoreTestCallback {
HRESULT LockGranted3(DWORD flags) {
EXPECT_TRUE(HasReadLock());
EXPECT_FALSE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ | TS_LF_SYNC, &result));
EXPECT_EQ(TS_E_SYNCHRONOUS, result);
return S_OK;
@@ -322,7 +333,7 @@ class SyncRequestLockTestCallback : public TSFTextStoreTestCallback {
HRESULT LockGranted4(DWORD flags) {
EXPECT_TRUE(HasReadLock());
EXPECT_FALSE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK,
text_store_->RequestLock(TS_LF_READWRITE | TS_LF_SYNC, &result));
EXPECT_EQ(TS_E_SYNCHRONOUS, result);
@@ -332,7 +343,7 @@ class SyncRequestLockTestCallback : public TSFTextStoreTestCallback {
HRESULT LockGranted5(DWORD flags) {
EXPECT_TRUE(HasReadLock());
EXPECT_TRUE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ | TS_LF_SYNC, &result));
EXPECT_EQ(TS_E_SYNCHRONOUS, result);
return S_OK;
@@ -341,12 +352,15 @@ class SyncRequestLockTestCallback : public TSFTextStoreTestCallback {
HRESULT LockGranted6(DWORD flags) {
EXPECT_TRUE(HasReadLock());
EXPECT_TRUE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK,
text_store_->RequestLock(TS_LF_READWRITE | TS_LF_SYNC, &result));
EXPECT_EQ(TS_E_SYNCHRONOUS, result);
return S_OK;
}
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(SyncRequestLockTestCallback);
};
TEST_F(TSFTextStoreTest, SynchronousRequestLockTest) {
@@ -359,21 +373,25 @@ TEST_F(TSFTextStoreTest, SynchronousRequestLockTest) {
.WillOnce(Invoke(&callback, &SyncRequestLockTestCallback::LockGranted5))
.WillOnce(Invoke(&callback, &SyncRequestLockTestCallback::LockGranted6));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ | TS_LF_SYNC, &result));
EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK,
text_store_->RequestLock(TS_LF_READWRITE | TS_LF_SYNC, &result));
EXPECT_EQ(S_OK, result);
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ | TS_LF_SYNC, &result));
EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ | TS_LF_SYNC, &result));
EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK,
text_store_->RequestLock(TS_LF_READWRITE | TS_LF_SYNC, &result));
EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK,
text_store_->RequestLock(TS_LF_READWRITE | TS_LF_SYNC, &result));
EXPECT_EQ(S_OK, result);
@@ -383,15 +401,14 @@ class AsyncRequestLockTestCallback : public TSFTextStoreTestCallback {
public:
explicit AsyncRequestLockTestCallback(TSFTextStore* text_store)
: TSFTextStoreTestCallback(text_store),
- state_(0) {
- }
+ state_(0) {}
HRESULT LockGranted1(DWORD flags) {
EXPECT_EQ(0, state_);
state_ = 1;
EXPECT_TRUE(HasReadLock());
EXPECT_FALSE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
EXPECT_EQ(TS_S_ASYNC, result);
EXPECT_EQ(1, state_);
@@ -403,7 +420,7 @@ class AsyncRequestLockTestCallback : public TSFTextStoreTestCallback {
EXPECT_EQ(2, state_);
EXPECT_TRUE(HasReadLock());
EXPECT_FALSE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
EXPECT_EQ(TS_S_ASYNC, result);
EXPECT_EQ(2, state_);
@@ -415,7 +432,7 @@ class AsyncRequestLockTestCallback : public TSFTextStoreTestCallback {
EXPECT_EQ(3, state_);
EXPECT_TRUE(HasReadLock());
EXPECT_TRUE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
EXPECT_EQ(TS_S_ASYNC, result);
EXPECT_EQ(3, state_);
@@ -427,7 +444,7 @@ class AsyncRequestLockTestCallback : public TSFTextStoreTestCallback {
EXPECT_EQ(4, state_);
EXPECT_TRUE(HasReadLock());
EXPECT_TRUE(HasReadWriteLock());
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
EXPECT_EQ(TS_S_ASYNC, result);
EXPECT_EQ(4, state_);
@@ -445,6 +462,8 @@ class AsyncRequestLockTestCallback : public TSFTextStoreTestCallback {
private:
int state_;
+
+ DISALLOW_COPY_AND_ASSIGN(AsyncRequestLockTestCallback);
};
TEST_F(TSFTextStoreTest, AsynchronousRequestLockTest) {
@@ -456,7 +475,7 @@ TEST_F(TSFTextStoreTest, AsynchronousRequestLockTest) {
.WillOnce(Invoke(&callback, &AsyncRequestLockTestCallback::LockGranted4))
.WillOnce(Invoke(&callback, &AsyncRequestLockTestCallback::LockGranted5));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
EXPECT_EQ(S_OK, result);
}
@@ -465,8 +484,7 @@ class RequestLockTextChangeTestCallback : public TSFTextStoreTestCallback {
public:
explicit RequestLockTextChangeTestCallback(TSFTextStore* text_store)
: TSFTextStoreTestCallback(text_store),
- state_(0) {
- }
+ state_(0) {}
HRESULT LockGranted1(DWORD flags) {
EXPECT_EQ(0, state_);
@@ -499,7 +517,7 @@ class RequestLockTextChangeTestCallback : public TSFTextStoreTestCallback {
HRESULT OnTextChange(DWORD flags, const TS_TEXTCHANGE* change) {
EXPECT_EQ(4, state_);
- HRESULT result;
+ HRESULT result = kInvalidResult;
state_ = 5;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
EXPECT_EQ(S_OK, result);
@@ -518,6 +536,8 @@ class RequestLockTextChangeTestCallback : public TSFTextStoreTestCallback {
private:
int state_;
+
+ DISALLOW_COPY_AND_ASSIGN(RequestLockTextChangeTestCallback);
};
TEST_F(TSFTextStoreTest, RequestLockOnTextChangeTest) {
@@ -542,7 +562,7 @@ TEST_F(TSFTextStoreTest, RequestLockOnTextChangeTest) {
.WillOnce(Invoke(&callback,
&RequestLockTextChangeTestCallback::SetCompositionText));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
EXPECT_EQ(S_OK, result);
}
@@ -550,8 +570,7 @@ TEST_F(TSFTextStoreTest, RequestLockOnTextChangeTest) {
class SelectionTestCallback : public TSFTextStoreTestCallback {
public:
explicit SelectionTestCallback(TSFTextStore* text_store)
- : TSFTextStoreTestCallback(text_store) {
- }
+ : TSFTextStoreTestCallback(text_store) {}
HRESULT ReadLockGranted(DWORD flags) {
SetInternalState(L"", 0, 0, 0);
@@ -631,23 +650,21 @@ TEST_F(TSFTextStoreTest, SetGetSelectionTest) {
.WillOnce(Invoke(&callback,
&SelectionTestCallback::ReadWriteLockGranted));
- TS_SELECTION_ACP selection_buffer;
- ULONG fetched_count;
+ TS_SELECTION_ACP selection_buffer = {};
+ ULONG fetched_count = 0;
EXPECT_EQ(TS_E_NOLOCK,
text_store_->GetSelection(0, 1, &selection_buffer,
&fetched_count));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
}
-
class SetGetTextTestCallback : public TSFTextStoreTestCallback {
public:
explicit SetGetTextTestCallback(TSFTextStore* text_store)
- : TSFTextStoreTestCallback(text_store) {
- }
+ : TSFTextStoreTestCallback(text_store) {}
HRESULT ReadLockGranted(DWORD flags) {
SetTextTest(0, 0, L"", TF_E_NOLOCK);
@@ -820,6 +837,9 @@ class SetGetTextTestCallback : public TSFTextStoreTestCallback {
return S_OK;
}
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(SetGetTextTestCallback);
};
TEST_F(TSFTextStoreTest, SetGetTextTest) {
@@ -829,19 +849,19 @@ TEST_F(TSFTextStoreTest, SetGetTextTest) {
.WillOnce(Invoke(&callback,
&SetGetTextTestCallback::ReadWriteLockGranted));
- wchar_t buffer[1024];
- ULONG text_buffer_copied;
- TS_RUNINFO run_info;
- ULONG run_info_buffer_copied;
- LONG next_acp;
+ wchar_t buffer[1024] = {};
+ ULONG text_buffer_copied = 0;
+ TS_RUNINFO run_info = {};
+ ULONG run_info_buffer_copied = 0;
+ LONG next_acp = 0;
EXPECT_EQ(TF_E_NOLOCK,
text_store_->GetText(0, -1, buffer, 1024, &text_buffer_copied,
&run_info, 1, &run_info_buffer_copied,
&next_acp));
- TS_TEXTCHANGE change;
+ TS_TEXTCHANGE change = {};
EXPECT_EQ(TF_E_NOLOCK, text_store_->SetText(0, 0, 0, L"abc", 3, &change));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
}
@@ -849,8 +869,7 @@ TEST_F(TSFTextStoreTest, SetGetTextTest) {
class InsertTextAtSelectionTestCallback : public TSFTextStoreTestCallback {
public:
explicit InsertTextAtSelectionTestCallback(TSFTextStore* text_store)
- : TSFTextStoreTestCallback(text_store) {
- }
+ : TSFTextStoreTestCallback(text_store) {}
HRESULT ReadLockGranted(DWORD flags) {
const wchar_t kBuffer[] = L"0123456789";
@@ -865,8 +884,9 @@ class InsertTextAtSelectionTestCallback : public TSFTextStoreTestCallback {
GetSelectionTest(2, 5);
InsertTextAtSelectionQueryOnlyTest(kBuffer, 0, 2, 5);
- LONG start, end;
- TS_TEXTCHANGE change;
+ LONG start = 0;
+ LONG end = 0;
+ TS_TEXTCHANGE change = {};
EXPECT_EQ(TS_E_NOLOCK,
text_store_->InsertTextAtSelection(0, kBuffer, 10,
&start, &end, &change));
@@ -908,6 +928,9 @@ class InsertTextAtSelectionTestCallback : public TSFTextStoreTestCallback {
return S_OK;
}
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(InsertTextAtSelectionTestCallback);
};
TEST_F(TSFTextStoreTest, InsertTextAtSelectionTest) {
@@ -919,16 +942,18 @@ TEST_F(TSFTextStoreTest, InsertTextAtSelectionTest) {
Invoke(&callback,
&InsertTextAtSelectionTestCallback::ReadWriteLockGranted));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
+ EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
+ EXPECT_EQ(S_OK, result);
}
class ScenarioTestCallback : public TSFTextStoreTestCallback {
public:
explicit ScenarioTestCallback(TSFTextStore* text_store)
- : TSFTextStoreTestCallback(text_store) {
- }
+ : TSFTextStoreTestCallback(text_store) {}
HRESULT LockGranted1(DWORD flags) {
SetSelectionTest(0, 0, S_OK);
@@ -1023,6 +1048,9 @@ class ScenarioTestCallback : public TSFTextStoreTestCallback {
EXPECT_EQ(0, composition.selection.end());
EXPECT_EQ(0, composition.underlines.size());
}
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(ScenarioTestCallback);
};
TEST_F(TSFTextStoreTest, ScenarioTest) {
@@ -1053,24 +1081,28 @@ TEST_F(TSFTextStoreTest, ScenarioTest) {
EXPECT_CALL(*sink_, OnTextChange(_, _))
.WillOnce(Return(S_OK));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
+ EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
+ EXPECT_EQ(S_OK, result);
+ result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READWRITE, &result));
+ EXPECT_EQ(S_OK, result);
}
class GetTextExtTestCallback : public TSFTextStoreTestCallback {
public:
explicit GetTextExtTestCallback(TSFTextStore* text_store)
: TSFTextStoreTestCallback(text_store),
- layout_prepared_character_num_(0) {
- }
+ layout_prepared_character_num_(0) {}
HRESULT LockGranted(DWORD flags) {
SetInternalState(L"0123456789012", 0, 0, 0);
layout_prepared_character_num_ = 13;
- TsViewCookie view_cookie;
+ TsViewCookie view_cookie = 0;
EXPECT_EQ(S_OK, text_store_->GetActiveView(&view_cookie));
GetTextExtTest(view_cookie, 0, 0, 11, 12, 11, 20);
GetTextExtTest(view_cookie, 0, 1, 11, 12, 20, 20);
@@ -1125,6 +1157,8 @@ class GetTextExtTestCallback : public TSFTextStoreTestCallback {
private:
uint32 layout_prepared_character_num_;
+
+ DISALLOW_COPY_AND_ASSIGN(GetTextExtTestCallback);
};
TEST_F(TSFTextStoreTest, GetTextExtTest) {
@@ -1141,8 +1175,80 @@ TEST_F(TSFTextStoreTest, GetTextExtTest) {
EXPECT_CALL(*sink_, OnLockGranted(_))
.WillOnce(Invoke(&callback, &GetTextExtTestCallback::LockGranted));
- HRESULT result;
+ HRESULT result = kInvalidResult;
EXPECT_EQ(S_OK, text_store_->RequestLock(TS_LF_READ, &result));
+ EXPECT_EQ(S_OK, result);
+}
+
+TEST_F(TSFTextStoreTest, RequestSupportedAttrs) {
+ EXPECT_CALL(text_input_client_, GetTextInputType())
+ .WillRepeatedly(Return(TEXT_INPUT_TYPE_TEXT));
+ EXPECT_CALL(text_input_client_, GetTextInputMode())
+ .WillRepeatedly(Return(TEXT_INPUT_MODE_DEFAULT));
+
+ EXPECT_HRESULT_FAILED(text_store_->RequestSupportedAttrs(0, 1, NULL));
+
+ const TS_ATTRID kUnknownAttributes[] = {GUID_NULL};
+ EXPECT_HRESULT_FAILED(text_store_->RequestSupportedAttrs(
+ 0, arraysize(kUnknownAttributes), kUnknownAttributes))
+ << "Must fail for unknown attributes";
+
+ const TS_ATTRID kAttributes[] = {GUID_NULL, GUID_PROP_INPUTSCOPE, GUID_NULL};
+ EXPECT_EQ(S_OK, text_store_->RequestSupportedAttrs(
+ 0, arraysize(kAttributes), kAttributes))
+ << "InputScope must be supported";
+
+ {
+ SCOPED_TRACE("Check if RequestSupportedAttrs fails while focus is lost");
+ // Emulate focus lost
+ text_store_->SetFocusedTextInputClient(NULL, NULL);
+ EXPECT_HRESULT_FAILED(text_store_->RequestSupportedAttrs(0, 0, NULL));
+ EXPECT_HRESULT_FAILED(text_store_->RequestSupportedAttrs(
+ 0, arraysize(kAttributes), kAttributes));
+ }
}
+TEST_F(TSFTextStoreTest, RetrieveRequestedAttrs) {
+ EXPECT_CALL(text_input_client_, GetTextInputType())
+ .WillRepeatedly(Return(TEXT_INPUT_TYPE_TEXT));
+ EXPECT_CALL(text_input_client_, GetTextInputMode())
+ .WillRepeatedly(Return(TEXT_INPUT_MODE_DEFAULT));
+
+ ULONG num_copied = 0xfffffff;
+ EXPECT_HRESULT_FAILED(text_store_->RetrieveRequestedAttrs(
+ 1, NULL, &num_copied));
+
+ {
+ SCOPED_TRACE("Make sure if InputScope is supported");
+ TS_ATTRVAL buffer[2] = {};
+ num_copied = 0xfffffff;
+ ASSERT_EQ(S_OK, text_store_->RetrieveRequestedAttrs(
+ arraysize(buffer), buffer, &num_copied));
+ bool input_scope_found = false;
+ for (size_t i = 0; i < num_copied; ++i) {
+ base::win::ScopedVariant variant;
+ // Move ownership from |buffer[i].varValue| to |variant|.
+ std::swap(*variant.Receive(), buffer[i].varValue);
+ if (IsEqualGUID(buffer[i].idAttr, GUID_PROP_INPUTSCOPE)) {
+ EXPECT_EQ(VT_UNKNOWN, variant.type());
+ base::win::ScopedComPtr<ITfInputScope> input_scope;
+ EXPECT_HRESULT_SUCCEEDED(input_scope.QueryFrom((&variant)->punkVal));
+ input_scope_found = true;
+ // we do not break here to clean up all the retrieved VARIANTs.
+ }
+ }
+ EXPECT_TRUE(input_scope_found);
+ }
+ {
+ SCOPED_TRACE("Check if RetrieveRequestedAttrs fails while focus is lost");
+ // Emulate focus lost
+ text_store_->SetFocusedTextInputClient(NULL, NULL);
+ num_copied = 0xfffffff;
+ TS_ATTRVAL buffer[2] = {};
+ EXPECT_HRESULT_FAILED(text_store_->RetrieveRequestedAttrs(
+ arraysize(buffer), buffer, &num_copied));
+ }
+}
+
+} // namespace
} // namespace ui
diff --git a/chromium/ui/base/keycodes/OWNERS b/chromium/ui/base/keycodes/OWNERS
index 7dc2fa7ba07..a49314c396b 100644
--- a/chromium/ui/base/keycodes/OWNERS
+++ b/chromium/ui/base/keycodes/OWNERS
@@ -1,2 +1,2 @@
-per-file usb_keycode_map*=garykac@chromium.org
-per-file usb_keycode_map*=wez@chromium.org
+garykac@chromium.org
+wez@chromium.org
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_android.h b/chromium/ui/base/keycodes/keyboard_code_conversion_android.h
deleted file mode 100644
index 8bf27899e93..00000000000
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_android.h
+++ /dev/null
@@ -1,17 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_ANDROID_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_ANDROID_H_
-
-#include "ui/base/keycodes/keyboard_codes_posix.h"
-#include "ui/base/ui_export.h"
-
-namespace ui {
-
-UI_EXPORT KeyboardCode KeyboardCodeFromAndroidKeyCode(int keycode);
-
-} // namespace ui
-
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_ANDROID_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_win.h b/chromium/ui/base/keycodes/keyboard_code_conversion_win.h
deleted file mode 100644
index 1cf91de3729..00000000000
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_win.h
+++ /dev/null
@@ -1,19 +0,0 @@
-// Copyright (c) 2011 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_WIN_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_WIN_H_
-
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/ui_export.h"
-
-namespace ui {
-
-// Methods to convert ui::KeyboardCode/Windows virtual key type methods.
-UI_EXPORT WORD WindowsKeyCodeForKeyboardCode(KeyboardCode keycode);
-UI_EXPORT KeyboardCode KeyboardCodeForWindowsKeyCode(WORD keycode);
-
-} // namespace ui
-
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_WIN_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_x.h b/chromium/ui/base/keycodes/keyboard_code_conversion_x.h
deleted file mode 100644
index f394de17b9b..00000000000
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_x.h
+++ /dev/null
@@ -1,31 +0,0 @@
-// Copyright (c) 2011 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_X_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_X_H_
-
-#include "base/basictypes.h"
-#include "ui/base/keycodes/keyboard_codes_posix.h"
-#include "ui/base/ui_export.h"
-
-typedef union _XEvent XEvent;
-
-namespace ui {
-
-UI_EXPORT KeyboardCode KeyboardCodeFromXKeyEvent(XEvent* xev);
-
-UI_EXPORT KeyboardCode KeyboardCodeFromXKeysym(unsigned int keysym);
-
-// Returns a character on a standard US PC keyboard from an XEvent.
-UI_EXPORT uint16 GetCharacterFromXEvent(XEvent* xev);
-
-// Converts a KeyboardCode into an X KeySym.
-UI_EXPORT int XKeysymForWindowsKeyCode(KeyboardCode keycode, bool shift);
-
-// Converts an X keycode into an X KeySym.
-unsigned int DefaultXKeysymFromHardwareKeycode(unsigned int keycode);
-
-} // namespace ui
-
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_X_H_
diff --git a/chromium/ui/base/keycodes/keycode_converter.cc b/chromium/ui/base/keycodes/keycode_converter.cc
new file mode 100644
index 00000000000..a7010aaca2d
--- /dev/null
+++ b/chromium/ui/base/keycodes/keycode_converter.cc
@@ -0,0 +1,115 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/keycodes/keycode_converter.h"
+
+namespace ui {
+
+namespace {
+
+#if defined(OS_WIN)
+#define USB_KEYMAP(usb, xkb, win, mac, code) {usb, win, code}
+#elif defined(OS_LINUX)
+#define USB_KEYMAP(usb, xkb, win, mac, code) {usb, xkb, code}
+#elif defined(OS_MACOSX)
+#define USB_KEYMAP(usb, xkb, win, mac, code) {usb, mac, code}
+#else
+#define USB_KEYMAP(usb, xkb, win, mac, code) {usb, 0, code}
+#endif
+#include "ui/base/keycodes/keycode_converter_data.h"
+
+const size_t kKeycodeMapEntries = arraysize(usb_keycode_map);
+
+} // namespace
+
+KeycodeConverter::KeycodeConverter() {
+}
+
+KeycodeConverter* KeycodeConverter::GetInstance() {
+ return Singleton<KeycodeConverter>::get();
+}
+
+size_t KeycodeConverter::NumKeycodeMapEntriesForTest() {
+ return kKeycodeMapEntries;
+}
+
+const KeycodeMapEntry* KeycodeConverter::GetKeycodeMapForTest() {
+ return &usb_keycode_map[0];
+}
+
+uint16_t KeycodeConverter::InvalidNativeKeycode() {
+ return usb_keycode_map[0].native_keycode;
+}
+
+const char* KeycodeConverter::InvalidKeyboardEventCode() {
+ return "Unidentified";
+}
+
+const char* KeycodeConverter::NativeKeycodeToCode(uint16_t native_keycode) {
+ for (size_t i = 0; i < kKeycodeMapEntries; ++i) {
+ if (usb_keycode_map[i].native_keycode == native_keycode) {
+ if (usb_keycode_map[i].code != NULL)
+ return usb_keycode_map[i].code;
+ break;
+ }
+ }
+ return InvalidKeyboardEventCode();
+}
+
+uint16_t KeycodeConverter::CodeToNativeKeycode(const char* code) {
+ if (!code ||
+ strcmp(code, InvalidKeyboardEventCode()) == 0) {
+ return InvalidNativeKeycode();
+ }
+
+ for (size_t i = 0; i < kKeycodeMapEntries; ++i) {
+ if (usb_keycode_map[i].code &&
+ strcmp(usb_keycode_map[i].code, code) == 0) {
+ return usb_keycode_map[i].native_keycode;
+ }
+ }
+ return InvalidNativeKeycode();
+}
+
+// USB keycodes
+// Note that USB keycodes are not part of any web standard.
+// Please don't use USB keycodes in new code.
+
+uint16_t KeycodeConverter::InvalidUsbKeycode() {
+ return usb_keycode_map[0].usb_keycode;
+}
+
+uint16_t KeycodeConverter::UsbKeycodeToNativeKeycode(uint32_t usb_keycode) {
+ // Deal with some special-cases that don't fit the 1:1 mapping.
+ if (usb_keycode == 0x070032) // non-US hash.
+ usb_keycode = 0x070031; // US backslash.
+#if defined(OS_MACOSX)
+ if (usb_keycode == 0x070046) // PrintScreen.
+ usb_keycode = 0x070068; // F13.
+#endif
+
+ for (size_t i = 0; i < kKeycodeMapEntries; ++i) {
+ if (usb_keycode_map[i].usb_keycode == usb_keycode)
+ return usb_keycode_map[i].native_keycode;
+ }
+ return InvalidNativeKeycode();
+}
+
+uint32_t KeycodeConverter::NativeKeycodeToUsbKeycode(uint16_t native_keycode) {
+ for (size_t i = 0; i < kKeycodeMapEntries; ++i) {
+ if (usb_keycode_map[i].native_keycode == native_keycode)
+ return usb_keycode_map[i].usb_keycode;
+ }
+ return InvalidUsbKeycode();
+}
+
+const char* KeycodeConverter::UsbKeycodeToCode(uint32_t usb_keycode) {
+ for (size_t i = 0; i < kKeycodeMapEntries; ++i) {
+ if (usb_keycode_map[i].usb_keycode == usb_keycode)
+ return usb_keycode_map[i].code;
+ }
+ return InvalidKeyboardEventCode();
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/keycodes/keycode_converter.h b/chromium/ui/base/keycodes/keycode_converter.h
new file mode 100644
index 00000000000..cd9ac431574
--- /dev/null
+++ b/chromium/ui/base/keycodes/keycode_converter.h
@@ -0,0 +1,87 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_BASE_KEYCODES_KEYCODE_CONVERTER_H_
+#define UI_BASE_KEYCODES_KEYCODE_CONVERTER_H_
+
+#include <stdint.h>
+#include "base/basictypes.h"
+#include "base/memory/singleton.h"
+
+// For reference, the W3C UI Event spec is located at:
+// http://www.w3.org/TR/uievents/
+
+namespace ui {
+
+// This structure is used to define the keycode mapping table.
+// It is defined here because the unittests need access to it.
+typedef struct {
+ // USB keycode:
+ // Upper 16-bits: USB Usage Page.
+ // Lower 16-bits: USB Usage Id: Assigned ID within this usage page.
+ uint32_t usb_keycode;
+
+ // Contains one of the following:
+ // On Linux: XKB scancode
+ // On Windows: Windows OEM scancode
+ // On Mac: Mac keycode
+ uint16_t native_keycode;
+
+ // The UIEvents (aka: DOM4Events) |code| value as defined in:
+ // https://dvcs.w3.org/hg/d4e/raw-file/tip/source_respec.htm
+ const char* code;
+} KeycodeMapEntry;
+
+// A class to convert between the current platform's native keycode (scancode)
+// and platform-neutral |code| values (as defined in the W3C UI Events
+// spec (http://www.w3.org/TR/uievents/).
+class KeycodeConverter {
+ public:
+ static KeycodeConverter* GetInstance();
+
+ // Return the value that identifies an invalid native keycode.
+ uint16_t InvalidNativeKeycode();
+
+ // Return the string that indentifies an invalid UI Event |code|.
+ // The returned pointer references a static global string.
+ const char* InvalidKeyboardEventCode();
+
+ // Convert a native (Mac/Win/Linux) keycode into the |code| string.
+ // The returned pointer references a static global string.
+ const char* NativeKeycodeToCode(uint16_t native_keycode);
+
+ // Convert a UI Events |code| string value into a native keycode.
+ uint16_t CodeToNativeKeycode(const char* code);
+
+ // The following methods relate to USB keycodes.
+ // Note that USB keycodes are not part of any web standard.
+ // Please don't use USB keycodes in new code.
+
+ // Return the value that identifies an invalid USB keycode.
+ uint16_t InvalidUsbKeycode();
+
+ // Convert a USB keycode into an equivalent platform native keycode.
+ uint16_t UsbKeycodeToNativeKeycode(uint32_t usb_keycode);
+
+ // Convert a platform native keycode into an equivalent USB keycode.
+ uint32_t NativeKeycodeToUsbKeycode(uint16_t native_keycode);
+
+ // Convert a USB keycode into the string with the UI Event |code| value.
+ // The returned pointer references a static global string.
+ const char* UsbKeycodeToCode(uint32_t usb_keycode);
+
+ // Static methods to support testing.
+ size_t NumKeycodeMapEntriesForTest();
+ const KeycodeMapEntry* GetKeycodeMapForTest();
+
+ private:
+ KeycodeConverter();
+ friend struct DefaultSingletonTraits<KeycodeConverter>;
+
+ DISALLOW_COPY_AND_ASSIGN(KeycodeConverter);
+};
+
+} // namespace ui
+
+#endif // UI_BASE_KEYCODE_CONVERTER_H_
diff --git a/chromium/ui/base/keycodes/keycode_converter_data.h b/chromium/ui/base/keycodes/keycode_converter_data.h
new file mode 100644
index 00000000000..d7788e5ba97
--- /dev/null
+++ b/chromium/ui/base/keycodes/keycode_converter_data.h
@@ -0,0 +1,379 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_BASE_KEYCODES_KEYCODE_CONVERTER_DATA_H_
+#define UI_BASE_KEYCODES_KEYCODE_CONVERTER_DATA_H_
+
+// Data in this file was created by referencing:
+// USB HID Usage Tables (v1.11) 27 June 2001
+// HIToolbox/Events.h (Mac)
+
+const KeycodeMapEntry usb_keycode_map[] = {
+
+ // USB XKB Win Mac Code
+ USB_KEYMAP(0x000000, 0x0000, 0x0000, 0xffff, NULL), // Invalid
+
+ // =========================================
+ // USB Usage Page 0x01: Generic Desktop Page
+ // =========================================
+
+ // Sleep could be encoded as USB#0c0032, but there's no corresponding WakeUp
+ // in the 0x0c USB page.
+
+ // USB XKB Win Mac
+ USB_KEYMAP(0x010082, 0x0096, 0x0000, 0xffff, NULL), // SystemSleep
+ USB_KEYMAP(0x010083, 0x0097, 0x0000, 0xffff, NULL), // SystemWakeUp
+
+ // =========================================
+ // USB Usage Page 0x07: Keyboard/Keypad Page
+ // =========================================
+
+ // TODO(garykac):
+ // XKB#005c ISO Level3 Shift (AltGr)
+ // XKB#005e <>||
+ // XKB#006d Linefeed
+ // XKB#008a SunProps cf. USB#0700a3 CrSel/Props
+ // XKB#008e SunOpen
+ // Mac#003f kVK_Function
+ // Mac#000a kVK_ISO_Section (ISO keyboards only)
+ // Mac#0066 kVK_JIS_Eisu (USB#07008a Henkan?)
+
+ // USB XKB Win Mac
+ USB_KEYMAP(0x070000, 0x0000, 0x0000, 0xffff, NULL), // Reserved
+ USB_KEYMAP(0x070001, 0x0000, 0x0000, 0xffff, NULL), // ErrorRollOver
+ USB_KEYMAP(0x070002, 0x0000, 0x0000, 0xffff, NULL), // POSTFail
+ USB_KEYMAP(0x070003, 0x0000, 0x0000, 0xffff, NULL), // ErrorUndefined
+ USB_KEYMAP(0x070004, 0x0026, 0x001e, 0x0000, "KeyA"), // aA
+ USB_KEYMAP(0x070005, 0x0038, 0x0030, 0x000b, "KeyB"), // bB
+ USB_KEYMAP(0x070006, 0x0036, 0x002e, 0x0008, "KeyC"), // cC
+ USB_KEYMAP(0x070007, 0x0028, 0x0020, 0x0002, "KeyD"), // dD
+
+ USB_KEYMAP(0x070008, 0x001a, 0x0012, 0x000e, "KeyE"), // eEo
+ USB_KEYMAP(0x070009, 0x0029, 0x0021, 0x0003, "KeyF"), // fF
+ USB_KEYMAP(0x07000a, 0x002a, 0x0022, 0x0005, "KeyG"), // gG
+ USB_KEYMAP(0x07000b, 0x002b, 0x0023, 0x0004, "KeyH"), // hH
+ USB_KEYMAP(0x07000c, 0x001f, 0x0017, 0x0022, "KeyI"), // iI
+ USB_KEYMAP(0x07000d, 0x002c, 0x0024, 0x0026, "KeyJ"), // jJ
+ USB_KEYMAP(0x07000e, 0x002d, 0x0025, 0x0028, "KeyK"), // kK
+ USB_KEYMAP(0x07000f, 0x002e, 0x0026, 0x0025, "KeyL"), // lL
+
+ USB_KEYMAP(0x070010, 0x003a, 0x0032, 0x002e, "KeyM"), // mM
+ USB_KEYMAP(0x070011, 0x0039, 0x0031, 0x002d, "KeyN"), // nN
+ USB_KEYMAP(0x070012, 0x0020, 0x0018, 0x001f, "KeyO"), // oO
+ USB_KEYMAP(0x070013, 0x0021, 0x0019, 0x0023, "KeyP"), // pP
+ USB_KEYMAP(0x070014, 0x0018, 0x0010, 0x000c, "KeyQ"), // qQ
+ USB_KEYMAP(0x070015, 0x001b, 0x0013, 0x000f, "KeyR"), // rR
+ USB_KEYMAP(0x070016, 0x0027, 0x001f, 0x0001, "KeyS"), // sS
+ USB_KEYMAP(0x070017, 0x001c, 0x0014, 0x0011, "KeyT"), // tT
+
+ USB_KEYMAP(0x070018, 0x001e, 0x0016, 0x0020, "KeyU"), // uU
+ USB_KEYMAP(0x070019, 0x0037, 0x002f, 0x0009, "KeyV"), // vV
+ USB_KEYMAP(0x07001a, 0x0019, 0x0011, 0x000d, "KeyW"), // wW
+ USB_KEYMAP(0x07001b, 0x0035, 0x002d, 0x0007, "KeyX"), // xX
+ USB_KEYMAP(0x07001c, 0x001d, 0x0015, 0x0010, "KeyY"), // yY
+ USB_KEYMAP(0x07001d, 0x0034, 0x002c, 0x0006, "KeyZ"), // zZ
+ USB_KEYMAP(0x07001e, 0x000a, 0x0002, 0x0012, "Digit1"), // 1!
+ USB_KEYMAP(0x07001f, 0x000b, 0x0003, 0x0013, "Digit2"), // 2@
+
+ USB_KEYMAP(0x070020, 0x000c, 0x0004, 0x0014, "Digit3"), // 3#
+ USB_KEYMAP(0x070021, 0x000d, 0x0005, 0x0015, "Digit4"), // 4$
+ USB_KEYMAP(0x070022, 0x000e, 0x0006, 0x0017, "Digit5"), // 5%
+ USB_KEYMAP(0x070023, 0x000f, 0x0007, 0x0016, "Digit6"), // 6^
+ USB_KEYMAP(0x070024, 0x0010, 0x0008, 0x001a, "Digit7"), // 7&
+ USB_KEYMAP(0x070025, 0x0011, 0x0009, 0x001c, "Digit8"), // 8*
+ USB_KEYMAP(0x070026, 0x0012, 0x000a, 0x0019, "Digit9"), // 9(
+ USB_KEYMAP(0x070027, 0x0013, 0x000b, 0x001d, "Digit0"), // 0)
+
+ USB_KEYMAP(0x070028, 0x0024, 0x001c, 0x0024, "Enter"),
+ USB_KEYMAP(0x070029, 0x0009, 0x0001, 0x0035, "Escape"),
+ USB_KEYMAP(0x07002a, 0x0016, 0x000e, 0x0033, "Backspace"),
+ USB_KEYMAP(0x07002b, 0x0017, 0x000f, 0x0030, "Tab"),
+ USB_KEYMAP(0x07002c, 0x0041, 0x0039, 0x0031, "Space"), // Spacebar
+ USB_KEYMAP(0x07002d, 0x0014, 0x000c, 0x001b, "Minus"), // -_
+ USB_KEYMAP(0x07002e, 0x0015, 0x000d, 0x0018, "Equal"), // =+
+ USB_KEYMAP(0x07002f, 0x0022, 0x001a, 0x0021, "BracketLeft"),// [{
+
+ USB_KEYMAP(0x070030, 0x0023, 0x001b, 0x001e, "BracketRight"), // ]}
+ USB_KEYMAP(0x070031, 0x0033, 0x002b, 0x002a, "Backslash"), // \| (US keyboard only)
+ // USB#070032 never appears on keyboards that have USB#070031.
+ // Platforms use the same scancode as for the two keys.
+ // The keycap varies on international keyboards:
+ // Dan: '* Dutch: <> Ger: #' UK: #~
+ // TODO(garykac): Verify Mac intl keyboard.
+ //USB_KEYMAP(0x070032, 0x0033, 0x002b, 0x002a, "IntlHash"), // #~ (Non-US)
+ USB_KEYMAP(0x070033, 0x002f, 0x0027, 0x0029, "Semicolon"), // ;:
+ USB_KEYMAP(0x070034, 0x0030, 0x0028, 0x0027, "Quote"), // '"
+ USB_KEYMAP(0x070035, 0x0031, 0x0029, 0x0032, "Backquote"), // `~
+ USB_KEYMAP(0x070036, 0x003b, 0x0033, 0x002b, "Comma"), // ,<
+ USB_KEYMAP(0x070037, 0x003c, 0x0034, 0x002f, "Period"), // .>
+
+ USB_KEYMAP(0x070038, 0x003d, 0x0035, 0x002c, "Slash"), // /?
+ // TODO(garykac): CapsLock requires special handling for each platform.
+ USB_KEYMAP(0x070039, 0x0042, 0x003a, 0x0039, "CapsLock"),
+ USB_KEYMAP(0x07003a, 0x0043, 0x003b, 0x007a, "F1"),
+ USB_KEYMAP(0x07003b, 0x0044, 0x003c, 0x0078, "F2"),
+ USB_KEYMAP(0x07003c, 0x0045, 0x003d, 0x0063, "F3"),
+ USB_KEYMAP(0x07003d, 0x0046, 0x003e, 0x0076, "F4"),
+ USB_KEYMAP(0x07003e, 0x0047, 0x003f, 0x0060, "F5"),
+ USB_KEYMAP(0x07003f, 0x0048, 0x0040, 0x0061, "F6"),
+
+ USB_KEYMAP(0x070040, 0x0049, 0x0041, 0x0062, "F7"),
+ USB_KEYMAP(0x070041, 0x004a, 0x0042, 0x0064, "F8"),
+ USB_KEYMAP(0x070042, 0x004b, 0x0043, 0x0065, "F9"),
+ USB_KEYMAP(0x070043, 0x004c, 0x0044, 0x006d, "F10"),
+ USB_KEYMAP(0x070044, 0x005f, 0x0057, 0x0067, "F11"),
+ USB_KEYMAP(0x070045, 0x0060, 0x0058, 0x006f, "F12"),
+ // PrintScreen is effectively F13 on Mac OS X.
+ USB_KEYMAP(0x070046, 0x006b, 0xe037, 0xffff, "PrintScreen"),
+ USB_KEYMAP(0x070047, 0x004e, 0x0046, 0xffff, "ScrollLock"),
+
+ USB_KEYMAP(0x070048, 0x007f, 0x0000, 0xffff, "Pause"),
+ // Labeled "Help/Insert" on Mac.
+ USB_KEYMAP(0x070049, 0x0076, 0xe052, 0x0072, "Insert"),
+ USB_KEYMAP(0x07004a, 0x006e, 0xe047, 0x0073, "Home"),
+ USB_KEYMAP(0x07004b, 0x0070, 0xe049, 0x0074, "PageUp"),
+ // Delete (Forward Delete)
+ USB_KEYMAP(0x07004c, 0x0077, 0xe053, 0x0075, "Delete"),
+ USB_KEYMAP(0x07004d, 0x0073, 0xe04f, 0x0077, "End"),
+ USB_KEYMAP(0x07004e, 0x0075, 0xe051, 0x0079, "PageDown"),
+ USB_KEYMAP(0x07004f, 0x0072, 0xe04d, 0x007c, "ArrowRight"),
+
+ USB_KEYMAP(0x070050, 0x0071, 0xe04b, 0x007b, "ArrowLeft"),
+ USB_KEYMAP(0x070051, 0x0074, 0xe050, 0x007d, "ArrowDown"),
+ USB_KEYMAP(0x070052, 0x006f, 0xe048, 0x007e, "ArrowUp"),
+ USB_KEYMAP(0x070053, 0x004d, 0x0045, 0x0047, "NumLock"), // Keypad_NumLock Clear
+ USB_KEYMAP(0x070054, 0x006a, 0xe035, 0x004b, "NumpadDivide"), // Keypad_/
+ USB_KEYMAP(0x070055, 0x003f, 0x0037, 0x0043, "NumpadMultiply"),// Keypad_*
+ USB_KEYMAP(0x070056, 0x0052, 0x004a, 0x004e, "NumpadSubtract"),// Keypad_-
+ USB_KEYMAP(0x070057, 0x0056, 0x004e, 0x0045, "NumpadAdd"), // Keypad_+
+
+ USB_KEYMAP(0x070058, 0x0068, 0xe01c, 0x004c, "NumpadEnter"), // Keypad_Enter
+ USB_KEYMAP(0x070059, 0x0057, 0x004f, 0x0053, "Numpad1"), // Keypad_1 End
+ USB_KEYMAP(0x07005a, 0x0058, 0x0050, 0x0054, "Numpad2"), // Keypad_2 DownArrow
+ USB_KEYMAP(0x07005b, 0x0059, 0x0051, 0x0055, "Numpad3"), // Keypad_3 PageDown
+ USB_KEYMAP(0x07005c, 0x0053, 0x004b, 0x0056, "Numpad4"), // Keypad_4 LeftArrow
+ USB_KEYMAP(0x07005d, 0x0054, 0x004c, 0x0057, "Numpad5"), // Keypad_5
+ USB_KEYMAP(0x07005e, 0x0055, 0x004d, 0x0058, "Numpad6"), // Keypad_6 RightArrow
+ USB_KEYMAP(0x07005f, 0x004f, 0x0047, 0x0059, "Numpad7"), // Keypad_7 Home
+
+ USB_KEYMAP(0x070060, 0x0050, 0x0048, 0x005b, "Numpad8"), // Keypad_8 UpArrow
+ USB_KEYMAP(0x070061, 0x0051, 0x0049, 0x005c, "Numpad9"), // Keypad_9 PageUp
+ USB_KEYMAP(0x070062, 0x005a, 0x0052, 0x0052, "Numpad0"), // Keypad_0 Insert
+ USB_KEYMAP(0x070063, 0x005b, 0x0053, 0x0041, "NumpadDecimal"), // Keypad_. Delete
+ // USB#070064 is not present on US keyboard.
+ // This key is typically located near LeftShift key.
+ // The keycap varies on international keyboards:
+ // Dan: <> Dutch: ][ Ger: <> UK: \|
+ USB_KEYMAP(0x070064, 0x005e, 0x0056, 0x000a, "IntlBackslash"), // Non-US \|
+ // AppMenu (next to RWin key)
+ USB_KEYMAP(0x070065, 0x0087, 0xe05d, 0x006e, "ContextMenu"),
+ USB_KEYMAP(0x070066, 0x007c, 0x0000, 0xffff, "Power"),
+ USB_KEYMAP(0x070067, 0x007d, 0x0000, 0x0051, "NumpadEqual"), // Keypad_=
+
+ USB_KEYMAP(0x070068, 0x0000, 0x005b, 0x0069, "F13"),
+ USB_KEYMAP(0x070069, 0x0000, 0x005c, 0x006b, "F14"),
+ USB_KEYMAP(0x07006a, 0x0000, 0x005d, 0x0071, "F15"),
+ USB_KEYMAP(0x07006b, 0x0000, 0x0063, 0x006a, "F16"),
+ USB_KEYMAP(0x07006c, 0x0000, 0x0064, 0x0040, "F17"),
+ USB_KEYMAP(0x07006d, 0x0000, 0x0065, 0x004f, "F18"),
+ USB_KEYMAP(0x07006e, 0x0000, 0x0066, 0x0050, "F19"),
+ USB_KEYMAP(0x07006f, 0x0000, 0x0067, 0x005a, "F20"),
+
+ USB_KEYMAP(0x070070, 0x0000, 0x0068, 0xffff, "F21"),
+ USB_KEYMAP(0x070071, 0x0000, 0x0069, 0xffff, "F22"),
+ USB_KEYMAP(0x070072, 0x0000, 0x006a, 0xffff, "F23"),
+ USB_KEYMAP(0x070073, 0x0000, 0x006b, 0xffff, "F24"),
+ USB_KEYMAP(0x070074, 0x0000, 0x0000, 0xffff, NULL), // Execute
+ USB_KEYMAP(0x070075, 0x0092, 0xe03b, 0xffff, "Help"),
+ USB_KEYMAP(0x070076, 0x0093, 0x0000, 0xffff, NULL), // Menu
+ //USB_KEYMAP(0x070077, 0x0000, 0x0000, 0xffff, NULL), // Select
+
+ //USB_KEYMAP(0x070078, 0x0000, 0x0000, 0xffff, NULL), // Stop
+ USB_KEYMAP(0x070079, 0x0089, 0x0000, 0xffff, NULL), // Again (Redo)
+ USB_KEYMAP(0x07007a, 0x008b, 0xe008, 0xffff, "Undo"),
+ USB_KEYMAP(0x07007b, 0x0091, 0xe017, 0xffff, "Cut"),
+ USB_KEYMAP(0x07007c, 0x008d, 0xe018, 0xffff, "Copy"),
+ USB_KEYMAP(0x07007d, 0x008f, 0xe00a, 0xffff, "Paste"),
+ USB_KEYMAP(0x07007e, 0x0090, 0x0000, 0xffff, NULL), // Find
+ USB_KEYMAP(0x07007f, 0x0079, 0xe020, 0x004a, "VolumeMute"),
+
+ USB_KEYMAP(0x070080, 0x007b, 0xe030, 0x0048, "VolumeUp"),
+ USB_KEYMAP(0x070081, 0x007a, 0xe02e, 0x0049, "VolumeDown"),
+ //USB_KEYMAP(0x070082, 0x0000, 0x0000, 0xffff, NULL), // LockingCapsLock
+ //USB_KEYMAP(0x070083, 0x0000, 0x0000, 0xffff, NULL), // LockingNumLock
+ //USB_KEYMAP(0x070084, 0x0000, 0x0000, 0xffff, NULL), // LockingScrollLock
+ // USB#070085 is used as Brazilian Keypad_.
+ USB_KEYMAP(0x070085, 0x0000, 0x0000, 0x005f, "NumpadComma"), // Keypad_Comma
+
+ // International1
+ // USB#070086 is used on AS/400 keyboards. Standard Keypad_= is USB#070067.
+ //USB_KEYMAP(0x070086, 0x0000, 0x0000, 0xffff, NULL), // Keypad_=
+ // USB#070087 is used for Brazilian /? and Japanese _ 'ro'.
+ USB_KEYMAP(0x070087, 0x0061, 0x0000, 0x005e, "IntlRo"),
+ // International2
+ // USB#070088 is used as Japanese Hiragana/Katakana key.
+ USB_KEYMAP(0x070088, 0x0065, 0x0000, 0x0068, "KanaMode"),
+ // International3
+ // USB#070089 is used as Japanese Yen key.
+ USB_KEYMAP(0x070089, 0x0084, 0x007d, 0x005d, "IntlYen"),
+ // International4
+ // USB#07008a is used as Japanese Henkan (Convert) key.
+ USB_KEYMAP(0x07008a, 0x0064, 0x0000, 0xffff, "Convert"),
+ // International5
+ // USB#07008b is used as Japanese Muhenkan (No-convert) key.
+ USB_KEYMAP(0x07008b, 0x0066, 0x0000, 0xffff, "NoConvert"),
+ //USB_KEYMAP(0x07008c, 0x0000, 0x0000, 0xffff, NULL), // International6
+ //USB_KEYMAP(0x07008d, 0x0000, 0x0000, 0xffff, NULL), // International7
+ //USB_KEYMAP(0x07008e, 0x0000, 0x0000, 0xffff, NULL), // International8
+ //USB_KEYMAP(0x07008f, 0x0000, 0x0000, 0xffff, NULL), // International9
+
+ // LANG1
+ // USB#070090 is used as Korean Hangul/English toggle key.
+ USB_KEYMAP(0x070090, 0x0082, 0x0000, 0xffff, "HangulMode"),
+ // LANG2
+ // USB#070091 is used as Korean Hanja conversion key.
+ USB_KEYMAP(0x070091, 0x0083, 0x0000, 0xffff, "Hanja"),
+ // LANG3
+ // USB#070092 is used as Japanese Katakana key.
+ USB_KEYMAP(0x070092, 0x0062, 0x0000, 0xffff, NULL),
+ // LANG4
+ // USB#070093 is used as Japanese Hiragana key.
+ USB_KEYMAP(0x070093, 0x0063, 0x0000, 0xffff, NULL),
+ // LANG5
+ // USB#070094 is used as Japanese Zenkaku/Hankaku (Fullwidth/halfwidth) key.
+ //USB_KEYMAP(0x070094, 0x0000, 0x0000, 0xffff, NULL),
+ //USB_KEYMAP(0x070095, 0x0000, 0x0000, 0xffff, NULL), // LANG6
+ //USB_KEYMAP(0x070096, 0x0000, 0x0000, 0xffff, NULL), // LANG7
+ //USB_KEYMAP(0x070097, 0x0000, 0x0000, 0xffff, NULL), // LANG8
+ //USB_KEYMAP(0x070098, 0x0000, 0x0000, 0xffff, NULL), // LANG9
+
+ //USB_KEYMAP(0x070099, 0x0000, 0x0000, 0xffff, NULL), // AlternateErase
+ //USB_KEYMAP(0x07009a, 0x0000, 0x0000, 0xffff, NULL), // SysReq/Attention
+ USB_KEYMAP(0x07009b, 0x0088, 0x0000, 0xffff, "Cancel"),
+ //USB_KEYMAP(0x07009c, 0x0000, 0x0000, 0xffff, NULL), // Clear
+ //USB_KEYMAP(0x07009d, 0x0000, 0x0000, 0xffff, NULL), // Prior
+ //USB_KEYMAP(0x07009e, 0x0000, 0x0000, 0xffff, NULL), // Return
+ //USB_KEYMAP(0x07009f, 0x0000, 0x0000, 0xffff, NULL), // Separator
+
+ //USB_KEYMAP(0x0700a0, 0x0000, 0x0000, 0xffff, NULL), // Out
+ //USB_KEYMAP(0x0700a1, 0x0000, 0x0000, 0xffff, NULL), // Oper
+ //USB_KEYMAP(0x0700a2, 0x0000, 0x0000, 0xffff, NULL), // Clear/Again
+ //USB_KEYMAP(0x0700a3, 0x0000, 0x0000, 0xffff, NULL), // CrSel/Props
+ //USB_KEYMAP(0x0700a4, 0x0000, 0x0000, 0xffff, NULL), // ExSel
+
+ //USB_KEYMAP(0x0700b0, 0x0000, 0x0000, 0xffff, NULL), // Keypad_00
+ //USB_KEYMAP(0x0700b1, 0x0000, 0x0000, 0xffff, NULL), // Keypad_000
+ //USB_KEYMAP(0x0700b2, 0x0000, 0x0000, 0xffff, NULL), // ThousandsSeparator
+ //USB_KEYMAP(0x0700b3, 0x0000, 0x0000, 0xffff, NULL), // DecimalSeparator
+ //USB_KEYMAP(0x0700b4, 0x0000, 0x0000, 0xffff, NULL), // CurrencyUnit
+ //USB_KEYMAP(0x0700b5, 0x0000, 0x0000, 0xffff, NULL), // CurrencySubunit
+ USB_KEYMAP(0x0700b6, 0x00bb, 0x0000, 0xffff, "NumpadParenLeft"), // Keypad_(
+ USB_KEYMAP(0x0700b7, 0x00bc, 0x0000, 0xffff, "NumpadParenRight"), // Keypad_)
+
+ //USB_KEYMAP(0x0700b8, 0x0000, 0x0000, 0xffff, NULL), // Keypad_{
+ //USB_KEYMAP(0x0700b9, 0x0000, 0x0000, 0xffff, NULL), // Keypad_}
+ //USB_KEYMAP(0x0700ba, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Tab
+ //USB_KEYMAP(0x0700bb, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Backspace
+ //USB_KEYMAP(0x0700bc, 0x0000, 0x0000, 0xffff, NULL), // Keypad_A
+ //USB_KEYMAP(0x0700bd, 0x0000, 0x0000, 0xffff, NULL), // Keypad_B
+ //USB_KEYMAP(0x0700be, 0x0000, 0x0000, 0xffff, NULL), // Keypad_C
+ //USB_KEYMAP(0x0700bf, 0x0000, 0x0000, 0xffff, NULL), // Keypad_D
+
+ //USB_KEYMAP(0x0700c0, 0x0000, 0x0000, 0xffff, NULL), // Keypad_E
+ //USB_KEYMAP(0x0700c1, 0x0000, 0x0000, 0xffff, NULL), // Keypad_F
+ //USB_KEYMAP(0x0700c2, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Xor
+ //USB_KEYMAP(0x0700c3, 0x0000, 0x0000, 0xffff, NULL), // Keypad_^
+ //USB_KEYMAP(0x0700c4, 0x0000, 0x0000, 0xffff, NULL), // Keypad_%
+ //USB_KEYMAP(0x0700c5, 0x0000, 0x0000, 0xffff, NULL), // Keypad_<
+ //USB_KEYMAP(0x0700c6, 0x0000, 0x0000, 0xffff, NULL), // Keypad_>
+ //USB_KEYMAP(0x0700c7, 0x0000, 0x0000, 0xffff, NULL), // Keypad_&
+
+ //USB_KEYMAP(0x0700c8, 0x0000, 0x0000, 0xffff, NULL), // Keypad_&&
+ //USB_KEYMAP(0x0700c9, 0x0000, 0x0000, 0xffff, NULL), // Keypad_|
+ //USB_KEYMAP(0x0700ca, 0x0000, 0x0000, 0xffff, NULL), // Keypad_||
+ //USB_KEYMAP(0x0700cb, 0x0000, 0x0000, 0xffff, NULL), // Keypad_:
+ //USB_KEYMAP(0x0700cc, 0x0000, 0x0000, 0xffff, NULL), // Keypad_#
+ //USB_KEYMAP(0x0700cd, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Space
+ //USB_KEYMAP(0x0700ce, 0x0000, 0x0000, 0xffff, NULL), // Keypad_@
+ //USB_KEYMAP(0x0700cf, 0x0000, 0x0000, 0xffff, NULL), // Keypad_!
+
+ //USB_KEYMAP(0x0700d0, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemoryStore
+ //USB_KEYMAP(0x0700d1, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemoryRecall
+ //USB_KEYMAP(0x0700d2, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemoryClear
+ //USB_KEYMAP(0x0700d3, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemoryAdd
+ //USB_KEYMAP(0x0700d4, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemorySubtract
+ //USB_KEYMAP(0x0700d5, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemoryMultiply
+ //USB_KEYMAP(0x0700d6, 0x0000, 0x0000, 0xffff, NULL), // Keypad_MemoryDivide
+ USB_KEYMAP(0x0700d7, 0x007e, 0x0000, 0xffff, "NumpadChangeSign"), // Keypad_+/-
+
+ //USB_KEYMAP(0x0700d8, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Clear
+ //USB_KEYMAP(0x0700d9, 0x0000, 0x0000, 0xffff, NULL), // Keypad_ClearEntry
+ //USB_KEYMAP(0x0700da, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Binary
+ //USB_KEYMAP(0x0700db, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Octal
+ USB_KEYMAP(0x0700dc, 0x0081, 0x0000, 0xffff, NULL), // Keypad_Decimal
+ //USB_KEYMAP(0x0700dd, 0x0000, 0x0000, 0xffff, NULL), // Keypad_Hexadecimal
+ // USB#0700de - #0700df are reserved.
+
+ USB_KEYMAP(0x0700e0, 0x0025, 0x001d, 0x003b, "ControlLeft"),
+ USB_KEYMAP(0x0700e1, 0x0032, 0x002a, 0x0038, "ShiftLeft"),
+ USB_KEYMAP(0x0700e2, 0x0040, 0x0038, 0x003a, "AltLeft"), // LeftAlt/Option
+ USB_KEYMAP(0x0700e3, 0x0085, 0xe05b, 0x0037, "OSLeft"), // LeftGUI/Super/Win/Cmd
+ USB_KEYMAP(0x0700e4, 0x0069, 0xe01d, 0x003e, "ControlRight"),
+ USB_KEYMAP(0x0700e5, 0x003e, 0x0036, 0x003c, "ShiftRight"),
+ USB_KEYMAP(0x0700e6, 0x006c, 0xe038, 0x003d, "AltRight"), // RightAlt/Option
+ USB_KEYMAP(0x0700e7, 0x0086, 0xe05c, 0x0036, "OSRight"), // RightGUI/Super/Win/Cmd
+
+ // USB#0700e8 - #07ffff are reserved
+
+ // ==================================
+ // USB Usage Page 0x0c: Consumer Page
+ // ==================================
+ // AL = Application Launch
+ // AC = Application Control
+
+ // TODO(garykac): Many XF86 keys have multiple scancodes mapping to them.
+ // We need to map all of these into a canonical USB scancode without
+ // confusing the reverse-lookup - most likely by simply returning the first
+ // found match.
+
+ // TODO(garykac): Find appropriate mappings for:
+ // Win#e06b LaunchApp1 (My Computer?)
+ // Win#e021 LaunchApp2 (Calculator?)
+ // Win#e03c Music - USB#0c0193 is AL_AVCapturePlayback
+ // Win#e06d Video - USB#0c0193 is AL_AVCapturePlayback
+ // Win#e064 Pictures
+ // XKB#0080 XF86LaunchA
+ // XKB#0097 XF86WakeUp
+ // XKB#0099 XF86Send
+ // XKB#009b XF86Xfer
+ // XKB#009c XF86Launch1
+ // XKB#009d XF86Launch2
+ // XKB... remaining XF86 keys
+
+ // USB XKB Win Mac
+ USB_KEYMAP(0x0c00b5, 0x0000, 0xe019, 0xffff, "MediaTrackNext"),
+ USB_KEYMAP(0x0c00b6, 0x0000, 0xe010, 0xffff, "MediaTrackPrevious"),
+ USB_KEYMAP(0x0c00b7, 0x0000, 0xe024, 0xffff, "MediaStop"),
+ USB_KEYMAP(0x0c00b8, 0x0000, 0xe02c, 0xffff, "Eject"),
+ USB_KEYMAP(0x0c00cd, 0x0000, 0xe022, 0xffff, "MediaPlayPause"),
+ USB_KEYMAP(0x0c018a, 0x0000, 0xe01e, 0xffff, "LaunchMail"), // AL_EmailReader
+ USB_KEYMAP(0x0c0192, 0x0094, 0x0000, 0xffff, NULL), // AL_Calculator
+ // USB#0c0194: My Computer
+ USB_KEYMAP(0x0c0194, 0x00a5, 0x0000, 0xffff, NULL), // AL_LocalMachineBrowser
+ USB_KEYMAP(0x0c01a7, 0x00f3, 0x0000, 0xffff, NULL), // AL_Documents
+ // USB#0c01b4: Home Directory
+ USB_KEYMAP(0x0c01b4, 0x0098, 0x0000, 0xffff, NULL), // AL_FileBrowser (Explorer)
+ USB_KEYMAP(0x0c0221, 0x0000, 0xe065, 0xffff, "BrowserSearch"), // AC_Search
+ USB_KEYMAP(0x0c0223, 0x0000, 0xe032, 0xffff, "BrowserHome"), // AC_Home
+ USB_KEYMAP(0x0c0224, 0x00a6, 0xe06a, 0xffff, "BrowserBack"), // AC_Back
+ USB_KEYMAP(0x0c0225, 0x00a7, 0xe069, 0xffff, "BrowserForward"), // AC_Forward
+ USB_KEYMAP(0x0c0226, 0x0000, 0xe068, 0xffff, "BrowserStop"), // AC_Stop
+ USB_KEYMAP(0x0c0227, 0x00b5, 0xe067, 0xffff, "BrowserRefresh"), // AC_Refresh (Reload)
+ USB_KEYMAP(0x0c022a, 0x00a4, 0xe066, 0xffff, NULL), // AC_Bookmarks (Favorites)
+ USB_KEYMAP(0x0c0289, 0x00f0, 0x0000, 0xffff, NULL), // AC_Reply
+ USB_KEYMAP(0x0c028b, 0x00f1, 0x0000, 0xffff, NULL), // AC_ForwardMsg (MailForward)
+ USB_KEYMAP(0x0c028c, 0x00ef, 0x0000, 0xffff, NULL), // AC_Send
+};
+
+#endif // UI_BASE_KEYCODES_KEYCODE_CONVERTER_DATA_H_
diff --git a/chromium/ui/base/keycodes/keycode_converter_unittest.cc b/chromium/ui/base/keycodes/keycode_converter_unittest.cc
new file mode 100644
index 00000000000..3362d535684
--- /dev/null
+++ b/chromium/ui/base/keycodes/keycode_converter_unittest.cc
@@ -0,0 +1,110 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/keycodes/keycode_converter.h"
+
+#include <map>
+
+#include "base/basictypes.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+using ui::KeycodeConverter;
+
+namespace {
+
+#if defined(OS_WIN)
+const size_t kExpectedMappedKeyCount = 138;
+#elif defined(OS_LINUX)
+const size_t kExpectedMappedKeyCount = 145;
+#elif defined(OS_MACOSX)
+const size_t kExpectedMappedKeyCount = 118;
+#else
+const size_t kExpectedMappedKeyCount = 0;
+#endif
+
+const uint32_t kUsbNonExistentKeycode = 0xffffff;
+const uint32_t kUsbUsBackslash = 0x070031;
+const uint32_t kUsbNonUsHash = 0x070032;
+
+TEST(UsbKeycodeMap, Basic) {
+ ui::KeycodeConverter* key_converter = ui::KeycodeConverter::GetInstance();
+ // Verify that the first element in the table is the "invalid" code.
+ const ui::KeycodeMapEntry* keycode_map =
+ key_converter->GetKeycodeMapForTest();
+ EXPECT_EQ(key_converter->InvalidUsbKeycode(), keycode_map[0].usb_keycode);
+ EXPECT_EQ(key_converter->InvalidNativeKeycode(),
+ keycode_map[0].native_keycode);
+ EXPECT_STREQ(key_converter->InvalidKeyboardEventCode(), "Unidentified");
+ EXPECT_EQ(key_converter->InvalidNativeKeycode(),
+ key_converter->CodeToNativeKeycode("Unidentified"));
+
+ // Verify that there are no duplicate entries in the mapping.
+ std::map<uint32_t, uint16_t> usb_to_native;
+ std::map<uint16_t, uint32_t> native_to_usb;
+ size_t numEntries = key_converter->NumKeycodeMapEntriesForTest();
+ for (size_t i = 0; i < numEntries; ++i) {
+ const ui::KeycodeMapEntry* entry = &keycode_map[i];
+ // Don't test keys with no native keycode mapping on this platform.
+ if (entry->native_keycode == key_converter->InvalidNativeKeycode())
+ continue;
+
+ // Verify UsbKeycodeToNativeKeycode works for this key.
+ EXPECT_EQ(entry->native_keycode,
+ key_converter->UsbKeycodeToNativeKeycode(entry->usb_keycode));
+
+ // Verify CodeToNativeKeycode and NativeKeycodeToCode work correctly.
+ if (entry->code) {
+ EXPECT_EQ(entry->native_keycode,
+ key_converter->CodeToNativeKeycode(entry->code));
+ EXPECT_STREQ(entry->code,
+ key_converter->NativeKeycodeToCode(entry->native_keycode));
+ }
+ else {
+ EXPECT_EQ(key_converter->InvalidNativeKeycode(),
+ key_converter->CodeToNativeKeycode(entry->code));
+ }
+
+ // Verify that the USB or native codes aren't duplicated.
+ EXPECT_EQ(0U, usb_to_native.count(entry->usb_keycode))
+ << " duplicate of USB code 0x" << std::hex << std::setfill('0')
+ << std::setw(6) << entry->usb_keycode
+ << " to native 0x"
+ << std::setw(4) << entry->native_keycode
+ << " (previous was 0x"
+ << std::setw(4) << usb_to_native[entry->usb_keycode]
+ << ")";
+ usb_to_native[entry->usb_keycode] = entry->native_keycode;
+ EXPECT_EQ(0U, native_to_usb.count(entry->native_keycode))
+ << " duplicate of native code 0x" << std::hex << std::setfill('0')
+ << std::setw(4) << entry->native_keycode
+ << " to USB 0x"
+ << std::setw(6) << entry->usb_keycode
+ << " (previous was 0x"
+ << std::setw(6) << native_to_usb[entry->native_keycode]
+ << ")";
+ native_to_usb[entry->native_keycode] = entry->usb_keycode;
+ }
+ ASSERT_EQ(usb_to_native.size(), native_to_usb.size());
+
+ // Verify that the number of mapped keys is what we expect, i.e. we haven't
+ // lost any, and if we've added some then the expectation has been updated.
+ EXPECT_EQ(kExpectedMappedKeyCount, usb_to_native.size());
+}
+
+TEST(UsbKeycodeMap, NonExistent) {
+ // Verify that UsbKeycodeToNativeKeycode works for a non-existent USB keycode.
+ ui::KeycodeConverter* key_converter = ui::KeycodeConverter::GetInstance();
+ EXPECT_EQ(key_converter->InvalidNativeKeycode(),
+ key_converter->UsbKeycodeToNativeKeycode(kUsbNonExistentKeycode));
+}
+
+TEST(UsbKeycodeMap, UsBackslashIsNonUsHash) {
+ // Verify that UsbKeycodeToNativeKeycode treats the non-US "hash" key
+ // as equivalent to the US "backslash" key.
+ ui::KeycodeConverter* key_converter = ui::KeycodeConverter::GetInstance();
+ EXPECT_EQ(key_converter->UsbKeycodeToNativeKeycode(kUsbUsBackslash),
+ key_converter->UsbKeycodeToNativeKeycode(kUsbNonUsHash));
+}
+
+} // namespace
diff --git a/chromium/ui/base/keycodes/usb_keycode_map.h b/chromium/ui/base/keycodes/usb_keycode_map.h
deleted file mode 100644
index a5fca425589..00000000000
--- a/chromium/ui/base/keycodes/usb_keycode_map.h
+++ /dev/null
@@ -1,409 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-// Data in this file was created by referencing:
-// USB HID Usage Tables (v1.11) 27 June 2001
-// HIToolbox/Events.h (Mac)
-
-#include <stdint.h>
-
-typedef struct {
- // USB keycode:
- // Upper 16-bits: USB Usage Page.
- // Lower 16-bits: USB Usage Id: Assigned ID within this usage page.
- uint32_t usb_keycode;
-
- // Contains one of the following:
- // On Linux: XKB scancode
- // On Windows: Windows OEM scancode
- // On Mac: Mac keycode
- uint16_t native_keycode;
-} usb_keymap;
-
-const usb_keymap usb_keycode_map[] = {
-
- // USB XKB Win Mac
- USB_KEYMAP(0x000000, 0x0000, 0x0000, 0xffff), // Invalid
-
- // =========================================
- // USB Usage Page 0x01: Generic Desktop Page
- // =========================================
-
- // Sleep could be encoded as USB#0c0032, but there's no corresponding WakeUp
- // in the 0x0c USB page.
-
- // USB XKB Win Mac
- USB_KEYMAP(0x010082, 0x0096, 0x0000, 0xffff), // SystemSleep
- USB_KEYMAP(0x010083, 0x0097, 0x0000, 0xffff), // SystemWakeUp
-
- // =========================================
- // USB Usage Page 0x07: Keyboard/Keypad Page
- // =========================================
-
- // TODO(garykac):
- // XKB#005c ISO Level3 Shift
- // XKB#005e <>||
- // XKB#006d Linefeed
- // XKB#008a SunProps cf. USB#0700a3 CrSel/Props
- // XKB#008e SunOpen
- // Mac#003f kVK_Function
- // Mac#000a kVK_ISO_Section (ISO keyboards only)
- // Mac#0066 kVK_JIS_Eisu (USB#07008a Henkan?)
-
- // USB XKB Win Mac
- USB_KEYMAP(0x070000, 0x0000, 0x0000, 0xffff), // Reserved
- USB_KEYMAP(0x070001, 0x0000, 0x0000, 0xffff), // ErrorRollOver
- USB_KEYMAP(0x070002, 0x0000, 0x0000, 0xffff), // POSTFail
- USB_KEYMAP(0x070003, 0x0000, 0x0000, 0xffff), // ErrorUndefined
- USB_KEYMAP(0x070004, 0x0026, 0x001e, 0x0000), // aA
- USB_KEYMAP(0x070005, 0x0038, 0x0030, 0x000b), // bB
- USB_KEYMAP(0x070006, 0x0036, 0x002e, 0x0008), // cC
- USB_KEYMAP(0x070007, 0x0028, 0x0020, 0x0002), // dD
-
- USB_KEYMAP(0x070008, 0x001a, 0x0012, 0x000e), // eE
- USB_KEYMAP(0x070009, 0x0029, 0x0021, 0x0003), // fF
- USB_KEYMAP(0x07000a, 0x002a, 0x0022, 0x0005), // gG
- USB_KEYMAP(0x07000b, 0x002b, 0x0023, 0x0004), // hH
- USB_KEYMAP(0x07000c, 0x001f, 0x0017, 0x0022), // iI
- USB_KEYMAP(0x07000d, 0x002c, 0x0024, 0x0026), // jJ
- USB_KEYMAP(0x07000e, 0x002d, 0x0025, 0x0028), // kK
- USB_KEYMAP(0x07000f, 0x002e, 0x0026, 0x0025), // lL
-
- USB_KEYMAP(0x070010, 0x003a, 0x0032, 0x002e), // mM
- USB_KEYMAP(0x070011, 0x0039, 0x0031, 0x002d), // nN
- USB_KEYMAP(0x070012, 0x0020, 0x0018, 0x001f), // oO
- USB_KEYMAP(0x070013, 0x0021, 0x0019, 0x0023), // pP
- USB_KEYMAP(0x070014, 0x0018, 0x0010, 0x000c), // qQ
- USB_KEYMAP(0x070015, 0x001b, 0x0013, 0x000f), // rR
- USB_KEYMAP(0x070016, 0x0027, 0x001f, 0x0001), // sS
- USB_KEYMAP(0x070017, 0x001c, 0x0014, 0x0011), // tT
-
- USB_KEYMAP(0x070018, 0x001e, 0x0016, 0x0020), // uU
- USB_KEYMAP(0x070019, 0x0037, 0x002f, 0x0009), // vV
- USB_KEYMAP(0x07001a, 0x0019, 0x0011, 0x000d), // wW
- USB_KEYMAP(0x07001b, 0x0035, 0x002d, 0x0007), // xX
- USB_KEYMAP(0x07001c, 0x001d, 0x0015, 0x0010), // yY
- USB_KEYMAP(0x07001d, 0x0034, 0x002c, 0x0006), // zZ
- USB_KEYMAP(0x07001e, 0x000a, 0x0002, 0x0012), // 1!
- USB_KEYMAP(0x07001f, 0x000b, 0x0003, 0x0013), // 2@
-
- USB_KEYMAP(0x070020, 0x000c, 0x0004, 0x0014), // 3#
- USB_KEYMAP(0x070021, 0x000d, 0x0005, 0x0015), // 4$
- USB_KEYMAP(0x070022, 0x000e, 0x0006, 0x0017), // 5%
- USB_KEYMAP(0x070023, 0x000f, 0x0007, 0x0016), // 6^
- USB_KEYMAP(0x070024, 0x0010, 0x0008, 0x001a), // 7&
- USB_KEYMAP(0x070025, 0x0011, 0x0009, 0x001c), // 8*
- USB_KEYMAP(0x070026, 0x0012, 0x000a, 0x0019), // 9(
- USB_KEYMAP(0x070027, 0x0013, 0x000b, 0x001d), // 0)
-
- USB_KEYMAP(0x070028, 0x0024, 0x001c, 0x0024), // Return
- USB_KEYMAP(0x070029, 0x0009, 0x0001, 0x0035), // Escape
- USB_KEYMAP(0x07002a, 0x0016, 0x000e, 0x0033), // Backspace
- USB_KEYMAP(0x07002b, 0x0017, 0x000f, 0x0030), // Tab
- USB_KEYMAP(0x07002c, 0x0041, 0x0039, 0x0031), // Spacebar
- USB_KEYMAP(0x07002d, 0x0014, 0x000c, 0x001b), // -_
- USB_KEYMAP(0x07002e, 0x0015, 0x000d, 0x0018), // =+
- USB_KEYMAP(0x07002f, 0x0022, 0x001a, 0x0021), // [{
-
- USB_KEYMAP(0x070030, 0x0023, 0x001b, 0x001e), // }]
- USB_KEYMAP(0x070031, 0x0033, 0x002b, 0x002a), // \| (US keyboard only)
- // USB#070032 never appears on keyboards that have USB#070031.
- // Platforms use the same scancode as for the two keys.
- // The keycap varies on international keyboards:
- // Dan: '* Dutch: <> Ger: #' UK: #~
- // TODO(garykac): Verify Mac intl keyboard.
- //USB_KEYMAP(0x070032, 0x0033, 0x002b, 0x002a), // #~ (Non-US)
- USB_KEYMAP(0x070033, 0x002f, 0x0027, 0x0029), // ;:
- USB_KEYMAP(0x070034, 0x0030, 0x0028, 0x0027), // '"
- USB_KEYMAP(0x070035, 0x0031, 0x0029, 0x0032), // `~
- USB_KEYMAP(0x070036, 0x003b, 0x0033, 0x002b), // ,<
- USB_KEYMAP(0x070037, 0x003c, 0x0034, 0x002f), // .>
-
- USB_KEYMAP(0x070038, 0x003d, 0x0035, 0x002c), // /?
- // TODO(garykac): CapsLock requires special handling for each platform.
- USB_KEYMAP(0x070039, 0x0042, 0x003a, 0x0039), // CapsLock
- USB_KEYMAP(0x07003a, 0x0043, 0x003b, 0x007a), // F1
- USB_KEYMAP(0x07003b, 0x0044, 0x003c, 0x0078), // F2
- USB_KEYMAP(0x07003c, 0x0045, 0x003d, 0x0063), // F3
- USB_KEYMAP(0x07003d, 0x0046, 0x003e, 0x0076), // F4
- USB_KEYMAP(0x07003e, 0x0047, 0x003f, 0x0060), // F5
- USB_KEYMAP(0x07003f, 0x0048, 0x0040, 0x0061), // F6
-
- USB_KEYMAP(0x070040, 0x0049, 0x0041, 0x0062), // F7
- USB_KEYMAP(0x070041, 0x004a, 0x0042, 0x0064), // F8
- USB_KEYMAP(0x070042, 0x004b, 0x0043, 0x0065), // F9
- USB_KEYMAP(0x070043, 0x004c, 0x0044, 0x006d), // F10
- USB_KEYMAP(0x070044, 0x005f, 0x0057, 0x0067), // F11
- USB_KEYMAP(0x070045, 0x0060, 0x0058, 0x006f), // F12
- // PrintScreen is effectively F13 on Mac OS X.
- USB_KEYMAP(0x070046, 0x006b, 0xe037, 0xffff), // PrintScreen
- USB_KEYMAP(0x070047, 0x004e, 0x0046, 0xffff), // ScrollLock
-
- USB_KEYMAP(0x070048, 0x007f, 0x0000, 0xffff), // Pause
- // Labeled "Help/Insert" on Mac.
- USB_KEYMAP(0x070049, 0x0076, 0xe052, 0x0072), // Insert
- USB_KEYMAP(0x07004a, 0x006e, 0xe047, 0x0073), // Home
- USB_KEYMAP(0x07004b, 0x0070, 0xe049, 0x0074), // PageUp
- USB_KEYMAP(0x07004c, 0x0077, 0xe053, 0x0075), // Delete (Forward Delete)
- USB_KEYMAP(0x07004d, 0x0073, 0xe04f, 0x0077), // End
- USB_KEYMAP(0x07004e, 0x0075, 0xe051, 0x0079), // PageDown
- USB_KEYMAP(0x07004f, 0x0072, 0xe04d, 0x007c), // RightArrow
-
- USB_KEYMAP(0x070050, 0x0071, 0xe04b, 0x007b), // LeftArrow
- USB_KEYMAP(0x070051, 0x0074, 0xe050, 0x007d), // DownArrow
- USB_KEYMAP(0x070052, 0x006f, 0xe048, 0x007e), // UpArrow
- USB_KEYMAP(0x070053, 0x004d, 0x0045, 0x0047), // Keypad_NumLock Clear
- USB_KEYMAP(0x070054, 0x006a, 0xe035, 0x004b), // Keypad_/
- USB_KEYMAP(0x070055, 0x003f, 0x0037, 0x0043), // Keypad_*
- USB_KEYMAP(0x070056, 0x0052, 0x004a, 0x004e), // Keypad_-
- USB_KEYMAP(0x070057, 0x0056, 0x004e, 0x0045), // Keypad_+
-
- USB_KEYMAP(0x070058, 0x0068, 0xe01c, 0x004c), // Keypad_Enter
- USB_KEYMAP(0x070059, 0x0057, 0x004f, 0x0053), // Keypad_1 End
- USB_KEYMAP(0x07005a, 0x0058, 0x0050, 0x0054), // Keypad_2 DownArrow
- USB_KEYMAP(0x07005b, 0x0059, 0x0051, 0x0055), // Keypad_3 PageDown
- USB_KEYMAP(0x07005c, 0x0053, 0x004b, 0x0056), // Keypad_4 LeftArrow
- USB_KEYMAP(0x07005d, 0x0054, 0x004c, 0x0057), // Keypad_5
- USB_KEYMAP(0x07005e, 0x0055, 0x004d, 0x0058), // Keypad_6 RightArrow
- USB_KEYMAP(0x07005f, 0x004f, 0x0047, 0x0059), // Keypad_7 Home
-
- USB_KEYMAP(0x070060, 0x0050, 0x0048, 0x005b), // Keypad_8 UpArrow
- USB_KEYMAP(0x070061, 0x0051, 0x0049, 0x005c), // Keypad_9 PageUp
- USB_KEYMAP(0x070062, 0x005a, 0x0052, 0x0052), // Keypad_0 Insert
- USB_KEYMAP(0x070063, 0x005b, 0x0053, 0x0041), // Keypad_. Delete
- // USB#070064 is not present on US keyboard.
- // This key is typically located near LeftShift key.
- // The keycap varies on international keyboards:
- // Dan: <> Dutch: ][ Ger: <> UK: \|
- USB_KEYMAP(0x070064, 0x005e, 0x0056, 0x000a), // Non-US \|
- USB_KEYMAP(0x070065, 0x0087, 0xe05d, 0x006e), // AppMenu (next to RWin key)
- USB_KEYMAP(0x070066, 0x007c, 0x0000, 0xffff), // Power
- USB_KEYMAP(0x070067, 0x007d, 0x0000, 0x0051), // Keypad_=
-
- USB_KEYMAP(0x070068, 0x0000, 0x005b, 0x0069), // F13
- USB_KEYMAP(0x070069, 0x0000, 0x005c, 0x006b), // F14
- USB_KEYMAP(0x07006a, 0x0000, 0x005d, 0x0071), // F15
- USB_KEYMAP(0x07006b, 0x0000, 0x0063, 0x006a), // F16
- USB_KEYMAP(0x07006c, 0x0000, 0x0064, 0x0040), // F17
- USB_KEYMAP(0x07006d, 0x0000, 0x0065, 0x004f), // F18
- USB_KEYMAP(0x07006e, 0x0000, 0x0066, 0x0050), // F19
- USB_KEYMAP(0x07006f, 0x0000, 0x0067, 0x005a), // F20
-
- USB_KEYMAP(0x070070, 0x0000, 0x0068, 0xffff), // F21
- USB_KEYMAP(0x070071, 0x0000, 0x0069, 0xffff), // F22
- USB_KEYMAP(0x070072, 0x0000, 0x006a, 0xffff), // F23
- USB_KEYMAP(0x070073, 0x0000, 0x006b, 0xffff), // F24
- USB_KEYMAP(0x070074, 0x0000, 0x0000, 0xffff), // Execute
- USB_KEYMAP(0x070075, 0x0092, 0xe03b, 0xffff), // Help
- USB_KEYMAP(0x070076, 0x0093, 0x0000, 0xffff), // Menu
- USB_KEYMAP(0x070077, 0x0000, 0x0000, 0xffff), // Select
-
- USB_KEYMAP(0x070078, 0x0000, 0x0000, 0xffff), // Stop
- USB_KEYMAP(0x070079, 0x0089, 0x0000, 0xffff), // Again (Redo)
- USB_KEYMAP(0x07007a, 0x008b, 0xe008, 0xffff), // Undo
- USB_KEYMAP(0x07007b, 0x0091, 0xe017, 0xffff), // Cut
- USB_KEYMAP(0x07007c, 0x008d, 0xe018, 0xffff), // Copy
- USB_KEYMAP(0x07007d, 0x008f, 0xe00a, 0xffff), // Paste
- USB_KEYMAP(0x07007e, 0x0090, 0x0000, 0xffff), // Find
- USB_KEYMAP(0x07007f, 0x0079, 0xe020, 0x004a), // Mute
-
- USB_KEYMAP(0x070080, 0x007b, 0xe030, 0x0048), // VolumeUp
- USB_KEYMAP(0x070081, 0x007a, 0xe02e, 0x0049), // VolumeDown
- USB_KEYMAP(0x070082, 0x0000, 0x0000, 0xffff), // LockingCapsLock
- USB_KEYMAP(0x070083, 0x0000, 0x0000, 0xffff), // LockingNumLock
- USB_KEYMAP(0x070084, 0x0000, 0x0000, 0xffff), // LockingScrollLock
- // USB#070085 is used as Brazilian Keypad_.
- USB_KEYMAP(0x070085, 0x0000, 0x0000, 0x005f), // Keypad_Comma
- // USB#070086 is used on AS/400 keyboards. Standard Keypad_= is USB#070067.
- //USB_KEYMAP(0x070086, 0x0000, 0x0000, 0xffff), // Keypad_=
- // USB#070087 is used for Brazilian /? and Japanese _ 'ro'.
- USB_KEYMAP(0x070087, 0x0061, 0x0000, 0x005e), // International1
-
- // USB#070088 is used as Japanese Hiragana/Katakana key.
- USB_KEYMAP(0x070088, 0x0065, 0x0000, 0x0068), // International2
- // USB#070089 is used as Japanese Yen key.
- USB_KEYMAP(0x070089, 0x0084, 0x007d, 0x005d), // International3
- // USB#07008a is used as Japanese Henkan (Convert) key.
- USB_KEYMAP(0x07008a, 0x0064, 0x0000, 0xffff), // International4
- // USB#07008b is used as Japanese Muhenkan (No-convert) key.
- USB_KEYMAP(0x07008b, 0x0066, 0x0000, 0xffff), // International5
- USB_KEYMAP(0x07008c, 0x0000, 0x0000, 0xffff), // International6
- USB_KEYMAP(0x07008d, 0x0000, 0x0000, 0xffff), // International7
- USB_KEYMAP(0x07008e, 0x0000, 0x0000, 0xffff), // International8
- USB_KEYMAP(0x07008f, 0x0000, 0x0000, 0xffff), // International9
-
- // USB#070090 is used as Korean Hangul/English toggle key.
- USB_KEYMAP(0x070090, 0x0082, 0x0000, 0xffff), // LANG1
- // USB#070091 is used as Korean Hanja conversion key.
- USB_KEYMAP(0x070091, 0x0083, 0x0000, 0xffff), // LANG2
- // USB#070092 is used as Japanese Katakana key.
- USB_KEYMAP(0x070092, 0x0062, 0x0000, 0xffff), // LANG3
- // USB#070093 is used as Japanese Hiragana key.
- USB_KEYMAP(0x070093, 0x0063, 0x0000, 0xffff), // LANG4
- // USB#070094 is used as Japanese Zenkaku/Hankaku (Fullwidth/halfwidth) key.
- USB_KEYMAP(0x070094, 0x0000, 0x0000, 0xffff), // LANG5
- USB_KEYMAP(0x070095, 0x0000, 0x0000, 0xffff), // LANG6
- USB_KEYMAP(0x070096, 0x0000, 0x0000, 0xffff), // LANG7
- USB_KEYMAP(0x070097, 0x0000, 0x0000, 0xffff), // LANG8
-
- USB_KEYMAP(0x070098, 0x0000, 0x0000, 0xffff), // LANG9
- USB_KEYMAP(0x070099, 0x0000, 0x0000, 0xffff), // AlternateErase
- USB_KEYMAP(0x07009a, 0x0000, 0x0000, 0xffff), // SysReq/Attention
- USB_KEYMAP(0x07009b, 0x0088, 0x0000, 0xffff), // Cancel
- USB_KEYMAP(0x07009c, 0x0000, 0x0000, 0xffff), // Clear
- USB_KEYMAP(0x07009d, 0x0000, 0x0000, 0xffff), // Prior
- USB_KEYMAP(0x07009e, 0x0000, 0x0000, 0xffff), // Return
- USB_KEYMAP(0x07009f, 0x0000, 0x0000, 0xffff), // Separator
-
- USB_KEYMAP(0x0700a0, 0x0000, 0x0000, 0xffff), // Out
- USB_KEYMAP(0x0700a1, 0x0000, 0x0000, 0xffff), // Oper
- USB_KEYMAP(0x0700a2, 0x0000, 0x0000, 0xffff), // Clear/Again
- USB_KEYMAP(0x0700a3, 0x0000, 0x0000, 0xffff), // CrSel/Props
- USB_KEYMAP(0x0700a4, 0x0000, 0x0000, 0xffff), // ExSel
-
- //USB_KEYMAP(0x0700b0, 0x0000, 0x0000, 0xffff), // Keypad_00
- //USB_KEYMAP(0x0700b1, 0x0000, 0x0000, 0xffff), // Keypad_000
- //USB_KEYMAP(0x0700b2, 0x0000, 0x0000, 0xffff), // ThousandsSeparator
- //USB_KEYMAP(0x0700b3, 0x0000, 0x0000, 0xffff), // DecimalSeparator
- //USB_KEYMAP(0x0700b4, 0x0000, 0x0000, 0xffff), // CurrencyUnit
- //USB_KEYMAP(0x0700b5, 0x0000, 0x0000, 0xffff), // CurrencySubunit
- USB_KEYMAP(0x0700b6, 0x00bb, 0x0000, 0xffff), // Keypad_(
- USB_KEYMAP(0x0700b7, 0x00bc, 0x0000, 0xffff), // Keypad_)
-
- //USB_KEYMAP(0x0700b8, 0x0000, 0x0000, 0xffff), // Keypad_{
- //USB_KEYMAP(0x0700b9, 0x0000, 0x0000, 0xffff), // Keypad_}
- //USB_KEYMAP(0x0700ba, 0x0000, 0x0000, 0xffff), // Keypad_Tab
- //USB_KEYMAP(0x0700bb, 0x0000, 0x0000, 0xffff), // Keypad_Backspace
- //USB_KEYMAP(0x0700bc, 0x0000, 0x0000, 0xffff), // Keypad_A
- //USB_KEYMAP(0x0700bd, 0x0000, 0x0000, 0xffff), // Keypad_B
- //USB_KEYMAP(0x0700be, 0x0000, 0x0000, 0xffff), // Keypad_C
- //USB_KEYMAP(0x0700bf, 0x0000, 0x0000, 0xffff), // Keypad_D
-
- //USB_KEYMAP(0x0700c0, 0x0000, 0x0000, 0xffff), // Keypad_E
- //USB_KEYMAP(0x0700c1, 0x0000, 0x0000, 0xffff), // Keypad_F
- //USB_KEYMAP(0x0700c2, 0x0000, 0x0000, 0xffff), // Keypad_Xor
- //USB_KEYMAP(0x0700c3, 0x0000, 0x0000, 0xffff), // Keypad_^
- //USB_KEYMAP(0x0700c4, 0x0000, 0x0000, 0xffff), // Keypad_%
- //USB_KEYMAP(0x0700c5, 0x0000, 0x0000, 0xffff), // Keypad_<
- //USB_KEYMAP(0x0700c6, 0x0000, 0x0000, 0xffff), // Keypad_>
- //USB_KEYMAP(0x0700c7, 0x0000, 0x0000, 0xffff), // Keypad_&
-
- //USB_KEYMAP(0x0700c8, 0x0000, 0x0000, 0xffff), // Keypad_&&
- //USB_KEYMAP(0x0700c9, 0x0000, 0x0000, 0xffff), // Keypad_|
- //USB_KEYMAP(0x0700ca, 0x0000, 0x0000, 0xffff), // Keypad_||
- //USB_KEYMAP(0x0700cb, 0x0000, 0x0000, 0xffff), // Keypad_:
- //USB_KEYMAP(0x0700cc, 0x0000, 0x0000, 0xffff), // Keypad_#
- //USB_KEYMAP(0x0700cd, 0x0000, 0x0000, 0xffff), // Keypad_Space
- //USB_KEYMAP(0x0700ce, 0x0000, 0x0000, 0xffff), // Keypad_@
- //USB_KEYMAP(0x0700cf, 0x0000, 0x0000, 0xffff), // Keypad_!
-
- //USB_KEYMAP(0x0700d0, 0x0000, 0x0000, 0xffff), // Keypad_MemoryStore
- //USB_KEYMAP(0x0700d1, 0x0000, 0x0000, 0xffff), // Keypad_MemoryRecall
- //USB_KEYMAP(0x0700d2, 0x0000, 0x0000, 0xffff), // Keypad_MemoryClear
- //USB_KEYMAP(0x0700d3, 0x0000, 0x0000, 0xffff), // Keypad_MemoryAdd
- //USB_KEYMAP(0x0700d4, 0x0000, 0x0000, 0xffff), // Keypad_MemorySubtract
- //USB_KEYMAP(0x0700d5, 0x0000, 0x0000, 0xffff), // Keypad_MemoryMultiply
- //USB_KEYMAP(0x0700d6, 0x0000, 0x0000, 0xffff), // Keypad_MemoryDivide
- USB_KEYMAP(0x0700d7, 0x007e, 0x0000, 0xffff), // Keypad_+/-
-
- //USB_KEYMAP(0x0700d8, 0x0000, 0x0000, 0xffff), // Keypad_Clear
- //USB_KEYMAP(0x0700d9, 0x0000, 0x0000, 0xffff), // Keypad_ClearEntry
- //USB_KEYMAP(0x0700da, 0x0000, 0x0000, 0xffff), // Keypad_Binary
- //USB_KEYMAP(0x0700db, 0x0000, 0x0000, 0xffff), // Keypad_Octal
- USB_KEYMAP(0x0700dc, 0x0081, 0x0000, 0xffff), // Keypad_Decimal
- //USB_KEYMAP(0x0700dd, 0x0000, 0x0000, 0xffff), // Keypad_Hexadecimal
- // USB#0700de - #0700df are reserved.
-
- USB_KEYMAP(0x0700e0, 0x0025, 0x001d, 0x003b), // LeftControl
- USB_KEYMAP(0x0700e1, 0x0032, 0x002a, 0x0038), // LeftShift
- USB_KEYMAP(0x0700e2, 0x0040, 0x0038, 0x003a), // LeftAlt/Option
- USB_KEYMAP(0x0700e3, 0x0085, 0xe05b, 0x0037), // LeftGUI/Super/Win/Cmd
- USB_KEYMAP(0x0700e4, 0x0069, 0xe01d, 0x003e), // RightControl
- USB_KEYMAP(0x0700e5, 0x003e, 0x0036, 0x003c), // RightShift
- USB_KEYMAP(0x0700e6, 0x006c, 0xe038, 0x003d), // RightAlt/Option
- USB_KEYMAP(0x0700e7, 0x0086, 0xe05c, 0x0036), // RightGUI/Super/Win/Cmd
-
- // USB#0700e8 - #07ffff are reserved
-
- // ==================================
- // USB Usage Page 0x0c: Consumer Page
- // ==================================
- // AL = Application Launch
- // AC = Application Control
-
- // TODO(garykac): Many XF86 keys have multiple scancodes mapping to them.
- // We need to map all of these into a canonical USB scancode without
- // confusing the reverse-lookup - most likely by simply returning the first
- // found match.
-
- // TODO(garykac): Find appropriate mappings for:
- // Win#e06b LaunchApp1 (My Computer?)
- // Win#e021 LaunchApp2 (Calculator?)
- // Win#e03c Music - USB#0c0193 is AL_AVCapturePlayback
- // Win#e06d Video - USB#0c0193 is AL_AVCapturePlayback
- // Win#e064 Pictures
- // XKB#0080 XF86LaunchA
- // XKB#0097 XF86WakeUp
- // XKB#0099 XF86Send
- // XKB#009b XF86Xfer
- // XKB#009c XF86Launch1
- // XKB#009d XF86Launch2
- // XKB... remaining XF86 keys
-
- // USB XKB Win Mac
- USB_KEYMAP(0x0c00b5, 0x0000, 0xe019, 0xffff), // ScanNextTrack
- USB_KEYMAP(0x0c00b6, 0x0000, 0xe010, 0xffff), // ScanPreviousTrack
- USB_KEYMAP(0x0c00b7, 0x0000, 0xe024, 0xffff), // Stop
- USB_KEYMAP(0x0c00b8, 0x0000, 0xe02c, 0xffff), // Eject
- USB_KEYMAP(0x0c00cd, 0x0000, 0xe022, 0xffff), // Play/Pause
- USB_KEYMAP(0x0c018a, 0x0000, 0xe01e, 0xffff), // AL_EmailReader
- USB_KEYMAP(0x0c0192, 0x0094, 0x0000, 0xffff), // AL_Calculator
- // USB#0c0194: My Computer
- USB_KEYMAP(0x0c0194, 0x00a5, 0x0000, 0xffff), // AL_LocalMachineBrowser
- USB_KEYMAP(0x0c01a7, 0x00f3, 0x0000, 0xffff), // AL_Documents
- // USB#0c01b4: Home Directory
- USB_KEYMAP(0x0c01b4, 0x0098, 0x0000, 0xffff), // AL_FileBrowser (Explorer)
- USB_KEYMAP(0x0c0221, 0x0000, 0xe065, 0xffff), // AC_Search
- USB_KEYMAP(0x0c0223, 0x0000, 0xe032, 0xffff), // AC_Home
- USB_KEYMAP(0x0c0224, 0x00a6, 0xe06a, 0xffff), // AC_Back
- USB_KEYMAP(0x0c0225, 0x00a7, 0xe069, 0xffff), // AC_Forward
- USB_KEYMAP(0x0c0226, 0x0000, 0xe068, 0xffff), // AC_Stop
- USB_KEYMAP(0x0c0227, 0x00b5, 0xe067, 0xffff), // AC_Refresh (Reload)
- USB_KEYMAP(0x0c022a, 0x00a4, 0xe066, 0xffff), // AC_Bookmarks (Favorites)
- USB_KEYMAP(0x0c0289, 0x00f0, 0x0000, 0xffff), // AC_Reply
- USB_KEYMAP(0x0c028b, 0x00f1, 0x0000, 0xffff), // AC_ForwardMsg (MailForward)
- USB_KEYMAP(0x0c028c, 0x00ef, 0x0000, 0xffff), // AC_Send
-};
-
-inline uint16_t InvalidNativeKeycode() {
- return usb_keycode_map[0].native_keycode;
-}
-
-inline uint16_t InvalidUsbKeycode() {
- return usb_keycode_map[0].usb_keycode;
-}
-
-inline uint16_t UsbKeycodeToNativeKeycode(uint32_t usb_keycode) {
- // Deal with some special-cases that don't fit the 1:1 mapping.
- if (usb_keycode == 0x070032) // non-US hash.
- usb_keycode = 0x070031; // US backslash.
-#if defined(OS_MACOSX)
- if (usb_keycode == 0x070046) // PrintScreen.
- usb_keycode = 0x070068; // F13.
-#endif
-
- for (size_t i = 0; i < arraysize(usb_keycode_map); ++i) {
- if (usb_keycode_map[i].usb_keycode == usb_keycode)
- return usb_keycode_map[i].native_keycode;
- }
- return InvalidNativeKeycode();
-}
-
-inline uint32_t NativeKeycodeToUsbKeycode(uint16_t native_keycode) {
- for (size_t i = 0; i < arraysize(usb_keycode_map); ++i) {
- if (usb_keycode_map[i].native_keycode == native_keycode)
- return usb_keycode_map[i].usb_keycode;
- }
- return InvalidUsbKeycode();
-}
diff --git a/chromium/ui/base/keycodes/usb_keycode_map_unittest.cc b/chromium/ui/base/keycodes/usb_keycode_map_unittest.cc
deleted file mode 100644
index 46093bc50f1..00000000000
--- a/chromium/ui/base/keycodes/usb_keycode_map_unittest.cc
+++ /dev/null
@@ -1,92 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include <map>
-
-#include "base/basictypes.h"
-#include "testing/gtest/include/gtest/gtest.h"
-
-namespace {
-
-#if defined(OS_WIN)
-const size_t kExpectedMappedKeyCount = 138;
-#define USB_KEYMAP(usb, xkb, win, mac) {usb, win}
-#elif defined(OS_LINUX)
-const size_t kExpectedMappedKeyCount = 145;
-#define USB_KEYMAP(usb, xkb, win, mac) {usb, xkb}
-#elif defined(OS_MACOSX)
-const size_t kExpectedMappedKeyCount = 118;
-#define USB_KEYMAP(usb, xkb, win, mac) {usb, mac}
-#else
-const size_t kExpectedMappedKeyCount = 0;
-#define USB_KEYMAP(usb, xkb, win, mac) {usb, 0}
-#endif
-#include "ui/base/keycodes/usb_keycode_map.h"
-#undef USB_KEYMAP
-
-const uint32_t kUsbNonExistentKeycode = 0xffffff;
-const uint32_t kUsbUsBackslash = 0x070031;
-const uint32_t kUsbNonUsHash = 0x070032;
-
-TEST(UsbKeycodeMap, Basic) {
- // Verify that the first element in the table is the "invalid" code.
- EXPECT_EQ(InvalidUsbKeycode(), usb_keycode_map[0].usb_keycode);
- EXPECT_EQ(InvalidNativeKeycode(), usb_keycode_map[0].native_keycode);
-
- // Verify that there are no duplicate entries in the mapping.
- std::map<uint32_t, uint16_t> usb_to_native;
- std::map<uint16_t, uint32_t> native_to_usb;
- for (size_t i = 0; i < arraysize(usb_keycode_map); ++i) {
- // Don't test keys with no native keycode mapping on this platform.
- if (usb_keycode_map[i].native_keycode == InvalidNativeKeycode())
- continue;
-
- // Verify UsbKeycodeToNativeKeycode works for this key.
- EXPECT_EQ(usb_keycode_map[i].native_keycode,
- UsbKeycodeToNativeKeycode(usb_keycode_map[i].usb_keycode));
-
- // Verify that the USB or native codes aren't duplicated.
- EXPECT_EQ(0U, usb_to_native.count(usb_keycode_map[i].usb_keycode))
- << " duplicate of USB code 0x" << std::hex << std::setfill('0')
- << std::setw(6) << usb_keycode_map[i].usb_keycode
- << " to native 0x"
- << std::setw(4) << usb_keycode_map[i].native_keycode
- << " (previous was 0x"
- << std::setw(4) << usb_to_native[usb_keycode_map[i].usb_keycode]
- << ")";
- usb_to_native[usb_keycode_map[i].usb_keycode] =
- usb_keycode_map[i].native_keycode;
- EXPECT_EQ(0U, native_to_usb.count(usb_keycode_map[i].native_keycode))
- << " duplicate of native code 0x" << std::hex << std::setfill('0')
- << std::setw(4) << usb_keycode_map[i].native_keycode
- << " to USB 0x"
- << std::setw(6) << usb_keycode_map[i].usb_keycode
- << " (previous was 0x"
- << std::setw(6) << native_to_usb[usb_keycode_map[i].native_keycode]
- << ")";
- native_to_usb[usb_keycode_map[i].native_keycode] =
- usb_keycode_map[i].usb_keycode;
- }
- ASSERT_EQ(usb_to_native.size(), native_to_usb.size());
-
- // Verify that the number of mapped keys is what we expect, i.e. we haven't
- // lost any, and if we've added some then the expectation has been updated.
- EXPECT_EQ(kExpectedMappedKeyCount, usb_to_native.size());
-}
-
-TEST(UsbKeycodeMap, NonExistent) {
- // Verify that UsbKeycodeToNativeKeycode works for a non-existent USB keycode.
- EXPECT_EQ(InvalidNativeKeycode(),
- UsbKeycodeToNativeKeycode(kUsbNonExistentKeycode));
-}
-
-TEST(UsbKeycodeMap, UsBackslashIsNonUsHash) {
- // Verify that UsbKeycodeToNativeKeycode treats the non-US "hash" key
- // as equivalent to the US "backslash" key.
- EXPECT_EQ(UsbKeycodeToNativeKeycode(kUsbUsBackslash),
- UsbKeycodeToNativeKeycode(kUsbNonUsHash));
-
-}
-
-} // namespace
diff --git a/chromium/ui/base/l10n/l10n_util.cc b/chromium/ui/base/l10n/l10n_util.cc
index 513a615a141..96dfa8e868b 100644
--- a/chromium/ui/base/l10n/l10n_util.cc
+++ b/chromium/ui/base/l10n/l10n_util.cc
@@ -28,6 +28,7 @@
#include "third_party/icu/source/common/unicode/rbbi.h"
#include "third_party/icu/source/common/unicode/uloc.h"
#include "ui/base/l10n/l10n_util_collator.h"
+#include "ui/base/l10n/l10n_util_plurals.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/base/ui_base_paths.h"
@@ -35,7 +36,7 @@
#include "ui/base/l10n/l10n_util_android.h"
#endif
-#if defined(OS_LINUX)
+#if defined(OS_POSIX) && !defined(OS_MACOSX) && !defined(OS_ANDROID)
#include <glib.h>
#endif
@@ -452,7 +453,7 @@ std::string GetApplicationLocale(const std::string& pref_locale) {
// On Android, query java.util.Locale for the default locale.
candidates.push_back(GetDefaultLocale());
-#elif defined(OS_LINUX)
+#elif defined(OS_POSIX)
// If we're on a different Linux system, we have glib.
// GLib implements correct environment variable parsing with
@@ -831,6 +832,27 @@ bool StringComparator<string16>::operator()(const string16& lhs,
UCOL_LESS;
};
+string16 GetPluralStringFUTF16(const std::vector<int>& message_ids,
+ int number) {
+ scoped_ptr<icu::PluralFormat> format = BuildPluralFormat(message_ids);
+ DCHECK(format);
+
+ UErrorCode err = U_ZERO_ERROR;
+ icu::UnicodeString result_files_string = format->format(number, err);
+ int capacity = result_files_string.length() + 1;
+ DCHECK_GT(capacity, 1);
+ string16 result;
+ result_files_string.extract(
+ static_cast<UChar*>(WriteInto(&result, capacity)), capacity, err);
+ DCHECK(U_SUCCESS(err));
+ return result;
+}
+
+std::string GetPluralStringFUTF8(const std::vector<int>& message_ids,
+ int number) {
+ return base::UTF16ToUTF8(GetPluralStringFUTF16(message_ids, number));
+}
+
void SortStrings16(const std::string& locale,
std::vector<string16>* strings) {
SortVectorWithStringKey(locale, strings, false);
diff --git a/chromium/ui/base/l10n/l10n_util.h b/chromium/ui/base/l10n/l10n_util.h
index 7c26b803467..d7753365d00 100644
--- a/chromium/ui/base/l10n/l10n_util.h
+++ b/chromium/ui/base/l10n/l10n_util.h
@@ -139,6 +139,14 @@ UI_EXPORT string16 GetStringFUTF16(int message_id,
UI_EXPORT string16 GetStringFUTF16Int(int message_id, int a);
string16 GetStringFUTF16Int(int message_id, int64 a);
+// Get a resource string using |number| to decide which of |message_ids| should
+// be used. |message_ids| must be size 6 and in order: default, singular, zero,
+// two, few, many.
+UI_EXPORT string16 GetPluralStringFUTF16(const std::vector<int>& message_ids,
+ int number);
+UI_EXPORT std::string GetPluralStringFUTF8(const std::vector<int>& message_ids,
+ int number);
+
// In place sorting of string16 strings using collation rules for |locale|.
UI_EXPORT void SortStrings16(const std::string& locale,
std::vector<string16>* strings);
diff --git a/chromium/ui/base/l10n/l10n_util_plurals.cc b/chromium/ui/base/l10n/l10n_util_plurals.cc
new file mode 100644
index 00000000000..0dc008ff06e
--- /dev/null
+++ b/chromium/ui/base/l10n/l10n_util_plurals.cc
@@ -0,0 +1,64 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/l10n/l10n_util_plurals.h"
+
+#include "base/memory/scoped_ptr.h"
+#include "ui/base/l10n/l10n_util.h"
+
+namespace l10n_util {
+
+scoped_ptr<icu::PluralRules> BuildPluralRules() {
+ UErrorCode err = U_ZERO_ERROR;
+ scoped_ptr<icu::PluralRules> rules(
+ icu::PluralRules::forLocale(icu::Locale::getDefault(), err));
+ if (U_FAILURE(err)) {
+ err = U_ZERO_ERROR;
+ icu::UnicodeString fallback_rules("one: n is 1", -1, US_INV);
+ rules.reset(icu::PluralRules::createRules(fallback_rules, err));
+ DCHECK(U_SUCCESS(err));
+ }
+ return rules.Pass();
+}
+
+scoped_ptr<icu::PluralFormat> BuildPluralFormat(
+ const std::vector<int>& message_ids) {
+ const icu::UnicodeString kKeywords[] = {
+ UNICODE_STRING_SIMPLE("other"),
+ UNICODE_STRING_SIMPLE("one"),
+ UNICODE_STRING_SIMPLE("zero"),
+ UNICODE_STRING_SIMPLE("two"),
+ UNICODE_STRING_SIMPLE("few"),
+ UNICODE_STRING_SIMPLE("many"),
+ };
+ DCHECK_EQ(message_ids.size(), arraysize(kKeywords));
+ UErrorCode err = U_ZERO_ERROR;
+ scoped_ptr<icu::PluralRules> rules(BuildPluralRules());
+
+ icu::UnicodeString pattern;
+ for (size_t i = 0; i < arraysize(kKeywords); ++i) {
+ int msg_id = message_ids[i];
+ std::string sub_pattern = GetStringUTF8(msg_id);
+ // NA means this keyword is not used in the current locale.
+ // Even if a translator translated for this keyword, we do not
+ // use it unless it's 'other' (i=0) or it's defined in the rules
+ // for the current locale. Special-casing of 'other' will be removed
+ // once ICU's isKeyword is fixed to return true for isKeyword('other').
+ if (sub_pattern.compare("NA") != 0 &&
+ (i == 0 || rules->isKeyword(kKeywords[i]))) {
+ pattern += kKeywords[i];
+ pattern += UNICODE_STRING_SIMPLE("{");
+ pattern += icu::UnicodeString(sub_pattern.c_str(), "UTF-8");
+ pattern += UNICODE_STRING_SIMPLE("}");
+ }
+ }
+ scoped_ptr<icu::PluralFormat> format = scoped_ptr<icu::PluralFormat>(
+ new icu::PluralFormat(*rules, pattern, err));
+ if (!U_SUCCESS(err)) {
+ return scoped_ptr<icu::PluralFormat>();
+ }
+ return format.Pass();
+}
+
+} // namespace l10n_util
diff --git a/chromium/ui/base/l10n/l10n_util_plurals.h b/chromium/ui/base/l10n/l10n_util_plurals.h
new file mode 100644
index 00000000000..203797d6c44
--- /dev/null
+++ b/chromium/ui/base/l10n/l10n_util_plurals.h
@@ -0,0 +1,30 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file contains utility functions for dealing with pluralization of
+// localized content.
+
+#ifndef UI_BASE_L10N_L10N_UTIL_PLURALS_H_
+#define UI_BASE_L10N_L10N_UTIL_PLURALS_H_
+
+#include <string>
+#include <vector>
+
+#include "base/memory/scoped_ptr.h"
+#include "third_party/icu/source/i18n/unicode/plurfmt.h"
+#include "third_party/icu/source/i18n/unicode/plurrule.h"
+
+namespace l10n_util {
+
+// Returns a PluralRules for the current locale.
+scoped_ptr<icu::PluralRules> BuildPluralRules();
+
+// Returns a PluralFormat from |message_ids|. |message_ids| must be size 6 and
+// in order: default, singular, zero, two, few, many.
+scoped_ptr<icu::PluralFormat> BuildPluralFormat(
+ const std::vector<int>& message_ids);
+
+} // namespace l10n_util
+
+#endif // UI_BASE_L10N_L10N_UTIL_PLURALS_H_
diff --git a/chromium/ui/base/l10n/l10n_util_win.cc b/chromium/ui/base/l10n/l10n_util_win.cc
index 123b74f6abf..0fa34cfbfaf 100644
--- a/chromium/ui/base/l10n/l10n_util_win.cc
+++ b/chromium/ui/base/l10n/l10n_util_win.cc
@@ -15,7 +15,7 @@
#include "base/win/windows_version.h"
#include "grit/app_locale_settings.h"
#include "ui/base/l10n/l10n_util.h"
-#include "ui/base/win/dpi.h"
+#include "ui/gfx/win/dpi.h"
namespace {
@@ -151,7 +151,7 @@ bool NeedOverrideDefaultUIFont(string16* override_font_family,
}
void AdjustUIFont(LOGFONT* logfont) {
- AdjustUIFontForDIP(ui::GetDPIScale(), logfont);
+ AdjustUIFontForDIP(gfx::GetDPIScale(), logfont);
}
void AdjustUIFontForDIP(float dpi_scale, LOGFONT* logfont) {
diff --git a/chromium/ui/base/l10n/l10n_util_win_unittest.cc b/chromium/ui/base/l10n/l10n_util_win_unittest.cc
index 10e496338bc..c4ae8885b7e 100644
--- a/chromium/ui/base/l10n/l10n_util_win_unittest.cc
+++ b/chromium/ui/base/l10n/l10n_util_win_unittest.cc
@@ -9,7 +9,7 @@
#include "base/win/win_util.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "testing/platform_test.h"
-#include "ui/base/win/dpi.h"
+#include "ui/gfx/win/dpi.h"
typedef PlatformTest L10nUtilWinTest;
diff --git a/chromium/ui/base/l10n/time_format.cc b/chromium/ui/base/l10n/time_format.cc
index 5ba606c3dfb..aaa35a99699 100644
--- a/chromium/ui/base/l10n/time_format.cc
+++ b/chromium/ui/base/l10n/time_format.cc
@@ -21,6 +21,7 @@
#include "third_party/icu/source/i18n/unicode/plurrule.h"
#include "third_party/icu/source/i18n/unicode/smpdtfmt.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/base/l10n/l10n_util_plurals.h"
using base::Time;
using base::TimeDelta;
@@ -240,49 +241,20 @@ static base::LazyInstance<TimeFormatter> g_time_formatter =
void TimeFormatter::BuildFormats(
FormatType format_type, ScopedVector<icu::PluralFormat>* time_formats) {
- const icu::UnicodeString kKeywords[] = {
- UNICODE_STRING_SIMPLE("other"), UNICODE_STRING_SIMPLE("one"),
- UNICODE_STRING_SIMPLE("zero"), UNICODE_STRING_SIMPLE("two"),
- UNICODE_STRING_SIMPLE("few"), UNICODE_STRING_SIMPLE("many")
- };
- UErrorCode err = U_ZERO_ERROR;
- scoped_ptr<icu::PluralRules> rules(
- icu::PluralRules::forLocale(icu::Locale::getDefault(), err));
- if (U_FAILURE(err)) {
- err = U_ZERO_ERROR;
- icu::UnicodeString fallback_rules("one: n is 1", -1, US_INV);
- rules.reset(icu::PluralRules::createRules(fallback_rules, err));
- DCHECK(U_SUCCESS(err));
- }
-
const MessageIDs& message_ids = GetMessageIDs(format_type);
for (int i = 0; i < 4; ++i) {
icu::UnicodeString pattern;
- for (size_t j = 0; j < arraysize(kKeywords); ++j) {
- int msg_id = message_ids.ids[i][j];
- std::string sub_pattern = l10n_util::GetStringUTF8(msg_id);
- // NA means this keyword is not used in the current locale.
- // Even if a translator translated for this keyword, we do not
- // use it unless it's 'other' (j=0) or it's defined in the rules
- // for the current locale. Special-casing of 'other' will be removed
- // once ICU's isKeyword is fixed to return true for isKeyword('other').
- if (sub_pattern.compare("NA") != 0 &&
- (j == 0 || rules->isKeyword(kKeywords[j]))) {
- pattern += kKeywords[j];
- pattern += UNICODE_STRING_SIMPLE("{");
- pattern += icu::UnicodeString(sub_pattern.c_str(), "UTF-8");
- pattern += UNICODE_STRING_SIMPLE("}");
- }
+ std::vector<int> ids;
+ for (size_t j = 0; j < arraysize(message_ids.ids[i]); ++j) {
+ ids.push_back(message_ids.ids[i][j]);
}
- icu::PluralFormat* format = new icu::PluralFormat(*rules, pattern, err);
- if (U_SUCCESS(err)) {
- time_formats->push_back(format);
+ scoped_ptr<icu::PluralFormat> format = l10n_util::BuildPluralFormat(ids);
+ if (format) {
+ time_formats->push_back(format.release());
} else {
- delete format;
+ scoped_ptr<icu::PluralRules> rules(l10n_util::BuildPluralRules());
time_formats->push_back(createFallbackFormat(*rules, i, format_type));
- // Reset it so that next ICU call can proceed.
- err = U_ZERO_ERROR;
}
}
}
diff --git a/chromium/ui/base/layout.cc b/chromium/ui/base/layout.cc
index 024948cd5ee..40a0a9ccc32 100644
--- a/chromium/ui/base/layout.cc
+++ b/chromium/ui/base/layout.cc
@@ -23,7 +23,7 @@
#if defined(OS_WIN)
#include "base/win/metro.h"
-#include "ui/base/win/dpi.h"
+#include "ui/gfx/win/dpi.h"
#include <Windows.h>
#endif // defined(OS_WIN)
@@ -66,7 +66,8 @@ bool UseTouchOptimizedUI() {
}
#endif // defined(OS_WIN)
-const float kScaleFactorScales[] = {1.0f, 1.0f, 1.33f, 1.4f, 1.5f, 1.8f, 2.0f};
+const float kScaleFactorScales[] = {1.0f, 1.0f, 1.25f, 1.33f, 1.4f, 1.5f, 1.8f,
+ 2.0f};
COMPILE_ASSERT(NUM_SCALE_FACTORS == arraysize(kScaleFactorScales),
kScaleFactorScales_incorrect_size);
const size_t kScaleFactorScalesLength = arraysize(kScaleFactorScales);
@@ -123,7 +124,7 @@ std::vector<ScaleFactor>& GetSupportedScaleFactorsInternal() {
// Have high-DPI resources for 140% and 180% scaling on Windows based on
// default scaling for Metro mode. Round to nearest supported scale in
// all cases.
- if (ui::IsInHighDPIMode()) {
+ if (gfx::IsInHighDPIMode()) {
supported_scale_factors->push_back(SCALE_FACTOR_140P);
supported_scale_factors->push_back(SCALE_FACTOR_180P);
}
diff --git a/chromium/ui/base/layout.h b/chromium/ui/base/layout.h
index 236e58ece61..1292c38f2c5 100644
--- a/chromium/ui/base/layout.h
+++ b/chromium/ui/base/layout.h
@@ -36,6 +36,7 @@ UI_EXPORT DisplayLayout GetDisplayLayout();
enum ScaleFactor {
SCALE_FACTOR_NONE = 0,
SCALE_FACTOR_100P,
+ SCALE_FACTOR_125P,
SCALE_FACTOR_133P,
SCALE_FACTOR_140P,
SCALE_FACTOR_150P,
diff --git a/chromium/ui/base/layout_unittest.cc b/chromium/ui/base/layout_unittest.cc
index a230d5ae666..8a741821e8c 100644
--- a/chromium/ui/base/layout_unittest.cc
+++ b/chromium/ui/base/layout_unittest.cc
@@ -15,6 +15,7 @@ namespace ui {
TEST(LayoutTest, GetScaleFactorScale) {
EXPECT_FLOAT_EQ(1.0f, GetScaleFactorScale(SCALE_FACTOR_100P));
+ EXPECT_FLOAT_EQ(1.25f, GetScaleFactorScale(SCALE_FACTOR_125P));
EXPECT_FLOAT_EQ(1.33f, GetScaleFactorScale(SCALE_FACTOR_133P));
EXPECT_FLOAT_EQ(1.4f, GetScaleFactorScale(SCALE_FACTOR_140P));
EXPECT_FLOAT_EQ(1.5f, GetScaleFactorScale(SCALE_FACTOR_150P));
@@ -47,8 +48,9 @@ TEST(LayoutTest, GetScaleFactorFromScaleAllSupported) {
EXPECT_EQ(SCALE_FACTOR_100P, GetScaleFactorFromScale(0.1f));
EXPECT_EQ(SCALE_FACTOR_100P, GetScaleFactorFromScale(0.9f));
EXPECT_EQ(SCALE_FACTOR_100P, GetScaleFactorFromScale(1.0f));
- EXPECT_EQ(SCALE_FACTOR_133P, GetScaleFactorFromScale(1.19f));
- EXPECT_EQ(SCALE_FACTOR_133P, GetScaleFactorFromScale(1.21f));
+ EXPECT_EQ(SCALE_FACTOR_125P, GetScaleFactorFromScale(1.19f));
+ EXPECT_EQ(SCALE_FACTOR_125P, GetScaleFactorFromScale(1.21f));
+ EXPECT_EQ(SCALE_FACTOR_133P, GetScaleFactorFromScale(1.291f));
EXPECT_EQ(SCALE_FACTOR_133P, GetScaleFactorFromScale(1.3f));
EXPECT_EQ(SCALE_FACTOR_140P, GetScaleFactorFromScale(1.4f));
EXPECT_EQ(SCALE_FACTOR_150P, GetScaleFactorFromScale(1.59f));
diff --git a/chromium/ui/base/models/list_selection_model.h b/chromium/ui/base/models/list_selection_model.h
index 95194700852..8a175092ebb 100644
--- a/chromium/ui/base/models/list_selection_model.h
+++ b/chromium/ui/base/models/list_selection_model.h
@@ -51,7 +51,7 @@ class UI_EXPORT ListSelectionModel {
// This is used when a new tab is inserted into the tabstrip.
void IncrementFrom(int index);
- // Shifts all indices < |index| down by 1. If |index| is selected, it is
+ // Shifts all indices > |index| down by 1. If |index| is selected, it is
// removed. For example, if the selection consists of [0, 1, 5] and this is
// invoked with 1, it results in [0, 4]. This is used when a tab is removed
// from the tabstrip.
diff --git a/chromium/ui/base/models/menu_model.cc b/chromium/ui/base/models/menu_model.cc
index c6ddd86f4a7..e88742ebe12 100644
--- a/chromium/ui/base/models/menu_model.cc
+++ b/chromium/ui/base/models/menu_model.cc
@@ -36,11 +36,11 @@ base::string16 MenuModel::GetSublabelAt(int index) const {
return base::string16();
}
-const gfx::Font* MenuModel::GetLabelFontAt(int index) const {
- return NULL;
+base::string16 MenuModel::GetMinorTextAt(int index) const {
+ return base::string16();
}
-const gfx::Font* MenuModel::GetSublabelFontAt(int index) const {
+const gfx::Font* MenuModel::GetLabelFontAt(int index) const {
return NULL;
}
diff --git a/chromium/ui/base/models/menu_model.h b/chromium/ui/base/models/menu_model.h
index 2af4463d559..bd3730c07b7 100644
--- a/chromium/ui/base/models/menu_model.h
+++ b/chromium/ui/base/models/menu_model.h
@@ -58,9 +58,13 @@ class UI_EXPORT MenuModel {
virtual base::string16 GetLabelAt(int index) const = 0;
// Returns the sublabel of the item at the specified index. The sublabel
- // is rendered beneath the label and using the font GetSublabelFontAt().
+ // is rendered beneath the label and using the font GetLabelFontAt().
virtual base::string16 GetSublabelAt(int index) const;
+ // Returns the minor text of the item at the specified index. The minor text
+ // is rendered to the right of the label and using the font GetLabelFontAt().
+ virtual base::string16 GetMinorTextAt(int index) const;
+
// Returns true if the menu item (label/sublabel/icon) at the specified
// index can change over the course of the menu's lifetime. If this function
// returns true, the label, sublabel and icon of the menu item will be
@@ -71,10 +75,6 @@ class UI_EXPORT MenuModel {
// If NULL, then the default font should be used.
virtual const gfx::Font* GetLabelFontAt(int index) const;
- // Returns the font used for the sublabel at the specified index.
- // If NULL, then the default font should be used.
- virtual const gfx::Font* GetSublabelFontAt(int index) const;
-
// Gets the acclerator information for the specified index, returning true if
// there is a shortcut accelerator for the item, false otherwise.
virtual bool GetAcceleratorAt(int index,
diff --git a/chromium/ui/base/models/simple_menu_model.cc b/chromium/ui/base/models/simple_menu_model.cc
index 2687822f1f9..1ce2d35951e 100644
--- a/chromium/ui/base/models/simple_menu_model.cc
+++ b/chromium/ui/base/models/simple_menu_model.cc
@@ -17,6 +17,7 @@ struct SimpleMenuModel::Item {
int command_id;
base::string16 label;
base::string16 sublabel;
+ base::string16 minor_text;
gfx::Image icon;
ItemType type;
int group_id;
@@ -47,6 +48,11 @@ base::string16 SimpleMenuModel::Delegate::GetSublabelForCommandId(
return base::string16();
}
+base::string16 SimpleMenuModel::Delegate::GetMinorTextForCommandId(
+ int command_id) const {
+ return base::string16();
+}
+
bool SimpleMenuModel::Delegate::GetIconForCommandId(
int command_id, gfx::Image* image_skia) const {
return false;
@@ -79,8 +85,8 @@ SimpleMenuModel::~SimpleMenuModel() {
}
void SimpleMenuModel::AddItem(int command_id, const base::string16& label) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_COMMAND, -1, NULL, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_COMMAND, -1, NULL, NULL, NORMAL_SEPARATOR };
AppendItem(item);
}
@@ -90,8 +96,8 @@ void SimpleMenuModel::AddItemWithStringId(int command_id, int string_id) {
void SimpleMenuModel::AddCheckItem(int command_id,
const base::string16& label) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_CHECK, -1, NULL, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_CHECK, -1, NULL, NULL, NORMAL_SEPARATOR };
AppendItem(item);
}
@@ -102,8 +108,9 @@ void SimpleMenuModel::AddCheckItemWithStringId(int command_id, int string_id) {
void SimpleMenuModel::AddRadioItem(int command_id,
const base::string16& label,
int group_id) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_RADIO, group_id, NULL, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_RADIO, group_id, NULL, NULL,
+ NORMAL_SEPARATOR };
AppendItem(item);
}
@@ -127,28 +134,31 @@ void SimpleMenuModel::AddSeparator(MenuSeparatorType separator_type) {
if (separator_type != NORMAL_SEPARATOR)
NOTIMPLEMENTED();
#endif
- Item item = { kSeparatorId, base::string16(), base::string16(), gfx::Image(),
- TYPE_SEPARATOR, -1, NULL, NULL , separator_type };
+ Item item = { kSeparatorId, base::string16(), base::string16(),
+ base::string16(), gfx::Image(), TYPE_SEPARATOR, -1, NULL, NULL,
+ separator_type };
AppendItem(item);
}
void SimpleMenuModel::RemoveTrailingSeparators() {
while (!items_.empty() && items_.back().type == TYPE_SEPARATOR)
items_.pop_back();
+ MenuItemsChanged();
}
void SimpleMenuModel::AddButtonItem(int command_id,
ButtonMenuItemModel* model) {
- Item item = { command_id, base::string16(), base::string16(), gfx::Image(),
- TYPE_BUTTON_ITEM, -1, NULL, model, NORMAL_SEPARATOR };
+ Item item = { command_id, base::string16(), base::string16(),
+ base::string16(), gfx::Image(), TYPE_BUTTON_ITEM, -1, NULL,
+ model, NORMAL_SEPARATOR };
AppendItem(item);
}
void SimpleMenuModel::AddSubMenu(int command_id,
const base::string16& label,
MenuModel* model) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_SUBMENU, -1, model, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_SUBMENU, -1, model, NULL, NORMAL_SEPARATOR };
AppendItem(item);
}
@@ -160,8 +170,8 @@ void SimpleMenuModel::AddSubMenuWithStringId(int command_id,
void SimpleMenuModel::InsertItemAt(int index,
int command_id,
const base::string16& label) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_COMMAND, -1, NULL, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_COMMAND, -1, NULL, NULL, NORMAL_SEPARATOR };
InsertItemAtIndex(item, index);
}
@@ -177,16 +187,17 @@ void SimpleMenuModel::InsertSeparatorAt(int index,
NOTIMPLEMENTED();
}
#endif
- Item item = { kSeparatorId, base::string16(), base::string16(), gfx::Image(),
- TYPE_SEPARATOR, -1, NULL, NULL, separator_type };
+ Item item = { kSeparatorId, base::string16(), base::string16(),
+ base::string16(), gfx::Image(), TYPE_SEPARATOR, -1, NULL, NULL,
+ separator_type };
InsertItemAtIndex(item, index);
}
void SimpleMenuModel::InsertCheckItemAt(int index,
int command_id,
const base::string16& label) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_CHECK, -1, NULL, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_CHECK, -1, NULL, NULL, NORMAL_SEPARATOR };
InsertItemAtIndex(item, index);
}
@@ -199,8 +210,9 @@ void SimpleMenuModel::InsertRadioItemAt(int index,
int command_id,
const base::string16& label,
int group_id) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_RADIO, group_id, NULL, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_RADIO, group_id, NULL, NULL,
+ NORMAL_SEPARATOR };
InsertItemAtIndex(item, index);
}
@@ -214,8 +226,9 @@ void SimpleMenuModel::InsertSubMenuAt(int index,
int command_id,
const base::string16& label,
MenuModel* model) {
- Item item = { command_id, label, base::string16(), gfx::Image(),
- TYPE_SUBMENU, -1, model, NULL, NORMAL_SEPARATOR };
+ Item item = { command_id, label, base::string16(), base::string16(),
+ gfx::Image(), TYPE_SUBMENU, -1, model, NULL,
+ NORMAL_SEPARATOR };
InsertItemAtIndex(item, index);
}
@@ -227,14 +240,22 @@ void SimpleMenuModel::InsertSubMenuWithStringIdAt(
void SimpleMenuModel::SetIcon(int index, const gfx::Image& icon) {
items_[ValidateItemIndex(index)].icon = icon;
+ MenuItemsChanged();
}
void SimpleMenuModel::SetSublabel(int index, const base::string16& sublabel) {
items_[ValidateItemIndex(index)].sublabel = sublabel;
+ MenuItemsChanged();
+}
+
+void SimpleMenuModel::SetMinorText(int index,
+ const base::string16& minor_text) {
+ items_[ValidateItemIndex(index)].minor_text = minor_text;
}
void SimpleMenuModel::Clear() {
items_.clear();
+ MenuItemsChanged();
}
int SimpleMenuModel::GetIndexOfCommandId(int command_id) {
@@ -285,6 +306,12 @@ base::string16 SimpleMenuModel::GetSublabelAt(int index) const {
return items_[ValidateItemIndex(index)].sublabel;
}
+base::string16 SimpleMenuModel::GetMinorTextAt(int index) const {
+ if (IsItemDynamicAt(index))
+ return delegate_->GetMinorTextForCommandId(GetCommandIdAt(index));
+ return items_[ValidateItemIndex(index)].minor_text;
+}
+
bool SimpleMenuModel::IsItemDynamicAt(int index) const {
if (delegate_)
return delegate_->IsItemForCommandIdDynamic(GetCommandIdAt(index));
@@ -390,6 +417,12 @@ void SimpleMenuModel::OnMenuClosed() {
}
////////////////////////////////////////////////////////////////////////////////
+// SimpleMenuModel, Protected:
+
+void SimpleMenuModel::MenuItemsChanged() {
+}
+
+////////////////////////////////////////////////////////////////////////////////
// SimpleMenuModel, Private:
int SimpleMenuModel::ValidateItemIndex(int index) const {
@@ -401,11 +434,13 @@ int SimpleMenuModel::ValidateItemIndex(int index) const {
void SimpleMenuModel::AppendItem(const Item& item) {
ValidateItem(item);
items_.push_back(item);
+ MenuItemsChanged();
}
void SimpleMenuModel::InsertItemAtIndex(const Item& item, int index) {
ValidateItem(item);
items_.insert(items_.begin() + index, item);
+ MenuItemsChanged();
}
void SimpleMenuModel::ValidateItem(const Item& item) {
diff --git a/chromium/ui/base/models/simple_menu_model.h b/chromium/ui/base/models/simple_menu_model.h
index 2204b982fa2..00c93b2a5c9 100644
--- a/chromium/ui/base/models/simple_menu_model.h
+++ b/chromium/ui/base/models/simple_menu_model.h
@@ -38,10 +38,12 @@ class UI_EXPORT SimpleMenuModel : public MenuModel {
int command_id,
ui::Accelerator* accelerator) = 0;
- // Some command ids have labels, sublabels and icons that change over time.
+ // Some command ids have labels, sublabels, minor text and icons that change
+ // over time.
virtual bool IsItemForCommandIdDynamic(int command_id) const;
virtual base::string16 GetLabelForCommandId(int command_id) const;
virtual base::string16 GetSublabelForCommandId(int command_id) const;
+ virtual base::string16 GetMinorTextForCommandId(int command_id) const;
// Gets the icon for the item with the specified id, returning true if there
// is an icon, false otherwise.
virtual bool GetIconForCommandId(int command_id,
@@ -125,6 +127,9 @@ class UI_EXPORT SimpleMenuModel : public MenuModel {
// Sets the sublabel for the item at |index|.
void SetSublabel(int index, const base::string16& sublabel);
+ // Sets the minor text for the item at |index|.
+ void SetMinorText(int index, const base::string16& minor_text);
+
// Clears all items. Note that it does not free MenuModel of submenu.
void Clear();
@@ -140,6 +145,7 @@ class UI_EXPORT SimpleMenuModel : public MenuModel {
virtual int GetCommandIdAt(int index) const OVERRIDE;
virtual base::string16 GetLabelAt(int index) const OVERRIDE;
virtual base::string16 GetSublabelAt(int index) const OVERRIDE;
+ virtual base::string16 GetMinorTextAt(int index) const OVERRIDE;
virtual bool IsItemDynamicAt(int index) const OVERRIDE;
virtual bool GetAcceleratorAt(int index,
ui::Accelerator* accelerator) const OVERRIDE;
@@ -164,6 +170,10 @@ class UI_EXPORT SimpleMenuModel : public MenuModel {
void set_delegate(Delegate* delegate) { delegate_ = delegate; }
Delegate* delegate() { return delegate_; }
+ // One or more of the menu menu items associated with the model has changed.
+ // Do any handling if necessary.
+ virtual void MenuItemsChanged();
+
private:
struct Item;
diff --git a/chromium/ui/base/resource/resource_bundle.cc b/chromium/ui/base/resource/resource_bundle.cc
index 70623c29bc2..31aed58d5bc 100644
--- a/chromium/ui/base/resource/resource_bundle.cc
+++ b/chromium/ui/base/resource/resource_bundle.cc
@@ -35,6 +35,11 @@
#include "ui/gfx/size_conversions.h"
#include "ui/gfx/skbitmap_operations.h"
+#if defined(OS_CHROMEOS)
+#include "ui/base/l10n/l10n_util.h"
+#include "ui/gfx/platform_font_pango.h"
+#endif
+
namespace ui {
namespace {
@@ -52,6 +57,13 @@ const unsigned char kPngDataChunkType[4] = { 'I', 'D', 'A', 'T' };
ResourceBundle* g_shared_instance_ = NULL;
+void InitDefaultFont() {
+#if defined(OS_CHROMEOS)
+ gfx::PlatformFontPango::SetDefaultFontDescription(
+ l10n_util::GetStringUTF8(IDS_UI_FONT_FAMILY_CROS));
+#endif
+}
+
} // namespace
// An ImageSkiaSource that loads bitmaps for the requested scale factor from
@@ -118,6 +130,7 @@ std::string ResourceBundle::InitSharedInstanceWithLocale(
g_shared_instance_->LoadCommonResources();
std::string result = g_shared_instance_->LoadLocaleResources(pref_locale);
+ InitDefaultFont();
return result;
}
@@ -128,6 +141,7 @@ std::string ResourceBundle::InitSharedInstanceLocaleOnly(
g_shared_instance_ = new ResourceBundle(delegate);
std::string result = g_shared_instance_->LoadLocaleResources(pref_locale);
+ InitDefaultFont();
return result;
}
@@ -147,6 +161,7 @@ void ResourceBundle::InitSharedInstanceWithPakFile(
return;
}
g_shared_instance_->locale_resources_data_.reset(data_pack.release());
+ InitDefaultFont();
}
// static
@@ -155,6 +170,8 @@ void ResourceBundle::InitSharedInstanceWithPakPath(const base::FilePath& path) {
g_shared_instance_ = new ResourceBundle(NULL);
g_shared_instance_->LoadTestResources(path, path);
+
+ InitDefaultFont();
}
// static
@@ -321,7 +338,7 @@ gfx::Image& ResourceBundle::GetImageNamed(int resource_id) {
image = delegate_->GetImageNamed(resource_id);
if (image.IsEmpty()) {
- DCHECK(!delegate_ && !data_packs_.empty()) <<
+ DCHECK(!data_packs_.empty()) <<
"Missing call to SetResourcesDataDLL?";
// TODO(oshima): Consider reading the image size from png IHDR chunk and
diff --git a/chromium/ui/base/resource/resource_bundle_android.cc b/chromium/ui/base/resource/resource_bundle_android.cc
index c701a291252..b1942696603 100644
--- a/chromium/ui/base/resource/resource_bundle_android.cc
+++ b/chromium/ui/base/resource/resource_bundle_android.cc
@@ -19,8 +19,6 @@ namespace ui {
void ResourceBundle::LoadCommonResources() {
base::FilePath path;
PathService::Get(ui::DIR_RESOURCE_PAKS_ANDROID, &path);
- AddDataPackFromPath(path.AppendASCII("chrome.pak"),
- SCALE_FACTOR_NONE);
AddDataPackFromPath(path.AppendASCII("chrome_100_percent.pak"),
SCALE_FACTOR_100P);
}
diff --git a/chromium/ui/base/resource/resource_bundle_auralinux.cc b/chromium/ui/base/resource/resource_bundle_auralinux.cc
index 4bc7ee69665..d5357175a7b 100644
--- a/chromium/ui/base/resource/resource_bundle_auralinux.cc
+++ b/chromium/ui/base/resource/resource_bundle_auralinux.cc
@@ -33,9 +33,6 @@ void ResourceBundle::LoadCommonResources() {
// Always load the 1x data pack first as the 2x data pack contains both 1x and
// 2x images. The 1x data pack only has 1x images, thus passes in an accurate
// scale factor to gfx::ImageSkia::AddRepresentation.
-
- AddDataPackFromPath(GetResourcesPakFilePath("chrome.pak"),
- SCALE_FACTOR_NONE);
AddDataPackFromPath(GetResourcesPakFilePath(
"chrome_100_percent.pak"), SCALE_FACTOR_100P);
diff --git a/chromium/ui/base/resource/resource_bundle_gtk.cc b/chromium/ui/base/resource/resource_bundle_gtk.cc
index 4d16b618e34..2578dc29d37 100644
--- a/chromium/ui/base/resource/resource_bundle_gtk.cc
+++ b/chromium/ui/base/resource/resource_bundle_gtk.cc
@@ -10,11 +10,11 @@
#include "base/path_service.h"
#include "base/synchronization/lock.h"
#include "third_party/skia/include/core/SkBitmap.h"
-#include "ui/base/gtk/scoped_gobject.h"
#include "ui/base/layout.h"
#include "ui/base/resource/resource_handle.h"
#include "ui/base/ui_base_paths.h"
#include "ui/gfx/image/image.h"
+#include "ui/gfx/scoped_gobject.h"
#include <gtk/gtk.h>
@@ -65,8 +65,6 @@ base::FilePath GetResourcesPakFilePath(const std::string& pak_name) {
} // namespace
void ResourceBundle::LoadCommonResources() {
- AddDataPackFromPath(GetResourcesPakFilePath("chrome.pak"),
- SCALE_FACTOR_NONE);
AddDataPackFromPath(GetResourcesPakFilePath(
"chrome_100_percent.pak"),
SCALE_FACTOR_100P);
diff --git a/chromium/ui/base/resource/resource_bundle_mac.mm b/chromium/ui/base/resource/resource_bundle_mac.mm
index 5de8eccc839..56d16d5ed64 100644
--- a/chromium/ui/base/resource/resource_bundle_mac.mm
+++ b/chromium/ui/base/resource/resource_bundle_mac.mm
@@ -49,8 +49,6 @@ base::FilePath GetResourcesPakFilePath(NSString* name, NSString* mac_locale) {
} // namespace
void ResourceBundle::LoadCommonResources() {
- AddDataPackFromPath(GetResourcesPakFilePath(@"chrome", nil),
- SCALE_FACTOR_NONE);
AddDataPackFromPath(GetResourcesPakFilePath(@"chrome_100_percent",
nil), SCALE_FACTOR_100P);
AddDataPackFromPath(GetResourcesPakFilePath(@"webkit_resources_100_percent",
diff --git a/chromium/ui/base/resource/resource_bundle_win.cc b/chromium/ui/base/resource/resource_bundle_win.cc
index ec47d4c079f..0a2b185e67e 100644
--- a/chromium/ui/base/resource/resource_bundle_win.cc
+++ b/chromium/ui/base/resource/resource_bundle_win.cc
@@ -10,7 +10,7 @@
#include "ui/base/layout.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/base/resource/resource_data_dll_win.h"
-#include "ui/base/win/dpi.h"
+#include "ui/gfx/win/dpi.h"
namespace ui {
@@ -42,7 +42,7 @@ void ResourceBundle::LoadCommonResources() {
// default scaling for Metro mode. If high-DPI mode is enabled, load resource
// pak closest to the desired scale factor. The high-DPI resources are
// scaled up from 100% touch.
- float scale = ui::win::GetDeviceScaleFactor();
+ float scale = gfx::win::GetDeviceScaleFactor();
bool force_touch_resources = false;
switch(ui::GetScaleFactorFromScale(scale)) {
case ui::SCALE_FACTOR_180P:
diff --git a/chromium/ui/base/sequential_id_generator.cc b/chromium/ui/base/sequential_id_generator.cc
new file mode 100644
index 00000000000..ac3b1a0ed41
--- /dev/null
+++ b/chromium/ui/base/sequential_id_generator.cc
@@ -0,0 +1,82 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/sequential_id_generator.h"
+
+#include "base/logging.h"
+
+namespace {
+
+// Removes |key| from |first|, and |first[key]| from |second|.
+template<typename T>
+void Remove(uint32 key, T* first, T* second) {
+ typename T::iterator iter = first->find(key);
+ if (iter == first->end())
+ return;
+
+ uint32 second_key = iter->second;
+ first->erase(iter);
+
+ iter = second->find(second_key);
+ DCHECK(iter != second->end());
+ second->erase(iter);
+}
+
+} // namespace
+
+namespace ui {
+
+SequentialIDGenerator::SequentialIDGenerator(uint32 min_id)
+ : min_id_(min_id),
+ min_available_id_(min_id) {
+}
+
+SequentialIDGenerator::~SequentialIDGenerator() {
+}
+
+uint32 SequentialIDGenerator::GetGeneratedID(uint32 number) {
+ IDMap::iterator find = number_to_id_.find(number);
+ if (find != number_to_id_.end())
+ return find->second;
+
+ int id = GetNextAvailableID();
+ number_to_id_.insert(std::make_pair(number, id));
+ id_to_number_.insert(std::make_pair(id, number));
+ return id;
+}
+
+bool SequentialIDGenerator::HasGeneratedIDFor(uint32 number) const {
+ return number_to_id_.find(number) != number_to_id_.end();
+}
+
+void SequentialIDGenerator::ReleaseGeneratedID(uint32 id) {
+ UpdateNextAvailableIDAfterRelease(id);
+ Remove(id, &id_to_number_, &number_to_id_);
+}
+
+void SequentialIDGenerator::ReleaseNumber(uint32 number) {
+ DCHECK_GT(number_to_id_.count(number), 0U);
+ UpdateNextAvailableIDAfterRelease(number_to_id_[number]);
+ Remove(number, &number_to_id_, &id_to_number_);
+}
+
+uint32 SequentialIDGenerator::GetNextAvailableID() {
+ const uint32 kMaxID = 128;
+ while (id_to_number_.count(min_available_id_) > 0 &&
+ min_available_id_ < kMaxID) {
+ ++min_available_id_;
+ }
+ if (min_available_id_ >= kMaxID)
+ min_available_id_ = min_id_;
+ return min_available_id_;
+}
+
+void SequentialIDGenerator::UpdateNextAvailableIDAfterRelease(uint32 id) {
+ if (id < min_available_id_) {
+ min_available_id_ = id;
+ DCHECK_GE(min_available_id_, min_id_);
+ }
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/sequential_id_generator.h b/chromium/ui/base/sequential_id_generator.h
new file mode 100644
index 00000000000..0adc8bf0c66
--- /dev/null
+++ b/chromium/ui/base/sequential_id_generator.h
@@ -0,0 +1,60 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_BASE_SEQUENTIAL_ID_GENERATOR_H_
+#define UI_BASE_SEQUENTIAL_ID_GENERATOR_H_
+
+#include <map>
+
+#include "base/basictypes.h"
+#include "base/containers/hash_tables.h"
+#include "ui/base/ui_export.h"
+
+namespace ui {
+
+// This is used to generate a series of sequential ID numbers in a way that a
+// new ID is always the lowest possible ID in the sequence.
+class UI_EXPORT SequentialIDGenerator {
+ public:
+ // Creates a new generator with the specified lower bound for the IDs.
+ explicit SequentialIDGenerator(uint32 min_id);
+ ~SequentialIDGenerator();
+
+ // Generates a unique ID to represent |number|. The generated ID is the
+ // smallest available ID greater than or equal to the |min_id| specified
+ // during creation of the generator.
+ uint32 GetGeneratedID(uint32 number);
+
+ // Checks to see if the generator currently has a unique ID generated for
+ // |number|.
+ bool HasGeneratedIDFor(uint32 number) const;
+
+ // Removes the generated ID |id| from the internal mapping. Since the ID is
+ // no longer mapped to any number, subsequent calls to |GetGeneratedID()| can
+ // use this ID.
+ void ReleaseGeneratedID(uint32 id);
+
+ // Removes the ID previously generated for |number| by calling
+ // |GetGeneratedID()|.
+ void ReleaseNumber(uint32 number);
+
+ private:
+ typedef base::hash_map<uint32, uint32> IDMap;
+
+ uint32 GetNextAvailableID();
+
+ void UpdateNextAvailableIDAfterRelease(uint32 id);
+
+ IDMap number_to_id_;
+ IDMap id_to_number_;
+
+ uint32 min_id_;
+ uint32 min_available_id_;
+
+ DISALLOW_COPY_AND_ASSIGN(SequentialIDGenerator);
+};
+
+} // namespace ui
+
+#endif // UI_BASE_SEQUENTIAL_ID_GENERATOR_H_
diff --git a/chromium/ui/base/sequential_id_generator_unittest.cc b/chromium/ui/base/sequential_id_generator_unittest.cc
new file mode 100644
index 00000000000..be703bd7d3f
--- /dev/null
+++ b/chromium/ui/base/sequential_id_generator_unittest.cc
@@ -0,0 +1,62 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/sequential_id_generator.h"
+
+#include "base/logging.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace ui {
+
+typedef testing::Test SequentialIDGeneratorTest;
+
+TEST(SequentialIDGeneratorTest, AddRemove) {
+ const uint32 kMinID = 2;
+ SequentialIDGenerator generator(kMinID);
+
+ EXPECT_EQ(2U, generator.GetGeneratedID(45));
+ EXPECT_EQ(3U, generator.GetGeneratedID(23));
+ EXPECT_EQ(2U, generator.GetGeneratedID(45));
+ EXPECT_TRUE(generator.HasGeneratedIDFor(45));
+ EXPECT_TRUE(generator.HasGeneratedIDFor(23));
+
+ generator.ReleaseGeneratedID(2);
+ EXPECT_FALSE(generator.HasGeneratedIDFor(45));
+ EXPECT_TRUE(generator.HasGeneratedIDFor(23));
+ EXPECT_EQ(3U, generator.GetGeneratedID(23));
+
+ EXPECT_FALSE(generator.HasGeneratedIDFor(1));
+ EXPECT_EQ(2U, generator.GetGeneratedID(1));
+ EXPECT_TRUE(generator.HasGeneratedIDFor(1));
+
+ generator.ReleaseGeneratedID(3);
+ EXPECT_EQ(3U, generator.GetGeneratedID(45));
+ EXPECT_TRUE(generator.HasGeneratedIDFor(45));
+
+ generator.ReleaseNumber(45);
+ EXPECT_FALSE(generator.HasGeneratedIDFor(45));
+}
+
+TEST(SequentialIDGeneratorTest, RemoveMultipleNumbers) {
+ const uint32 kMinID = 4;
+ SequentialIDGenerator generator(kMinID);
+
+ EXPECT_EQ(4U, generator.GetGeneratedID(45));
+ EXPECT_EQ(5U, generator.GetGeneratedID(55));
+ EXPECT_EQ(6U, generator.GetGeneratedID(15));
+
+ generator.ReleaseNumber(45);
+ EXPECT_FALSE(generator.HasGeneratedIDFor(45));
+ generator.ReleaseNumber(15);
+ EXPECT_FALSE(generator.HasGeneratedIDFor(15));
+
+ EXPECT_EQ(5U, generator.GetGeneratedID(55));
+ EXPECT_EQ(4U, generator.GetGeneratedID(12));
+
+ generator.ReleaseNumber(12);
+ generator.ReleaseNumber(55);
+ EXPECT_EQ(4U, generator.GetGeneratedID(0));
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/strings/app_locale_settings.grd b/chromium/ui/base/strings/app_locale_settings.grd
index 2b862d50cb3..d285e9275b0 100644
--- a/chromium/ui/base/strings/app_locale_settings.grd
+++ b/chromium/ui/base/strings/app_locale_settings.grd
@@ -31,7 +31,13 @@
<output filename="app_locale_settings_eo.pak" type="data_package" lang="eo" />
</if>
<output filename="app_locale_settings_es.pak" type="data_package" lang="es" />
- <output filename="app_locale_settings_es-419.pak" type="data_package" lang="es-419" />
+ <if expr="is_ios">
+ <!-- iOS uses es-MX for es-419 -->
+ <output filename="app_locale_settings_es-MX.pak" type="data_package" lang="es-419" />
+ </if>
+ <if expr="not is_ios">
+ <output filename="app_locale_settings_es-419.pak" type="data_package" lang="es-419" />
+ </if>
<output filename="app_locale_settings_et.pak" type="data_package" lang="et" />
<if expr="pp_ifdef('use_third_party_translations')">
<output filename="app_locale_settings_eu.pak" type="data_package" lang="eu" />
@@ -75,11 +81,11 @@
be 'nb'. -->
<output filename="app_locale_settings_nb.pak" type="data_package" lang="no" />
<output filename="app_locale_settings_pl.pak" type="data_package" lang="pl" />
- <if expr="pp_ifdef('ios')">
+ <if expr="is_ios">
<!-- iOS uses pt for pt-BR -->
<output filename="app_locale_settings_pt.pak" type="data_package" lang="pt-BR" />
</if>
- <if expr="not pp_ifdef('ios')">
+ <if expr="not is_ios">
<output filename="app_locale_settings_pt-BR.pak" type="data_package" lang="pt-BR" />
</if>
<output filename="app_locale_settings_pt-PT.pak" type="data_package" lang="pt-PT" />
@@ -212,7 +218,7 @@
75%
</message>
</if>
- <if expr="is_macosx">
+ <if expr="is_macosx or is_ios">
<!-- The font used in Web UI (e.g. History). -->
<message name="IDS_WEB_FONT_FAMILY" use_name_for_id="true">
'Lucida Grande', sans-serif
diff --git a/chromium/ui/base/strings/app_locale_settings_ja.xtb b/chromium/ui/base/strings/app_locale_settings_ja.xtb
index 9edc4a10c8d..1e843b0ad73 100644
--- a/chromium/ui/base/strings/app_locale_settings_ja.xtb
+++ b/chromium/ui/base/strings/app_locale_settings_ja.xtb
@@ -7,7 +7,7 @@
<translation id="IDS_WEB_FONT_FAMILY">'Segoe UI',Arial,Meiryo,'MS PGothic',sans-serif</translation>
<translation id="IDS_WEB_FONT_FAMILY_XP">Arial,Meiryo,'MS PGothic',sans-serif</translation>
</if>
-<if expr="is_macosx">
+<if expr="is_macosx or is_ios">
<translation id="IDS_WEB_FONT_FAMILY">Helvetica,Hiragino Kaku Gothic Pro,sans-serif</translation>
</if>
<if expr="is_linux and not pp_ifdef('chromeos')">
diff --git a/chromium/ui/base/strings/app_locale_settings_ko.xtb b/chromium/ui/base/strings/app_locale_settings_ko.xtb
index 9d7f042d593..e1db12edb41 100644
--- a/chromium/ui/base/strings/app_locale_settings_ko.xtb
+++ b/chromium/ui/base/strings/app_locale_settings_ko.xtb
@@ -7,7 +7,7 @@
<translation id="IDS_WEB_FONT_FAMILY">'Segoe UI',Arial,'Malgun Gothic',Gulim,sans-serif</translation>
<translation id="IDS_WEB_FONT_FAMILY_XP">Arial,'Malgun Gothic',Gulim,sans-serif</translation>
</if>
-<if expr="is_macosx">
+<if expr="is_macosx or is_ios">
<translation id="IDS_WEB_FONT_FAMILY">Helvetica,AppleGothic,sans-serif</translation>
</if>
<if expr="is_linux and not pp_ifdef('chromeos')">
diff --git a/chromium/ui/base/strings/app_locale_settings_zh-CN.xtb b/chromium/ui/base/strings/app_locale_settings_zh-CN.xtb
index 6b4c7008649..e67b6c12e12 100644
--- a/chromium/ui/base/strings/app_locale_settings_zh-CN.xtb
+++ b/chromium/ui/base/strings/app_locale_settings_zh-CN.xtb
@@ -7,7 +7,7 @@
<translation id="IDS_WEB_FONT_FAMILY">'Segoe UI',Arial,'Microsoft Yahei',Simsun,sans-serif</translation>
<translation id="IDS_WEB_FONT_FAMILY_XP">Arial,'Microsoft Yahei',Simsun,sans-serif</translation>
</if>
-<if expr="is_macosx">
+<if expr="is_macosx or is_ios">
<translation id="IDS_WEB_FONT_FAMILY">Helvetica,STHeiti,sans-serif</translation>
</if>
<if expr="pp_ifdef('chromeos') and pp_ifdef('_google_chrome')">
diff --git a/chromium/ui/base/strings/app_locale_settings_zh-TW.xtb b/chromium/ui/base/strings/app_locale_settings_zh-TW.xtb
index 14ae8b0da2b..2492fbc3138 100644
--- a/chromium/ui/base/strings/app_locale_settings_zh-TW.xtb
+++ b/chromium/ui/base/strings/app_locale_settings_zh-TW.xtb
@@ -7,7 +7,7 @@
<translation id="IDS_WEB_FONT_FAMILY">'Segoe UI',Arial,'Microsoft Jhenghei',PMingLiu,sans-serif</translation>
<translation id="IDS_WEB_FONT_FAMILY_XP">Arial,'Microsoft Jhenghei',PMingLiu,sans-serif</translation>
</if>
-<if expr="is_macosx">
+<if expr="is_macosx or is_ios">
<translation id="IDS_WEB_FONT_FAMILY">Helvetica,LiHei Pro,sans-serif</translation>
</if>
<if expr="pp_ifdef('chromeos') and pp_ifdef('_google_chrome')">
diff --git a/chromium/ui/base/strings/ui_strings.grd b/chromium/ui/base/strings/ui_strings.grd
index ec198ad05f1..590613857ab 100644
--- a/chromium/ui/base/strings/ui_strings.grd
+++ b/chromium/ui/base/strings/ui_strings.grd
@@ -42,7 +42,13 @@ need to be translated for each locale.-->
<output filename="ui_strings_eo.pak" type="data_package" lang="eo" />
</if>
<output filename="ui_strings_es.pak" type="data_package" lang="es" />
- <output filename="ui_strings_es-419.pak" type="data_package" lang="es-419" />
+ <if expr="is_ios">
+ <!-- iOS uses es-MX for es-419 -->
+ <output filename="ui_strings_es-MX.pak" type="data_package" lang="es-419" />
+ </if>
+ <if expr="not is_ios">
+ <output filename="ui_strings_es-419.pak" type="data_package" lang="es-419" />
+ </if>
<output filename="ui_strings_et.pak" type="data_package" lang="et" />
<if expr="pp_ifdef('use_third_party_translations')">
<output filename="ui_strings_eu.pak" type="data_package" lang="eu" />
@@ -86,11 +92,11 @@ need to be translated for each locale.-->
be 'nb'. -->
<output filename="ui_strings_nb.pak" type="data_package" lang="no" />
<output filename="ui_strings_pl.pak" type="data_package" lang="pl" />
- <if expr="pp_ifdef('ios')">
+ <if expr="is_ios">
<!-- iOS uses pt for pt-BR -->
<output filename="ui_strings_pt.pak" type="data_package" lang="pt-BR" />
</if>
- <if expr="not pp_ifdef('ios')">
+ <if expr="not is_ios">
<output filename="ui_strings_pt-BR.pak" type="data_package" lang="pt-BR" />
</if>
<output filename="ui_strings_pt-PT.pak" type="data_package" lang="pt-PT" />
@@ -1458,6 +1464,18 @@ need to be translated for each locale.-->
<message name="IDS_APP_PERIOD_KEY" desc="Period key">
Period
</message>
+ <message name="IDS_APP_MEDIA_NEXT_TRACK_KEY" desc="Media next track key">
+ Media Next Track
+ </message>
+ <message name="IDS_APP_MEDIA_PLAY_PAUSE_KEY" desc="Media play pause key">
+ Media Play/Pause
+ </message>
+ <message name="IDS_APP_MEDIA_PREV_TRACK_KEY" desc="Media previous track key">
+ Media Previous Track
+ </message>
+ <message name="IDS_APP_MEDIA_STOP_KEY" desc="Media stop key">
+ Media Stop
+ </message>
<!-- Shortcut Modifiers -->
<message name="IDS_APP_CONTROL_MODIFIER" desc="Control key shortcut modifier">
@@ -1515,11 +1533,8 @@ need to be translated for each locale.-->
<message name="IDS_MESSAGE_CENTER_ACCESSIBLE_NAME" desc="The accessible name for the Notification Center window.">
Notification Center
</message>
- <message name="IDS_MESSAGE_CENTER_EXTENSIONS_DISABLE" desc="The menu entry for disabling extensions from a notification.">
- Disable notifications from <ph name="extension_name">$1<ex>Notification Galore!</ex></ph>
- </message>
- <message name="IDS_MESSAGE_CENTER_SITE_DISABLE" desc="The menu entry for disabling notification from a site.">
- Disable notifications from <ph name="site">$1<ex>mail.google.com</ex></ph>
+ <message name="IDS_MESSAGE_CENTER_NOTIFIER_DISABLE" desc="The menu entry for disabling a notifier from a notification.">
+ Disable notifications from <ph name="notifier_name">$1<ex>Notification Galore!</ex></ph>
</message>
<message name="IDS_MESSAGE_CENTER_FOOTER_TITLE" desc="The label in the footer of the message center">
Notifications
diff --git a/chromium/ui/base/strings/ui_strings_am.xtb b/chromium/ui/base/strings/ui_strings_am.xtb
index d3576a6c805..81d224ae737 100644
--- a/chromium/ui/base/strings/ui_strings_am.xtb
+++ b/chromium/ui/base/strings/ui_strings_am.xtb
@@ -6,16 +6,17 @@
<translation id="6135826906199951471">Del</translation>
<translation id="528468243742722775">ጨርስ</translation>
<translation id="5341849548509163798">ከ<ph name="NUMBER_MANY"/> ሰዓቶች በፊት</translation>
-<translation id="6310545596129886942"><ph name="NUMBER_FEW"/> ሰከንድ ይቀራል</translation>
-<translation id="9213479837033539041"><ph name="NUMBER_MANY"/> ሰከንድ ይቀራል</translation>
+<translation id="6310545596129886942"><ph name="NUMBER_FEW"/> ሴኮንድ ይቀራል</translation>
+<translation id="9213479837033539041"><ph name="NUMBER_MANY"/> ሴኮንድ ይቀራል</translation>
<translation id="1209866192426315618"><ph name="NUMBER_DEFAULT"/> ደቂቃ ይቀራል</translation>
<translation id="1801827354178857021">ነቁጥ</translation>
<translation id="1190609913194133056">የማሳወቂያ ማዕከል</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> ደቂቃዎች ቀርተዋል</translation>
<translation id="5613020302032141669">ግራ ቀስት</translation>
+<translation id="4971687151119236543">የሚዲያ ቀዳሚ ትራክ</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ፋይል(.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918">ከ<ph name="NUMBER_ZERO"/> ደቂቃ በፊት</translation>
-<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> ሰከንድ</translation>
+<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> ሴኮንድ</translation>
<translation id="7511635910912978956"><ph name="NUMBER_FEW"/> ሰዓቶች ይቀራሉ</translation>
<translation id="5948410903763073882">Alt+<ph name="KEY_COMBO_NAME"/></translation>
<translation id="7658239707568436148">ሰርዝ</translation>
@@ -30,7 +31,7 @@
<translation id="932327136139879170">መነሻ</translation>
<translation id="5600907569873192868"><ph name="NUMBER_MANY"/> ደቂቃ ይቀራል</translation>
<translation id="8666066831007952346"><ph name="NUMBER_TWO"/> ቀናት ይቀራሉ</translation>
-<translation id="6390842777729054533">ከ<ph name="NUMBER_ZERO"/> ሰከንድ በፊት</translation>
+<translation id="6390842777729054533">ከ<ph name="NUMBER_ZERO"/> ሴኮንድ በፊት</translation>
<translation id="3909791450649380159">&amp;ቁረጥ</translation>
<translation id="2560788951337264832"><ph name="NUMBER_ZERO"/> ደቂቃዎች ቀርተዋል</translation>
<translation id="688711909580084195">ርዕስ-አልባ ድረ-ገጽ</translation>
@@ -58,10 +59,10 @@
<translation id="1572103024875503863"><ph name="NUMBER_MANY"/> ቀናት</translation>
<translation id="7163503212501929773"><ph name="NUMBER_MANY"/> ሰዓቶች ይቀራሉ</translation>
<translation id="5329858601952122676">&amp;ሠርዝ</translation>
-<translation id="8088823334188264070"><ph name="NUMBER_MANY"/> ሰከንድ</translation>
+<translation id="8088823334188264070"><ph name="NUMBER_MANY"/> ሴኮንድ</translation>
<translation id="8901569739625249689"><ph name="QUANTITY"/> ኪባ</translation>
<translation id="7712011264267466734"><ph name="NUMBER_MANY"/> ደቂቃዎች</translation>
-<translation id="7275974018215686543">ከ<ph name="NUMBER_MANY"/> ሰከንድ በፊት</translation>
+<translation id="7275974018215686543">ከ<ph name="NUMBER_MANY"/> ሴኮንድ በፊት</translation>
<translation id="7781829728241885113">ትናንት</translation>
<translation id="3424538384153559412"><ph name="NUMBER_TWO"/> ደቂቃዎች</translation>
<translation id="50960180632766478"><ph name="NUMBER_FEW"/> ደቂቃ ይቀራል</translation>
@@ -72,11 +73,11 @@
<translation id="2497284189126895209">ሁሉም ፋይሎች</translation>
<translation id="7487278341251176613"><ph name="NUMBER_TWO"/> ደቂቃዎች ቀርተዋል</translation>
<translation id="5110450810124758964">ከ<ph name="NUMBER_ONE"/> ቀን በፊት</translation>
-<translation id="2820806154655529776"><ph name="NUMBER_ONE"/> ሰከንድ</translation>
+<translation id="2820806154655529776"><ph name="NUMBER_ONE"/> ሴኮንድ</translation>
<translation id="7814458197256864873">&amp;ቅዳ</translation>
<translation id="3889424535448813030">ቀኝ ቀስት</translation>
-<translation id="4229495110203539533">ከ<ph name="NUMBER_ONE"/> ሰከንድ በፊት</translation>
-<translation id="2544782972264605588">ከ<ph name="NUMBER_DEFAULT"/> ሰከንድ በፊት</translation>
+<translation id="4229495110203539533">ከ<ph name="NUMBER_ONE"/> ሴኮንድ በፊት</translation>
+<translation id="2544782972264605588">ከ<ph name="NUMBER_DEFAULT"/> ሴኮንድ በፊት</translation>
<translation id="6829324100069873704">ወደ ማሳወቂያዎች ተመለስ።</translation>
<translation id="6528179044667508675">አትረብሽ</translation>
<translation id="5066177358602611309"><ph name="NUMBER_DEFAULT"/> ሰከንዶች</translation>
@@ -95,7 +96,7 @@
<translation id="9107059250669762581"><ph name="NUMBER_DEFAULT"/> ቀን</translation>
<translation id="6463061331681402734"><ph name="NUMBER_MANY"/> ደቂቃ</translation>
<translation id="7634624804467787019"><ph name="NUMBER_ONE"/> ደቂቃ</translation>
-<translation id="8448317557906454022">ከ<ph name="NUMBER_ZERO"/> ሰከንድ በፊት</translation>
+<translation id="8448317557906454022">ከ<ph name="NUMBER_ZERO"/> ሴኮንድ በፊት</translation>
<translation id="4927753642311223124">እዚህ ምንም የሚታይ ነገር የለም፣ ይቀጥሉ።</translation>
<translation id="2482878487686419369">ማስታወቂያዎች</translation>
<translation id="6357135709975569075"><ph name="NUMBER_ZERO"/> ቀን</translation>
@@ -104,24 +105,26 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ሰዓቶች</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> ኪባ/ሰ</translation>
+<translation id="8394908167088220973">ሚዲያ አጫውት/ለአፍታ አቁም</translation>
<translation id="2148716181193084225">ዛሬ</translation>
<translation id="7960078400008666149">ለአንድ ሰዓት አትረብሽ</translation>
<translation id="4373894838514502496">ከ<ph name="NUMBER_FEW"/> ደቂቃ በፊት</translation>
<translation id="4115153316875436289"><ph name="NUMBER_TWO"/> ቀናት</translation>
<translation id="2190355936436201913">(ባዶ)</translation>
<translation id="1164369517022005061"><ph name="NUMBER_DEFAULT"/> ሰዓት ይቀራል</translation>
-<translation id="152482086482215392"><ph name="NUMBER_ONE"/> ሰከንድ ይቀራል</translation>
+<translation id="152482086482215392"><ph name="NUMBER_ONE"/> ሴኮንድ ይቀራል</translation>
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">ወደ ቀኝ ሸብልል</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> ሰዓት ይቀራል</translation>
+<translation id="1413622004203049571">ከ<ph name="NOTIFIER_NAME"/> የሚመጡ ማሳወቂያዎችን አሰናክል</translation>
<translation id="2666092431469916601">ላይ</translation>
<translation id="8331626408530291785">ወደ ላይ ሸብልል</translation>
-<translation id="4773379706300191099">የ<ph name="EXTENSION_NAME"/> ማሳወቂያዎችን አሰናክል</translation>
<translation id="7907591526440419938">ፋይል ክፈት</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> ቀን ይቀራል</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">ከ<ph name="NUMBER_DEFAULT"/> ሰዓት በፊት</translation>
<translation id="815598010540052116">ወደ ታች ሸብልል</translation>
+<translation id="6808150112686056157">ሚዲያ አቁም</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> ደቂቃ ይቀራል</translation>
<translation id="3157931365184549694">እነበረበት መልስ</translation>
<translation id="1243314992276662751">ስቀል</translation>
@@ -131,14 +134,14 @@
<translation id="9170848237812810038">&amp;ቀልብስ</translation>
<translation id="1285266685456062655">ከ<ph name="NUMBER_FEW"/> ሰዓቶች በፊት</translation>
<translation id="6918245111648057970">ከሚከተሉት ውስጥ ለእያንዳንዱ ተጠቃሚ ማሳወቂያዎችን ይፍቀዱ፦</translation>
-<translation id="5489830104927132166"><ph name="NUMBER_ONE"/> ሰከንድ</translation>
+<translation id="5489830104927132166"><ph name="NUMBER_ONE"/> ሴኮንድ</translation>
<translation id="3994835489895548312"><ph name="NUMBER_MANY"/> ደቂቃዎች ቀርተዋል</translation>
-<translation id="6358975074282722691">ከ<ph name="NUMBER_TWO"/> ሰከንድ በፊት</translation>
+<translation id="6358975074282722691">ከ<ph name="NUMBER_TWO"/> ሴኮንድ በፊት</translation>
<translation id="520299402983819650"><ph name="QUANTITY"/> ፔታ</translation>
<translation id="2983818520079887040">ቅንብሮች ...</translation>
<translation id="6845383723252244143">አቃፊ ምረጥ</translation>
<translation id="7600770490873519066"><ph name="NUMBER_FEW"/> ሰከንዶች</translation>
-<translation id="1095623615273566396"><ph name="NUMBER_FEW"/> ሰከንድ</translation>
+<translation id="1095623615273566396"><ph name="NUMBER_FEW"/> ሴኮንድ</translation>
<translation id="5583640892426849032">Backspace</translation>
<translation id="5263972071113911534">ከ<ph name="NUMBER_MANY"/> ቀናት በፊት</translation>
<translation id="8355915647418390920"><ph name="NUMBER_FEW"/> ቀናት</translation>
@@ -147,11 +150,11 @@
<translation id="8788572795284305350">ከ<ph name="NUMBER_ZERO"/> ሰዓት በፊት</translation>
<translation id="3740362395218339114"><ph name="QUANTITY"/> ጊባ/ሰ</translation>
<translation id="6644971472240498405"><ph name="NUMBER_ONE"/> ቀን</translation>
-<translation id="9098468523912235228">ከ<ph name="NUMBER_DEFAULT"/> ሰከንድ በፊት</translation>
-<translation id="494645311413743213"><ph name="NUMBER_TWO"/> ሰከንድ ይቀራል</translation>
+<translation id="9098468523912235228">ከ<ph name="NUMBER_DEFAULT"/> ሴኮንድ በፊት</translation>
+<translation id="494645311413743213"><ph name="NUMBER_TWO"/> ሴኮንድ ይቀራል</translation>
<translation id="4570886800634958009">ማሳወቂያ ዘርጋ</translation>
<translation id="436869212180315161">ተጫን</translation>
-<translation id="4860787810836767172">ከ<ph name="NUMBER_FEW"/> ሰከንድ በፊት</translation>
+<translation id="4860787810836767172">ከ<ph name="NUMBER_FEW"/> ሴኮንድ በፊት</translation>
<translation id="2297836609126180313"><ph name="QUANTITY"/> ቴባ/ሰ</translation>
<translation id="6956540737482608074"><ph name="NUMBER_ZERO"/> ደቂቃዎች</translation>
<translation id="1858722859751911017"><ph name="NUMBER_FEW"/> ደቂቃዎች ቀርተዋል</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">ከ<ph name="NUMBER_MANY"/> ደቂቃ በፊት</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> ባ/ሰ</translation>
<translation id="7649070708921625228">እገዛ</translation>
+<translation id="6699343763173986273">የሚዲያ ቀጣይ ትራክ</translation>
<translation id="8226233771743600312">ለአንድ ቀን አትረብሽ</translation>
<translation id="7457942297256758195">ሁሉንም አጽዳ</translation>
<translation id="822618367988303761">ከ<ph name="NUMBER_TWO"/> ቀናት በፊት</translation>
@@ -168,8 +172,8 @@
<translation id="5906719743126878045"><ph name="NUMBER_TWO"/> ሰዓቶች ይቀራሉ</translation>
<translation id="8959208747503200525">ከ<ph name="NUMBER_TWO"/> ሰዓቶች በፊት</translation>
<translation id="8400147561352026160">Shift+<ph name="KEY_COMBO_NAME"/></translation>
-<translation id="8421864404045570940"><ph name="NUMBER_DEFAULT"/> ሰከንድ</translation>
-<translation id="4197700912384709145"><ph name="NUMBER_ZERO"/> ሰከንድ</translation>
+<translation id="8421864404045570940"><ph name="NUMBER_DEFAULT"/> ሴኮንድ</translation>
+<translation id="4197700912384709145"><ph name="NUMBER_ZERO"/> ሴኮንድ</translation>
<translation id="27199337101878275"><ph name="NUMBER_MANY"/> ሰከንዶች</translation>
<translation id="3759876923365568382"><ph name="NUMBER_FEW"/> ቀን ይቀራል</translation>
<translation id="6907759265145635167"><ph name="QUANTITY"/> ፔባ/ሰ</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496">ከ<ph name="NUMBER_ZERO"/> ቀን በፊት</translation>
<translation id="5941711191222866238">አሳንስ</translation>
<translation id="6394627529324717982">ኮማ</translation>
-<translation id="4469842253116033348">ማስታወቂያዎችን ከ<ph name="SITE"/> አሰናክል</translation>
<translation id="3036649622769666520">ፋይሎች ክፈት</translation>
<translation id="8328145009876646418">የግራ ጠርዝ</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> ሰከንዶች</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ar.xtb b/chromium/ui/base/strings/ui_strings_ar.xtb
index d9769f3f4bb..29d95e82cc9 100644
--- a/chromium/ui/base/strings/ui_strings_ar.xtb
+++ b/chromium/ui/base/strings/ui_strings_ar.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">مركز الإشعارات</translation>
<translation id="7470933019269157899">عدد الدقائق المتبقية: <ph name="NUMBER_DEFAULT"/></translation>
<translation id="5613020302032141669">مفتاح سهم إلى اليسار</translation>
+<translation id="4971687151119236543">المقطع الصوتي السابق للوسائط</translation>
<translation id="8602707065186045623">ملف <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918">قبل <ph name="NUMBER_ZERO"/> دقيقة</translation>
<translation id="7121570032414343252">عدد الثواني: <ph name="NUMBER_TWO"/></translation>
@@ -97,13 +98,14 @@
<translation id="7634624804467787019"><ph name="NUMBER_ONE"/> دقيقة واحدة</translation>
<translation id="8448317557906454022">قبل <ph name="NUMBER_ZERO"/> ثانية</translation>
<translation id="4927753642311223124">ليس هناك شيء تراه هنا، انتقل إلى مكان آخر.</translation>
-<translation id="2482878487686419369">التنبيهات</translation>
+<translation id="2482878487686419369">الاشعارات</translation>
<translation id="6357135709975569075"><ph name="NUMBER_ZERO"/> يوم</translation>
<translation id="3183922693828471536">التمرير إلى هنا</translation>
<translation id="4552416320897244156">‏مفتاح PgDwn (صفحة إلى أسفل)</translation>
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ساعة</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> كيلوبايت/ثانية</translation>
+<translation id="8394908167088220973">تشغيل/إيقاف الوسائط</translation>
<translation id="2148716181193084225">اليوم</translation>
<translation id="7960078400008666149">الرجاء عدم الإزعاج لمدة ساعة واحدة</translation>
<translation id="4373894838514502496">قبل <ph name="NUMBER_FEW"/> دقيقة</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">‏مفتاح PgUp (صفحة إلى أعلى)</translation>
<translation id="4588090240171750605">التمرير إلى اليسار</translation>
<translation id="7414887922320653780">عدد الساعات المتبقية: <ph name="NUMBER_ONE"/></translation>
+<translation id="1413622004203049571">تعطيل الإشعارات من <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">أعلى</translation>
<translation id="8331626408530291785">التمرير إلى أعلى</translation>
-<translation id="4773379706300191099">تعطيل الإشعارات من <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">فتح ملف</translation>
<translation id="2864069933652346933">متبقٍ <ph name="NUMBER_ZERO"/> يوم</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">قبل <ph name="NUMBER_DEFAULT"/> ساعة</translation>
<translation id="815598010540052116">التمرير إلى أسفل</translation>
+<translation id="6808150112686056157">إيقاف الوسائط</translation>
<translation id="1308727876662951186">متبقٍ <ph name="NUMBER_ZERO"/> دقيقة</translation>
<translation id="3157931365184549694">استعادة</translation>
<translation id="1243314992276662751">تحميل</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">قبل <ph name="NUMBER_MANY"/> دقيقة</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> بايت/ثانية</translation>
<translation id="7649070708921625228">مساعدة</translation>
+<translation id="6699343763173986273">المقطع الصوتي التالي للوسائط</translation>
<translation id="8226233771743600312">الرجاء عدم الإزعاج لمدة يوم واحد</translation>
<translation id="7457942297256758195">محو الكل</translation>
<translation id="822618367988303761">قبل <ph name="NUMBER_TWO"/> يوم</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496">قبل <ph name="NUMBER_ZERO"/> يوم</translation>
<translation id="5941711191222866238">تصغير</translation>
<translation id="6394627529324717982">فاصلة</translation>
-<translation id="4469842253116033348">تعطيل التنبيهات من الموقع <ph name="SITE"/></translation>
<translation id="3036649622769666520">فتح الملفات</translation>
<translation id="8328145009876646418">الحافة اليمنى</translation>
<translation id="7372005818821648611">ثانيتان (<ph name="NUMBER_TWO"/>)</translation>
diff --git a/chromium/ui/base/strings/ui_strings_bg.xtb b/chromium/ui/base/strings/ui_strings_bg.xtb
index 859ba008b87..427b3abfe9f 100644
--- a/chromium/ui/base/strings/ui_strings_bg.xtb
+++ b/chromium/ui/base/strings/ui_strings_bg.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Център за известия</translation>
<translation id="7470933019269157899">Остават <ph name="NUMBER_DEFAULT"/> минути</translation>
<translation id="5613020302032141669">Стрелка наляво</translation>
+<translation id="4971687151119236543">Мултимедия, предишният запис</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> файл (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> сек</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> часа</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> КБ/сек</translation>
+<translation id="8394908167088220973">Мултимедия, пускане/пауза</translation>
<translation id="2148716181193084225">Днес</translation>
<translation id="7960078400008666149">Не безпокойте за един час</translation>
<translation id="4373894838514502496">преди <ph name="NUMBER_FEW"/> мин</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Превъртане надясно</translation>
<translation id="7414887922320653780">Остава <ph name="NUMBER_ONE"/> час</translation>
+<translation id="1413622004203049571">Деактивиране на известията от <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Най-горе</translation>
<translation id="8331626408530291785">Превъртане нагоре</translation>
-<translation id="4773379706300191099">Деактивиране на известията от <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Отваряне на файл</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">преди <ph name="NUMBER_DEFAULT"/> часа</translation>
<translation id="815598010540052116">Превъртане надолу</translation>
+<translation id="6808150112686056157">Мултимедия, стоп</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Възстановяване</translation>
<translation id="1243314992276662751">Качване</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">преди <ph name="NUMBER_MANY"/> мин</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> Б/сек</translation>
<translation id="7649070708921625228">Помощ</translation>
+<translation id="6699343763173986273">Мултимедия, следващият запис</translation>
<translation id="8226233771743600312">Не безпокойте за един ден</translation>
<translation id="7457942297256758195">Изчистване на всички</translation>
<translation id="822618367988303761">преди <ph name="NUMBER_TWO"/> дни</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Намаляване</translation>
<translation id="6394627529324717982">Запетая</translation>
-<translation id="4469842253116033348">Деактивиране на известията от <ph name="SITE"/></translation>
<translation id="3036649622769666520">Отваряне на файлове</translation>
<translation id="8328145009876646418">Ляв край</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> секунди</translation>
diff --git a/chromium/ui/base/strings/ui_strings_bn.xtb b/chromium/ui/base/strings/ui_strings_bn.xtb
index 2466e539ce5..de6f7dc3984 100644
--- a/chromium/ui/base/strings/ui_strings_bn.xtb
+++ b/chromium/ui/base/strings/ui_strings_bn.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">বিজ্ঞপ্তি কেন্দ্র</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> মিনিট বাকি</translation>
<translation id="5613020302032141669">Left Arrow</translation>
+<translation id="4971687151119236543">মিডিয়া পূর্ববর্তী ট্র্যাক</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ফাইল (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> সেকেন্ড</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ঘন্টা</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">মিডিয়া প্লে করুন/বিরতি</translation>
<translation id="2148716181193084225">আজ</translation>
<translation id="7960078400008666149">এক ঘন্টার জন্য বিরক্ত করবেন না</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">ডান দিকে স্ক্রোল করুন</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> ঘন্টা বাকি</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> এর থেকে বিজ্ঞপ্তিগুলি অক্ষম করুন</translation>
<translation id="2666092431469916601">শীর্ষ</translation>
<translation id="8331626408530291785">উপরে স্ক্রোল করুন</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> থেকে বিজ্ঞপ্তিগুলি অক্ষম করুন</translation>
<translation id="7907591526440419938">খোলা ফাইল</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> ঘন্টা আগে</translation>
<translation id="815598010540052116">নীচে স্ক্রোল করুন</translation>
+<translation id="6808150112686056157">মিডিয়া থামান</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">পুনরুদ্ধার করুন</translation>
<translation id="1243314992276662751">আপলোড</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">সহায়তা</translation>
+<translation id="6699343763173986273">মিডিয়া পরবর্তী ট্র্যাক</translation>
<translation id="8226233771743600312">এক দিনের জন্য বিরক্ত করবেন না</translation>
<translation id="7457942297256758195">সমস্ত সাফ করুন</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">ছোট করুন</translation>
<translation id="6394627529324717982">কমা</translation>
-<translation id="4469842253116033348"><ph name="SITE"/>-এর থেকে বিজ্ঞপ্তি অক্ষম করুন</translation>
<translation id="3036649622769666520">খোলা ফাইল</translation>
<translation id="8328145009876646418">বাম প্রান্ত</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> সেকেন্ড</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ca.xtb b/chromium/ui/base/strings/ui_strings_ca.xtb
index d07f75bcad8..4f61bb41fae 100644
--- a/chromium/ui/base/strings/ui_strings_ca.xtb
+++ b/chromium/ui/base/strings/ui_strings_ca.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centre de notificacions</translation>
<translation id="7470933019269157899">Queden <ph name="NUMBER_DEFAULT"/> minuts</translation>
<translation id="5613020302032141669">Fletxa esquerra</translation>
+<translation id="4971687151119236543">Fitxer multimèdia: pista anterior</translation>
<translation id="8602707065186045623">Fitxer <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> segons</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> hores</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Fitxer multimèdia: reprodueix/posa en pausa</translation>
<translation id="2148716181193084225">Avui</translation>
<translation id="7960078400008666149">No molesteu durant una hora</translation>
<translation id="4373894838514502496">Fa <ph name="NUMBER_FEW"/> minuts</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">Re Pàg</translation>
<translation id="4588090240171750605">Desplaçament a la dreta</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> hores restants</translation>
+<translation id="1413622004203049571">Desactiva les notificacions de <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Superior</translation>
<translation id="8331626408530291785">Desplaçament amunt</translation>
-<translation id="4773379706300191099">Desactiva les notificacions de <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Obre un fitxer</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Fa <ph name="NUMBER_DEFAULT"/> hores</translation>
<translation id="815598010540052116">Desplaçament avall</translation>
+<translation id="6808150112686056157">Fitxer multimèdia: atura</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restaura</translation>
<translation id="1243314992276662751">Penja</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Fa <ph name="NUMBER_MANY"/> minuts</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Ajuda</translation>
+<translation id="6699343763173986273">Fitxer multimèdia: pista següent</translation>
<translation id="8226233771743600312">No molesteu durant un dia</translation>
<translation id="7457942297256758195">Esborra-ho tot</translation>
<translation id="822618367988303761">Fa <ph name="NUMBER_TWO"/> dies</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimitza</translation>
<translation id="6394627529324717982">Coma</translation>
-<translation id="4469842253116033348">Desactiva les notificacions de <ph name="SITE"/></translation>
<translation id="3036649622769666520">Obre fitxers</translation>
<translation id="8328145009876646418">Extrem esquerre</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> segons</translation>
diff --git a/chromium/ui/base/strings/ui_strings_cs.xtb b/chromium/ui/base/strings/ui_strings_cs.xtb
index d6882c7751c..b6e4dcc291a 100644
--- a/chromium/ui/base/strings/ui_strings_cs.xtb
+++ b/chromium/ui/base/strings/ui_strings_cs.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centrum oznámení</translation>
<translation id="7470933019269157899">Zbývá <ph name="NUMBER_DEFAULT"/> min</translation>
<translation id="5613020302032141669">Klávesa šipka vlevo</translation>
+<translation id="4971687151119236543">Média – předchozí skladba</translation>
<translation id="8602707065186045623">Soubor <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> s</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> hod</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Média – přehrát/pozastavit</translation>
<translation id="2148716181193084225">Dnes</translation>
<translation id="7960078400008666149">Nerušit jednu hodinu</translation>
<translation id="4373894838514502496">před <ph name="NUMBER_FEW"/> minutami</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">Klávesa PgUp</translation>
<translation id="4588090240171750605">Posuv doprava</translation>
<translation id="7414887922320653780">Zbývá: <ph name="NUMBER_ONE"/> hod</translation>
+<translation id="1413622004203049571">Deaktivovat oznámení ze služby <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Nahoru</translation>
<translation id="8331626408530291785">Posuv nahoru</translation>
-<translation id="4773379706300191099">Deaktivovat oznámení rozšíření <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Otevřít soubor</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Klávesa Esc</translation>
<translation id="2797524280730715045">Před <ph name="NUMBER_DEFAULT"/> hodinami</translation>
<translation id="815598010540052116">Posuv dolů</translation>
+<translation id="6808150112686056157">Média – zastavit</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Obnovit</translation>
<translation id="1243314992276662751">Nahrát</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Nápověda</translation>
+<translation id="6699343763173986273">Média – další skladba</translation>
<translation id="8226233771743600312">Nerušit jeden den</translation>
<translation id="7457942297256758195">Vymazat vše</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimalizovat</translation>
<translation id="6394627529324717982">Čárka</translation>
-<translation id="4469842253116033348">Deaktivovat oznámení z webu <ph name="SITE"/></translation>
<translation id="3036649622769666520">Otevřít soubory</translation>
<translation id="8328145009876646418">Levý okraj</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> s</translation>
diff --git a/chromium/ui/base/strings/ui_strings_da.xtb b/chromium/ui/base/strings/ui_strings_da.xtb
index abd0fe6edf9..8befca3e7e5 100644
--- a/chromium/ui/base/strings/ui_strings_da.xtb
+++ b/chromium/ui/base/strings/ui_strings_da.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Underretningcenter</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minutter tilbage</translation>
<translation id="5613020302032141669">Venstrepil</translation>
+<translation id="4971687151119236543">Medie: Forrige nummer</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Fil (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sek.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> timer</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/sek.</translation>
+<translation id="8394908167088220973">Medie: Afspil/Pause</translation>
<translation id="2148716181193084225">I dag</translation>
<translation id="7960078400008666149">Vil ikke forstyrres i en time</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> minutter siden</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Scroll til højre</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> timer tilbage</translation>
+<translation id="1413622004203049571">Deaktiver underretninger fra <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Top</translation>
<translation id="8331626408530291785">Scroll Up</translation>
-<translation id="4773379706300191099">Deaktiver underretninger fra <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Åbn fil</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> timer siden</translation>
<translation id="815598010540052116">Scroll Down</translation>
+<translation id="6808150112686056157">Medie: Stop</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Gendan</translation>
<translation id="1243314992276662751">Upload</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> minutter siden</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/sek.</translation>
<translation id="7649070708921625228">Hjælp</translation>
+<translation id="6699343763173986273">Medie: Næste nummer</translation>
<translation id="8226233771743600312">Vil ikke forstyrres i et døgn</translation>
<translation id="7457942297256758195">Ryd alle</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> dage siden</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimer</translation>
<translation id="6394627529324717982">Komma</translation>
-<translation id="4469842253116033348">Deaktiver meddelelser fra <ph name="SITE"/></translation>
<translation id="3036649622769666520">Åbn filer</translation>
<translation id="8328145009876646418">Venstre kant</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> sekunder</translation>
diff --git a/chromium/ui/base/strings/ui_strings_de.xtb b/chromium/ui/base/strings/ui_strings_de.xtb
index df63bb041ac..b2ba42282d1 100644
--- a/chromium/ui/base/strings/ui_strings_de.xtb
+++ b/chromium/ui/base/strings/ui_strings_de.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Benachrichtigungscenter</translation>
<translation id="7470933019269157899">Noch <ph name="NUMBER_DEFAULT"/> Minuten</translation>
<translation id="5613020302032141669">Linkspfeil</translation>
+<translation id="4971687151119236543">Medien – vorheriger Titel</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/>-Datei (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> Sekunden</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> Stunden</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Medien – Wiedergabe/Pause</translation>
<translation id="2148716181193084225">Heute</translation>
<translation id="7960078400008666149">1 Stunde nicht stören</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">BildAuf</translation>
<translation id="4588090240171750605">Nach rechts blättern</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> Stunde übrig</translation>
+<translation id="1413622004203049571">Benachrichtigungen von <ph name="NOTIFIER_NAME"/> deaktivieren</translation>
<translation id="2666092431469916601">Oben</translation>
<translation id="8331626408530291785">Nach oben blättern</translation>
-<translation id="4773379706300191099">Benachrichtigungen von <ph name="EXTENSION_NAME"/> deaktivieren</translation>
<translation id="7907591526440419938">Datei öffnen</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Vor <ph name="NUMBER_DEFAULT"/> Stunden</translation>
<translation id="815598010540052116">Nach unten blättern</translation>
+<translation id="6808150112686056157">Medien – Stopp</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Wiederherstellen</translation>
<translation id="1243314992276662751">Hochladen</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> Byte/s</translation>
<translation id="7649070708921625228">Hilfe</translation>
+<translation id="6699343763173986273">Medien – nächster Titel</translation>
<translation id="8226233771743600312">1 Tag nicht stören</translation>
<translation id="7457942297256758195">Alle löschen</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Verkleinern</translation>
<translation id="6394627529324717982">Komma</translation>
-<translation id="4469842253116033348">Benachrichtigungen von <ph name="SITE"/> deaktivieren</translation>
<translation id="3036649622769666520">Dateien öffnen</translation>
<translation id="8328145009876646418">Linker Rand</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> Sekunden</translation>
diff --git a/chromium/ui/base/strings/ui_strings_el.xtb b/chromium/ui/base/strings/ui_strings_el.xtb
index 7fbfbf0c735..3cb7bdfcfe1 100644
--- a/chromium/ui/base/strings/ui_strings_el.xtb
+++ b/chromium/ui/base/strings/ui_strings_el.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Κέντρο ειδοποιήσεων</translation>
<translation id="7470933019269157899">Υπολείπονται <ph name="NUMBER_DEFAULT"/> λεπτά</translation>
<translation id="5613020302032141669">Αριστερό βέλος</translation>
+<translation id="4971687151119236543">Προηγούμενο κομμάτι πολυμέσων</translation>
<translation id="8602707065186045623">Αρχείο <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> δευτερόλεπτα</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">Πλήκτρο F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ώρες</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Αναπαραγωγή/παύση πολυμέσων</translation>
<translation id="2148716181193084225">Σήμερα</translation>
<translation id="7960078400008666149">Μην ενοχλείτε για μία ώρα</translation>
<translation id="4373894838514502496">Πριν από <ph name="NUMBER_FEW"/> λεπτά</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Κύλιση δεξιά</translation>
<translation id="7414887922320653780">Υπολείπεται <ph name="NUMBER_ONE"/> ώρα</translation>
+<translation id="1413622004203049571">Απενεργοποίηση ειδοποιήσεων από <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Κορυφή</translation>
<translation id="8331626408530291785">Κύλιση επάνω</translation>
-<translation id="4773379706300191099">Απενεργοποίηση ειδοποιήσεων από <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Άνοιγμα Αρχείου</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Πριν από <ph name="NUMBER_DEFAULT"/> ώρες</translation>
<translation id="815598010540052116">Κύλιση κάτω</translation>
+<translation id="6808150112686056157">Διακοπή πολυμέσων</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Επαναφορά</translation>
<translation id="1243314992276662751">Μεταφόρτωση</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Πριν από <ph name="NUMBER_MANY"/> λεπτά</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Βοήθεια</translation>
+<translation id="6699343763173986273">Επόμενο κομμάτι πολυμέσων</translation>
<translation id="8226233771743600312">Μην ενοχλείτε για μία ημέρα</translation>
<translation id="7457942297256758195">Εκκαθάριση όλων</translation>
<translation id="822618367988303761">Πριν από <ph name="NUMBER_TWO"/> ημέρες</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Ελαχιστοποίηση</translation>
<translation id="6394627529324717982">Κόμμα</translation>
-<translation id="4469842253116033348">Απενεργοποίηση ειδοποιήσεων από τον ιστότοπο <ph name="SITE"/></translation>
<translation id="3036649622769666520">Άνοιγμα Αρχείων</translation>
<translation id="8328145009876646418">Αριστερή άκρη</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> δευτερόλεπτα</translation>
diff --git a/chromium/ui/base/strings/ui_strings_en-GB.xtb b/chromium/ui/base/strings/ui_strings_en-GB.xtb
index fbe4dbd26d6..c620e94f938 100644
--- a/chromium/ui/base/strings/ui_strings_en-GB.xtb
+++ b/chromium/ui/base/strings/ui_strings_en-GB.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Notification Centre</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minutes left</translation>
<translation id="5613020302032141669">Left Arrow</translation>
+<translation id="4971687151119236543">Media Previous Track</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> File (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> secs</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> hours</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Media Play/Pause</translation>
<translation id="2148716181193084225">Today</translation>
<translation id="7960078400008666149">Do not disturb for one hour</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Scroll Right</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> hour left</translation>
+<translation id="1413622004203049571">Disable notifications from <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Top</translation>
<translation id="8331626408530291785">Scroll Up</translation>
-<translation id="4773379706300191099">Disable notifications from <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Open File</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">Scroll Down</translation>
+<translation id="6808150112686056157">Media Stop</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restore</translation>
<translation id="1243314992276662751">Upload</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Help</translation>
+<translation id="6699343763173986273">Media Next Track</translation>
<translation id="8226233771743600312">Do not disturb for one day</translation>
<translation id="7457942297256758195">Clear All</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimise</translation>
<translation id="6394627529324717982">Comma</translation>
-<translation id="4469842253116033348">Disable notifications from <ph name="SITE"/></translation>
<translation id="3036649622769666520">Open Files</translation>
<translation id="8328145009876646418">Left Edge</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_es-419.xtb b/chromium/ui/base/strings/ui_strings_es-419.xtb
index 8ad1a3de438..d585d2676e8 100644
--- a/chromium/ui/base/strings/ui_strings_es-419.xtb
+++ b/chromium/ui/base/strings/ui_strings_es-419.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centro de notificaciones</translation>
<translation id="7470933019269157899">Faltan <ph name="NUMBER_DEFAULT"/> minutos.</translation>
<translation id="5613020302032141669">Flecha izquierda</translation>
+<translation id="4971687151119236543">Pista multimedia anterior</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Archivo (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> seg.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> horas</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Reproducir o pausar contenido multimedia</translation>
<translation id="2148716181193084225">Hoy</translation>
<translation id="7960078400008666149">No molestar durante una hora</translation>
<translation id="4373894838514502496">Hace <ph name="NUMBER_FEW"/> minutos</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">RePág</translation>
<translation id="4588090240171750605">Desplazar a la derecha</translation>
<translation id="7414887922320653780">Falta <ph name="NUMBER_ONE"/> hora</translation>
+<translation id="1413622004203049571">Inhabilitar notificaciones de <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Superior</translation>
<translation id="8331626408530291785">Desplazar hacia arriba</translation>
-<translation id="4773379706300191099">Inhabilitar las notificaciones de <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Abrir archivo</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Hace <ph name="NUMBER_DEFAULT"/> horas</translation>
<translation id="815598010540052116">Desplazar hacia abajo</translation>
+<translation id="6808150112686056157">Detener contenido multimedia</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restaurar</translation>
<translation id="1243314992276662751">Cargar</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Hace <ph name="NUMBER_MANY"/> minutos</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Ayuda</translation>
+<translation id="6699343763173986273">Pista multimedia siguiente</translation>
<translation id="8226233771743600312">No molestar durante un día</translation>
<translation id="7457942297256758195">Borrar todo</translation>
<translation id="822618367988303761">Hace <ph name="NUMBER_TWO"/> días</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimizar</translation>
<translation id="6394627529324717982">Coma</translation>
-<translation id="4469842253116033348">Inhabilitar las notificaciones desde <ph name="SITE"/></translation>
<translation id="3036649622769666520">Abrir archivos</translation>
<translation id="8328145009876646418">Borde izquierdo</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_es.xtb b/chromium/ui/base/strings/ui_strings_es.xtb
index 5394cc732bc..3e631195762 100644
--- a/chromium/ui/base/strings/ui_strings_es.xtb
+++ b/chromium/ui/base/strings/ui_strings_es.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centro de notificaciones</translation>
<translation id="7470933019269157899">Quedan <ph name="NUMBER_DEFAULT"/> minutos</translation>
<translation id="5613020302032141669">Flecha izquierda</translation>
+<translation id="4971687151119236543">Pista anterior multimedia</translation>
<translation id="8602707065186045623">Archivo <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> seg.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> horas</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Pausar/Reproducir contenido multimedia</translation>
<translation id="2148716181193084225">Hoy</translation>
<translation id="7960078400008666149">No molestar durante una hora</translation>
<translation id="4373894838514502496">hace <ph name="NUMBER_FEW"/> minutos</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">RePág</translation>
<translation id="4588090240171750605">Desplazar a la derecha</translation>
<translation id="7414887922320653780">Falta <ph name="NUMBER_ONE"/> hora</translation>
+<translation id="1413622004203049571">Inhabilitar notificaciones de <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Superior</translation>
<translation id="8331626408530291785">Desplazar hacia arriba</translation>
-<translation id="4773379706300191099">Inhabilitar notificaciones de <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Abrir archivo</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">hace <ph name="NUMBER_DEFAULT"/> horas</translation>
<translation id="815598010540052116">Desplazar hacia abajo</translation>
+<translation id="6808150112686056157">Detener contenido multimedia</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restaurar</translation>
<translation id="1243314992276662751">Subir</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">hace <ph name="NUMBER_MANY"/> minutos</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Ayuda</translation>
+<translation id="6699343763173986273">Siguiente pista multimedia</translation>
<translation id="8226233771743600312">No molestar durante un día</translation>
<translation id="7457942297256758195">Borrar todo</translation>
<translation id="822618367988303761">hace <ph name="NUMBER_TWO"/> días</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimizar</translation>
<translation id="6394627529324717982">Coma</translation>
-<translation id="4469842253116033348">Inhabilitar notificaciones de <ph name="SITE"/></translation>
<translation id="3036649622769666520">Abrir archivos</translation>
<translation id="8328145009876646418">Borde izquierdo</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> segundos</translation>
diff --git a/chromium/ui/base/strings/ui_strings_et.xtb b/chromium/ui/base/strings/ui_strings_et.xtb
index d5d9b6b63ab..3934ea29a88 100644
--- a/chromium/ui/base/strings/ui_strings_et.xtb
+++ b/chromium/ui/base/strings/ui_strings_et.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Märguannete keskus</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minutit on jäänud</translation>
<translation id="5613020302032141669">Vasaknool</translation>
+<translation id="4971687151119236543">Meediumi eelmine lugu</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Fail (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sekundit</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> tundi</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Meediumi esitamine/peatamine</translation>
<translation id="2148716181193084225">Täna</translation>
<translation id="7960078400008666149">Mitte segada üks tund</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> minutit tagasi</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Keri paremale</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> tundi jäänud</translation>
+<translation id="1413622004203049571">Keela märguanded: <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Üles</translation>
<translation id="8331626408530291785">Keri üles</translation>
-<translation id="4773379706300191099">Keela märguanded laiendusest <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Faili avamine</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> tundi tagasi</translation>
<translation id="815598010540052116">Keri alla</translation>
+<translation id="6808150112686056157">Meediumi peatamine</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Taasta</translation>
<translation id="1243314992276662751">Laadi üles</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> minutit tagasi</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Abi</translation>
+<translation id="6699343763173986273">Meediumi järgmine lugu</translation>
<translation id="8226233771743600312">Mitte segada üks päev</translation>
<translation id="7457942297256758195">Kustuta kõik</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> päeva tagasi</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimeeri</translation>
<translation id="6394627529324717982">Koma</translation>
-<translation id="4469842253116033348">Keela teated saidilt <ph name="SITE"/></translation>
<translation id="3036649622769666520">Failide avamine</translation>
<translation id="8328145009876646418">Vasak serv</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_fa.xtb b/chromium/ui/base/strings/ui_strings_fa.xtb
index 2cb91114128..62e36aae2af 100644
--- a/chromium/ui/base/strings/ui_strings_fa.xtb
+++ b/chromium/ui/base/strings/ui_strings_fa.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">مرکز اعلان</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> دقیقه باقیمانده</translation>
<translation id="5613020302032141669">پیکان چپ</translation>
+<translation id="4971687151119236543">آهنگ قبلی رسانه</translation>
<translation id="8602707065186045623">فایل <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> secs</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> hours</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> کیلوبایت/ثانیه</translation>
+<translation id="8394908167088220973">پخش/توقف موقت رسانه</translation>
<translation id="2148716181193084225">امروز</translation>
<translation id="7960078400008666149">یک ساعت مزاحم نشوید</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">پیمایش به راست</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> ساعت مانده</translation>
+<translation id="1413622004203049571">غیرفعال کردن اعلان‌ها از <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">بالا</translation>
<translation id="8331626408530291785">پیمایش به بالا</translation>
-<translation id="4773379706300191099">از کار انداختن اعلان‌های <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">باز کردن فایل</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> ساعت قبل</translation>
<translation id="815598010540052116">پیمایش به پایین</translation>
+<translation id="6808150112686056157">توقف رسانه</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">بازیابی</translation>
<translation id="1243314992276662751">آپلود</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> بایت/ثانیه</translation>
<translation id="7649070708921625228">راهنما</translation>
+<translation id="6699343763173986273">آهنگ بعدی رسانه</translation>
<translation id="8226233771743600312">یک روز مزاحم نشوید</translation>
<translation id="7457942297256758195">پاک کردن همه</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">کوچک کردن</translation>
<translation id="6394627529324717982">کاما</translation>
-<translation id="4469842253116033348">غیر فعال کردن اعلام های <ph name="SITE"/></translation>
<translation id="3036649622769666520">باز کردن فایل‌ها</translation>
<translation id="8328145009876646418">حاشیه چپ</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> ثانیه</translation>
diff --git a/chromium/ui/base/strings/ui_strings_fi.xtb b/chromium/ui/base/strings/ui_strings_fi.xtb
index a6b04bf63eb..73eae4fd3b1 100644
--- a/chromium/ui/base/strings/ui_strings_fi.xtb
+++ b/chromium/ui/base/strings/ui_strings_fi.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Ilmoituskeskus</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minuuttia jäljellä</translation>
<translation id="5613020302032141669">Nuoli vas.</translation>
+<translation id="4971687151119236543">Media: edellinen kappale</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/>-tiedosto (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sekuntia</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> tuntia</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kt/s</translation>
+<translation id="8394908167088220973">Media: toista/keskeytä</translation>
<translation id="2148716181193084225">Tänään</translation>
<translation id="7960078400008666149">Älä häiritse tuntiin</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Vieritä oikealle</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> tuntia jäljellä</translation>
+<translation id="1413622004203049571">Poista ilmoitukset käytöstä sovellukselta <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Yleisin</translation>
<translation id="8331626408530291785">Vieritä ylös</translation>
-<translation id="4773379706300191099">Poista ilmoitukset käytöstä laajennukselta <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Avaa tiedosto</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> tuntia sitten</translation>
<translation id="815598010540052116">Vieritä alas</translation>
+<translation id="6808150112686056157">Media: pysäytä</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Palauta</translation>
<translation id="1243314992276662751">Lähetä</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> t/s</translation>
<translation id="7649070708921625228">Ohje</translation>
+<translation id="6699343763173986273">Media: seuraava kappale</translation>
<translation id="8226233771743600312">Älä häiritse päivään</translation>
<translation id="7457942297256758195">Tyhjennä kaikki</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Pienennä</translation>
<translation id="6394627529324717982">Pilkku</translation>
-<translation id="4469842253116033348">Poista sivuston <ph name="SITE"/> ilmoitukset käytöstä</translation>
<translation id="3036649622769666520">Avaa tiedostot</translation>
<translation id="8328145009876646418">Vasen reuna</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_fil.xtb b/chromium/ui/base/strings/ui_strings_fil.xtb
index 5ef326400c3..31dbaeca296 100644
--- a/chromium/ui/base/strings/ui_strings_fil.xtb
+++ b/chromium/ui/base/strings/ui_strings_fil.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Notification Center</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> (na) minuto ang natitira</translation>
<translation id="5613020302032141669">KAliwang Arrow</translation>
+<translation id="4971687151119236543">Nakaraang Track ng Media</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> File (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> segundo</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> mga oras</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">I-Play/I-Pause ang Media</translation>
<translation id="2148716181193084225">Ngayon</translation>
<translation id="7960078400008666149">Huwag istorbohin sa loob ng isang oras</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> minuto ang nakalipas</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Mag-scroll Pakanan</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> natitirang oras</translation>
+<translation id="1413622004203049571">I-disable ang mga notification mula sa <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Tuktok</translation>
<translation id="8331626408530291785">Mag-scroll Pataas</translation>
-<translation id="4773379706300191099">I-disable ang mga notification mula sa <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Buksan ang File</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> na oras ang nakalipas</translation>
<translation id="815598010540052116">Mag-scroll Pababa</translation>
+<translation id="6808150112686056157">Media Ihinto</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Ipanumbalik</translation>
<translation id="1243314992276662751">I-upload</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> minuto ang nakalipas</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> (na) B/s</translation>
<translation id="7649070708921625228">Tulong</translation>
+<translation id="6699343763173986273">Susunod na Track ng Media</translation>
<translation id="8226233771743600312">Huwag istorbohin sa loob ng isang araw</translation>
<translation id="7457942297256758195">I-clear Lahat</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> araw ang nakalipas</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimize</translation>
<translation id="6394627529324717982">Kuwit</translation>
-<translation id="4469842253116033348">Huwag paganahin ang mga abiso mula sa <ph name="SITE"/></translation>
<translation id="3036649622769666520">Buksan ang Mga File</translation>
<translation id="8328145009876646418">Kalwang Edge</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> segundo</translation>
diff --git a/chromium/ui/base/strings/ui_strings_fr.xtb b/chromium/ui/base/strings/ui_strings_fr.xtb
index d6d48faca18..7c6cc69c636 100644
--- a/chromium/ui/base/strings/ui_strings_fr.xtb
+++ b/chromium/ui/base/strings/ui_strings_fr.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centre de notification</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minutes restantes</translation>
<translation id="5613020302032141669">Gauche</translation>
+<translation id="4971687151119236543">Contenu multimédia : titre précédent</translation>
<translation id="8602707065186045623">Fichier <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> secondes</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> heures</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> Ko/s</translation>
+<translation id="8394908167088220973">Contenu multimédia : lecture/pause</translation>
<translation id="2148716181193084225">Aujourd'hui</translation>
<translation id="7960078400008666149">Ne pas déranger pendant une heure</translation>
<translation id="4373894838514502496">il y a <ph name="NUMBER_FEW"/> minutes</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgPréc</translation>
<translation id="4588090240171750605">Défilement vers la droite</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> heure restante</translation>
+<translation id="1413622004203049571">Désactiver les notifications <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">En haut</translation>
<translation id="8331626408530291785">Défilement vers le haut</translation>
-<translation id="4773379706300191099">Désactiver les notifications de l'extension &quot;<ph name="EXTENSION_NAME"/>&quot;</translation>
<translation id="7907591526440419938">Ouvrir le fichier</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Échap</translation>
<translation id="2797524280730715045">il y a <ph name="NUMBER_DEFAULT"/> heures</translation>
<translation id="815598010540052116">Défilement vers le bas</translation>
+<translation id="6808150112686056157">Contenu multimédia : arrêt</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restaurer</translation>
<translation id="1243314992276662751">Importer</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> o/s</translation>
<translation id="7649070708921625228">Aide</translation>
+<translation id="6699343763173986273">Contenu multimédia : titre suivant</translation>
<translation id="8226233771743600312">Ne pas déranger pendant un jour</translation>
<translation id="7457942297256758195">Tout effacer</translation>
<translation id="822618367988303761">il y a <ph name="NUMBER_TWO"/> jours</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Réduire</translation>
<translation id="6394627529324717982">Virgule</translation>
-<translation id="4469842253116033348">Désactiver les notifications de <ph name="SITE"/></translation>
<translation id="3036649622769666520">Ouvrir les fichiers</translation>
<translation id="8328145009876646418">Côté gauche</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_gu.xtb b/chromium/ui/base/strings/ui_strings_gu.xtb
index 0cf8377e178..5a24f98cc94 100644
--- a/chromium/ui/base/strings/ui_strings_gu.xtb
+++ b/chromium/ui/base/strings/ui_strings_gu.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">સૂચના કેન્દ્ર</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> મિનિટ બાકી</translation>
<translation id="5613020302032141669">ડાબો એરો</translation>
+<translation id="4971687151119236543">મીડિયા પહેલાંનું ટ્રૅક</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ફાઇલ (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> મિનિટ પહેલા</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> સેકંડ</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> કલાક</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">મીડિયા ચલાવો/થોભાવો</translation>
<translation id="2148716181193084225">આજે</translation>
<translation id="7960078400008666149">એક કલાક માટે ખલેલ પાડશો નહીં</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">જમણે સ્ક્રોલ કરો</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> કલાક બાકી</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> તરફથી સૂચનાઓ અક્ષમ કરો</translation>
<translation id="2666092431469916601">ઉપર</translation>
<translation id="8331626408530291785">ઉપર સ્ક્રોલ કરો</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> થી સૂચનાઓને અક્ષમ કરો</translation>
<translation id="7907591526440419938">ફાઇલ ખોલો</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> દિવસ બાકી</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">નીચે સ્ક્રોલ કરો</translation>
+<translation id="6808150112686056157">મીડિયા સ્ટોપ</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> મિનિટ બાકી</translation>
<translation id="3157931365184549694">પુનઃસ્થાપિત કરો</translation>
<translation id="1243314992276662751">અપલોડ કરો</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">સહાય</translation>
+<translation id="6699343763173986273">મીડિયા આગલો ટ્રૅક</translation>
<translation id="8226233771743600312">એક દિવસ માટે ખલેલ પાડશો નહીં</translation>
<translation id="7457942297256758195">બધું સાફ કરો</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> દિવસ પહેલા</translation>
<translation id="5941711191222866238">નાનું કરો</translation>
<translation id="6394627529324717982">અલ્પવિરામ</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> તરફની સૂચનાઓ અક્ષમ કરો </translation>
<translation id="3036649622769666520">ફાઇલો ખોલો</translation>
<translation id="8328145009876646418">ડાબી કિનારી</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> સેકંડ</translation>
diff --git a/chromium/ui/base/strings/ui_strings_hi.xtb b/chromium/ui/base/strings/ui_strings_hi.xtb
index 3b842bc2126..6d03ce17e67 100644
--- a/chromium/ui/base/strings/ui_strings_hi.xtb
+++ b/chromium/ui/base/strings/ui_strings_hi.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">सूचना केंद्र</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> मिनट शेष</translation>
<translation id="5613020302032141669">बायां तीर</translation>
+<translation id="4971687151119236543">मीडिया पिछला ट्रैक</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> फ़ाइल (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> सेकंड</translation>
@@ -105,6 +106,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> घंटे</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">मीडिया चलाएं/रोकें</translation>
<translation id="2148716181193084225">आज</translation>
<translation id="7960078400008666149">एक घंटे तक परेशान न करें</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -115,20 +117,21 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">दाएं स्क्रॉल करें</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> घंटे शेष</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> से सूचनाएं अक्षम करें</translation>
<translation id="2666092431469916601">शीर्ष</translation>
<translation id="8331626408530291785">ऊपर स्क्रॉल करें</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> की सूचनाएं अक्षम करें</translation>
<translation id="7907591526440419938">फ़ाइल खोलें</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> घंटे पहले</translation>
<translation id="815598010540052116">नीचे स्क्रॉल करें</translation>
+<translation id="6808150112686056157">मीडिया रोकें</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">पुनर्स्थापित करें</translation>
<translation id="1243314992276662751">अपलोड करें</translation>
<translation id="50030952220075532"><ph name="NUMBER_ONE"/> दिन शेष</translation>
<translation id="8179976553408161302">प्रविष्ट करें</translation>
-<translation id="945522503751344254">फ़ीडबैक भेजें</translation>
+<translation id="945522503751344254">सुझाव भेजें</translation>
<translation id="9170848237812810038">&amp;पूर्ववत् करें</translation>
<translation id="1285266685456062655"><ph name="NUMBER_FEW"/> घंटे पहले</translation>
<translation id="6918245111648057970">प्रत्येक उपयोगकर्ता के लिए निम्न में से सूचनाओं की अनुमति दें:</translation>
@@ -161,6 +164,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">सहायता</translation>
+<translation id="6699343763173986273">मीडिया अगला ट्रैक</translation>
<translation id="8226233771743600312">एक दिन तक परेशान न करें</translation>
<translation id="7457942297256758195">सभी साफ़ करें</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> दिन पहले</translation>
@@ -180,7 +184,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> दिन पहले</translation>
<translation id="5941711191222866238">छोटा करें</translation>
<translation id="6394627529324717982">अल्पविराम</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> से सूचनाएं अक्षम करें</translation>
<translation id="3036649622769666520">फ़ाइलें खोलें</translation>
<translation id="8328145009876646418">बायां सिरा</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> सेकंड</translation>
diff --git a/chromium/ui/base/strings/ui_strings_hr.xtb b/chromium/ui/base/strings/ui_strings_hr.xtb
index a10b9321851..aa88cb0fdfc 100644
--- a/chromium/ui/base/strings/ui_strings_hr.xtb
+++ b/chromium/ui/base/strings/ui_strings_hr.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centar za obavijesti</translation>
<translation id="7470933019269157899">Preostalo minuta: <ph name="NUMBER_DEFAULT"/></translation>
<translation id="5613020302032141669">Strelica lijevo</translation>
+<translation id="4971687151119236543">Prethodni zapis Medija</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Datoteka (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252">Broj sekundi: <ph name="NUMBER_TWO"/></translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401">Sati: <ph name="NUMBER_MANY"/></translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Reproduciraj/pauziraj Medije</translation>
<translation id="2148716181193084225">Danas</translation>
<translation id="7960078400008666149">Ne ometaj jedan sat</translation>
<translation id="4373894838514502496">Prije <ph name="NUMBER_FEW"/> min</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Pomakni se desno</translation>
<translation id="7414887922320653780">Preostalo sati: <ph name="NUMBER_ONE"/></translation>
+<translation id="1413622004203049571">Onemogući obavijesti pošiljatelja <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Gornji</translation>
<translation id="8331626408530291785">Pomakni se gore</translation>
-<translation id="4773379706300191099">Onemogućivanje obavijesti proširenja <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Otvori datoteku</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Prije <ph name="NUMBER_DEFAULT"/> sati</translation>
<translation id="815598010540052116">Pomakni se dolje</translation>
+<translation id="6808150112686056157">Zaustavi Medije</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Vrati</translation>
<translation id="1243314992276662751">Prenesi</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Pomoć</translation>
+<translation id="6699343763173986273">Sljedeći zapis Medija</translation>
<translation id="8226233771743600312">Ne ometaj jedan dan</translation>
<translation id="7457942297256758195">Očisti sve</translation>
<translation id="822618367988303761">Prije <ph name="NUMBER_TWO"/> dana</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimiziraj</translation>
<translation id="6394627529324717982">Zarez</translation>
-<translation id="4469842253116033348">Onemogući obavijesti s web-lokacije <ph name="SITE"/></translation>
<translation id="3036649622769666520">Otvori datoteke</translation>
<translation id="8328145009876646418">Lijevi rub</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_hu.xtb b/chromium/ui/base/strings/ui_strings_hu.xtb
index 8266d2cede9..c48a91b34dc 100644
--- a/chromium/ui/base/strings/ui_strings_hu.xtb
+++ b/chromium/ui/base/strings/ui_strings_hu.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Értesítési központ</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> perc van hátra</translation>
<translation id="5613020302032141669">Bal nyíl</translation>
+<translation id="4971687151119236543">Előző szám</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> fájl (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> másodperc</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> óra</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Lejátszás/szüneteltetés</translation>
<translation id="2148716181193084225">Ma</translation>
<translation id="7960078400008666149">Ne zavarj egy óráig</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Görgetés jobbra</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> óra van hátra</translation>
+<translation id="1413622004203049571">A(z) <ph name="NOTIFIER_NAME"/> értesítéseinek kikapcsolása</translation>
<translation id="2666092431469916601">Felülre</translation>
<translation id="8331626408530291785">Görgetés felfelé</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> értesítéseinek kikapcsolása</translation>
<translation id="7907591526440419938">Fájl megnyitása</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> órája</translation>
<translation id="815598010540052116">Görgetés lefelé</translation>
+<translation id="6808150112686056157">Leállítás</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Visszaállítás</translation>
<translation id="1243314992276662751">Feltöltés</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Súgó</translation>
+<translation id="6699343763173986273">Következő szám</translation>
<translation id="8226233771743600312">Ne zavarj egy napig</translation>
<translation id="7457942297256758195">Összes törlése</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Kicsinyítés</translation>
<translation id="6394627529324717982">Vessző</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> értesítéseinek kikapcsolása</translation>
<translation id="3036649622769666520">Fájlok megnyitása</translation>
<translation id="8328145009876646418">Bal sarok</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> másodperc</translation>
diff --git a/chromium/ui/base/strings/ui_strings_id.xtb b/chromium/ui/base/strings/ui_strings_id.xtb
index 3175df4f9eb..747a5c8d8d0 100644
--- a/chromium/ui/base/strings/ui_strings_id.xtb
+++ b/chromium/ui/base/strings/ui_strings_id.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Pusat Pemberitahuan</translation>
<translation id="7470933019269157899">Tersisa <ph name="NUMBER_DEFAULT"/> menit</translation>
<translation id="5613020302032141669">Panah Kiri</translation>
+<translation id="4971687151119236543">Lacak Media Sebelumnya</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> File (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> detik</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> jam</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/dtk</translation>
+<translation id="8394908167088220973">Putar/Jeda Media</translation>
<translation id="2148716181193084225">Hari ini</translation>
<translation id="7960078400008666149">Jangan ganggu selama satu jam</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mnt. yang lalu</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Gulir ke Kanan</translation>
<translation id="7414887922320653780">Tersisa <ph name="NUMBER_ONE"/> jam</translation>
+<translation id="1413622004203049571">Nonaktifkan pemberitahuan dari <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Atas</translation>
<translation id="8331626408530291785">Gulir ke Atas</translation>
-<translation id="4773379706300191099">Nonaktifkan pemberitahuan dari <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Buka File</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> jam yang lalu</translation>
<translation id="815598010540052116">Gulir ke Bawah</translation>
+<translation id="6808150112686056157">Hentikan Media</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Pulihkan</translation>
<translation id="1243314992276662751">Unggah</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mnt. yang lalu</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/dtk</translation>
<translation id="7649070708921625228">Bantuan</translation>
+<translation id="6699343763173986273">Lacak Media Berikutnya</translation>
<translation id="8226233771743600312">Jangan ganggu selama satu hari</translation>
<translation id="7457942297256758195">Hapus Semua</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> hari yang lalu</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Perkecil</translation>
<translation id="6394627529324717982">Koma</translation>
-<translation id="4469842253116033348">Nonaktifkan pemberitahuan dari <ph name="SITE"/></translation>
<translation id="3036649622769666520">Buka File</translation>
<translation id="8328145009876646418">Tepi Kiri</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> detik</translation>
diff --git a/chromium/ui/base/strings/ui_strings_it.xtb b/chromium/ui/base/strings/ui_strings_it.xtb
index 003abcf6928..3df1779e5c3 100644
--- a/chromium/ui/base/strings/ui_strings_it.xtb
+++ b/chromium/ui/base/strings/ui_strings_it.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centro notifiche</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minuti rimanenti</translation>
<translation id="5613020302032141669">Freccia sinistra</translation>
+<translation id="4971687151119236543">Traccia precedente contenuti multimediali</translation>
<translation id="8602707065186045623">File <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sec.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ore</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Play/Pausa contenuti multimediali</translation>
<translation id="2148716181193084225">Oggi</translation>
<translation id="7960078400008666149">Non disturbare per un'ora</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> minuti fa</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PGSU</translation>
<translation id="4588090240171750605">Scorri a destra</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> ora rimanente</translation>
+<translation id="1413622004203049571">Disabilita notifiche da <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">In alto</translation>
<translation id="8331626408530291785">Scorri verso l'alto</translation>
-<translation id="4773379706300191099">Disattiva notifiche da <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Apri file</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> ore fa</translation>
<translation id="815598010540052116">Scorri verso il basso</translation>
+<translation id="6808150112686056157">Interrompi contenuti multimediali</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Ripristina</translation>
<translation id="1243314992276662751">Carica</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> minuti fa</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Guida</translation>
+<translation id="6699343763173986273">Traccia successiva contenuti multimediali</translation>
<translation id="8226233771743600312">Non disturbare per un giorno</translation>
<translation id="7457942297256758195">Cancella tutto</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> giorni fa</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Riduci a icona</translation>
<translation id="6394627529324717982">Virgola</translation>
-<translation id="4469842253116033348">Disabilita notifiche da <ph name="SITE"/></translation>
<translation id="3036649622769666520">Apri file</translation>
<translation id="8328145009876646418">Margine sinistro</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_iw.xtb b/chromium/ui/base/strings/ui_strings_iw.xtb
index 80040340423..7f640838a2b 100644
--- a/chromium/ui/base/strings/ui_strings_iw.xtb
+++ b/chromium/ui/base/strings/ui_strings_iw.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">מרכז התראות</translation>
<translation id="7470933019269157899">נותרו <ph name="NUMBER_DEFAULT"/> דקות</translation>
<translation id="5613020302032141669">חץ לשמאל</translation>
+<translation id="4971687151119236543">רצועה קודמת במדיה</translation>
<translation id="8602707065186045623">קובץ <ph name="SAVEAS_EXTENSION_TYPE"/> (<ph name="SAVEAS_EXTENSION_NAME"/>.)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> שניות</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> שעות</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s‎</translation>
+<translation id="8394908167088220973">הפעלה/השהיה של המדיה</translation>
<translation id="2148716181193084225">היום</translation>
<translation id="7960078400008666149">נא לא להפריע למשך שעה</translation>
<translation id="4373894838514502496">לפני <ph name="NUMBER_FEW"/> דקות</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">גלול ימינה</translation>
<translation id="7414887922320653780">נותרו <ph name="NUMBER_ONE"/> שעות</translation>
+<translation id="1413622004203049571">השבת הודעות מאת <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">למעלה</translation>
<translation id="8331626408530291785">גלול למעלה</translation>
-<translation id="4773379706300191099">השבת התראות מהתוסף <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">פתח קובץ</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">לפני <ph name="NUMBER_DEFAULT"/> שעות</translation>
<translation id="815598010540052116">גלול למטה</translation>
+<translation id="6808150112686056157">עצור מדיה</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">שחזר</translation>
<translation id="1243314992276662751">העלה</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">לפני <ph name="NUMBER_MANY"/> דקות</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">עזרה</translation>
+<translation id="6699343763173986273">הרצועה הבאה במדיה</translation>
<translation id="8226233771743600312">נא לא להפריע ליום אחד</translation>
<translation id="7457942297256758195">נקה הכל</translation>
<translation id="822618367988303761">לפני <ph name="NUMBER_TWO"/> ימים</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">מזער</translation>
<translation id="6394627529324717982">פסיק</translation>
-<translation id="4469842253116033348">השבת הודעות מ-<ph name="SITE"/></translation>
<translation id="3036649622769666520">פתח קבצים</translation>
<translation id="8328145009876646418">קצה שמאלי</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> שניות</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ja.xtb b/chromium/ui/base/strings/ui_strings_ja.xtb
index 06b3c8cb05d..5dc08123b1d 100644
--- a/chromium/ui/base/strings/ui_strings_ja.xtb
+++ b/chromium/ui/base/strings/ui_strings_ja.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">通知センター</translation>
<translation id="7470933019269157899">残り <ph name="NUMBER_DEFAULT"/> 分</translation>
<translation id="5613020302032141669">左矢印キー</translation>
+<translation id="4971687151119236543">メディアの前のトラック</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ファイル (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> 秒</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> 時間</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/秒</translation>
+<translation id="8394908167088220973">メディアの再生/一時停止</translation>
<translation id="2148716181193084225">今日</translation>
<translation id="7960078400008666149">通知を 1 時間ミュート</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> 分前</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PageUp</translation>
<translation id="4588090240171750605">右にスクロール</translation>
<translation id="7414887922320653780">残り <ph name="NUMBER_ONE"/> 時間</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> からの通知を無効にする</translation>
<translation id="2666092431469916601">一番上</translation>
<translation id="8331626408530291785">上にスクロール</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> の通知を無効にする</translation>
<translation id="7907591526440419938">ファイルを開く</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> 時間前</translation>
<translation id="815598010540052116">下にスクロール</translation>
+<translation id="6808150112686056157">メディアの停止</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">復元</translation>
<translation id="1243314992276662751">アップロード</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> 分前</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/秒</translation>
<translation id="7649070708921625228">ヘルプ</translation>
+<translation id="6699343763173986273">メディアの次のトラック</translation>
<translation id="8226233771743600312">通知を 1 日間ミュート</translation>
<translation id="7457942297256758195">すべて消去</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> 日前</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">最小化</translation>
<translation id="6394627529324717982">カンマ</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> からの通知を無効にする</translation>
<translation id="3036649622769666520">ファイルを開く</translation>
<translation id="8328145009876646418">左端</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> 秒</translation>
diff --git a/chromium/ui/base/strings/ui_strings_kn.xtb b/chromium/ui/base/strings/ui_strings_kn.xtb
index a5cc7982f4c..421ecec6388 100644
--- a/chromium/ui/base/strings/ui_strings_kn.xtb
+++ b/chromium/ui/base/strings/ui_strings_kn.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">ಅಧಿಸೂಚನೆಯ ಕೇಂದ್ರ</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> ನಿಮಿಷಗಳು ಉಳಿದಿವೆ</translation>
<translation id="5613020302032141669">ಎಡ ಬಾಣದ ಗುರುತು</translation>
+<translation id="4971687151119236543">ಮೀಡಿಯಾದ ಹಿಂದಿನ ಟ್ರ್ಯಾಕ್</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ಫೈಲ್ (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> ಸೆಕೆಂಡುಗಳು</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ಗಂಟೆಗಳು</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s </translation>
+<translation id="8394908167088220973">ಮೀಡಿಯಾ ಪ್ಲೇ/ವಿರಾಮ</translation>
<translation id="2148716181193084225">ಇಂದು</translation>
<translation id="7960078400008666149">ಒಂದು ಗಂಟೆಯ ಕಾಲ ಅಡಚಣೆ ಮಾಡಬೇಡಿ</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">ಬಲಕ್ಕೆ ಸ್ಕ್ರೋಲ್ ಮಾಡಿ</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> ಗಂಟೆಗಳು ಉಳಿದಿದೆ</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> ಅವರ ಅಧಿಸೂಚನೆಗಳನ್ನು ನಿಷ್ಕ್ರಿಯಗೊಳಿಸಿ</translation>
<translation id="2666092431469916601">ಮೇಲೆ</translation>
<translation id="8331626408530291785">ಮೇಲೆ ಸ್ಕ್ರೋಲ್ ಮಾಡು</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> ನಿಂದ ಅಧಿಸೂಚನೆಗಳನ್ನು ನಿಷ್ಕ್ರಿಯಗೊಳಿಸಿ</translation>
<translation id="7907591526440419938">ಫೈಲ್ ತೆರೆಯಿರಿ</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">ಕೆಳಗೆ ಸ್ಕ್ರೋಲ್ ಮಾಡು</translation>
+<translation id="6808150112686056157">ಮೀಡಿಯಾ ನಿಲುಗಡೆ</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">ಪುನಃಸ್ಥಾಪನೆ</translation>
<translation id="1243314992276662751">ಅಪ್‌ಲೋಡ್</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">ಸಹಾಯ</translation>
+<translation id="6699343763173986273">ಮೀಡಿಯಾದ ಮುಂದಿನ ಟ್ರ್ಯಾಕ್</translation>
<translation id="8226233771743600312">ಒಂದು ದಿನದವರೆಗೆ ಅಡಚಣೆ ಮಾಡಬೇಡಿ</translation>
<translation id="7457942297256758195">ಎಲ್ಲವನ್ನೂ ತೆರವುಗೊಳಿಸಿ</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">ಕುಗ್ಗಿಸು</translation>
<translation id="6394627529324717982">ಅರ್ಧವಿರಾಮ</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> ನಿಂದ ಪ್ರಕಟಣೆ‌ಗಳನ್ನು ನಿಷ್ಕ್ರಿಯಗೊಳಿಸಿ</translation>
<translation id="3036649622769666520">ಫೈಲ್‌ಗಳನ್ನು ತೆರೆಯಿರಿ</translation>
<translation id="8328145009876646418">ಎಡ ಬದಿ</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> ಸೆಕೆಂಡುಗಳು</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ko.xtb b/chromium/ui/base/strings/ui_strings_ko.xtb
index 2403ee083e9..3794c67ca3b 100644
--- a/chromium/ui/base/strings/ui_strings_ko.xtb
+++ b/chromium/ui/base/strings/ui_strings_ko.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">알림 센터</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/>분 남음</translation>
<translation id="5613020302032141669">왼쪽 화살표</translation>
+<translation id="4971687151119236543">미디어 이전 트랙</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> 파일(.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/>초</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/>시간</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/>KB/초</translation>
+<translation id="8394908167088220973">미디어 재생/일시중지</translation>
<translation id="2148716181193084225">오늘</translation>
<translation id="7960078400008666149">1시간 동안 알림 일시중지</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/>분 전</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PageUp</translation>
<translation id="4588090240171750605">오른쪽 스크롤</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/>시간 남음</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/>의 알림 사용 중지</translation>
<translation id="2666092431469916601">맨 위</translation>
<translation id="8331626408530291785">위로 스크롤</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> 알림 사용 안함</translation>
<translation id="7907591526440419938">파일 열기</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/>시간 전</translation>
<translation id="815598010540052116">아래로 스크롤</translation>
+<translation id="6808150112686056157">미디어 중지</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">복구</translation>
<translation id="1243314992276662751">업로드</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/>분 전</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/>B/s</translation>
<translation id="7649070708921625228">도움말</translation>
+<translation id="6699343763173986273">미디어 다음 트랙</translation>
<translation id="8226233771743600312">하루 동안 알림 일시중지</translation>
<translation id="7457942297256758195">모두 지우기</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/>일 전</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">최소화</translation>
<translation id="6394627529324717982">콤마</translation>
-<translation id="4469842253116033348"><ph name="SITE"/>의 알림을 표시 안함</translation>
<translation id="3036649622769666520">파일 열기</translation>
<translation id="8328145009876646418">왼쪽 모서리</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/>초</translation>
diff --git a/chromium/ui/base/strings/ui_strings_lt.xtb b/chromium/ui/base/strings/ui_strings_lt.xtb
index afe0ced61dd..f36210e5675 100644
--- a/chromium/ui/base/strings/ui_strings_lt.xtb
+++ b/chromium/ui/base/strings/ui_strings_lt.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Pranešimų centras</translation>
<translation id="7470933019269157899">Liko <ph name="NUMBER_DEFAULT"/> min.</translation>
<translation id="5613020302032141669">Rodyklė į kairę</translation>
+<translation id="4971687151119236543">Ankstesnis medijos takelis</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> failas (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sek.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> valandos (-ų)</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB per sek.</translation>
+<translation id="8394908167088220973">Leisti / pristabdyti mediją</translation>
<translation id="2148716181193084225">Šiandien</translation>
<translation id="7960078400008666149">Netrukdyti vieną valandą</translation>
<translation id="4373894838514502496">Prieš <ph name="NUMBER_FEW"/> min.</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Slinkti į dešinę</translation>
<translation id="7414887922320653780">liko <ph name="NUMBER_ONE"/> val.</translation>
+<translation id="1413622004203049571">Išjungti pranešimus nuo <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Į viršų</translation>
<translation id="8331626408530291785">Slinkti į viršų</translation>
-<translation id="4773379706300191099">Neleisti „<ph name="EXTENSION_NAME"/>“ pranešimų.</translation>
<translation id="7907591526440419938">Atidaryti failą</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Prieš <ph name="NUMBER_DEFAULT"/> val.</translation>
<translation id="815598010540052116">Slinkti žemyn</translation>
+<translation id="6808150112686056157">Sustabdyti mediją</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Atkurti</translation>
<translation id="1243314992276662751">Įkelti</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Prieš <ph name="NUMBER_MANY"/> min.</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Žinynas</translation>
+<translation id="6699343763173986273">Kitas medijos takelis</translation>
<translation id="8226233771743600312">Netrukdyti vieną dieną</translation>
<translation id="7457942297256758195">Išvalyti viską</translation>
<translation id="822618367988303761">Prieš <ph name="NUMBER_TWO"/> dienas</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Sumažinti</translation>
<translation id="6394627529324717982">Kablelis</translation>
-<translation id="4469842253116033348">Neleisti <ph name="SITE"/> plėtinių</translation>
<translation id="3036649622769666520">Atidaryti failus</translation>
<translation id="8328145009876646418">Kairysis kraštas</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> sek.</translation>
diff --git a/chromium/ui/base/strings/ui_strings_lv.xtb b/chromium/ui/base/strings/ui_strings_lv.xtb
index 65622f1a695..6de184fa0fe 100644
--- a/chromium/ui/base/strings/ui_strings_lv.xtb
+++ b/chromium/ui/base/strings/ui_strings_lv.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Paziņojumu centrs</translation>
<translation id="7470933019269157899">Atlikušas <ph name="NUMBER_DEFAULT"/> minūtes</translation>
<translation id="5613020302032141669">Kreisā bulta</translation>
+<translation id="4971687151119236543">Multivide — iepriekšējā dziesma</translation>
<translation id="8602707065186045623">Fails <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sekundes</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">taustiņš F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> stundas</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Multivide — atskaņot/apturēt</translation>
<translation id="2148716181193084225">Šodien</translation>
<translation id="7960078400008666149">Netraucēt stundu</translation>
<translation id="4373894838514502496">Pirms <ph name="NUMBER_FEW"/> minūtēm</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">Augšup</translation>
<translation id="4588090240171750605">Ritināt pa labi</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> stundas atlikušas</translation>
+<translation id="1413622004203049571">Atspējot paziņojumu saņemšanu no: <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Augša</translation>
<translation id="8331626408530291785">Ritināt augšup</translation>
-<translation id="4773379706300191099">Atspējot paziņojumu saņemšanu no: <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Atvērt failu</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Atsolis</translation>
<translation id="2797524280730715045">Pirms <ph name="NUMBER_DEFAULT"/> stundām</translation>
<translation id="815598010540052116">Ritināt lejup</translation>
+<translation id="6808150112686056157">Multivide — pārtraukt</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Atjaunot</translation>
<translation id="1243314992276662751">Augšupielādēt</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Palīdzība</translation>
+<translation id="6699343763173986273">Multivide — nākamā dziesma</translation>
<translation id="8226233771743600312">Netraucēt dienu</translation>
<translation id="7457942297256758195">Notīrīt visu</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimizēt</translation>
<translation id="6394627529324717982">Komats</translation>
-<translation id="4469842253116033348">Atspējot vietnes <ph name="SITE"/> paziņojumus</translation>
<translation id="3036649622769666520">Atvērt failus</translation>
<translation id="8328145009876646418">Kreisā mala</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ml.xtb b/chromium/ui/base/strings/ui_strings_ml.xtb
index 13bb6e29370..a960d411b0b 100644
--- a/chromium/ui/base/strings/ui_strings_ml.xtb
+++ b/chromium/ui/base/strings/ui_strings_ml.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">അറിയിപ്പ് കേന്ദ്രം</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> മിനിറ്റ് ശേഷിക്കുന്നു</translation>
<translation id="5613020302032141669">ഇടത് ആരോ അടയാളം</translation>
+<translation id="4971687151119236543">മുമ്പത്തെ മീഡിയ ട്രാക്ക്</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ഫയല്‍ (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> സെക്കന്റ്</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> മണിക്കൂര്‍</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">മീഡിയ പ്ലേ ചെയ്യുക/താൽക്കാലികമായി നിർത്തുക</translation>
<translation id="2148716181193084225">ഇന്ന്</translation>
<translation id="7960078400008666149">ഒരു മണിക്കൂർ നേരത്തേക്ക് ശല്യപ്പെടുത്തരുത്</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">വലത്തോട്ട് സ്ക്രോള്‍ ചെയ്യുക</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> മണിക്കൂര്‍ ശേഷിക്കുന്നു</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> എന്നതിൽ നിന്നുള്ള അറിയിപ്പുകൾ പ്രവർത്തനരഹിതമാക്കുക</translation>
<translation id="2666092431469916601">മുകളിലേക്ക്</translation>
<translation id="8331626408530291785">മുകളിലേക്ക് സ്ക്രോള്‍ ചെയ്യൂ</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> എന്നതിൽ നിന്നുള്ള അറിയിപ്പുകൾ പ്രവർത്തനരഹിതമാക്കുക</translation>
<translation id="7907591526440419938">ഫയല്‍ തുറക്കുക</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">താഴേക്ക് സ്ക്രോള്‍ചെയ്യൂ</translation>
+<translation id="6808150112686056157">മീഡിയ ‌നിർത്തുക</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">പുനഃസ്ഥാപിക്കുക</translation>
<translation id="1243314992276662751">അപ്‌ലോഡുചെയ്യുക</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">സഹായം</translation>
+<translation id="6699343763173986273">അടുത്ത മീഡിയ ട്രാക്ക്</translation>
<translation id="8226233771743600312">ഒരു ദിവസത്തേക്ക് ശല്യപ്പെടുത്തരുത്</translation>
<translation id="7457942297256758195">എല്ലാം മായ്‌ക്കുക</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">ചെറുതാക്കുക‍</translation>
<translation id="6394627529324717982">കോമ</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> ല്‍‌ നിന്നുള്ള വിജ്ഞാപനങ്ങള്‍‌ അപ്രാപ്‌തമാക്കുക</translation>
<translation id="3036649622769666520">ഫയലുകള്‍‌ തുറക്കുക</translation>
<translation id="8328145009876646418">ഇടത് അഗ്രം</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> സെക്കൻഡ്</translation>
diff --git a/chromium/ui/base/strings/ui_strings_mr.xtb b/chromium/ui/base/strings/ui_strings_mr.xtb
index a21baf7ae77..d8f026de83d 100644
--- a/chromium/ui/base/strings/ui_strings_mr.xtb
+++ b/chromium/ui/base/strings/ui_strings_mr.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">सूचना केंद्र</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> मिनिटे शिल्लक</translation>
<translation id="5613020302032141669">Left Arrow</translation>
+<translation id="4971687151119236543">मीडिया मागील ट्रॅक</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> फाइल (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> से</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> तास</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">मीडिया प्ले करा/विराम द्या</translation>
<translation id="2148716181193084225">आज</translation>
<translation id="7960078400008666149">एक तास व्यत्यय आणू नका</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">उजवे स्क्रोल करा</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> तास बाकी</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> वरील सूचना अक्षम करा</translation>
<translation id="2666092431469916601">शीर्ष</translation>
<translation id="8331626408530291785">वर स्क्रोल करा</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> वरील सूचना अक्षम करा</translation>
<translation id="7907591526440419938">फाइल उघडा</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">खाली स्क्रोल करा</translation>
+<translation id="6808150112686056157">मीडिया थांबवा</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">पुनर्संचयित करा</translation>
<translation id="1243314992276662751">अपलोड करा</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">मदत</translation>
+<translation id="6699343763173986273">मीडिया पुढील ट्रॅक</translation>
<translation id="8226233771743600312">एक दिवस व्यत्यय आणू नका</translation>
<translation id="7457942297256758195">सर्व साफ करा</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">लहान करा</translation>
<translation id="6394627529324717982">स्वल्पविराम</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> कडील सूचना अक्षम करा</translation>
<translation id="3036649622769666520">फायली उघडा</translation>
<translation id="8328145009876646418">डावे काठ</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> सेकंद</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ms.xtb b/chromium/ui/base/strings/ui_strings_ms.xtb
index 51fbc90f5bd..68a15bbfc46 100644
--- a/chromium/ui/base/strings/ui_strings_ms.xtb
+++ b/chromium/ui/base/strings/ui_strings_ms.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Pusat Pemberitahuan</translation>
<translation id="7470933019269157899">Tinggal <ph name="NUMBER_DEFAULT"/> minit</translation>
<translation id="5613020302032141669">Anak Panah Kiri</translation>
+<translation id="4971687151119236543">Lagu Media Sebelumnya</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Fail (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> minit yang lalu</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> saat</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> jam</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Main/Jeda Media</translation>
<translation id="2148716181193084225">Hari ini</translation>
<translation id="7960078400008666149">Jangan ganggu selama sejam</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> minit yang lalu</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">AtsHlmn</translation>
<translation id="4588090240171750605">Tatal ke Kanan</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> jam lagi</translation>
+<translation id="1413622004203049571">Lumpuhkan pemberitahuan daripada <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Atas</translation>
<translation id="8331626408530291785">Tatal Ke Atas</translation>
-<translation id="4773379706300191099">Lumpuhkan pemberitahuan daripada <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Buka Fail</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> hari lagi</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> jam lalu</translation>
<translation id="815598010540052116">Tatal Ke Bawah</translation>
+<translation id="6808150112686056157">Media Berhenti</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> minit lagi</translation>
<translation id="3157931365184549694">Pulihkan</translation>
<translation id="1243314992276662751">Muat naik</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> minit yang lalu</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Bantuan</translation>
+<translation id="6699343763173986273">Lagu Media Seterusnya</translation>
<translation id="8226233771743600312">Jangan ganggu selama sehari</translation>
<translation id="7457942297256758195">Kosongkan Semua</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> hari yang lalu</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> hari yang lalu</translation>
<translation id="5941711191222866238">Minimumkan</translation>
<translation id="6394627529324717982">Koma</translation>
-<translation id="4469842253116033348">Lumpuhkan pemberitahuan daripada <ph name="SITE"/></translation>
<translation id="3036649622769666520">Buka Fail</translation>
<translation id="8328145009876646418">Tepi Kiri</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> saat</translation>
diff --git a/chromium/ui/base/strings/ui_strings_nl.xtb b/chromium/ui/base/strings/ui_strings_nl.xtb
index bced1229f7e..d4b81d423b5 100644
--- a/chromium/ui/base/strings/ui_strings_nl.xtb
+++ b/chromium/ui/base/strings/ui_strings_nl.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Meldingscentrum</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minuten resterend</translation>
<translation id="5613020302032141669">Pijl-links</translation>
+<translation id="4971687151119236543">Vorige track voor media</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/>-bestand (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> seconden</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> uur</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Media afspelen/onderbreken</translation>
<translation id="2148716181193084225">Vandaag</translation>
<translation id="7960078400008666149">Een uur niet storen</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> minuten geleden</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Naar rechts bladeren</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> uur resterend</translation>
+<translation id="1413622004203049571">Meldingen van <ph name="NOTIFIER_NAME"/> uitschakelen</translation>
<translation id="2666092431469916601">Boven</translation>
<translation id="8331626408530291785">Omhoog bladeren</translation>
-<translation id="4773379706300191099">Meldingen van <ph name="EXTENSION_NAME"/> uitschakelen</translation>
<translation id="7907591526440419938">Bestand openen</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> uur geleden</translation>
<translation id="815598010540052116">Omlaag bladeren</translation>
+<translation id="6808150112686056157">Media stoppen</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Herstellen</translation>
<translation id="1243314992276662751">Uploaden</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> minuten geleden</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Help</translation>
+<translation id="6699343763173986273">Volgende track voor media</translation>
<translation id="8226233771743600312">Een dag niet storen</translation>
<translation id="7457942297256758195">Alles wissen</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> dagen geleden</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimaliseren</translation>
<translation id="6394627529324717982">Komma</translation>
-<translation id="4469842253116033348">Meldingen van <ph name="SITE"/> uitschakelen</translation>
<translation id="3036649622769666520">Bestanden openen</translation>
<translation id="8328145009876646418">Linkerzijde</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconden</translation>
diff --git a/chromium/ui/base/strings/ui_strings_no.xtb b/chromium/ui/base/strings/ui_strings_no.xtb
index 5f2cac11a18..6e4a12f93d3 100644
--- a/chromium/ui/base/strings/ui_strings_no.xtb
+++ b/chromium/ui/base/strings/ui_strings_no.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Varselsenter</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minutter igjen</translation>
<translation id="5613020302032141669">Pil venstre</translation>
+<translation id="4971687151119236543">Media – forrige spor</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Fil (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sekunder</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> timer</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB per sek</translation>
+<translation id="8394908167088220973">Media – spill av / pause</translation>
<translation id="2148716181193084225">I dag</translation>
<translation id="7960078400008666149">Ikke forstyrr i én time</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Rull mot høyre</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> time igjen</translation>
+<translation id="1413622004203049571">Deaktiver varsler fra <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Topp</translation>
<translation id="8331626408530291785">Rull opp</translation>
-<translation id="4773379706300191099">Deaktiver varsler fra <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Åpne filen</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">For <ph name="NUMBER_DEFAULT"/> timer siden</translation>
<translation id="815598010540052116">Rull ned</translation>
+<translation id="6808150112686056157">Media – stopp</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Gjenopprett</translation>
<translation id="1243314992276662751">Last opp</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B per sek</translation>
<translation id="7649070708921625228">Hjelp</translation>
+<translation id="6699343763173986273">Media – neste spor</translation>
<translation id="8226233771743600312">Ikke forstyrr i en dag</translation>
<translation id="7457942297256758195">Fjern alle</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimer</translation>
<translation id="6394627529324717982">Komma</translation>
-<translation id="4469842253116033348">Deaktiver varslinger fra <ph name="SITE"/></translation>
<translation id="3036649622769666520">Åpne filer</translation>
<translation id="8328145009876646418">Venstre kant</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> sekunder</translation>
diff --git a/chromium/ui/base/strings/ui_strings_pl.xtb b/chromium/ui/base/strings/ui_strings_pl.xtb
index 43aa6a4bd6b..4051dd44f15 100644
--- a/chromium/ui/base/strings/ui_strings_pl.xtb
+++ b/chromium/ui/base/strings/ui_strings_pl.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centrum powiadomień</translation>
<translation id="7470933019269157899">Pozostało <ph name="NUMBER_DEFAULT"/> minut</translation>
<translation id="5613020302032141669">Strzałka w lewo</translation>
+<translation id="4971687151119236543">Poprzedni utwór multimedialny</translation>
<translation id="8602707065186045623">Plik <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> s</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> godz.</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Odtwórz/wstrzymaj multimedia</translation>
<translation id="2148716181193084225">Dzisiaj</translation>
<translation id="7960078400008666149">Nie przeszkadzać przez godzinę</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> min temu</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Przewiń w prawo</translation>
<translation id="7414887922320653780">Pozostała <ph name="NUMBER_ONE"/> godzina</translation>
+<translation id="1413622004203049571">Wyłącz powiadomienia z <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Do góry</translation>
<translation id="8331626408530291785">Przewiń w górę</translation>
-<translation id="4773379706300191099">Wyłącz powiadomienia z <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Otwórz plik</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> godz. temu</translation>
<translation id="815598010540052116">Przewiń w dół</translation>
+<translation id="6808150112686056157">Zatrzymaj multimedia</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Przywróć</translation>
<translation id="1243314992276662751">Prześlij</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Pomoc</translation>
+<translation id="6699343763173986273">Następny utwór multimedialny</translation>
<translation id="8226233771743600312">Nie przeszkadzać przez jeden dzień</translation>
<translation id="7457942297256758195">Wyczyść wszystkie</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> dni temu</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimalizuj</translation>
<translation id="6394627529324717982">Przecinek</translation>
-<translation id="4469842253116033348">Wyłącz powiadomienia z witryny <ph name="SITE"/></translation>
<translation id="3036649622769666520">Otwórz pliki</translation>
<translation id="8328145009876646418">Krawędź po lewej</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_pt-BR.xtb b/chromium/ui/base/strings/ui_strings_pt-BR.xtb
index 90d7f8a3951..5472366e9a4 100644
--- a/chromium/ui/base/strings/ui_strings_pt-BR.xtb
+++ b/chromium/ui/base/strings/ui_strings_pt-BR.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Central de Notificações</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minutos restantes</translation>
<translation id="5613020302032141669">Seta para a esquerda</translation>
+<translation id="4971687151119236543">Faixa anterior da mídia</translation>
<translation id="8602707065186045623">Arquivo <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> s</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> horas</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Reproduzir/pausar mídia</translation>
<translation id="2148716181193084225">Hoje</translation>
<translation id="7960078400008666149">Não perturbe por uma hora</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Percorrer à direita</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> hora restante</translation>
+<translation id="1413622004203049571">Desativar notificações de <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Parte superior</translation>
<translation id="8331626408530291785">Percorrer para cima</translation>
-<translation id="4773379706300191099">Desativar notificações de <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Abrir arquivo</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> horas atrás</translation>
<translation id="815598010540052116">Percorrer para baixo</translation>
+<translation id="6808150112686056157">Parar mídia</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restaurar</translation>
<translation id="1243314992276662751">Fazer upload</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Ajuda</translation>
+<translation id="6699343763173986273">Próxima faixa da mídia</translation>
<translation id="8226233771743600312">Não perturbe por um dia</translation>
<translation id="7457942297256758195">Limpar tudo</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimizar</translation>
<translation id="6394627529324717982">Vírgula</translation>
-<translation id="4469842253116033348">Desativar notificações de <ph name="SITE"/></translation>
<translation id="3036649622769666520">Abrir arquivos</translation>
<translation id="8328145009876646418">Borda esquerda</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> segundos</translation>
diff --git a/chromium/ui/base/strings/ui_strings_pt-PT.xtb b/chromium/ui/base/strings/ui_strings_pt-PT.xtb
index 76369e75a2e..5f633635103 100644
--- a/chromium/ui/base/strings/ui_strings_pt-PT.xtb
+++ b/chromium/ui/base/strings/ui_strings_pt-PT.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centro de Notificações</translation>
<translation id="7470933019269157899">Faltam <ph name="NUMBER_DEFAULT"/> minutos</translation>
<translation id="5613020302032141669">Seta para a esquerda</translation>
+<translation id="4971687151119236543">Faixa anterior de multimédia</translation>
<translation id="8602707065186045623">Ficheiro <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> seg.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> horas</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Reproduzir/interromper multimédia</translation>
<translation id="2148716181193084225">Hoje</translation>
<translation id="7960078400008666149">Não incomodar durante uma hora</translation>
<translation id="4373894838514502496">Há <ph name="NUMBER_FEW"/> min.</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Deslocar-se para a direita</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> hora restante</translation>
+<translation id="1413622004203049571">Desativar notificações de <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Parte superior</translation>
<translation id="8331626408530291785">Deslocar-se para cima</translation>
-<translation id="4773379706300191099">Desativar notificações de <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Abrir ficheiro</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Há <ph name="NUMBER_DEFAULT"/> horas</translation>
<translation id="815598010540052116">Deslocar-se para baixo</translation>
+<translation id="6808150112686056157">Parar multimédia</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Restaurar</translation>
<translation id="1243314992276662751">Carregar</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Há <ph name="NUMBER_MANY"/> min.</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Ajuda</translation>
+<translation id="6699343763173986273">Faixa seguinte de multimédia</translation>
<translation id="8226233771743600312">Não incomodar durante um dia</translation>
<translation id="7457942297256758195">Limpar Tudo</translation>
<translation id="822618367988303761">Há <ph name="NUMBER_TWO"/> dias</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimizar</translation>
<translation id="6394627529324717982">Vírgula</translation>
-<translation id="4469842253116033348">Desactivar notificações de <ph name="SITE"/></translation>
<translation id="3036649622769666520">Abrir ficheiros</translation>
<translation id="8328145009876646418">Margem esquerda</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> segundos</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ro.xtb b/chromium/ui/base/strings/ui_strings_ro.xtb
index 4f1ed1ae442..b2d57a05223 100644
--- a/chromium/ui/base/strings/ui_strings_ro.xtb
+++ b/chromium/ui/base/strings/ui_strings_ro.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centrul pentru notificări</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minute rămase</translation>
<translation id="5613020302032141669">Săgeata spre stânga</translation>
+<translation id="4971687151119236543">Melodia anterioară din conținutul media</translation>
<translation id="8602707065186045623">Fișier <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918">Cu <ph name="NUMBER_ZERO"/> minute în urmă</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> secunde</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ore</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KO/s</translation>
+<translation id="8394908167088220973">Redați/întrerupeți conținutul media</translation>
<translation id="2148716181193084225">Astăzi</translation>
<translation id="7960078400008666149">Nu deranja o oră</translation>
<translation id="4373894838514502496">Cu <ph name="NUMBER_FEW"/> minute în urmă</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp (o pagină mai sus)</translation>
<translation id="4588090240171750605">Derulați spre dreapta</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> oră rămasă</translation>
+<translation id="1413622004203049571">Dezactivați notificările de la <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Sus</translation>
<translation id="8331626408530291785">Derulați în sus</translation>
-<translation id="4773379706300191099">Dezactivați notificările de la <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Deschideți fișierul</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> zile rămase</translation>
<translation id="1293699935367580298">Esc (Ieșiți)</translation>
<translation id="2797524280730715045">Cu <ph name="NUMBER_DEFAULT"/> (de) ore în urmă</translation>
<translation id="815598010540052116">Derulați în jos</translation>
+<translation id="6808150112686056157">Opriți conținutul media</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> minute rămase</translation>
<translation id="3157931365184549694">Restabiliți</translation>
<translation id="1243314992276662751">Încărcați</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Cu <ph name="NUMBER_MANY"/> (de) minute în urmă</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> O/s</translation>
<translation id="7649070708921625228">Ajutor</translation>
+<translation id="6699343763173986273">Melodia următoare din conținutul media</translation>
<translation id="8226233771743600312">Nu deranja o zi</translation>
<translation id="7457942297256758195">Ștergeți-le pe toate</translation>
<translation id="822618367988303761">Cu <ph name="NUMBER_TWO"/> zile în urmă</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496">Cu <ph name="NUMBER_ZERO"/> zile în urmă</translation>
<translation id="5941711191222866238">Minimizați</translation>
<translation id="6394627529324717982">Virgulă</translation>
-<translation id="4469842253116033348">Dezactivați notificările de la <ph name="SITE"/></translation>
<translation id="3036649622769666520">Deschideți fișierele</translation>
<translation id="8328145009876646418">Marginea stângă</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> secunde</translation>
diff --git a/chromium/ui/base/strings/ui_strings_ru.xtb b/chromium/ui/base/strings/ui_strings_ru.xtb
index 32dfd2c2fd1..dd7f2c37ac2 100644
--- a/chromium/ui/base/strings/ui_strings_ru.xtb
+++ b/chromium/ui/base/strings/ui_strings_ru.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Центр оповещений</translation>
<translation id="7470933019269157899">Осталось <ph name="NUMBER_DEFAULT"/> минут</translation>
<translation id="5613020302032141669">Стрелка влево</translation>
+<translation id="4971687151119236543">Предыдущий трек</translation>
<translation id="8602707065186045623">Файл <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> сек.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ч.</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> КБ/с</translation>
+<translation id="8394908167088220973">Воспроизведение/пауза</translation>
<translation id="2148716181193084225">Сегодня</translation>
<translation id="7960078400008666149">Не беспокоить (1 час)</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> мин. назад</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Прокрутка вправо</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> ч.</translation>
+<translation id="1413622004203049571">Отключить оповещения от <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Наверх</translation>
<translation id="8331626408530291785">Прокрутка вверх</translation>
-<translation id="4773379706300191099">Отключить оповещения от <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Открытие файла</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> ч. назад</translation>
<translation id="815598010540052116">Прокрутка вниз</translation>
+<translation id="6808150112686056157">Остановить</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Восстановить</translation>
<translation id="1243314992276662751">Загрузить</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> Б/с</translation>
<translation id="7649070708921625228">Справка</translation>
+<translation id="6699343763173986273">Следующий трек</translation>
<translation id="8226233771743600312">Не беспокоить (1 день)</translation>
<translation id="7457942297256758195">Очистить все</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Свернуть</translation>
<translation id="6394627529324717982">Запятая</translation>
-<translation id="4469842253116033348">Отключить уведомления с этого адреса: <ph name="SITE"/></translation>
<translation id="3036649622769666520">Открытие файлов</translation>
<translation id="8328145009876646418">Левый край</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> сек.</translation>
diff --git a/chromium/ui/base/strings/ui_strings_sk.xtb b/chromium/ui/base/strings/ui_strings_sk.xtb
index 00fc533fcfb..0996629ec1c 100644
--- a/chromium/ui/base/strings/ui_strings_sk.xtb
+++ b/chromium/ui/base/strings/ui_strings_sk.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Centrum upozornení</translation>
<translation id="7470933019269157899">Zostáva <ph name="NUMBER_DEFAULT"/> minút</translation>
<translation id="5613020302032141669">Šípka doľava</translation>
+<translation id="4971687151119236543">Média – predchádzajúca stopa</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> Súbor (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252">Počet sekúnd: <ph name="NUMBER_TWO"/></translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401">Počet hodín: <ph name="NUMBER_MANY"/></translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/s</translation>
+<translation id="8394908167088220973">Média – prehrať / pozastaviť</translation>
<translation id="2148716181193084225">Dnes</translation>
<translation id="7960078400008666149">Nerušiť jednu hodinu</translation>
<translation id="4373894838514502496">Pred <ph name="NUMBER_FEW"/> min</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Rolovať doprava</translation>
<translation id="7414887922320653780">Zostáva <ph name="NUMBER_ONE"/> hodina</translation>
+<translation id="1413622004203049571">Zakázať upozornenia od <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Vrch</translation>
<translation id="8331626408530291785">Rolovať nahor</translation>
-<translation id="4773379706300191099">Vypnúť prijímanie upozornení od rozšírenia <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Otvoriť súbor</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Pred <ph name="NUMBER_DEFAULT"/> hodinami</translation>
<translation id="815598010540052116">Rolovať nadol</translation>
+<translation id="6808150112686056157">Médiá – zastaviť</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Obnoviť</translation>
<translation id="1243314992276662751">Odovzdať</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Pomocník</translation>
+<translation id="6699343763173986273">Média – ďalšia stopa</translation>
<translation id="8226233771743600312">Nerušiť jeden deň</translation>
<translation id="7457942297256758195">Vymazať všetky</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimalizovať</translation>
<translation id="6394627529324717982">Čiarka</translation>
-<translation id="4469842253116033348">Zakázať upozornenia z webových stránok <ph name="SITE"/></translation>
<translation id="3036649622769666520">Otvoriť súbory</translation>
<translation id="8328145009876646418">Ľavý okraj</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> sekundy</translation>
diff --git a/chromium/ui/base/strings/ui_strings_sl.xtb b/chromium/ui/base/strings/ui_strings_sl.xtb
index 6f811ed4d2b..a49f23ce958 100644
--- a/chromium/ui/base/strings/ui_strings_sl.xtb
+++ b/chromium/ui/base/strings/ui_strings_sl.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Središče za obvestila</translation>
<translation id="7470933019269157899">še <ph name="NUMBER_DEFAULT"/> min</translation>
<translation id="5613020302032141669">Puščica levo</translation>
+<translation id="4971687151119236543">Prejšnja skladba</translation>
<translation id="8602707065186045623">Datoteka <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sek</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ur</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Ustavitev/začasna ustavitev</translation>
<translation id="2148716181193084225">Danes</translation>
<translation id="7960078400008666149">Ne moti eno uro</translation>
<translation id="4373894838514502496">Pred <ph name="NUMBER_FEW"/> min</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Pomik desno</translation>
<translation id="7414887922320653780">še <ph name="NUMBER_ONE"/> ura</translation>
+<translation id="1413622004203049571">Izklop obvestil za <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Na vrh</translation>
<translation id="8331626408530291785">Pomik gor</translation>
-<translation id="4773379706300191099">Onemogoči obvestila aplikacije <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Odpri datoteko</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Pred <ph name="NUMBER_DEFAULT"/> h</translation>
<translation id="815598010540052116">Pomik dol</translation>
+<translation id="6808150112686056157">Ustavitev</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Obnovi</translation>
<translation id="1243314992276662751">Prenesi</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497">Pred <ph name="NUMBER_MANY"/> min</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Pomoč</translation>
+<translation id="6699343763173986273">Naslednja skladba</translation>
<translation id="8226233771743600312">Ne moti en dan</translation>
<translation id="7457942297256758195">Izbriši vse</translation>
<translation id="822618367988303761">Pred <ph name="NUMBER_TWO"/> dnevoma</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Pomanjšaj</translation>
<translation id="6394627529324717982">Vejica</translation>
-<translation id="4469842253116033348">Onemogoči obvestila spletnega mesta <ph name="SITE"/></translation>
<translation id="3036649622769666520">Odpri datoteke</translation>
<translation id="8328145009876646418">Levi rob</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> sekundi</translation>
diff --git a/chromium/ui/base/strings/ui_strings_sr.xtb b/chromium/ui/base/strings/ui_strings_sr.xtb
index e036fd1c3d6..c84c2d5f675 100644
--- a/chromium/ui/base/strings/ui_strings_sr.xtb
+++ b/chromium/ui/base/strings/ui_strings_sr.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Центар за обавештења</translation>
<translation id="7470933019269157899">Преостало је <ph name="NUMBER_DEFAULT"/> минута</translation>
<translation id="5613020302032141669">Стрелица налево</translation>
+<translation id="4971687151119236543">Претходна песма медија</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> датотека (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> сек.</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401">Сати: <ph name="NUMBER_MANY"/></translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Пуштање/паузирање медија</translation>
<translation id="2148716181193084225">Данас</translation>
<translation id="7960078400008666149">Не узнемиравај у периоду од сат времена</translation>
<translation id="4373894838514502496">Пре <ph name="NUMBER_FEW"/> минута</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">Page Up</translation>
<translation id="4588090240171750605">Помери надесно</translation>
<translation id="7414887922320653780">Преостао <ph name="NUMBER_ONE"/> сат</translation>
+<translation id="1413622004203049571">Онемогући обавештења од <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Врх</translation>
<translation id="8331626408530291785">Помери нагоре</translation>
-<translation id="4773379706300191099">Онемогући обавештења из додатка <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Отварање датотеке</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Пре <ph name="NUMBER_DEFAULT"/> сата</translation>
<translation id="815598010540052116">Помери надоле</translation>
+<translation id="6808150112686056157">Заустављање медија</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Поново отвори</translation>
<translation id="1243314992276662751">Отпреми</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Помоћ</translation>
+<translation id="6699343763173986273">Следећа песма медија</translation>
<translation id="8226233771743600312">Не узнемиравај у периоду од једног дана</translation>
<translation id="7457942297256758195">Обриши све</translation>
<translation id="822618367988303761">Пре <ph name="NUMBER_TWO"/> дана</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Смањи</translation>
<translation id="6394627529324717982">Зарез</translation>
-<translation id="4469842253116033348">Онемогући обавештења са <ph name="SITE"/></translation>
<translation id="3036649622769666520">Отварање датотека</translation>
<translation id="8328145009876646418">Лева ивица</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> секунде</translation>
diff --git a/chromium/ui/base/strings/ui_strings_sv.xtb b/chromium/ui/base/strings/ui_strings_sv.xtb
index d8de713c599..3beabc978d1 100644
--- a/chromium/ui/base/strings/ui_strings_sv.xtb
+++ b/chromium/ui/base/strings/ui_strings_sv.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Meddelandecenter</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> minuter kvar</translation>
<translation id="5613020302032141669">Vänsterpil</translation>
+<translation id="4971687151119236543">Föregående spår</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/>-fil (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> sekunder</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> timmar</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> kB/sek</translation>
+<translation id="8394908167088220973">Spela upp/Pausa</translation>
<translation id="2148716181193084225">Idag</translation>
<translation id="7960078400008666149">Stör inte i en timme</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Rulla åt höger</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> timmar kvar</translation>
+<translation id="1413622004203049571">Inaktivera aviseringar från <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Överst</translation>
<translation id="8331626408530291785">Rulla uppåt</translation>
-<translation id="4773379706300191099">Inaktivera meddelanden från <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Öppna fil</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">För <ph name="NUMBER_DEFAULT"/> timmar sedan</translation>
<translation id="815598010540052116">Rulla nedåt</translation>
+<translation id="6808150112686056157">Stoppa</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Återställ</translation>
<translation id="1243314992276662751">Överför</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/sek</translation>
<translation id="7649070708921625228">Hjälp</translation>
+<translation id="6699343763173986273">Nästa spår</translation>
<translation id="8226233771743600312">Stör inte i en dag</translation>
<translation id="7457942297256758195">Ta bort alla</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Minimera</translation>
<translation id="6394627529324717982">Komma</translation>
-<translation id="4469842253116033348">Inaktivera meddelanden från <ph name="SITE"/></translation>
<translation id="3036649622769666520">Öppna filer</translation>
<translation id="8328145009876646418">Vänsterkant</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> sekunder</translation>
diff --git a/chromium/ui/base/strings/ui_strings_sw.xtb b/chromium/ui/base/strings/ui_strings_sw.xtb
index 95cdd9bf1f6..efee106b110 100644
--- a/chromium/ui/base/strings/ui_strings_sw.xtb
+++ b/chromium/ui/base/strings/ui_strings_sw.xtb
@@ -11,8 +11,9 @@
<translation id="1209866192426315618">zimesalia dakika <ph name="NUMBER_DEFAULT"/></translation>
<translation id="1801827354178857021">Kikomo</translation>
<translation id="1190609913194133056">Kituo cha Arifa</translation>
-<translation id="7470933019269157899">Dakika <ph name="NUMBER_DEFAULT"/> zinasalia</translation>
+<translation id="7470933019269157899">Zimesalia dakika <ph name="NUMBER_DEFAULT"/></translation>
<translation id="5613020302032141669">Mshale Kushoto</translation>
+<translation id="4971687151119236543">Wimbo wa Awali wa Media</translation>
<translation id="8602707065186045623">Faili ya <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918">dakika <ph name="NUMBER_ZERO"/> zilizopita</translation>
<translation id="7121570032414343252">zimesalia sekunde <ph name="NUMBER_TWO"/></translation>
@@ -32,7 +33,7 @@
<translation id="8666066831007952346">zimesalia siku <ph name="NUMBER_TWO"/></translation>
<translation id="6390842777729054533">zimesalia sekunde <ph name="NUMBER_ZERO"/></translation>
<translation id="3909791450649380159">&amp;Kata</translation>
-<translation id="2560788951337264832">Dakika <ph name="NUMBER_ZERO"/> zinasalia</translation>
+<translation id="2560788951337264832">Zimesalia dakika <ph name="NUMBER_ZERO"/></translation>
<translation id="688711909580084195">Ukurasa wa Wavuti usio na Kichwa</translation>
<translation id="3353284378027041011">siku <ph name="NUMBER_FEW"/> zilizopita</translation>
<translation id="5076340679995252485">&amp;Bandika</translation>
@@ -70,7 +71,7 @@
<translation id="4988273303304146523">siku <ph name="NUMBER_DEFAULT"/> zilizopita</translation>
<translation id="8428213095426709021">Mipangilio</translation>
<translation id="2497284189126895209">Faili zote</translation>
-<translation id="7487278341251176613">Dakika <ph name="NUMBER_TWO"/> zinasalia</translation>
+<translation id="7487278341251176613">Zimesalia dakika <ph name="NUMBER_TWO"/></translation>
<translation id="5110450810124758964">siku <ph name="NUMBER_ONE"/> iliyopita</translation>
<translation id="2820806154655529776">sekunde <ph name="NUMBER_ONE"/></translation>
<translation id="7814458197256864873">&amp;Nakili</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401">saa <ph name="NUMBER_MANY"/></translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Cheza Media/Sitisha</translation>
<translation id="2148716181193084225">Leo</translation>
<translation id="7960078400008666149">Usinisumbue kwa saa moja</translation>
<translation id="4373894838514502496">dakika <ph name="NUMBER_FEW"/> zilizopita</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Sogeza Kulia</translation>
<translation id="7414887922320653780">limesalia saa <ph name="NUMBER_ONE"/></translation>
+<translation id="1413622004203049571">Zima arifa kutoka <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Ya Juu</translation>
<translation id="8331626408530291785">Sogeza Juu</translation>
-<translation id="4773379706300191099">Zima arifa kutoka <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Fungua Faili</translation>
<translation id="2864069933652346933">zimesalia siku <ph name="NUMBER_ZERO"/></translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045">Saa <ph name="NUMBER_DEFAULT"/> zilizopita</translation>
<translation id="815598010540052116">Sogeza Chini</translation>
+<translation id="6808150112686056157">Simamisha Media</translation>
<translation id="1308727876662951186">zimesalia dakika <ph name="NUMBER_ZERO"/></translation>
<translation id="3157931365184549694">Rejesha</translation>
<translation id="1243314992276662751">Pakia</translation>
@@ -132,7 +135,7 @@
<translation id="1285266685456062655">Saa <ph name="NUMBER_FEW"/> zilizopita</translation>
<translation id="6918245111648057970">Ruhusu arifa kutoka kwa wafuatao kwa kila mtumiaji:</translation>
<translation id="5489830104927132166">Sekunde <ph name="NUMBER_ONE"/></translation>
-<translation id="3994835489895548312">Dakika <ph name="NUMBER_MANY"/> zinasalia</translation>
+<translation id="3994835489895548312">Zimesalia dakika <ph name="NUMBER_MANY"/></translation>
<translation id="6358975074282722691">sekunde <ph name="NUMBER_TWO"/> zilizopita</translation>
<translation id="520299402983819650">PB <ph name="QUANTITY"/></translation>
<translation id="2983818520079887040">Mipangilio...</translation>
@@ -154,11 +157,12 @@
<translation id="4860787810836767172">sekunde <ph name="NUMBER_FEW"/> zilizopita</translation>
<translation id="2297836609126180313"><ph name="QUANTITY"/> TB/s</translation>
<translation id="6956540737482608074">Dakika <ph name="NUMBER_ZERO"/></translation>
-<translation id="1858722859751911017">Dakika <ph name="NUMBER_FEW"/> zinasalia</translation>
+<translation id="1858722859751911017">Zimesalia dakika <ph name="NUMBER_FEW"/></translation>
<translation id="6040143037577758943">Funga</translation>
<translation id="1101671447232096497">dakika <ph name="NUMBER_MANY"/> zilizopita</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">Usaidizi</translation>
+<translation id="6699343763173986273">Wimbo Unaofuata kwenye Media</translation>
<translation id="8226233771743600312">Usinisumbue kwa siku moja</translation>
<translation id="7457942297256758195">Futa Zote</translation>
<translation id="822618367988303761">siku <ph name="NUMBER_TWO"/> zilizopita</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496">siku <ph name="NUMBER_ZERO"/> zilizopita</translation>
<translation id="5941711191222866238">Punguza</translation>
<translation id="6394627529324717982">Koma</translation>
-<translation id="4469842253116033348">Lemaza arifa kutoka <ph name="SITE"/></translation>
<translation id="3036649622769666520">Fungua Mafaili</translation>
<translation id="8328145009876646418">Ncha ya Kushoto</translation>
<translation id="7372005818821648611">Sekunde <ph name="NUMBER_TWO"/></translation>
diff --git a/chromium/ui/base/strings/ui_strings_ta.xtb b/chromium/ui/base/strings/ui_strings_ta.xtb
index 008279fb712..ab43f69fe72 100644
--- a/chromium/ui/base/strings/ui_strings_ta.xtb
+++ b/chromium/ui/base/strings/ui_strings_ta.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">அறிவிப்பு மையம்</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> நிமிடங்கள் உள்ளன</translation>
<translation id="5613020302032141669">இடது அம்பு</translation>
+<translation id="4971687151119236543">ஊடகத்தின் முந்தைய டிராக்</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/>கோப்பு(.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> வினாடிகள்</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> மணிநேரம்</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> கி.பை./வி</translation>
+<translation id="8394908167088220973">ஊடகத்தை இயக்கு/இடைநிறுத்து</translation>
<translation id="2148716181193084225">இன்று</translation>
<translation id="7960078400008666149">ஒரு மணிநேரத்திற்குத் தொந்தரவு செய்ய வேண்டாம்</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">வலப்புறம் உருட்டு</translation>
<translation id="7414887922320653780">இன்னும் <ph name="NUMBER_ONE"/> மணிநேரம் உள்ளது</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> இடமிருந்து வரும் அறிவிப்புகளை முடக்கு</translation>
<translation id="2666092431469916601">மேலே</translation>
<translation id="8331626408530291785">மேலே உருட்டு</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> இலிருந்து வரும் அறிவிப்புகளை முடக்கு</translation>
<translation id="7907591526440419938">கோப்பைத் திற</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">கீழே உருட்டு</translation>
+<translation id="6808150112686056157">ஊடகத்தை நிறுத்து</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">மீட்டமை</translation>
<translation id="1243314992276662751">பதிவேற்று</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> பை/வி</translation>
<translation id="7649070708921625228">உதவி</translation>
+<translation id="6699343763173986273">ஊடகத்தின் அடுத்த டிராக்</translation>
<translation id="8226233771743600312">ஒரு நாள் தொந்தரவு செய்ய வேண்டாம்</translation>
<translation id="7457942297256758195">அனைத்தையும் அழி</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">சிறிதாக்கு</translation>
<translation id="6394627529324717982">கமா</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> இலிருந்து வரும் அறிவிப்புகளை முடக்கு</translation>
<translation id="3036649622769666520">கோப்புகளைத் திற</translation>
<translation id="8328145009876646418">இடதுபுற முனை</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> வினாடிகள்</translation>
diff --git a/chromium/ui/base/strings/ui_strings_te.xtb b/chromium/ui/base/strings/ui_strings_te.xtb
index e94d3eba4b1..bd65f556886 100644
--- a/chromium/ui/base/strings/ui_strings_te.xtb
+++ b/chromium/ui/base/strings/ui_strings_te.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">నోటిఫికేషన్ కేంద్రం</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> నిమిషాలు మిగిలి ఉన్నాయి</translation>
<translation id="5613020302032141669">ఎడమ బాణం</translation>
+<translation id="4971687151119236543">మీడియా మునుపటి ట్రాక్</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> ఫైల్ (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> సెకన్లు</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> గంటలు</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/సె</translation>
+<translation id="8394908167088220973">మీడియా ప్లే/పాజ్</translation>
<translation id="2148716181193084225">ఈ రోజు</translation>
<translation id="7960078400008666149">ఒక గంటపాటు అంతరాయం కలిగించవద్దు</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">కుడికి స్క్రోల్ చెయ్యి</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> గంటలు మిగిలా యి</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> నుండి వచ్చే నోటిఫికేషన్‌లను నిలిపివేయి</translation>
<translation id="2666092431469916601">పైన</translation>
<translation id="8331626408530291785">పైకి స్క్రోల్ చెయ్యి</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> నుండి నోటిఫికేషన్‌లను నిలిపివేయి</translation>
<translation id="7907591526440419938">ఫైల్‌ను తెరువు</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> hours ago</translation>
<translation id="815598010540052116">క్రిందికి స్క్రోల్ చేయి</translation>
+<translation id="6808150112686056157">మీడియా ఆపివేయి</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">పునరుద్ధరించు</translation>
<translation id="1243314992276662751">అప్‌లోడ్ చేయి</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">సహాయం</translation>
+<translation id="6699343763173986273">మీడియా తదుపరి ట్రాక్</translation>
<translation id="8226233771743600312">ఒక రోజుపాటు అంతరాయం కలిగించవద్దు</translation>
<translation id="7457942297256758195">అన్నీ క్లియర్ చేయి</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">కనిష్టీకరించు</translation>
<translation id="6394627529324717982">కామా</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> నుండి ప్రకటనలను ఆపివెయ్యి</translation>
<translation id="3036649622769666520">ఫైళ్ళను తెరువు</translation>
<translation id="8328145009876646418">ఎడమ హద్దు</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> సెకన్లు</translation>
diff --git a/chromium/ui/base/strings/ui_strings_th.xtb b/chromium/ui/base/strings/ui_strings_th.xtb
index 4ebb6112e4e..13a7accff80 100644
--- a/chromium/ui/base/strings/ui_strings_th.xtb
+++ b/chromium/ui/base/strings/ui_strings_th.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">ศูนย์การแจ้งเตือน</translation>
<translation id="7470933019269157899">เหลือ <ph name="NUMBER_DEFAULT"/> นาที</translation>
<translation id="5613020302032141669">ลูกศรซ้าย</translation>
+<translation id="4971687151119236543">แทร็กก่อนหน้าของสื่อ</translation>
<translation id="8602707065186045623">ไฟล์ <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> วินาที</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> ชั่วโมง</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/วินาที</translation>
+<translation id="8394908167088220973">เล่น/หยุดสื่อชั่วคราว</translation>
<translation id="2148716181193084225">วันนี้</translation>
<translation id="7960078400008666149">ห้ามรบกวนเป็นเวลาหนึ่งชั่วโมง</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> นาทีที่ผ่านมา</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">เลื่อนทางขวา</translation>
<translation id="7414887922320653780">เหลือ <ph name="NUMBER_ONE"/> ชั่วโมง</translation>
+<translation id="1413622004203049571">ปิดการแจ้งเตือนจาก <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">ด้านบน</translation>
<translation id="8331626408530291785">เลื่อนขึ้น</translation>
-<translation id="4773379706300191099">ปิดการแจ้งเตือนจาก <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">เปิดไฟล์</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> ชั่วโมงที่ผ่านมา</translation>
<translation id="815598010540052116">เลื่อนลง</translation>
+<translation id="6808150112686056157">หยุดสื่อ</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">คืนค่า</translation>
<translation id="1243314992276662751">อัปโหลด</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> นาทีที่ผ่านมา</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/วินาที</translation>
<translation id="7649070708921625228">ช่วยเหลือ</translation>
+<translation id="6699343763173986273">แทร็กถัดไปของสื่อ</translation>
<translation id="8226233771743600312">ห้ามรบกวนเป็นเวลาหนึ่งวัน</translation>
<translation id="7457942297256758195">ล้างทั้งหมด</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> วันที่ผ่านมา</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">ย่อ</translation>
<translation id="6394627529324717982">จุลภาค</translation>
-<translation id="4469842253116033348">ปิดการใช้งานการแจ้งเตือนจาก <ph name="SITE"/></translation>
<translation id="3036649622769666520">เปิดไฟล์</translation>
<translation id="8328145009876646418">ขอบซ้าย</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_tr.xtb b/chromium/ui/base/strings/ui_strings_tr.xtb
index b3b02cb551c..1d76aa7f9e2 100644
--- a/chromium/ui/base/strings/ui_strings_tr.xtb
+++ b/chromium/ui/base/strings/ui_strings_tr.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Bildirim Merkezi</translation>
<translation id="7470933019269157899"><ph name="NUMBER_DEFAULT"/> dakika kaldı</translation>
<translation id="5613020302032141669">Sol Ok</translation>
+<translation id="4971687151119236543">Medya Önceki Parça</translation>
<translation id="8602707065186045623">Dosyayı <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> saniye</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> saat</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/sn</translation>
+<translation id="8394908167088220973">Medyayı Oynat/Duraklat</translation>
<translation id="2148716181193084225">Bugün</translation>
<translation id="7960078400008666149">Bir saat süreyle rahatsız etmeyin</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> dakika önce</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Sağa Kaydır</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> saat kaldı</translation>
+<translation id="1413622004203049571"><ph name="NOTIFIER_NAME"/> bildirimlerini devre dışı bırak</translation>
<translation id="2666092431469916601">Üst</translation>
<translation id="8331626408530291785">Yukarı Kaydır</translation>
-<translation id="4773379706300191099"><ph name="EXTENSION_NAME"/> bildirimlerini devre dışı bırak</translation>
<translation id="7907591526440419938">Dosya Aç</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> saat önce</translation>
<translation id="815598010540052116">Aşağı Kaydır</translation>
+<translation id="6808150112686056157">Medyayı Durdur</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Geri yükle</translation>
<translation id="1243314992276662751">Yükle</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> dakika önce</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/sn</translation>
<translation id="7649070708921625228">Yardım</translation>
+<translation id="6699343763173986273">Medya Sonraki Parça</translation>
<translation id="8226233771743600312">Bir gün süreyle rahatsız etmeyin</translation>
<translation id="7457942297256758195">Tümünü Temizle</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> gün önce</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Simge durumuna küçült</translation>
<translation id="6394627529324717982">Virgül</translation>
-<translation id="4469842253116033348"><ph name="SITE"/> bildirimlerini devre dışı bırak</translation>
<translation id="3036649622769666520">Dosya Aç</translation>
<translation id="8328145009876646418">Sol Kenar</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_uk.xtb b/chromium/ui/base/strings/ui_strings_uk.xtb
index 1287a629908..22cdf216e7a 100644
--- a/chromium/ui/base/strings/ui_strings_uk.xtb
+++ b/chromium/ui/base/strings/ui_strings_uk.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Центр сповіщень</translation>
<translation id="7470933019269157899">Залишилося <ph name="NUMBER_DEFAULT"/> хвилини</translation>
<translation id="5613020302032141669">Курсор ліворуч</translation>
+<translation id="4971687151119236543">Попередня композиція</translation>
<translation id="8602707065186045623">файл <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> secs</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> годин</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> Кб/сек.</translation>
+<translation id="8394908167088220973">Відтворити чи призупинити</translation>
<translation id="2148716181193084225">Сьогодні</translation>
<translation id="7960078400008666149">Не турбувати впродовж однієї години</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> хв. тому</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">Прокрутка вправо</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> година залишилась</translation>
+<translation id="1413622004203049571">Вимкнути сповіщення від <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Верх</translation>
<translation id="8331626408530291785">Прокрутка вгору</translation>
-<translation id="4773379706300191099">Вимкнути сповіщення з розширення <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Відкрити файл</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> год. тому</translation>
<translation id="815598010540052116">Прокрутка вниз</translation>
+<translation id="6808150112686056157">Зупинити</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Відновити</translation>
<translation id="1243314992276662751">Завантажити</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> б/сек.</translation>
<translation id="7649070708921625228">Довідка</translation>
+<translation id="6699343763173986273">Наступна композиція</translation>
<translation id="8226233771743600312">Не турбувати впродовж одного дня</translation>
<translation id="7457942297256758195">Очистити все</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Зменшити</translation>
<translation id="6394627529324717982">Кома</translation>
-<translation id="4469842253116033348">Вимкнути сповіщення від <ph name="SITE"/></translation>
<translation id="3036649622769666520">Відкрити файли</translation>
<translation id="8328145009876646418">Лівий край</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> seconds</translation>
diff --git a/chromium/ui/base/strings/ui_strings_vi.xtb b/chromium/ui/base/strings/ui_strings_vi.xtb
index b5ef2dff826..7809cc6606f 100644
--- a/chromium/ui/base/strings/ui_strings_vi.xtb
+++ b/chromium/ui/base/strings/ui_strings_vi.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">Trung tâm thông báo</translation>
<translation id="7470933019269157899">Còn lại <ph name="NUMBER_DEFAULT"/> phút</translation>
<translation id="5613020302032141669">Mũi tên Trái</translation>
+<translation id="4971687151119236543">Bản nhạc trước của trình phát phương tiện</translation>
<translation id="8602707065186045623">Tệp <ph name="SAVEAS_EXTENSION_TYPE"/> (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> giây</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> giờ</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">Phát/Tạm dừng trình phát phương tiện</translation>
<translation id="2148716181193084225">Hôm nay</translation>
<translation id="7960078400008666149">Không làm phiền trong một giờ</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> mins ago</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">Trang Trên</translation>
<translation id="4588090240171750605">Cuộn qua Phải</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> giờ còn lại</translation>
+<translation id="1413622004203049571">Tắt thông báo từ <ph name="NOTIFIER_NAME"/></translation>
<translation id="2666092431469916601">Hàng đầu</translation>
<translation id="8331626408530291785">Cuộn Lên</translation>
-<translation id="4773379706300191099">Tắt thông báo từ <ph name="EXTENSION_NAME"/></translation>
<translation id="7907591526440419938">Mở Tệp</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Thoát</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> giờ trước</translation>
<translation id="815598010540052116">Cuộn Xuống</translation>
+<translation id="6808150112686056157">Dừng trình phát phương tiện</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">Khôi phục</translation>
<translation id="1243314992276662751">Tải lên</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> mins ago</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/giây</translation>
<translation id="7649070708921625228">Trợ giúp</translation>
+<translation id="6699343763173986273">Bản nhạc tiếp theo của trình phát phương tiện</translation>
<translation id="8226233771743600312">Không làm phiền trong một ngày</translation>
<translation id="7457942297256758195">Xóa tất cả</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> days ago</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">Thu nhỏ</translation>
<translation id="6394627529324717982">Dấu phẩy</translation>
-<translation id="4469842253116033348">Vô hiệu hóa thông báo từ <ph name="SITE"/></translation>
<translation id="3036649622769666520">Mở Tệp</translation>
<translation id="8328145009876646418">Cạnh Bên trái</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> giây</translation>
diff --git a/chromium/ui/base/strings/ui_strings_zh-CN.xtb b/chromium/ui/base/strings/ui_strings_zh-CN.xtb
index e38ba7895ad..bc02e6203e9 100644
--- a/chromium/ui/base/strings/ui_strings_zh-CN.xtb
+++ b/chromium/ui/base/strings/ui_strings_zh-CN.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">通知中心</translation>
<translation id="7470933019269157899">还剩 <ph name="NUMBER_DEFAULT"/> 分钟</translation>
<translation id="5613020302032141669">向左箭头</translation>
+<translation id="4971687151119236543">媒体上一曲</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> 文件 (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> secs</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> hours</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/s</translation>
+<translation id="8394908167088220973">媒体播放/暂停</translation>
<translation id="2148716181193084225">今天</translation>
<translation id="7960078400008666149">1 小时内请勿打扰</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> 分钟前</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">向右滚动</translation>
<translation id="7414887922320653780"><ph name="NUMBER_ONE"/> hour left</translation>
+<translation id="1413622004203049571">停用来自“<ph name="NOTIFIER_NAME"/>”的通知</translation>
<translation id="2666092431469916601">顶部</translation>
<translation id="8331626408530291785">向上滚动</translation>
-<translation id="4773379706300191099">停用来自“<ph name="EXTENSION_NAME"/>”的通知</translation>
<translation id="7907591526440419938">打开文件</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> 小时前</translation>
<translation id="815598010540052116">向下滚动</translation>
+<translation id="6808150112686056157">媒体停止</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">恢复</translation>
<translation id="1243314992276662751">上传</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> 分钟前</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/s</translation>
<translation id="7649070708921625228">帮助</translation>
+<translation id="6699343763173986273">媒体下一曲</translation>
<translation id="8226233771743600312">1 天内请勿打扰</translation>
<translation id="7457942297256758195">全部清除</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> 天前</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">最小化</translation>
<translation id="6394627529324717982">逗号</translation>
-<translation id="4469842253116033348">停用 <ph name="SITE"/> 的通知</translation>
<translation id="3036649622769666520">打开文件</translation>
<translation id="8328145009876646418">左边缘</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> 秒</translation>
diff --git a/chromium/ui/base/strings/ui_strings_zh-TW.xtb b/chromium/ui/base/strings/ui_strings_zh-TW.xtb
index 9a1074542a3..8cac9e71a6e 100644
--- a/chromium/ui/base/strings/ui_strings_zh-TW.xtb
+++ b/chromium/ui/base/strings/ui_strings_zh-TW.xtb
@@ -13,6 +13,7 @@
<translation id="1190609913194133056">通知中心</translation>
<translation id="7470933019269157899">剩下 <ph name="NUMBER_DEFAULT"/> 分鐘</translation>
<translation id="5613020302032141669">向左鍵</translation>
+<translation id="4971687151119236543">上一首媒體曲目</translation>
<translation id="8602707065186045623"><ph name="SAVEAS_EXTENSION_TYPE"/> 檔案 (.<ph name="SAVEAS_EXTENSION_NAME"/>)</translation>
<translation id="542155483965056918"><ph name="NUMBER_ZERO"/> mins ago</translation>
<translation id="7121570032414343252"><ph name="NUMBER_TWO"/> 秒</translation>
@@ -104,6 +105,7 @@
<translation id="7052633198403197513">F1 鍵</translation>
<translation id="2052389551707911401"><ph name="NUMBER_MANY"/> 小時</translation>
<translation id="8677655579646609597"><ph name="QUANTITY"/> KB/秒</translation>
+<translation id="8394908167088220973">媒體播放/暫停</translation>
<translation id="2148716181193084225">今天</translation>
<translation id="7960078400008666149">1 小時內請勿打擾</translation>
<translation id="4373894838514502496"><ph name="NUMBER_FEW"/> 分鐘前</translation>
@@ -114,14 +116,15 @@
<translation id="8447116497070723931">PgUp</translation>
<translation id="4588090240171750605">向右捲動</translation>
<translation id="7414887922320653780">剩下 <ph name="NUMBER_ONE"/> 小時</translation>
+<translation id="1413622004203049571">停用「<ph name="NOTIFIER_NAME"/>」的通知</translation>
<translation id="2666092431469916601">置頂</translation>
<translation id="8331626408530291785">向上捲動</translation>
-<translation id="4773379706300191099">停用 <ph name="EXTENSION_NAME"/> 的通知</translation>
<translation id="7907591526440419938">開啟檔案</translation>
<translation id="2864069933652346933"><ph name="NUMBER_ZERO"/> days left</translation>
<translation id="1293699935367580298">Esc</translation>
<translation id="2797524280730715045"><ph name="NUMBER_DEFAULT"/> 小時前</translation>
<translation id="815598010540052116">向下捲動</translation>
+<translation id="6808150112686056157">停止媒體播放</translation>
<translation id="1308727876662951186"><ph name="NUMBER_ZERO"/> mins left</translation>
<translation id="3157931365184549694">還原</translation>
<translation id="1243314992276662751">上傳</translation>
@@ -159,6 +162,7 @@
<translation id="1101671447232096497"><ph name="NUMBER_MANY"/> 分鐘前</translation>
<translation id="6142413573757616983"><ph name="QUANTITY"/> B/秒</translation>
<translation id="7649070708921625228">說明</translation>
+<translation id="6699343763173986273">下一首媒體曲目</translation>
<translation id="8226233771743600312">1 天內請勿打擾</translation>
<translation id="7457942297256758195">全部清除</translation>
<translation id="822618367988303761"><ph name="NUMBER_TWO"/> 天前</translation>
@@ -178,7 +182,6 @@
<translation id="6978839998405419496"><ph name="NUMBER_ZERO"/> days ago</translation>
<translation id="5941711191222866238">縮到最小</translation>
<translation id="6394627529324717982">逗號</translation>
-<translation id="4469842253116033348">停用 <ph name="SITE"/> 的通知</translation>
<translation id="3036649622769666520">開啟檔案</translation>
<translation id="8328145009876646418">左邊緣</translation>
<translation id="7372005818821648611"><ph name="NUMBER_TWO"/> 秒</translation>
diff --git a/chromium/ui/base/theme_provider.h b/chromium/ui/base/theme_provider.h
index 22f70a0025c..d12e2656235 100644
--- a/chromium/ui/base/theme_provider.h
+++ b/chromium/ui/base/theme_provider.h
@@ -59,7 +59,7 @@ class UI_EXPORT ThemeProvider {
// Get the property (e.g. an alignment expressed in an enum, or a width or
// height) specified by |id|.
- virtual bool GetDisplayProperty(int id, int* result) const = 0;
+ virtual int GetDisplayProperty(int id) const = 0;
// Whether we should use the native system frame (typically Aero glass) or
// a custom frame.
diff --git a/chromium/ui/base/touch/touch_factory_x11.cc b/chromium/ui/base/touch/touch_factory_x11.cc
index 79619f368f5..21fa6a2c7e4 100644
--- a/chromium/ui/base/touch/touch_factory_x11.cc
+++ b/chromium/ui/base/touch/touch_factory_x11.cc
@@ -19,7 +19,7 @@
#include "base/strings/string_split.h"
#include "ui/base/ui_base_switches.h"
#include "ui/base/x/device_list_cache_x.h"
-#include "ui/base/x/x11_util.h"
+#include "ui/gfx/x/x11_types.h"
namespace ui {
@@ -29,7 +29,7 @@ TouchFactory::TouchFactory()
touch_events_disabled_(false),
touch_device_list_(),
#if defined(USE_XI2_MT)
- min_available_slot_(0),
+ id_generator_(0),
#endif
slots_used_() {
#if defined(USE_AURA)
@@ -37,7 +37,7 @@ TouchFactory::TouchFactory()
return;
#endif
- Display* display = GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
UpdateDeviceList(display);
CommandLine* cmdline = CommandLine::ForCurrentProcess();
@@ -177,7 +177,7 @@ void TouchFactory::SetupXI2ForXWindow(Window window) {
// the events from uninteresting devices. We do the latter because that's
// simpler.
- Display* display = ui::GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
unsigned char mask[XIMaskLen(XI_LASTEVENT)];
memset(mask, 0, sizeof(mask));
@@ -225,46 +225,18 @@ bool TouchFactory::IsMultiTouchDevice(unsigned int deviceid) const {
#if defined(USE_XI2_MT)
bool TouchFactory::QuerySlotForTrackingID(uint32 tracking_id, int* slot) {
- TrackingIdMap::iterator itr = tracking_id_map_.find(tracking_id);
- if (itr != tracking_id_map_.end()) {
- *slot = itr->second;
- return true;
- }
- return false;
+ if (!id_generator_.HasGeneratedIDFor(tracking_id))
+ return false;
+ *slot = static_cast<int>(id_generator_.GetGeneratedID(tracking_id));
+ return true;
}
int TouchFactory::GetSlotForTrackingID(uint32 tracking_id) {
- TrackingIdMap::iterator itr = tracking_id_map_.find(tracking_id);
- if (itr != tracking_id_map_.end())
- return itr->second;
-
- int slot = min_available_slot_;
- if (slot == kMaxTouchPoints) {
- LOG(ERROR) << "Could not find available slot for touch point";
- return 0;
- }
- SetSlotUsed(slot, true);
- tracking_id_map_.insert(std::make_pair(tracking_id, slot));
-
- // Updates the minium available slot ID
- while (++min_available_slot_ < kMaxTouchPoints &&
- IsSlotUsed(min_available_slot_))
- continue;
-
- return slot;
+ return id_generator_.GetGeneratedID(tracking_id);
}
void TouchFactory::ReleaseSlotForTrackingID(uint32 tracking_id) {
- TrackingIdMap::iterator itr = tracking_id_map_.find(tracking_id);
- if (itr != tracking_id_map_.end()) {
- int slot = itr->second;
- SetSlotUsed(slot, false);
- tracking_id_map_.erase(itr);
- if (slot < min_available_slot_)
- min_available_slot_ = slot;
- } else {
- NOTREACHED() << "Cannot find slot mapping to tracking ID " << tracking_id;
- }
+ id_generator_.ReleaseNumber(tracking_id);
}
#endif
diff --git a/chromium/ui/base/touch/touch_factory_x11.h b/chromium/ui/base/touch/touch_factory_x11.h
index a6e8e296581..fbbf9633f1e 100644
--- a/chromium/ui/base/touch/touch_factory_x11.h
+++ b/chromium/ui/base/touch/touch_factory_x11.h
@@ -9,8 +9,8 @@
#include <map>
#include <vector>
-#include "base/containers/hash_tables.h"
#include "base/timer/timer.h"
+#include "ui/base/sequential_id_generator.h"
#include "ui/base/ui_export.h"
template <typename T> struct DefaultSingletonTraits;
@@ -122,14 +122,7 @@ class UI_EXPORT TouchFactory {
static const int kMaxTouchPoints = 32;
#if defined(USE_XI2_MT)
- // Stores the minimum available slot ID which helps get slot ID from
- // tracking ID. When it equals to kMaxTouchPoints, there is no available
- // slot.
- int min_available_slot_;
-
- // A hash table to map tracking ID to slot.
- typedef base::hash_map<uint32, int> TrackingIdMap;
- TrackingIdMap tracking_id_map_;
+ SequentialIDGenerator id_generator_;
#endif
// A lookup table for slots in use for a touch event.
diff --git a/chromium/ui/base/ui_base_switches.cc b/chromium/ui/base/ui_base_switches.cc
index 7e27ea6348e..ca4586bc217 100644
--- a/chromium/ui/base/ui_base_switches.cc
+++ b/chromium/ui/base/ui_base_switches.cc
@@ -9,9 +9,6 @@ namespace switches {
// Disables use of DWM composition for top level windows.
const char kDisableDwmComposition[] = "disable-dwm-composition";
-// Disables the new visual style for application dialogs and controls.
-const char kDisableNewDialogStyle[] = "disable-new-dialog-style";
-
// Disables touch adjustment.
const char kDisableTouchAdjustment[] = "disable-touch-adjustment";
@@ -24,9 +21,6 @@ const char kDisableTouchEditing[] = "disable-touch-editing";
// Disables the Views textfield on Windows.
const char kDisableViewsTextfield[] = "disable-views-textfield";
-// Enables the new visual style for application dialogs and controls.
-const char kEnableNewDialogStyle[] = "enable-new-dialog-style";
-
// Enable scroll prediction for scroll update events.
const char kEnableScrollPrediction[] = "enable-scroll-prediction";
@@ -39,12 +33,6 @@ const char kEnableTouchEditing[] = "enable-touch-editing";
// Enables the Views textfield on Windows.
const char kEnableViewsTextfield[] = "enable-views-textfield";
-// Enables/Disables High DPI support (windows)
-const char kHighDPISupport[] = "high-dpi-support";
-
-// Overrides the device scale factor for the browser UI and the contents.
-const char kForceDeviceScaleFactor[] = "force-device-scale-factor";
-
// If a resource is requested at a scale factor at which it is not available
// or the resource is the incorrect size (based on the size of the 1x resource),
// generates the missing resource and applies a red mask to the generated
diff --git a/chromium/ui/base/ui_base_switches.h b/chromium/ui/base/ui_base_switches.h
index 11887d47999..7e4c9a76e9f 100644
--- a/chromium/ui/base/ui_base_switches.h
+++ b/chromium/ui/base/ui_base_switches.h
@@ -13,18 +13,14 @@
namespace switches {
UI_EXPORT extern const char kDisableDwmComposition[];
-UI_EXPORT extern const char kDisableNewDialogStyle[];
UI_EXPORT extern const char kDisableTouchAdjustment[];
UI_EXPORT extern const char kDisableTouchDragDrop[];
UI_EXPORT extern const char kDisableTouchEditing[];
UI_EXPORT extern const char kDisableViewsTextfield[];
-UI_EXPORT extern const char kEnableNewDialogStyle[];
UI_EXPORT extern const char kEnableScrollPrediction[];
UI_EXPORT extern const char kEnableTouchDragDrop[];
UI_EXPORT extern const char kEnableTouchEditing[];
UI_EXPORT extern const char kEnableViewsTextfield[];
-UI_EXPORT extern const char kForceDeviceScaleFactor[];
-UI_EXPORT extern const char kHighDPISupport[];
UI_EXPORT extern const char kHighlightMissingScaledResources[];
UI_EXPORT extern const char kLang[];
UI_EXPORT extern const char kLocalePak[];
diff --git a/chromium/ui/base/ui_base_switches_util.cc b/chromium/ui/base/ui_base_switches_util.cc
index 32034218dd5..3089607af86 100644
--- a/chromium/ui/base/ui_base_switches_util.cc
+++ b/chromium/ui/base/ui_base_switches_util.cc
@@ -29,13 +29,4 @@ bool IsTouchEditingEnabled() {
#endif
}
-bool IsNewDialogStyleEnabled() {
- CommandLine* command_line = CommandLine::ForCurrentProcess();
- if (command_line->HasSwitch(switches::kDisableNewDialogStyle))
- return false;
- if (command_line->HasSwitch(switches::kEnableNewDialogStyle))
- return true;
- return true;
-}
-
} // namespace switches
diff --git a/chromium/ui/base/ui_base_switches_util.h b/chromium/ui/base/ui_base_switches_util.h
index 4c1026124a7..c64da8f6e3c 100644
--- a/chromium/ui/base/ui_base_switches_util.h
+++ b/chromium/ui/base/ui_base_switches_util.h
@@ -13,8 +13,6 @@ namespace switches {
UI_EXPORT bool IsTouchDragDropEnabled();
UI_EXPORT bool IsTouchEditingEnabled();
-UI_EXPORT bool IsNewDialogStyleEnabled();
-
} // namespace switches
#endif // UI_BASE_UI_BASE_SWITCHES_UTIL_H_
diff --git a/chromium/ui/base/ui_base_types.cc b/chromium/ui/base/ui_base_types.cc
index 2d3f812705e..e757edb1e6f 100644
--- a/chromium/ui/base/ui_base_types.cc
+++ b/chromium/ui/base/ui_base_types.cc
@@ -4,7 +4,7 @@
#include "ui/base/ui_base_types.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
namespace ui {
diff --git a/chromium/ui/base/win/events_win.cc b/chromium/ui/base/win/events_win.cc
index 6cabff9c22a..04b9cd058aa 100644
--- a/chromium/ui/base/win/events_win.cc
+++ b/chromium/ui/base/win/events_win.cc
@@ -4,15 +4,15 @@
#include <windowsx.h>
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "base/logging.h"
#include "base/time/time.h"
#include "base/win/win_util.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
-#include "ui/base/win/dpi.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
#include "ui/gfx/point.h"
+#include "ui/gfx/win/dpi.h"
namespace ui {
@@ -213,7 +213,7 @@ gfx::Point EventLocationFromNative(const base::NativeEvent& native_event) {
GET_Y_LPARAM(native_event.lParam) };
ScreenToClient(native_event.hwnd, &native_point);
gfx::Point location(native_point);
- location = ui::win::ScreenToDIPPoint(location);
+ location = gfx::win::ScreenToDIPPoint(location);
return location;
}
@@ -357,6 +357,8 @@ int GetModifiersFromKeyState() {
modifiers |= EF_CONTROL_DOWN;
if (base::win::IsAltPressed())
modifiers |= EF_ALT_DOWN;
+ if (base::win::IsAltGrPressed())
+ modifiers |= EF_ALTGR_DOWN;
return modifiers;
}
diff --git a/chromium/ui/base/win/foreground_helper.cc b/chromium/ui/base/win/foreground_helper.cc
index 0b03582a03d..219b26fc1fa 100644
--- a/chromium/ui/base/win/foreground_helper.cc
+++ b/chromium/ui/base/win/foreground_helper.cc
@@ -5,7 +5,7 @@
#include "ui/base/win/foreground_helper.h"
#include "base/logging.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
namespace ui {
diff --git a/chromium/ui/base/win/foreground_helper.h b/chromium/ui/base/win/foreground_helper.h
index 7fc1834dddc..e8101a05b5f 100644
--- a/chromium/ui/base/win/foreground_helper.h
+++ b/chromium/ui/base/win/foreground_helper.h
@@ -6,7 +6,7 @@
#define UI_BASE_WIN_FOREGROUND_HELPER_H_
#include "base/logging.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
namespace ui {
@@ -17,7 +17,7 @@ namespace ui {
// to be capable of moving to the foreground.
//
// This is probably leveraging a windows bug.
-class UI_EXPORT ForegroundHelper : public WindowImpl {
+class UI_EXPORT ForegroundHelper : public gfx::WindowImpl {
public:
ForegroundHelper() : window_(NULL) { }
diff --git a/chromium/ui/base/win/hidden_window.cc b/chromium/ui/base/win/hidden_window.cc
index fb4f4836b24..3b21519597c 100644
--- a/chromium/ui/base/win/hidden_window.cc
+++ b/chromium/ui/base/win/hidden_window.cc
@@ -4,7 +4,7 @@
#include "ui/base/win/hidden_window.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
namespace ui {
@@ -21,7 +21,7 @@ namespace {
// window that interact poorly with us.
//
// See: http://crbug.com/16476
-class TempParent : public ui::WindowImpl {
+class TempParent : public gfx::WindowImpl {
public:
static TempParent* Get() {
static TempParent* g_temp_parent;
diff --git a/chromium/ui/base/win/hwnd_subclass.cc b/chromium/ui/base/win/hwnd_subclass.cc
index c1133f0543d..34e2bf4fad6 100644
--- a/chromium/ui/base/win/hwnd_subclass.cc
+++ b/chromium/ui/base/win/hwnd_subclass.cc
@@ -9,8 +9,8 @@
#include "base/logging.h"
#include "base/memory/scoped_vector.h"
#include "base/memory/singleton.h"
-#include "ui/base/win/dpi.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/hwnd_util.h"
namespace {
const char kHWNDSubclassKey[] = "__UI_BASE_WIN_HWND_SUBCLASS_PROC__";
@@ -123,7 +123,7 @@ HWNDSubclass::HWNDSubclass(HWND target)
: target_(target),
original_wnd_proc_(GetCurrentWndProc(target)),
prop_(target, kHWNDSubclassKey, this) {
- ui::SetWindowProc(target_, &WndProc);
+ gfx::SetWindowProc(target_, &WndProc);
}
HWNDSubclass::~HWNDSubclass() {
@@ -143,8 +143,10 @@ LRESULT HWNDSubclass::OnWndProc(HWND hwnd,
if (GetTouchInputInfoWrapper(reinterpret_cast<HTOUCHINPUT>(l_param), 1,
&point, sizeof(TOUCHINPUT))) {
POINT touch_location = {
- TOUCH_COORD_TO_PIXEL(point.x) / ui::win::GetUndocumentedDPIScale(),
- TOUCH_COORD_TO_PIXEL(point.y) / ui::win::GetUndocumentedDPIScale()};
+ TOUCH_COORD_TO_PIXEL(point.x) /
+ gfx::win::GetUndocumentedDPITouchScale(),
+ TOUCH_COORD_TO_PIXEL(point.y) /
+ gfx::win::GetUndocumentedDPITouchScale()};
HWND actual_target = WindowFromPoint(touch_location);
if (actual_target != hwnd) {
return SendMessage(actual_target, message, w_param, l_param);
diff --git a/chromium/ui/base/win/hwnd_subclass_unittest.cc b/chromium/ui/base/win/hwnd_subclass_unittest.cc
index 5917ef2c101..520f52b4b16 100644
--- a/chromium/ui/base/win/hwnd_subclass_unittest.cc
+++ b/chromium/ui/base/win/hwnd_subclass_unittest.cc
@@ -6,13 +6,13 @@
#include "base/basictypes.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
namespace ui {
namespace {
-class TestWindow : public ui::WindowImpl {
+class TestWindow : public gfx::WindowImpl {
public:
TestWindow() : saw_message(false) {}
virtual ~TestWindow() {}
@@ -20,7 +20,7 @@ class TestWindow : public ui::WindowImpl {
bool saw_message;
private:
- // Overridden from ui::WindowImpl:
+ // Overridden from gfx::WindowImpl:
virtual BOOL ProcessWindowMessage(HWND window,
UINT message,
WPARAM w_param,
diff --git a/chromium/ui/base/win/mouse_wheel_util.cc b/chromium/ui/base/win/mouse_wheel_util.cc
index 941c069e005..223e3a8ee50 100644
--- a/chromium/ui/base/win/mouse_wheel_util.cc
+++ b/chromium/ui/base/win/mouse_wheel_util.cc
@@ -8,7 +8,7 @@
#include "base/auto_reset.h"
#include "ui/base/view_prop.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/gfx/win/hwnd_util.h"
namespace ui {
@@ -31,7 +31,7 @@ static bool WindowSupportsRerouteMouseWheel(HWND window) {
}
static bool IsCompatibleWithMouseWheelRedirection(HWND window) {
- std::wstring class_name = GetClassName(window);
+ std::wstring class_name = gfx::GetClassName(window);
// Mousewheel redirection to comboboxes is a surprising and
// undesireable user behavior.
return !(class_name == L"ComboBox" ||
@@ -39,7 +39,7 @@ static bool IsCompatibleWithMouseWheelRedirection(HWND window) {
}
static bool CanRedirectMouseWheelFrom(HWND window) {
- std::wstring class_name = GetClassName(window);
+ std::wstring class_name = gfx::GetClassName(window);
// Older Thinkpad mouse wheel drivers create a window under mouse wheel
// pointer. Detect if we are dealing with this window. In this case we
diff --git a/chromium/ui/base/win/shell.cc b/chromium/ui/base/win/shell.cc
index df90108ac4f..0f955375e52 100644
--- a/chromium/ui/base/win/shell.cc
+++ b/chromium/ui/base/win/shell.cc
@@ -98,6 +98,22 @@ bool OpenItemViaShellNoZoneCheck(const base::FilePath& full_path) {
SEE_MASK_NOZONECHECKS | SEE_MASK_FLAG_DDEWAIT);
}
+bool PreventWindowFromPinning(HWND hwnd) {
+ // This functionality is only available on Win7+. It also doesn't make sense
+ // to do this for Chrome Metro.
+ if (base::win::GetVersion() < base::win::VERSION_WIN7 ||
+ base::win::IsMetroProcess())
+ return false;
+ base::win::ScopedComPtr<IPropertyStore> pps;
+ HRESULT result = SHGetPropertyStoreForWindow(
+ hwnd, __uuidof(*pps), reinterpret_cast<void**>(pps.Receive()));
+ if (FAILED(result))
+ return false;
+
+ return base::win::SetBooleanValueForPropertyStore(
+ pps, PKEY_AppUserModel_PreventPinning, true);
+}
+
void SetAppIdForWindow(const string16& app_id, HWND hwnd) {
SetAppDetailsForWindow(app_id, string16(), string16(), string16(), hwnd);
}
diff --git a/chromium/ui/base/win/shell.h b/chromium/ui/base/win/shell.h
index 364b7a32712..31dbb889c2c 100644
--- a/chromium/ui/base/win/shell.h
+++ b/chromium/ui/base/win/shell.h
@@ -41,6 +41,11 @@ UI_EXPORT bool OpenAnyViaShell(const string16& full_path,
// Returns 'true' on successful open, 'false' otherwise.
bool OpenItemWithExternalApp(const string16& full_path);
+// Disables the ability of the specified window to be pinned to the taskbar or
+// the Start menu. This will remove "Pin this program to taskbar" from the
+// taskbar menu of the specified window.
+UI_EXPORT bool PreventWindowFromPinning(HWND hwnd);
+
// Sets the application id given as the Application Model ID for the window
// specified. This method is used to insure that different web applications
// do not group together on the Win7 task bar.
diff --git a/chromium/ui/base/window_open_disposition.cc b/chromium/ui/base/window_open_disposition.cc
index 5e27bcc209a..c0d131f4bfc 100644
--- a/chromium/ui/base/window_open_disposition.cc
+++ b/chromium/ui/base/window_open_disposition.cc
@@ -5,7 +5,7 @@
#include "ui/base/window_open_disposition.h"
#include "build/build_config.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
namespace ui {
diff --git a/chromium/ui/base/x/active_window_watcher_x.cc b/chromium/ui/base/x/active_window_watcher_x.cc
index a277ccde2c5..9d3e791fd53 100644
--- a/chromium/ui/base/x/active_window_watcher_x.cc
+++ b/chromium/ui/base/x/active_window_watcher_x.cc
@@ -8,11 +8,11 @@
#include <gdk/gdkx.h>
#include "base/memory/singleton.h"
-#include "ui/base/gtk/gdk_x_compat.h"
-#include "ui/base/gtk/gtk_compat.h"
#include "ui/base/x/active_window_watcher_x_observer.h"
#include "ui/base/x/root_window_property_watcher_x.h"
#include "ui/base/x/x11_util.h"
+#include "ui/gfx/gdk_compat.h"
+#include "ui/gfx/gtk_compat.h"
namespace ui {
diff --git a/chromium/ui/base/x/device_data_manager.cc b/chromium/ui/base/x/device_data_manager.cc
index 3dbd79dccba..784819f6b08 100644
--- a/chromium/ui/base/x/device_data_manager.cc
+++ b/chromium/ui/base/x/device_data_manager.cc
@@ -10,12 +10,11 @@
#include "base/logging.h"
#include "base/memory/singleton.h"
-#include "base/message_loop/message_pump_aurax11.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/touch/touch_factory_x11.h"
#include "ui/base/x/device_list_cache_x.h"
#include "ui/base/x/x11_util.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
// XIScrollClass was introduced in XI 2.1 so we need to define it here
// for backward-compatibility with older versions of XInput.
@@ -117,12 +116,12 @@ DeviceDataManager* DeviceDataManager::GetInstance() {
DeviceDataManager::DeviceDataManager()
: natural_scroll_enabled_(false),
- atom_cache_(ui::GetXDisplay(), kCachedAtoms) {
+ atom_cache_(gfx::GetXDisplay(), kCachedAtoms) {
InitializeXInputInternal();
// Make sure the sizes of enum and kCachedAtoms are aligned.
CHECK(arraysize(kCachedAtoms) == static_cast<size_t>(DT_LAST_ENTRY) + 1);
- UpdateDeviceList(ui::GetXDisplay());
+ UpdateDeviceList(gfx::GetXDisplay());
}
DeviceDataManager::~DeviceDataManager() {
@@ -133,7 +132,7 @@ bool DeviceDataManager::InitializeXInputInternal() {
xi_opcode_ = -1;
int opcode, event, error;
if (!XQueryExtension(
- ui::GetXDisplay(), "XInputExtension", &opcode, &event, &error)) {
+ gfx::GetXDisplay(), "XInputExtension", &opcode, &event, &error)) {
VLOG(1) << "X Input extension not available: error=" << error;
return false;
}
@@ -145,7 +144,7 @@ bool DeviceDataManager::InitializeXInputInternal() {
#else
int major = 2, minor = 0;
#endif
- if (XIQueryVersion(ui::GetXDisplay(), &major, &minor) == BadRequest) {
+ if (XIQueryVersion(gfx::GetXDisplay(), &major, &minor) == BadRequest) {
VLOG(1) << "XInput2 not supported in the server.";
return false;
}
diff --git a/chromium/ui/base/x/device_data_manager.h b/chromium/ui/base/x/device_data_manager.h
index 82718ab92c3..f07012f51e5 100644
--- a/chromium/ui/base/x/device_data_manager.h
+++ b/chromium/ui/base/x/device_data_manager.h
@@ -13,9 +13,9 @@
#include "base/basictypes.h"
#include "base/event_types.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/ui_export.h"
#include "ui/base/x/x11_atom_cache.h"
+#include "ui/events/event_constants.h"
template <typename T> struct DefaultSingletonTraits;
diff --git a/chromium/ui/base/x/events_x.cc b/chromium/ui/base/x/events_x.cc
index 51521689bf1..06301a9b086 100644
--- a/chromium/ui/base/x/events_x.cc
+++ b/chromium/ui/base/x/events_x.cc
@@ -2,24 +2,23 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include <string.h>
#include <X11/extensions/XInput.h>
#include <X11/extensions/XInput2.h>
#include <X11/Xlib.h>
-#include "base/command_line.h"
#include "base/logging.h"
#include "base/memory/singleton.h"
-#include "base/message_loop/message_pump_aurax11.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
+#include "base/message_loop/message_pump_x11.h"
#include "ui/base/touch/touch_factory_x11.h"
#include "ui/base/x/device_data_manager.h"
#include "ui/base/x/device_list_cache_x.h"
#include "ui/base/x/x11_atom_cache.h"
#include "ui/base/x/x11_util.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
#include "ui/gfx/display.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
@@ -33,19 +32,6 @@ const int kWheelScrollAmount = 53;
const int kMinWheelButton = 4;
const int kMaxWheelButton = 7;
-// A workaround for some incorrect implemented input drivers:
-// Ignore their mouse input valuators.
-bool IgnoreMouseValuators() {
- static bool initialized = false;
- static bool ignore_valuators = true;
- if (initialized)
- return ignore_valuators;
- ignore_valuators =
- CommandLine::ForCurrentProcess()->HasSwitch("disable-mouse-valuators");
- initialized = true;
- return ignore_valuators;
-}
-
// A class to track current modifier state on master device. Only track ctrl,
// alt, shift and caps lock keys currently. The tracked state can then be used
// by floating device.
@@ -274,13 +260,7 @@ double GetTouchParamFromXEvent(XEvent* xev,
}
Atom GetNoopEventAtom() {
- return XInternAtom(
-#if defined(USE_AURA)
- base::MessagePumpAuraX11::GetDefaultXDisplay(),
-#else
- XOpenDisplay(NULL),
-#endif
- "noop", False);
+ return XInternAtom(gfx::GetXDisplay(), "noop", False);
}
} // namespace
@@ -288,7 +268,7 @@ Atom GetNoopEventAtom() {
namespace ui {
void UpdateDeviceList() {
- Display* display = GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
DeviceListCacheX::GetInstance()->UpdateDeviceList(display);
TouchFactory::GetInstance()->UpdateDeviceList(display);
DeviceDataManager::GetInstance()->UpdateDeviceList(display);
@@ -480,40 +460,8 @@ gfx::Point EventLocationFromNative(const base::NativeEvent& native_event) {
case GenericEvent: {
XIDeviceEvent* xievent =
static_cast<XIDeviceEvent*>(native_event->xcookie.data);
-
-#if defined(USE_XI2_MT)
- // Touch event valuators aren't coordinates.
- // Return the |event_x|/|event_y| directly as event's position.
- if (xievent->evtype == XI_TouchBegin ||
- xievent->evtype == XI_TouchUpdate ||
- xievent->evtype == XI_TouchEnd)
- // Note: Touch events are always touch screen events.
- return gfx::Point(static_cast<int>(xievent->event_x),
- static_cast<int>(xievent->event_y));
-#endif
- if (IgnoreMouseValuators()) {
- return gfx::Point(static_cast<int>(xievent->event_x),
- static_cast<int>(xievent->event_y));
- }
- // Read the position from the valuators, because the location reported in
- // event_x/event_y seems to be different (and doesn't match for events
- // coming from slave device and master device) from the values in the
- // valuators. See more on crbug.com/103981. The position in the valuators
- // is in the global screen coordinates. But it is necessary to convert it
- // into the window's coordinates. If the valuator is not set, that means
- // the value hasn't changed, and so we can use the value from
- // event_x/event_y (which are in the window's coordinates).
- double* valuators = xievent->valuators.values;
-
- double x = xievent->event_x;
- if (XIMaskIsSet(xievent->valuators.mask, 0))
- x = *valuators++ - (xievent->root_x - xievent->event_x);
-
- double y = xievent->event_y;
- if (XIMaskIsSet(xievent->valuators.mask, 1))
- y = *valuators++ - (xievent->root_y - xievent->event_y);
-
- return gfx::Point(static_cast<int>(x), static_cast<int>(y));
+ return gfx::Point(static_cast<int>(xievent->event_x),
+ static_cast<int>(xievent->event_y));
}
}
return gfx::Point();
diff --git a/chromium/ui/base/x/events_x_unittest.cc b/chromium/ui/base/x/events_x_unittest.cc
index 42ed319bac4..3a85a0a0dfa 100644
--- a/chromium/ui/base/x/events_x_unittest.cc
+++ b/chromium/ui/base/x/events_x_unittest.cc
@@ -12,10 +12,11 @@
#undef None
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/touch/touch_factory_x11.h"
#include "ui/base/x/device_data_manager.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
#include "ui/gfx/point.h"
namespace ui {
@@ -234,6 +235,27 @@ TEST(EventsXTest, EnterLeaveEvent) {
EXPECT_EQ("230,240", ui::EventSystemLocationFromNative(&event).ToString());
}
+TEST(EventsXTest, ClickCount) {
+ XEvent event;
+ gfx::Point location(5, 10);
+
+ for (int i = 1; i <= 3; ++i) {
+ InitButtonEvent(&event, true, location, 1, 0);
+ {
+ MouseEvent mouseev(&event);
+ EXPECT_EQ(ui::ET_MOUSE_PRESSED, mouseev.type());
+ EXPECT_EQ(i, mouseev.GetClickCount());
+ }
+
+ InitButtonEvent(&event, false, location, 1, 0);
+ {
+ MouseEvent mouseev(&event);
+ EXPECT_EQ(ui::ET_MOUSE_RELEASED, mouseev.type());
+ EXPECT_EQ(i, mouseev.GetClickCount());
+ }
+ }
+}
+
#if defined(USE_XI2_MT)
TEST(EventsXTest, TouchEventBasic) {
std::vector<unsigned int> devices;
@@ -248,6 +270,7 @@ TEST(EventsXTest, TouchEventBasic) {
valuators.push_back(Valuator(DeviceDataManager::DT_TOUCH_ORIENTATION, 0.3f));
valuators.push_back(Valuator(DeviceDataManager::DT_TOUCH_PRESSURE, 100));
event = CreateTouchEvent(0, XI_TouchBegin, 5, gfx::Point(10, 10), valuators);
+ EXPECT_EQ(ui::ET_TOUCH_PRESSED, ui::EventTypeFromNative(event));
EXPECT_EQ("10,10", ui::EventLocationFromNative(event).ToString());
EXPECT_EQ(GetTouchId(event), 0);
EXPECT_EQ(GetTouchRadiusX(event), 10);
@@ -259,6 +282,7 @@ TEST(EventsXTest, TouchEventBasic) {
valuators.clear();
valuators.push_back(Valuator(DeviceDataManager::DT_TOUCH_ORIENTATION, 0.5f));
event = CreateTouchEvent(0, XI_TouchUpdate, 5, gfx::Point(20, 20), valuators);
+ EXPECT_EQ(ui::ET_TOUCH_MOVED, ui::EventTypeFromNative(event));
EXPECT_EQ("20,20", ui::EventLocationFromNative(event).ToString());
EXPECT_EQ(GetTouchId(event), 0);
EXPECT_EQ(GetTouchRadiusX(event), 10);
@@ -273,6 +297,7 @@ TEST(EventsXTest, TouchEventBasic) {
valuators.push_back(Valuator(DeviceDataManager::DT_TOUCH_PRESSURE, 500));
event = CreateTouchEvent(
0, XI_TouchBegin, 6, gfx::Point(200, 200), valuators);
+ EXPECT_EQ(ui::ET_TOUCH_PRESSED, ui::EventTypeFromNative(event));
EXPECT_EQ("200,200", ui::EventLocationFromNative(event).ToString());
EXPECT_EQ(GetTouchId(event), 1);
EXPECT_EQ(GetTouchRadiusX(event), 50);
@@ -285,6 +310,7 @@ TEST(EventsXTest, TouchEventBasic) {
valuators.clear();
valuators.push_back(Valuator(DeviceDataManager::DT_TOUCH_PRESSURE, 50));
event = CreateTouchEvent(0, XI_TouchEnd, 5, gfx::Point(30, 30), valuators);
+ EXPECT_EQ(ui::ET_TOUCH_RELEASED, ui::EventTypeFromNative(event));
EXPECT_EQ("30,30", ui::EventLocationFromNative(event).ToString());
EXPECT_EQ(GetTouchId(event), 0);
EXPECT_EQ(GetTouchRadiusX(event), 10);
@@ -297,6 +323,7 @@ TEST(EventsXTest, TouchEventBasic) {
valuators.clear();
valuators.push_back(Valuator(DeviceDataManager::DT_TOUCH_MAJOR, 50));
event = CreateTouchEvent(0, XI_TouchEnd, 6, gfx::Point(200, 200), valuators);
+ EXPECT_EQ(ui::ET_TOUCH_RELEASED, ui::EventTypeFromNative(event));
EXPECT_EQ("200,200", ui::EventLocationFromNative(event).ToString());
EXPECT_EQ(GetTouchId(event), 1);
EXPECT_EQ(GetTouchRadiusX(event), 25);
diff --git a/chromium/ui/base/x/selection_requestor.cc b/chromium/ui/base/x/selection_requestor.cc
index 405c0592f80..059ea3f1db5 100644
--- a/chromium/ui/base/x/selection_requestor.cc
+++ b/chromium/ui/base/x/selection_requestor.cc
@@ -4,7 +4,7 @@
#include "ui/base/x/selection_requestor.h"
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/run_loop.h"
#include "ui/base/x/selection_utils.h"
#include "ui/base/x/x11_util.h"
@@ -56,7 +56,7 @@ bool SelectionRequestor::PerformBlockingConvertSelection(
// for a response.
base::MessageLoopForUI* loop = base::MessageLoopForUI::current();
base::MessageLoop::ScopedNestableTaskAllower allow_nested(loop);
- base::RunLoop run_loop(base::MessagePumpAuraX11::Current());
+ base::RunLoop run_loop(base::MessagePumpX11::Current());
current_target_ = target;
in_nested_loop_ = true;
diff --git a/chromium/ui/base/x/selection_utils.cc b/chromium/ui/base/x/selection_utils.cc
index 4696b0047ad..e0f1d9b5e0c 100644
--- a/chromium/ui/base/x/selection_utils.cc
+++ b/chromium/ui/base/x/selection_utils.cc
@@ -104,6 +104,7 @@ SelectionFormatMap::~SelectionFormatMap() {}
void SelectionFormatMap::Insert(
::Atom atom,
const scoped_refptr<base::RefCountedMemory>& item) {
+ data_.erase(atom);
data_.insert(std::make_pair(atom, item));
}
@@ -132,7 +133,7 @@ std::vector< ::Atom> SelectionFormatMap::GetTypes() const {
SelectionData::SelectionData()
: type_(None),
- atom_cache_(ui::GetXDisplay(), kSelectionDataAtoms) {
+ atom_cache_(gfx::GetXDisplay(), kSelectionDataAtoms) {
}
SelectionData::SelectionData(
@@ -140,13 +141,13 @@ SelectionData::SelectionData(
const scoped_refptr<base::RefCountedMemory>& memory)
: type_(type),
memory_(memory),
- atom_cache_(ui::GetXDisplay(), kSelectionDataAtoms) {
+ atom_cache_(gfx::GetXDisplay(), kSelectionDataAtoms) {
}
SelectionData::SelectionData(const SelectionData& rhs)
: type_(rhs.type_),
memory_(rhs.memory_),
- atom_cache_(ui::GetXDisplay(), kSelectionDataAtoms) {
+ atom_cache_(gfx::GetXDisplay(), kSelectionDataAtoms) {
}
SelectionData::~SelectionData() {}
diff --git a/chromium/ui/base/x/x11_atom_cache.cc b/chromium/ui/base/x/x11_atom_cache.cc
index 1c49ddb2a4b..09e59f1ace8 100644
--- a/chromium/ui/base/x/x11_atom_cache.cc
+++ b/chromium/ui/base/x/x11_atom_cache.cc
@@ -6,8 +6,8 @@
#include <X11/Xatom.h>
+#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
-#include "base/message_loop/message_pump_aurax11.h"
namespace ui {
diff --git a/chromium/ui/base/x/x11_error_tracker.cc b/chromium/ui/base/x/x11_error_tracker.cc
new file mode 100644
index 00000000000..22bc798321b
--- /dev/null
+++ b/chromium/ui/base/x/x11_error_tracker.cc
@@ -0,0 +1,37 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/x/x11_error_tracker.h"
+
+#include "ui/base/x/x11_util.h"
+
+namespace {
+
+unsigned char g_x11_error_code = 0;
+
+int X11ErrorHandler(XDisplay* display, XErrorEvent* error) {
+ g_x11_error_code = error->error_code;
+ return 0;
+}
+
+}
+
+namespace ui {
+
+X11ErrorTracker::X11ErrorTracker() {
+ old_handler_ = XSetErrorHandler(X11ErrorHandler);
+}
+
+X11ErrorTracker::~X11ErrorTracker() {
+ XSetErrorHandler(old_handler_);
+}
+
+bool X11ErrorTracker::FoundNewError() {
+ XSync(gfx::GetXDisplay(), False);
+ unsigned char error = g_x11_error_code;
+ g_x11_error_code = 0;
+ return error != 0;
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/x/x11_error_tracker.h b/chromium/ui/base/x/x11_error_tracker.h
new file mode 100644
index 00000000000..57d46d1b3ac
--- /dev/null
+++ b/chromium/ui/base/x/x11_error_tracker.h
@@ -0,0 +1,33 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <X11/Xlib.h>
+
+#include "base/basictypes.h"
+#include "ui/base/ui_export.h"
+
+namespace ui {
+
+// X11ErrorTracker catches X11 errors in a non-fatal way. It does so by
+// temporarily changing the X11 error handler. The old error handler is
+// restored when the tracker is destroyed.
+class UI_EXPORT X11ErrorTracker {
+ public:
+ X11ErrorTracker();
+ ~X11ErrorTracker();
+
+ // Returns whether an X11 error happened since this function was last called
+ // (or since the creation of the tracker). This is potentially expensive,
+ // since this causes a sync with the X server.
+ bool FoundNewError();
+
+ private:
+#if !defined(TOOLKIT_GTK)
+ XErrorHandler old_handler_;
+#endif
+
+ DISALLOW_COPY_AND_ASSIGN(X11ErrorTracker);
+};
+
+} // namespace ui
diff --git a/chromium/ui/base/x/x11_error_tracker_gtk.cc b/chromium/ui/base/x/x11_error_tracker_gtk.cc
new file mode 100644
index 00000000000..2806d34b978
--- /dev/null
+++ b/chromium/ui/base/x/x11_error_tracker_gtk.cc
@@ -0,0 +1,29 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/base/x/x11_error_tracker.h"
+
+#include <gdk/gdkx.h>
+
+#include "base/logging.h"
+
+namespace ui {
+
+X11ErrorTracker::X11ErrorTracker() {
+ gdk_error_trap_push();
+}
+
+X11ErrorTracker::~X11ErrorTracker() {
+ gdk_error_trap_pop();
+}
+
+bool X11ErrorTracker::FoundNewError() {
+ gdk_flush();
+ bool found_error = gdk_error_trap_pop() != 0;
+
+ gdk_error_trap_push();
+ return found_error;
+}
+
+} // namespace ui
diff --git a/chromium/ui/base/x/x11_util.cc b/chromium/ui/base/x/x11_util.cc
index 836feae8e50..58c2c698a3c 100644
--- a/chromium/ui/base/x/x11_util.cc
+++ b/chromium/ui/base/x/x11_util.cc
@@ -32,11 +32,18 @@
#include "base/strings/stringprintf.h"
#include "base/sys_byteorder.h"
#include "base/threading/thread.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
+#include "third_party/skia/include/core/SkBitmap.h"
+#include "third_party/skia/include/core/SkPostConfig.h"
#include "ui/base/touch/touch_factory_x11.h"
#include "ui/base/x/device_data_manager.h"
+#include "ui/base/x/x11_error_tracker.h"
#include "ui/base/x/x11_util_internal.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
+#include "ui/gfx/canvas.h"
+#include "ui/gfx/image/image_skia.h"
+#include "ui/gfx/image/image_skia_rep.h"
+#include "ui/gfx/point.h"
#include "ui/gfx/point_conversions.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/size.h"
@@ -49,22 +56,14 @@
#if defined(USE_AURA)
#include <X11/Xcursor/Xcursor.h>
#include "skia/ext/image_operations.h"
-#include "third_party/skia/include/core/SkBitmap.h"
#include "ui/gfx/skia_util.h"
#endif
#if defined(TOOLKIT_GTK)
#include <gdk/gdk.h>
-#include <gdk/gdkx.h>
#include <gtk/gtk.h>
-#include "ui/base/gtk/gdk_x_compat.h"
-#include "ui/base/gtk/gtk_compat.h"
-#else
-// TODO(sad): Use the new way of handling X errors when
-// http://codereview.chromium.org/7889040/ lands.
-#define gdk_error_trap_push()
-#define gdk_error_trap_pop() false
-#define gdk_flush()
+#include "ui/gfx/gdk_compat.h"
+#include "ui/gfx/gtk_compat.h"
#endif
namespace ui {
@@ -73,11 +72,11 @@ namespace {
// Used to cache the XRenderPictFormat for a visual/display pair.
struct CachedPictFormat {
- bool equals(Display* display, Visual* visual) const {
+ bool equals(XDisplay* display, Visual* visual) const {
return display == this->display && visual == this->visual;
}
- Display* display;
+ XDisplay* display;
Visual* visual;
XRenderPictFormat* format;
};
@@ -95,7 +94,7 @@ CachedPictFormats* get_cached_pict_formats() {
// Maximum number of CachedPictFormats we keep around.
const size_t kMaxCacheSize = 5;
-int DefaultX11ErrorHandler(Display* d, XErrorEvent* e) {
+int DefaultX11ErrorHandler(XDisplay* d, XErrorEvent* e) {
if (base::MessageLoop::current()) {
base::MessageLoop::current()->PostTask(
FROM_HERE, base::Bind(&LogErrorEventDescription, d, *e));
@@ -110,7 +109,7 @@ int DefaultX11ErrorHandler(Display* d, XErrorEvent* e) {
return 0;
}
-int DefaultX11IOErrorHandler(Display* d) {
+int DefaultX11IOErrorHandler(XDisplay* d) {
// If there's an IO error it likely means the X server has gone away
LOG(ERROR) << "X IO error received (X server probably went away)";
_exit(1);
@@ -122,7 +121,7 @@ bool GetProperty(XID window, const std::string& property_name, long max_length,
unsigned char** property) {
Atom property_atom = GetAtom(property_name.c_str());
unsigned long remaining_bytes = 0;
- return XGetWindowProperty(GetXDisplay(),
+ return XGetWindowProperty(gfx::GetXDisplay(),
window,
property_atom,
0, // offset into property data to read
@@ -160,7 +159,7 @@ int XKeyEventType(ui::EventType type) {
// Converts KeyboardCode to XKeyEvent keycode.
unsigned int XKeyEventKeyCode(ui::KeyboardCode key_code,
int flags,
- Display* display) {
+ XDisplay* display) {
const int keysym = XKeysymForWindowsKeyCode(key_code,
flags & ui::EF_SHIFT_DOWN);
// Tests assume the keycode for XK_less is equal to the one of XK_comma,
@@ -183,14 +182,14 @@ class XCursorCache {
std::pair<std::map<int, ::Cursor>::iterator, bool> it = cache_.insert(
std::make_pair(cursor_shape, 0));
if (it.second) {
- Display* display = base::MessagePumpForUI::GetDefaultXDisplay();
+ XDisplay* display = base::MessagePumpForUI::GetDefaultXDisplay();
it.first->second = XCreateFontCursor(display, cursor_shape);
}
return it.first->second;
}
void Clear() {
- Display* display = base::MessagePumpForUI::GetDefaultXDisplay();
+ XDisplay* display = base::MessagePumpForUI::GetDefaultXDisplay();
for (std::map<int, ::Cursor>::iterator it =
cache_.begin(); it != cache_.end(); ++it) {
XFreeCursor(display, it->second);
@@ -244,12 +243,12 @@ class XCustomCursorCache {
XCustomCursor(XcursorImage* image)
: image_(image),
ref_(1) {
- cursor_ = XcursorImageLoadCursor(GetXDisplay(), image);
+ cursor_ = XcursorImageLoadCursor(gfx::GetXDisplay(), image);
}
~XCustomCursor() {
XcursorImageDestroy(image_);
- XFreeCursor(GetXDisplay(), cursor_);
+ XFreeCursor(gfx::GetXDisplay(), cursor_);
}
::Cursor cursor() const { return cursor_; }
@@ -293,7 +292,7 @@ class XButtonMap {
}
void UpdateMapping() {
- count_ = XGetPointerMapping(ui::GetXDisplay(), map_, arraysize(map_));
+ count_ = XGetPointerMapping(gfx::GetXDisplay(), map_, arraysize(map_));
}
int GetMappedButton(int button) {
@@ -318,7 +317,7 @@ class XButtonMap {
bool IsShapeAvailable() {
int dummy;
static bool is_shape_available =
- XShapeQueryExtension(ui::GetXDisplay(), &dummy, &dummy);
+ XShapeQueryExtension(gfx::GetXDisplay(), &dummy, &dummy);
return is_shape_available;
}
@@ -326,14 +325,10 @@ bool IsShapeAvailable() {
} // namespace
bool XDisplayExists() {
- return (GetXDisplay() != NULL);
+ return (gfx::GetXDisplay() != NULL);
}
-Display* GetXDisplay() {
- return base::MessagePumpForUI::GetDefaultXDisplay();
-}
-
-static SharedMemorySupport DoQuerySharedMemorySupport(Display* dpy) {
+static SharedMemorySupport DoQuerySharedMemorySupport(XDisplay* dpy) {
int dummy;
Bool pixmaps_supported;
// Query the server's support for XSHM.
@@ -370,14 +365,13 @@ static SharedMemorySupport DoQuerySharedMemorySupport(Display* dpy) {
memset(&shminfo, 0, sizeof(shminfo));
shminfo.shmid = shmkey;
- gdk_error_trap_push();
+ X11ErrorTracker err_tracker;
bool result = XShmAttach(dpy, &shminfo);
if (result)
VLOG(1) << "X got shared memory segment " << shmkey;
else
LOG(WARNING) << "X failed to attach to shared memory segment " << shmkey;
- XSync(dpy, False);
- if (gdk_error_trap_pop())
+ if (err_tracker.FoundNewError())
result = false;
shmdt(address);
if (!result) {
@@ -391,7 +385,7 @@ static SharedMemorySupport DoQuerySharedMemorySupport(Display* dpy) {
return pixmaps_supported ? SHARED_MEMORY_PIXMAP : SHARED_MEMORY_PUTIMAGE;
}
-SharedMemorySupport QuerySharedMemorySupport(Display* dpy) {
+SharedMemorySupport QuerySharedMemorySupport(XDisplay* dpy) {
static SharedMemorySupport shared_memory_support = SHARED_MEMORY_NONE;
static bool shared_memory_support_cached = false;
@@ -404,7 +398,7 @@ SharedMemorySupport QuerySharedMemorySupport(Display* dpy) {
return shared_memory_support;
}
-bool QueryRenderSupport(Display* dpy) {
+bool QueryRenderSupport(XDisplay* dpy) {
static bool render_supported = false;
static bool render_supported_cached = false;
@@ -420,7 +414,7 @@ bool QueryRenderSupport(Display* dpy) {
return render_supported;
}
-int GetDefaultScreen(Display* display) {
+int GetDefaultScreen(XDisplay* display) {
return XDefaultScreen(display);
}
@@ -495,7 +489,7 @@ int CoalescePendingMotionEvents(const XEvent* xev,
XEvent* last_event) {
XIDeviceEvent* xievent = static_cast<XIDeviceEvent*>(xev->xcookie.data);
int num_coalesced = 0;
- Display* display = xev->xany.display;
+ XDisplay* display = xev->xany.display;
int event_type = xev->xgeneric.evtype;
DCHECK_EQ(event_type, XI_Motion);
@@ -565,13 +559,13 @@ int CoalescePendingMotionEvents(const XEvent* xev,
void HideHostCursor() {
CR_DEFINE_STATIC_LOCAL(XScopedCursor, invisible_cursor,
- (CreateInvisibleCursor(), ui::GetXDisplay()));
- XDefineCursor(ui::GetXDisplay(), DefaultRootWindow(ui::GetXDisplay()),
+ (CreateInvisibleCursor(), gfx::GetXDisplay()));
+ XDefineCursor(gfx::GetXDisplay(), DefaultRootWindow(gfx::GetXDisplay()),
invisible_cursor.get());
}
::Cursor CreateInvisibleCursor() {
- Display* xdisplay = ui::GetXDisplay();
+ XDisplay* xdisplay = gfx::GetXDisplay();
::Cursor invisible_cursor;
char nodata[] = { 0, 0, 0, 0, 0, 0, 0, 0 };
XColor black;
@@ -586,7 +580,7 @@ void HideHostCursor() {
}
XID GetX11RootWindow() {
- return DefaultRootWindow(GetXDisplay());
+ return DefaultRootWindow(gfx::GetXDisplay());
}
bool GetCurrentDesktop(int* desktop) {
@@ -623,7 +617,7 @@ void* GetVisualFromGtkWidget(GtkWidget* widget) {
void SetHideTitlebarWhenMaximizedProperty(XID window,
HideTitlebarWhenMaximized property) {
uint32 hide = property;
- XChangeProperty(GetXDisplay(),
+ XChangeProperty(gfx::GetXDisplay(),
window,
GetAtom("_GTK_HIDE_TITLEBAR_WHEN_MAXIMIZED"),
XA_CARDINAL,
@@ -634,7 +628,7 @@ void SetHideTitlebarWhenMaximizedProperty(XID window,
}
void ClearX11DefaultRootWindow() {
- Display* display = GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
XID root_window = GetX11RootWindow();
gfx::Rect root_bounds;
if (!GetWindowRect(root_window, &root_bounds)) {
@@ -653,7 +647,7 @@ void ClearX11DefaultRootWindow() {
XFreeGC(display, gc);
}
-int BitsPerPixelForPixmapDepth(Display* dpy, int depth) {
+int BitsPerPixelForPixmapDepth(XDisplay* dpy, int depth) {
int count;
XPixmapFormatValues* formats = XListPixmapFormats(dpy, &count);
if (!formats)
@@ -673,7 +667,7 @@ int BitsPerPixelForPixmapDepth(Display* dpy, int depth) {
bool IsWindowVisible(XID window) {
XWindowAttributes win_attributes;
- if (!XGetWindowAttributes(GetXDisplay(), window, &win_attributes))
+ if (!XGetWindowAttributes(gfx::GetXDisplay(), window, &win_attributes))
return false;
if (win_attributes.map_state != IsViewable)
return false;
@@ -692,11 +686,11 @@ bool GetWindowRect(XID window, gfx::Rect* rect) {
unsigned int width, height;
unsigned int border_width, depth;
- if (!XGetGeometry(GetXDisplay(), window, &root, &x, &y,
+ if (!XGetGeometry(gfx::GetXDisplay(), window, &root, &x, &y,
&width, &height, &border_width, &depth))
return false;
- if (!XTranslateCoordinates(GetXDisplay(), window, root,
+ if (!XTranslateCoordinates(gfx::GetXDisplay(), window, root,
0, 0, &x, &y, &child))
return false;
@@ -725,7 +719,7 @@ bool WindowContainsPoint(XID window, gfx::Point screen_loc) {
int dummy;
int input_rects_size = 0;
XRectangle* input_rects = XShapeGetRectangles(
- ui::GetXDisplay(), window, ShapeInput, &input_rects_size, &dummy);
+ gfx::GetXDisplay(), window, ShapeInput, &input_rects_size, &dummy);
if (!input_rects)
return true;
bool is_in_input_rects = false;
@@ -773,7 +767,7 @@ bool GetRawBytesOfProperty(XID window,
Atom prop_type = None;
int prop_format = 0;
unsigned char* property_data = NULL;
- if (XGetWindowProperty(GetXDisplay(), window, property,
+ if (XGetWindowProperty(gfx::GetXDisplay(), window, property,
0, 0x1FFFFFFF /* MAXINT32 / 4 */, False,
AnyPropertyType, &prop_type, &prop_format,
&nitems, &nbytes, &property_data) != Success) {
@@ -958,8 +952,8 @@ bool SetIntArrayProperty(XID window,
for (size_t i = 0; i < value.size(); ++i)
data[i] = value[i];
- gdk_error_trap_push();
- XChangeProperty(ui::GetXDisplay(),
+ X11ErrorTracker err_tracker;
+ XChangeProperty(gfx::GetXDisplay(),
window,
name_atom,
type_atom,
@@ -967,8 +961,7 @@ bool SetIntArrayProperty(XID window,
PropModeReplace,
reinterpret_cast<const unsigned char*>(data.get()),
value.size()); // num items
- XSync(ui::GetXDisplay(), False);
- return gdk_error_trap_pop() == 0;
+ return !err_tracker.FoundNewError();
}
bool SetAtomArrayProperty(XID window,
@@ -984,8 +977,8 @@ bool SetAtomArrayProperty(XID window,
for (size_t i = 0; i < value.size(); ++i)
data[i] = value[i];
- gdk_error_trap_push();
- XChangeProperty(ui::GetXDisplay(),
+ X11ErrorTracker err_tracker;
+ XChangeProperty(gfx::GetXDisplay(),
window,
name_atom,
type_atom,
@@ -993,8 +986,7 @@ bool SetAtomArrayProperty(XID window,
PropModeReplace,
reinterpret_cast<const unsigned char*>(data.get()),
value.size()); // num items
- XSync(ui::GetXDisplay(), False);
- return gdk_error_trap_pop() == 0;
+ return !err_tracker.FoundNewError();
}
Atom GetAtom(const char* name) {
@@ -1003,16 +995,29 @@ Atom GetAtom(const char* name) {
gdk_display_get_default(), name);
#else
// TODO(derat): Cache atoms to avoid round-trips to the server.
- return XInternAtom(GetXDisplay(), name, false);
+ return XInternAtom(gfx::GetXDisplay(), name, false);
#endif
}
+void SetWindowClassHint(XDisplay* display,
+ XID window,
+ std::string res_name,
+ std::string res_class) {
+ XClassHint class_hints;
+ // const_cast is safe because XSetClassHint does not modify the strings.
+ // Just to be safe, the res_name and res_class parameters are local copies,
+ // not const references.
+ class_hints.res_name = const_cast<char*>(res_name.c_str());
+ class_hints.res_class = const_cast<char*>(res_class.c_str());
+ XSetClassHint(display, window, &class_hints);
+}
+
XID GetParentWindow(XID window) {
XID root = None;
XID parent = None;
XID* children = NULL;
unsigned int num_children = 0;
- XQueryTree(GetXDisplay(), window, &root, &parent, &children, &num_children);
+ XQueryTree(gfx::GetXDisplay(), window, &root, &parent, &children, &num_children);
if (children)
XFree(children);
return parent;
@@ -1033,7 +1038,7 @@ bool GetWindowDesktop(XID window, int* desktop) {
return GetIntProperty(window, "_NET_WM_DESKTOP", desktop);
}
-std::string GetX11ErrorString(Display* display, int err) {
+std::string GetX11ErrorString(XDisplay* display, int err) {
char buffer[256];
XGetErrorText(display, err, buffer, arraysize(buffer));
return buffer;
@@ -1042,7 +1047,7 @@ std::string GetX11ErrorString(Display* display, int err) {
// Returns true if |window| is a named window.
bool IsWindowNamed(XID window) {
XTextProperty prop;
- if (!XGetWMName(GetXDisplay(), window, &prop) || !prop.value)
+ if (!XGetWMName(gfx::GetXDisplay(), window, &prop) || !prop.value)
return false;
XFree(prop.value);
@@ -1056,7 +1061,7 @@ bool EnumerateChildren(EnumerateWindowsDelegate* delegate, XID window,
XID root, parent, *children;
unsigned int num_children;
- int status = XQueryTree(GetXDisplay(), window, &root, &parent, &children,
+ int status = XQueryTree(gfx::GetXDisplay(), window, &root, &parent, &children,
&num_children);
if (status == 0)
return false;
@@ -1148,10 +1153,10 @@ void RestackWindow(XID window, XID sibling, bool above) {
XWindowChanges changes;
changes.sibling = sibling;
changes.stack_mode = above ? Above : Below;
- XConfigureWindow(GetXDisplay(), window, CWSibling | CWStackMode, &changes);
+ XConfigureWindow(gfx::GetXDisplay(), window, CWSibling | CWStackMode, &changes);
}
-XSharedMemoryId AttachSharedMemory(Display* display, int shared_memory_key) {
+XSharedMemoryId AttachSharedMemory(XDisplay* display, int shared_memory_key) {
DCHECK(QuerySharedMemorySupport(display));
XShmSegmentInfo shminfo;
@@ -1172,7 +1177,7 @@ XSharedMemoryId AttachSharedMemory(Display* display, int shared_memory_key) {
return shminfo.shmseg;
}
-void DetachSharedMemory(Display* display, XSharedMemoryId shmseg) {
+void DetachSharedMemory(XDisplay* display, XSharedMemoryId shmseg) {
DCHECK(QuerySharedMemorySupport(display));
XShmSegmentInfo shminfo;
@@ -1183,14 +1188,63 @@ void DetachSharedMemory(Display* display, XSharedMemoryId shmseg) {
NOTREACHED();
}
-XID CreatePictureFromSkiaPixmap(Display* display, XID pixmap) {
+bool CopyAreaToCanvas(XID drawable,
+ gfx::Rect source_bounds,
+ gfx::Point dest_offset,
+ gfx::Canvas* canvas) {
+ ui::XScopedImage scoped_image(
+ XGetImage(gfx::GetXDisplay(), drawable,
+ source_bounds.x(), source_bounds.y(),
+ source_bounds.width(), source_bounds.height(),
+ AllPlanes, ZPixmap));
+ XImage* image = scoped_image.get();
+ if (!image) {
+ LOG(ERROR) << "XGetImage failed";
+ return false;
+ }
+
+ if (image->bits_per_pixel == 32) {
+ if ((0xff << SK_R32_SHIFT) != image->red_mask ||
+ (0xff << SK_G32_SHIFT) != image->green_mask ||
+ (0xff << SK_B32_SHIFT) != image->blue_mask) {
+ LOG(WARNING) << "XImage and Skia byte orders differ";
+ return false;
+ }
+
+ // Set the alpha channel before copying to the canvas. Otherwise, areas of
+ // the framebuffer that were cleared by ply-image rather than being obscured
+ // by an image during boot may end up transparent.
+ // TODO(derat|marcheu): Remove this if/when ply-image has been updated to
+ // set the framebuffer's alpha channel regardless of whether the device
+ // claims to support alpha or not.
+ for (int i = 0; i < image->width * image->height * 4; i += 4)
+ image->data[i + 3] = 0xff;
+
+ SkBitmap bitmap;
+ bitmap.setConfig(SkBitmap::kARGB_8888_Config,
+ image->width, image->height,
+ image->bytes_per_line);
+ bitmap.setPixels(image->data);
+ gfx::ImageSkia image_skia;
+ gfx::ImageSkiaRep image_rep(bitmap, canvas->scale_factor());
+ image_skia.AddRepresentation(image_rep);
+ canvas->DrawImageInt(image_skia, dest_offset.x(), dest_offset.y());
+ } else {
+ NOTIMPLEMENTED() << "Unsupported bits-per-pixel " << image->bits_per_pixel;
+ return false;
+ }
+
+ return true;
+}
+
+XID CreatePictureFromSkiaPixmap(XDisplay* display, XID pixmap) {
XID picture = XRenderCreatePicture(
display, pixmap, GetRenderARGB32Format(display), 0, NULL);
return picture;
}
-void PutARGBImage(Display* display,
+void PutARGBImage(XDisplay* display,
void* visual, int depth,
XID pixmap, void* pixmap_gc,
const uint8* data,
@@ -1204,7 +1258,7 @@ void PutARGBImage(Display* display,
width, height);
}
-void PutARGBImage(Display* display,
+void PutARGBImage(XDisplay* display,
void* visual, int depth,
XID pixmap, void* pixmap_gc,
const uint8* data,
@@ -1309,11 +1363,11 @@ void PutARGBImage(Display* display,
}
}
-void FreePicture(Display* display, XID picture) {
+void FreePicture(XDisplay* display, XID picture) {
XRenderFreePicture(display, picture);
}
-void FreePixmap(Display* display, XID pixmap) {
+void FreePixmap(XDisplay* display, XID pixmap) {
XFreePixmap(display, pixmap);
}
@@ -1335,21 +1389,18 @@ bool GetWindowManagerName(std::string* wm_name) {
// _NET_SUPPORTING_WM_CHECK property pointing to itself (to avoid a stale
// property referencing an ID that's been recycled for another window), so we
// check that too.
- gdk_error_trap_push();
+ X11ErrorTracker err_tracker;
int wm_window_property = 0;
bool result = GetIntProperty(
wm_window, "_NET_SUPPORTING_WM_CHECK", &wm_window_property);
- gdk_flush();
- bool got_error = gdk_error_trap_pop();
- if (got_error || !result || wm_window_property != wm_window)
+ if (err_tracker.FoundNewError() || !result ||
+ wm_window_property != wm_window) {
return false;
+ }
- gdk_error_trap_push();
result = GetStringProperty(
static_cast<XID>(wm_window), "_NET_WM_NAME", wm_name);
- gdk_flush();
- got_error = gdk_error_trap_pop();
- return !got_error && result;
+ return !err_tracker.FoundNewError() && result;
}
WindowManagerName GuessWindowManager() {
@@ -1402,7 +1453,7 @@ bool ChangeWindowDesktop(XID window, XID destination) {
event.xclient.data.l[0] = desktop;
event.xclient.data.l[1] = 1; // source indication
- int result = XSendEvent(GetXDisplay(), GetX11RootWindow(), False,
+ int result = XSendEvent(gfx::GetXDisplay(), GetX11RootWindow(), False,
SubstructureNotifyMask, &event);
return result == Success;
}
@@ -1453,7 +1504,7 @@ bool IsX11WindowFullScreen(XID window) {
//
// TODO(erg): Actually doing this correctly would require pulling out xrandr,
// which we don't even do in the desktop screen yet.
- ::Display* display = ui::GetXDisplay();
+ ::XDisplay* display = gfx::GetXDisplay();
::Screen* screen = DefaultScreenOfDisplay(display);
int width = WidthOfScreen(screen);
int height = HeightOfScreen(screen);
@@ -1481,7 +1532,7 @@ void InitXKeyEventForTesting(EventType type,
int flags,
XEvent* event) {
CHECK(event);
- Display* display = GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
XKeyEvent key_event;
key_event.type = XKeyEventType(type);
CHECK_NE(0, key_event.type);
@@ -1531,7 +1582,7 @@ void XScopedImage::reset(XImage* image) {
image_ = image;
}
-XScopedCursor::XScopedCursor(::Cursor cursor, Display* display)
+XScopedCursor::XScopedCursor(::Cursor cursor, XDisplay* display)
: cursor_(cursor),
display_(display) {
}
@@ -1553,7 +1604,7 @@ void XScopedCursor::reset(::Cursor cursor) {
// ----------------------------------------------------------------------------
// These functions are declared in x11_util_internal.h because they require
// XLib.h to be included, and it conflicts with many other headers.
-XRenderPictFormat* GetRenderARGB32Format(Display* dpy) {
+XRenderPictFormat* GetRenderARGB32Format(XDisplay* dpy) {
static XRenderPictFormat* pictformat = NULL;
if (pictformat)
return pictformat;
@@ -1589,7 +1640,7 @@ XRenderPictFormat* GetRenderARGB32Format(Display* dpy) {
return pictformat;
}
-XRenderPictFormat* GetRenderVisualFormat(Display* dpy, Visual* visual) {
+XRenderPictFormat* GetRenderVisualFormat(XDisplay* dpy, Visual* visual) {
DCHECK(QueryRenderSupport(dpy));
CachedPictFormats* formats = get_cached_pict_formats();
@@ -1633,7 +1684,7 @@ void SetX11ErrorHandlers(XErrorHandler error_handler,
io_error_handler ? io_error_handler : DefaultX11IOErrorHandler);
}
-void LogErrorEventDescription(Display* dpy,
+void LogErrorEventDescription(XDisplay* dpy,
const XErrorEvent& error_event) {
char error_str[256];
char request_str[256];
@@ -1665,7 +1716,7 @@ void LogErrorEventDescription(Display* dpy,
XFreeExtensionList(ext_list);
}
- LOG(ERROR)
+ LOG(WARNING)
<< "X error received: "
<< "serial " << error_event.serial << ", "
<< "error_code " << static_cast<int>(error_event.error_code)
diff --git a/chromium/ui/base/x/x11_util.h b/chromium/ui/base/x/x11_util.h
index c1c72ba0191..c528e908900 100644
--- a/chromium/ui/base/x/x11_util.h
+++ b/chromium/ui/base/x/x11_util.h
@@ -17,20 +17,17 @@
#include "base/basictypes.h"
#include "base/event_types.h"
#include "base/memory/ref_counted_memory.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/point.h"
+#include "ui/gfx/x/x11_types.h"
typedef unsigned long Atom;
-typedef unsigned long XID;
typedef unsigned long XSharedMemoryId; // ShmSeg in the X headers.
-typedef struct _XDisplay Display;
typedef unsigned long Cursor;
typedef struct _XcursorImage XcursorImage;
typedef union _XEvent XEvent;
-typedef struct _XImage XImage;
-typedef struct _XGC *GC;
#if defined(TOOLKIT_GTK)
typedef struct _GdkDrawable GdkWindow;
@@ -39,13 +36,15 @@ typedef struct _GtkWindow GtkWindow;
#endif
namespace gfx {
+class Canvas;
+class Point;
class Rect;
}
class SkBitmap;
namespace ui {
-// These functions use the GDK default display and this /must/ be called from
+// These functions use the default display and this /must/ be called from
// the UI thread. Thus, they don't support multiple displays.
// These functions cache their results ---------------------------------
@@ -54,11 +53,6 @@ namespace ui {
UI_EXPORT bool XDisplayExists();
// Return an X11 connection for the current, primary display.
-// TODO(oshima|evan): This assume there is one display and dosn't work
-// undef mutiple displays/monitor environment. Remove this and change the
-// chrome codebase to get the display from window.
-UI_EXPORT Display* GetXDisplay();
-
// X shared memory comes in three flavors:
// 1) No SHM support,
// 2) SHM putimage,
@@ -69,13 +63,13 @@ enum SharedMemorySupport {
SHARED_MEMORY_PIXMAP
};
// Return the shared memory type of our X connection.
-UI_EXPORT SharedMemorySupport QuerySharedMemorySupport(Display* dpy);
+UI_EXPORT SharedMemorySupport QuerySharedMemorySupport(XDisplay* dpy);
// Return true iff the display supports Xrender
-UI_EXPORT bool QueryRenderSupport(Display* dpy);
+UI_EXPORT bool QueryRenderSupport(XDisplay* dpy);
// Return the default screen number for the display
-int GetDefaultScreen(Display* display);
+int GetDefaultScreen(XDisplay* display);
// Returns an X11 Cursor, sharable across the process.
// |cursor_shape| is an X font cursor shape, see XCreateFontCursor().
@@ -151,7 +145,7 @@ UI_EXPORT void SetHideTitlebarWhenMaximizedProperty(
UI_EXPORT void ClearX11DefaultRootWindow();
// Return the number of bits-per-pixel for a pixmap of the given depth
-UI_EXPORT int BitsPerPixelForPixmapDepth(Display* display, int depth);
+UI_EXPORT int BitsPerPixelForPixmapDepth(XDisplay* display, int depth);
// Returns true if |window| is visible.
UI_EXPORT bool IsWindowVisible(XID window);
@@ -209,6 +203,12 @@ UI_EXPORT bool SetAtomArrayProperty(XID window,
// Gets the X atom for default display corresponding to atom_name.
Atom GetAtom(const char* atom_name);
+// Sets the WM_CLASS attribute for a given X11 window.
+UI_EXPORT void SetWindowClassHint(XDisplay* display,
+ XID window,
+ std::string res_name,
+ std::string res_class);
+
// Get |window|'s parent window, or None if |window| is the root window.
UI_EXPORT XID GetParentWindow(XID window);
@@ -221,7 +221,7 @@ static const int kAllDesktops = -1;
bool GetWindowDesktop(XID window, int* desktop);
// Translates an X11 error code into a printable string.
-UI_EXPORT std::string GetX11ErrorString(Display* display, int err);
+UI_EXPORT std::string GetX11ErrorString(XDisplay* display, int err);
// Implementers of this interface receive a notification for every X window of
// the main display.
@@ -255,19 +255,29 @@ void RestackWindow(XID window, XID sibling, bool above);
// Return a handle to a X ShmSeg. |shared_memory_key| is a SysV
// IPC key. The shared memory region must contain 32-bit pixels.
-UI_EXPORT XSharedMemoryId AttachSharedMemory(Display* display,
+UI_EXPORT XSharedMemoryId AttachSharedMemory(XDisplay* display,
int shared_memory_support);
-UI_EXPORT void DetachSharedMemory(Display* display, XSharedMemoryId shmseg);
+UI_EXPORT void DetachSharedMemory(XDisplay* display, XSharedMemoryId shmseg);
+
+// Copies |source_bounds| from |drawable| to |canvas| at offset |dest_offset|.
+// |source_bounds| is in physical pixels, while |dest_offset| is relative to
+// the canvas's scale. Note that this function is slow since it uses
+// XGetImage() to copy the data from the X server to this process before
+// copying it to |canvas|.
+UI_EXPORT bool CopyAreaToCanvas(XID drawable,
+ gfx::Rect source_bounds,
+ gfx::Point dest_offset,
+ gfx::Canvas* canvas);
// Return a handle to an XRender picture where |pixmap| is a handle to a
// pixmap containing Skia ARGB data.
-UI_EXPORT XID CreatePictureFromSkiaPixmap(Display* display, XID pixmap);
+UI_EXPORT XID CreatePictureFromSkiaPixmap(XDisplay* display, XID pixmap);
// Draws ARGB data on the given pixmap using the given GC, converting to the
// server side visual depth as needed. Destination is assumed to be the same
// dimensions as |data| or larger. |data| is also assumed to be in row order
// with each line being exactly |width| * 4 bytes long.
-UI_EXPORT void PutARGBImage(Display* display,
+UI_EXPORT void PutARGBImage(XDisplay* display,
void* visual, int depth,
XID pixmap, void* pixmap_gc,
const uint8* data,
@@ -277,7 +287,7 @@ UI_EXPORT void PutARGBImage(Display* display,
// - |data_width| and |data_height| refer to the data image
// - |src_x|, |src_y|, |copy_width| and |copy_height| define source region
// - |dst_x|, |dst_y|, |copy_width| and |copy_height| define destination region
-UI_EXPORT void PutARGBImage(Display* display,
+UI_EXPORT void PutARGBImage(XDisplay* display,
void* visual, int depth,
XID pixmap, void* pixmap_gc,
const uint8* data,
@@ -286,8 +296,8 @@ UI_EXPORT void PutARGBImage(Display* display,
int dst_x, int dst_y,
int copy_width, int copy_height);
-void FreePicture(Display* display, XID picture);
-void FreePixmap(Display* display, XID pixmap);
+void FreePicture(XDisplay* display, XID picture);
+void FreePixmap(XDisplay* display, XID pixmap);
enum WindowManagerName {
WM_UNKNOWN,
@@ -401,7 +411,7 @@ class UI_EXPORT XScopedImage {
class UI_EXPORT XScopedCursor {
public:
// Keeps track of |cursor| created with |display|.
- XScopedCursor(::Cursor cursor, Display* display);
+ XScopedCursor(::Cursor cursor, XDisplay* display);
~XScopedCursor();
::Cursor get() const;
@@ -409,7 +419,7 @@ class UI_EXPORT XScopedCursor {
private:
::Cursor cursor_;
- Display* display_;
+ XDisplay* display_;
DISALLOW_COPY_AND_ASSIGN(XScopedCursor);
};
diff --git a/chromium/ui/compositor/DEPS b/chromium/ui/compositor/DEPS
index 66c3932cf54..7a2d98ba46f 100644
--- a/chromium/ui/compositor/DEPS
+++ b/chromium/ui/compositor/DEPS
@@ -4,6 +4,5 @@
include_rules = [
"+cc",
"+third_party/WebKit/public/platform/WebGraphicsContext3D.h",
- "+third_party/WebKit/public/platform/WebString.h",
"+webkit/common/gpu",
]
diff --git a/chromium/ui/compositor/OWNERS b/chromium/ui/compositor/OWNERS
index 1faff3677f2..d2216223c29 100644
--- a/chromium/ui/compositor/OWNERS
+++ b/chromium/ui/compositor/OWNERS
@@ -1,3 +1,6 @@
danakj@chromium.org
piman@chromium.org
vollick@chromium.org
+
+# Animation
+per-file *animat*=ajuma@chromium.org
diff --git a/chromium/ui/compositor/compositor.cc b/chromium/ui/compositor/compositor.cc
index f16e56bf827..47ded5eb690 100644
--- a/chromium/ui/compositor/compositor.cc
+++ b/chromium/ui/compositor/compositor.cc
@@ -9,6 +9,7 @@
#include "base/bind.h"
#include "base/command_line.h"
+#include "base/debug/trace_event.h"
#include "base/memory/singleton.h"
#include "base/message_loop/message_loop.h"
#include "base/run_loop.h"
@@ -16,6 +17,8 @@
#include "base/threading/thread.h"
#include "base/threading/thread_restrictions.h"
#include "cc/base/switches.h"
+#include "cc/debug/test_context_provider.h"
+#include "cc/debug/test_web_graphics_context_3d.h"
#include "cc/input/input_handler.h"
#include "cc/layers/layer.h"
#include "cc/output/context_provider.h"
@@ -24,15 +27,14 @@
#include "third_party/skia/include/core/SkBitmap.h"
#include "ui/compositor/compositor_observer.h"
#include "ui/compositor/compositor_switches.h"
-#include "ui/compositor/context_provider_from_context_factory.h"
#include "ui/compositor/dip_util.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/reflector.h"
-#include "ui/compositor/test_web_graphics_context_3d.h"
#include "ui/gl/gl_context.h"
#include "ui/gl/gl_implementation.h"
#include "ui/gl/gl_surface.h"
#include "ui/gl/gl_switches.h"
+#include "webkit/common/gpu/context_provider_in_process.h"
#include "webkit/common/gpu/grcontext_for_webgraphicscontext3d.h"
#include "webkit/common/gpu/webgraphicscontext3d_in_process_command_buffer_impl.h"
@@ -108,13 +110,24 @@ bool DefaultContextFactory::Initialize() {
scoped_ptr<cc::OutputSurface> DefaultContextFactory::CreateOutputSurface(
Compositor* compositor) {
- return make_scoped_ptr(new cc::OutputSurface(
- CreateContextCommon(compositor, false)));
-}
+ WebKit::WebGraphicsContext3D::Attributes attrs;
+ attrs.depth = false;
+ attrs.stencil = false;
+ attrs.antialias = false;
+ attrs.shareResources = true;
-scoped_ptr<WebKit::WebGraphicsContext3D>
-DefaultContextFactory::CreateOffscreenContext() {
- return CreateContextCommon(NULL, true);
+ using webkit::gpu::WebGraphicsContext3DInProcessCommandBufferImpl;
+ scoped_ptr<WebGraphicsContext3DInProcessCommandBufferImpl> context3d(
+ WebGraphicsContext3DInProcessCommandBufferImpl::CreateViewContext(
+ attrs, compositor->widget()));
+ CHECK(context3d);
+
+ using webkit::gpu::ContextProviderInProcess;
+ scoped_refptr<ContextProviderInProcess> context_provider =
+ ContextProviderInProcess::Create(context3d.Pass(),
+ "UICompositor");
+
+ return make_scoped_ptr(new cc::OutputSurface(context_provider));
}
scoped_refptr<Reflector> DefaultContextFactory::CreateReflector(
@@ -132,7 +145,7 @@ DefaultContextFactory::OffscreenContextProviderForMainThread() {
if (!offscreen_contexts_main_thread_.get() ||
!offscreen_contexts_main_thread_->DestroyedOnMainThread()) {
offscreen_contexts_main_thread_ =
- ContextProviderFromContextFactory::CreateForOffscreen(this);
+ webkit::gpu::ContextProviderInProcess::CreateOffscreen();
if (offscreen_contexts_main_thread_.get() &&
!offscreen_contexts_main_thread_->BindToCurrentThread())
offscreen_contexts_main_thread_ = NULL;
@@ -145,7 +158,7 @@ DefaultContextFactory::OffscreenContextProviderForCompositorThread() {
if (!offscreen_contexts_compositor_thread_.get() ||
!offscreen_contexts_compositor_thread_->DestroyedOnMainThread()) {
offscreen_contexts_compositor_thread_ =
- ContextProviderFromContextFactory::CreateForOffscreen(this);
+ webkit::gpu::ContextProviderInProcess::CreateOffscreen();
}
return offscreen_contexts_compositor_thread_;
}
@@ -155,39 +168,14 @@ void DefaultContextFactory::RemoveCompositor(Compositor* compositor) {
bool DefaultContextFactory::DoesCreateTestContexts() { return false; }
-scoped_ptr<WebKit::WebGraphicsContext3D>
-DefaultContextFactory::CreateContextCommon(Compositor* compositor,
- bool offscreen) {
- DCHECK(offscreen || compositor);
- WebKit::WebGraphicsContext3D::Attributes attrs;
- attrs.depth = false;
- attrs.stencil = false;
- attrs.antialias = false;
- attrs.shareResources = true;
- using webkit::gpu::WebGraphicsContext3DInProcessCommandBufferImpl;
- if (offscreen) {
- return WebGraphicsContext3DInProcessCommandBufferImpl::
- CreateOffscreenContext(attrs);
- }
- return WebGraphicsContext3DInProcessCommandBufferImpl::CreateViewContext(
- attrs, compositor->widget());
-}
-
TestContextFactory::TestContextFactory() {}
TestContextFactory::~TestContextFactory() {}
scoped_ptr<cc::OutputSurface> TestContextFactory::CreateOutputSurface(
Compositor* compositor) {
- return make_scoped_ptr(new cc::OutputSurface(CreateOffscreenContext()));
-}
-
-scoped_ptr<WebKit::WebGraphicsContext3D>
-TestContextFactory::CreateOffscreenContext() {
- scoped_ptr<ui::TestWebGraphicsContext3D> context(
- new ui::TestWebGraphicsContext3D);
- context->Initialize();
- return context.PassAs<WebKit::WebGraphicsContext3D>();
+ return make_scoped_ptr(
+ new cc::OutputSurface(cc::TestContextProvider::Create()));
}
scoped_refptr<Reflector> TestContextFactory::CreateReflector(
@@ -203,8 +191,7 @@ scoped_refptr<cc::ContextProvider>
TestContextFactory::OffscreenContextProviderForMainThread() {
if (!offscreen_contexts_main_thread_.get() ||
offscreen_contexts_main_thread_->DestroyedOnMainThread()) {
- offscreen_contexts_main_thread_ =
- ContextProviderFromContextFactory::CreateForOffscreen(this);
+ offscreen_contexts_main_thread_ = cc::TestContextProvider::Create();
CHECK(offscreen_contexts_main_thread_->BindToCurrentThread());
}
return offscreen_contexts_main_thread_;
@@ -214,8 +201,7 @@ scoped_refptr<cc::ContextProvider>
TestContextFactory::OffscreenContextProviderForCompositorThread() {
if (!offscreen_contexts_compositor_thread_.get() ||
offscreen_contexts_compositor_thread_->DestroyedOnMainThread()) {
- offscreen_contexts_compositor_thread_ =
- ContextProviderFromContextFactory::CreateForOffscreen(this);
+ offscreen_contexts_compositor_thread_ = cc::TestContextProvider::Create();
}
return offscreen_contexts_compositor_thread_;
}
@@ -400,6 +386,8 @@ Compositor::Compositor(CompositorDelegate* delegate,
ContextFactory::GetInstance()->DoesCreateTestContexts()
? kTestRefreshRate
: kDefaultRefreshRate;
+ settings.deadline_scheduling_enabled =
+ switches::IsUIDeadlineSchedulingEnabled();
settings.partial_swap_enabled =
!command_line->HasSwitch(cc::switches::kUIDisablePartialSwap);
settings.per_tile_painting_enabled =
@@ -434,6 +422,8 @@ Compositor::Compositor(CompositorDelegate* delegate,
}
Compositor::~Compositor() {
+ TRACE_EVENT0("shutdown", "Compositor::destructor");
+
DCHECK(g_compositor_initialized);
CancelCompositorLock();
@@ -453,7 +443,10 @@ Compositor::~Compositor() {
// static
void Compositor::InitializeContextFactoryForTests(bool allow_test_contexts) {
- DCHECK(!g_context_factory) << "ContextFactory already initialized.";
+ // The factory may already have been initialized by the content layer, in
+ // which case, use that one.
+ if (g_context_factory)
+ return;
DCHECK(!g_implicit_factory) <<
"ContextFactory for tests already initialized.";
diff --git a/chromium/ui/compositor/compositor.gyp b/chromium/ui/compositor/compositor.gyp
index 57a4aafae21..de62e6d8af9 100644
--- a/chromium/ui/compositor/compositor.gyp
+++ b/chromium/ui/compositor/compositor.gyp
@@ -30,8 +30,6 @@
'compositor_observer.h',
'compositor_switches.cc',
'compositor_switches.h',
- 'context_provider_from_context_factory.cc',
- 'context_provider_from_context_factory.h',
'debug_utils.cc',
'debug_utils.h',
'dip_util.cc',
@@ -58,9 +56,6 @@
'scoped_animation_duration_scale_mode.h',
'scoped_layer_animation_settings.cc',
'scoped_layer_animation_settings.h',
- # UI tests need TestWebGraphicsContext3D, so we always build it.
- 'test_web_graphics_context_3d.cc',
- 'test_web_graphics_context_3d.h',
'transform_animation_curve_adapter.cc',
'transform_animation_curve_adapter.h',
],
@@ -128,6 +123,7 @@
'test/test_layer_animation_observer.h',
'test/test_utils.cc',
'test/test_utils.h',
+ 'transform_animation_curve_adapter_unittest.cc',
],
'conditions': [
# osmesa GL implementation is used on linux.
diff --git a/chromium/ui/compositor/compositor.h b/chromium/ui/compositor/compositor.h
index 92cdd7194f8..e6ce889f525 100644
--- a/chromium/ui/compositor/compositor.h
+++ b/chromium/ui/compositor/compositor.h
@@ -34,6 +34,7 @@ class ContextProvider;
class Layer;
class LayerTreeDebugState;
class LayerTreeHost;
+class TestContextProvider;
}
namespace gfx {
@@ -49,6 +50,13 @@ namespace WebKit {
class WebGraphicsContext3D;
}
+namespace webkit {
+namespace gpu {
+class ContextProviderInProcess;
+class WebGraphicsContext3DInProcessCommandBufferImpl;
+}
+}
+
namespace ui {
class Compositor;
@@ -80,10 +88,6 @@ class COMPOSITOR_EXPORT ContextFactory {
virtual scoped_ptr<cc::OutputSurface> CreateOutputSurface(
Compositor* compositor) = 0;
- // Creates a context used for offscreen rendering. This context can be shared
- // with all compositors.
- virtual scoped_ptr<WebKit::WebGraphicsContext3D> CreateOffscreenContext() = 0;
-
// Creates a reflector that copies the content of the |mirrored_compositor|
// onto |mirroing_layer|.
virtual scoped_refptr<Reflector> CreateReflector(
@@ -114,8 +118,6 @@ class COMPOSITOR_EXPORT DefaultContextFactory : public ContextFactory {
// ContextFactory implementation
virtual scoped_ptr<cc::OutputSurface> CreateOutputSurface(
Compositor* compositor) OVERRIDE;
- virtual scoped_ptr<WebKit::WebGraphicsContext3D> CreateOffscreenContext()
- OVERRIDE;
virtual scoped_refptr<Reflector> CreateReflector(
Compositor* compositor,
@@ -132,13 +134,9 @@ class COMPOSITOR_EXPORT DefaultContextFactory : public ContextFactory {
bool Initialize();
private:
- scoped_ptr<WebKit::WebGraphicsContext3D> CreateContextCommon(
- Compositor* compositor,
- bool offscreen);
-
- scoped_refptr<ContextProviderFromContextFactory>
+ scoped_refptr<webkit::gpu::ContextProviderInProcess>
offscreen_contexts_main_thread_;
- scoped_refptr<ContextProviderFromContextFactory>
+ scoped_refptr<webkit::gpu::ContextProviderInProcess>
offscreen_contexts_compositor_thread_;
DISALLOW_COPY_AND_ASSIGN(DefaultContextFactory);
@@ -153,8 +151,6 @@ class COMPOSITOR_EXPORT TestContextFactory : public ContextFactory {
// ContextFactory implementation
virtual scoped_ptr<cc::OutputSurface> CreateOutputSurface(
Compositor* compositor) OVERRIDE;
- virtual scoped_ptr<WebKit::WebGraphicsContext3D> CreateOffscreenContext()
- OVERRIDE;
virtual scoped_refptr<Reflector> CreateReflector(
Compositor* mirrored_compositor,
@@ -169,10 +165,8 @@ class COMPOSITOR_EXPORT TestContextFactory : public ContextFactory {
virtual bool DoesCreateTestContexts() OVERRIDE;
private:
- scoped_refptr<ContextProviderFromContextFactory>
- offscreen_contexts_main_thread_;
- scoped_refptr<ContextProviderFromContextFactory>
- offscreen_contexts_compositor_thread_;
+ scoped_refptr<cc::TestContextProvider> offscreen_contexts_main_thread_;
+ scoped_refptr<cc::TestContextProvider> offscreen_contexts_compositor_thread_;
DISALLOW_COPY_AND_ASSIGN(TestContextFactory);
};
diff --git a/chromium/ui/compositor/compositor_switches.cc b/chromium/ui/compositor/compositor_switches.cc
index 7f1bd230a25..39b929a954d 100644
--- a/chromium/ui/compositor/compositor_switches.cc
+++ b/chromium/ui/compositor/compositor_switches.cc
@@ -4,12 +4,18 @@
#include "ui/compositor/compositor_switches.h"
+#include "base/command_line.h"
+
namespace switches {
const char kDisableTestCompositor[] = "disable-test-compositor";
+const char kUIDisableDeadlineScheduling[] = "ui-disable-deadline-scheduling";
+
const char kUIDisableThreadedCompositing[] = "ui-disable-threaded-compositing";
+const char kUIEnableDeadlineScheduling[] = "ui-enable-deadline-scheduling";
+
const char kUIEnableSoftwareCompositing[] = "ui-enable-software-compositing";
const char kUIEnableThreadedCompositing[] = "ui-enable-threaded-compositing";
@@ -18,4 +24,17 @@ const char kUIMaxFramesPending[] = "ui-max-frames-pending";
const char kUIShowPaintRects[] = "ui-show-paint-rects";
+bool IsUIDeadlineSchedulingEnabled() {
+ const CommandLine& command_line = *CommandLine::ForCurrentProcess();
+
+ // Default to disabled.
+ bool enabled = false;
+
+ // Flags override.
+ enabled |= command_line.HasSwitch(switches::kUIEnableDeadlineScheduling);
+ enabled &= !command_line.HasSwitch(switches::kUIDisableDeadlineScheduling);
+
+ return enabled;
+}
+
} // namespace switches
diff --git a/chromium/ui/compositor/compositor_switches.h b/chromium/ui/compositor/compositor_switches.h
index 5b59477a948..2bf2b242260 100644
--- a/chromium/ui/compositor/compositor_switches.h
+++ b/chromium/ui/compositor/compositor_switches.h
@@ -10,12 +10,16 @@
namespace switches {
COMPOSITOR_EXPORT extern const char kDisableTestCompositor[];
+COMPOSITOR_EXPORT extern const char kUIDisableDeadlineScheduling[];
COMPOSITOR_EXPORT extern const char kUIDisableThreadedCompositing[];
+COMPOSITOR_EXPORT extern const char kUIEnableDeadlineScheduling[];
COMPOSITOR_EXPORT extern const char kUIEnableSoftwareCompositing[];
COMPOSITOR_EXPORT extern const char kUIEnableThreadedCompositing[];
COMPOSITOR_EXPORT extern const char kUIMaxFramesPending[];
COMPOSITOR_EXPORT extern const char kUIShowPaintRects[];
+COMPOSITOR_EXPORT bool IsUIDeadlineSchedulingEnabled();
+
} // namespace switches
#endif // UI_COMPOSITOR_COMPOSITOR_SWITCHES_H_
diff --git a/chromium/ui/compositor/context_provider_from_context_factory.cc b/chromium/ui/compositor/context_provider_from_context_factory.cc
deleted file mode 100644
index 262998a886a..00000000000
--- a/chromium/ui/compositor/context_provider_from_context_factory.cc
+++ /dev/null
@@ -1,76 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "context_provider_from_context_factory.h"
-
-#include "base/logging.h"
-
-namespace ui {
-
-// static
-scoped_refptr<ContextProviderFromContextFactory>
-ContextProviderFromContextFactory::CreateForOffscreen(ContextFactory* factory) {
- scoped_refptr<ContextProviderFromContextFactory> provider =
- new ContextProviderFromContextFactory(factory);
- if (!provider->InitializeOnMainThread())
- return NULL;
- return provider;
-}
-
-ContextProviderFromContextFactory::ContextProviderFromContextFactory(
- ContextFactory* factory)
- : factory_(factory),
- destroyed_(false) {
-}
-
-ContextProviderFromContextFactory::~ContextProviderFromContextFactory() {
-}
-
-bool ContextProviderFromContextFactory::BindToCurrentThread() {
- DCHECK(context3d_);
- return context3d_->makeContextCurrent();
-}
-
-WebKit::WebGraphicsContext3D* ContextProviderFromContextFactory::Context3d() {
- DCHECK(context3d_);
- return context3d_.get();
-}
-
-class GrContext* ContextProviderFromContextFactory::GrContext() {
- DCHECK(context3d_);
-
- if (!gr_context_) {
- gr_context_.reset(
- new webkit::gpu::GrContextForWebGraphicsContext3D(context3d_.get()));
- }
- return gr_context_->get();
-}
-
-void ContextProviderFromContextFactory::VerifyContexts() {
- DCHECK(context3d_);
-
- if (context3d_->isContextLost()) {
- base::AutoLock lock(destroyed_lock_);
- destroyed_ = true;
- }
-}
-
-bool ContextProviderFromContextFactory::DestroyedOnMainThread() {
- base::AutoLock lock(destroyed_lock_);
- return destroyed_;
-}
-
-void ContextProviderFromContextFactory::SetLostContextCallback(
- const LostContextCallback& cb) {
- NOTIMPLEMENTED();
-}
-
-bool ContextProviderFromContextFactory::InitializeOnMainThread() {
- if (context3d_)
- return true;
- context3d_ = factory_->CreateOffscreenContext();
- return !!context3d_;
-}
-
-} // namespace ui
diff --git a/chromium/ui/compositor/context_provider_from_context_factory.h b/chromium/ui/compositor/context_provider_from_context_factory.h
deleted file mode 100644
index 57be7f47efd..00000000000
--- a/chromium/ui/compositor/context_provider_from_context_factory.h
+++ /dev/null
@@ -1,45 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_COMPOSITOR_CONTEXT_PROVIDER_FROM_CONTEXT_FACTORY_H_
-#define UI_COMPOSITOR_CONTEXT_PROVIDER_FROM_CONTEXT_FACTORY_H_
-
-#include "base/synchronization/lock.h"
-#include "cc/output/context_provider.h"
-#include "third_party/WebKit/public/platform/WebGraphicsContext3D.h"
-#include "ui/compositor/compositor.h"
-#include "webkit/common/gpu/grcontext_for_webgraphicscontext3d.h"
-
-namespace ui {
-
-class ContextProviderFromContextFactory
- : public cc::ContextProvider {
- public:
- static scoped_refptr<ContextProviderFromContextFactory> CreateForOffscreen(
- ContextFactory* factory);
-
- virtual bool BindToCurrentThread() OVERRIDE;
- virtual WebKit::WebGraphicsContext3D* Context3d() OVERRIDE;
- virtual class GrContext* GrContext() OVERRIDE;
- virtual void VerifyContexts() OVERRIDE;
- virtual bool DestroyedOnMainThread() OVERRIDE;
- virtual void SetLostContextCallback(const LostContextCallback& cb) OVERRIDE;
-
- protected:
- ContextProviderFromContextFactory(ContextFactory* factory);
- virtual ~ContextProviderFromContextFactory();
-
- bool InitializeOnMainThread();
-
- private:
- ContextFactory* factory_;
- base::Lock destroyed_lock_;
- bool destroyed_;
- scoped_ptr<WebKit::WebGraphicsContext3D> context3d_;
- scoped_ptr<webkit::gpu::GrContextForWebGraphicsContext3D> gr_context_;
-};
-
-} // namespace ui
-
-#endif // UI_COMPOSITOR_CONTEXT_PROVIDER_FROM_CONTEXT_FACTORY_H_
diff --git a/chromium/ui/compositor/debug_utils.cc b/chromium/ui/compositor/debug_utils.cc
index 016ff17eeb1..e1f62f9d42d 100644
--- a/chromium/ui/compositor/debug_utils.cc
+++ b/chromium/ui/compositor/debug_utils.cc
@@ -28,9 +28,8 @@ void PrintLayerHierarchyImp(const Layer* layer,
gfx::Point mouse_location,
std::wostringstream* out) {
std::string indent_str(indent, ' ');
- std::string content_indent_str(indent+1, ' ');
- layer->transform().TransformPointReverse(mouse_location);
+ layer->transform().TransformPointReverse(&mouse_location);
bool mouse_inside_layer_bounds = layer->bounds().Contains(mouse_location);
mouse_location.Offset(-layer->bounds().x(), -layer->bounds().y());
diff --git a/chromium/ui/compositor/dip_util.cc b/chromium/ui/compositor/dip_util.cc
index 1f6309a42b5..2d95af63830 100644
--- a/chromium/ui/compositor/dip_util.cc
+++ b/chromium/ui/compositor/dip_util.cc
@@ -5,7 +5,6 @@
#include "ui/compositor/dip_util.h"
#include "base/command_line.h"
-#include "ui/base/ui_base_switches.h"
#include "ui/compositor/compositor.h"
#include "ui/compositor/compositor_switches.h"
#include "ui/compositor/layer.h"
diff --git a/chromium/ui/compositor/float_animation_curve_adapter.cc b/chromium/ui/compositor/float_animation_curve_adapter.cc
index e97fbf0b700..ec41f964d91 100644
--- a/chromium/ui/compositor/float_animation_curve_adapter.cc
+++ b/chromium/ui/compositor/float_animation_curve_adapter.cc
@@ -7,7 +7,7 @@
namespace ui {
FloatAnimationCurveAdapter::FloatAnimationCurveAdapter(
- Tween::Type tween_type,
+ gfx::Tween::Type tween_type,
float initial_value,
float target_value,
base::TimeDelta duration)
@@ -36,9 +36,10 @@ float FloatAnimationCurveAdapter::GetValue(double t) const {
if (t <= 0.0)
return initial_value_;
double progress = t / duration_.InSecondsF();
- return Tween::ValueBetween(Tween::CalculateValue(tween_type_, progress),
- initial_value_,
- target_value_);
+ return gfx::Tween::ValueBetween(
+ gfx::Tween::CalculateValue(tween_type_, progress),
+ initial_value_,
+ target_value_);
}
} // namespace ui
diff --git a/chromium/ui/compositor/float_animation_curve_adapter.h b/chromium/ui/compositor/float_animation_curve_adapter.h
index 0e073aaa73f..9959772769f 100644
--- a/chromium/ui/compositor/float_animation_curve_adapter.h
+++ b/chromium/ui/compositor/float_animation_curve_adapter.h
@@ -7,13 +7,13 @@
#include "base/time/time.h"
#include "cc/animation/animation_curve.h"
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/tween.h"
namespace ui {
class FloatAnimationCurveAdapter : public cc::FloatAnimationCurve {
public:
- FloatAnimationCurveAdapter(Tween::Type tween_type,
+ FloatAnimationCurveAdapter(gfx::Tween::Type tween_type,
float initial_value,
float target_value,
base::TimeDelta duration);
@@ -26,7 +26,7 @@ class FloatAnimationCurveAdapter : public cc::FloatAnimationCurve {
virtual float GetValue(double t) const OVERRIDE;
private:
- Tween::Type tween_type_;
+ gfx::Tween::Type tween_type_;
float initial_value_;
float target_value_;
base::TimeDelta duration_;
diff --git a/chromium/ui/compositor/layer.cc b/chromium/ui/compositor/layer.cc
index 6c0fde3e1c5..1e7a029f569 100644
--- a/chromium/ui/compositor/layer.cc
+++ b/chromium/ui/compositor/layer.cc
@@ -20,10 +20,10 @@
#include "cc/output/filter_operation.h"
#include "cc/output/filter_operations.h"
#include "cc/resources/transferable_resource.h"
-#include "ui/base/animation/animation.h"
#include "ui/compositor/compositor_switches.h"
#include "ui/compositor/dip_util.h"
#include "ui/compositor/layer_animator.h"
+#include "ui/gfx/animation/animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/display.h"
#include "ui/gfx/interpolated_transform.h"
@@ -444,6 +444,7 @@ void Layer::SwitchToLayer(scoped_refptr<cc::Layer> new_layer) {
DCHECK(parent_->cc_layer_);
parent_->cc_layer_->ReplaceChild(cc_layer_, new_layer);
}
+ cc_layer_->SetLayerClient(NULL);
cc_layer_->RemoveLayerAnimationEventObserver(this);
new_layer->SetOpacity(cc_layer_->opacity());
new_layer->SetTransform(cc_layer_->transform());
@@ -460,6 +461,7 @@ void Layer::SwitchToLayer(scoped_refptr<cc::Layer> new_layer) {
DCHECK(children_[i]->cc_layer_);
cc_layer_->AddChild(children_[i]->cc_layer_);
}
+ cc_layer_->SetLayerClient(this);
cc_layer_->SetAnchorPoint(gfx::PointF());
cc_layer_->SetContentsOpaque(fills_bounds_opaquely_);
cc_layer_->SetForceRenderSurface(force_render_surface_);
@@ -496,13 +498,16 @@ void Layer::SetExternalTexture(Texture* texture) {
cc::ContentLayer::Create(this);
SwitchToLayer(new_layer);
content_layer_ = new_layer;
+ mailbox_ = cc::TextureMailbox();
}
}
RecomputeDrawsContentAndUVRect();
}
-void Layer::SetTextureMailbox(const cc::TextureMailbox& mailbox,
- float scale_factor) {
+void Layer::SetTextureMailbox(
+ const cc::TextureMailbox& mailbox,
+ scoped_ptr<cc::SingleReleaseCallback> release_callback,
+ float scale_factor) {
DCHECK_EQ(type_, LAYER_TEXTURED);
DCHECK(!solid_color_layer_.get());
layer_updated_externally_ = true;
@@ -514,7 +519,7 @@ void Layer::SetTextureMailbox(const cc::TextureMailbox& mailbox,
SwitchToLayer(new_layer);
texture_layer_ = new_layer;
}
- texture_layer_->SetTextureMailbox(mailbox);
+ texture_layer_->SetTextureMailbox(mailbox, release_callback.Pass());
mailbox_ = mailbox;
mailbox_scale_factor_ = scale_factor;
RecomputeDrawsContentAndUVRect();
@@ -523,8 +528,7 @@ void Layer::SetTextureMailbox(const cc::TextureMailbox& mailbox,
cc::TextureMailbox Layer::GetTextureMailbox(float* scale_factor) {
if (scale_factor)
*scale_factor = mailbox_scale_factor_;
- cc::TextureMailbox::ReleaseCallback callback;
- return mailbox_.CopyWithNewCallback(callback);
+ return mailbox_;
}
void Layer::SetDelegatedFrame(scoped_ptr<cc::DelegatedFrameData> frame,
@@ -552,7 +556,7 @@ void Layer::SetDelegatedFrame(scoped_ptr<cc::DelegatedFrameData> frame,
}
void Layer::TakeUnusedResourcesForChildCompositor(
- cc::TransferableResourceArray* list) {
+ cc::ReturnedResourceArray* list) {
if (delegated_renderer_layer_.get())
delegated_renderer_layer_->TakeUnusedResourcesForChildCompositor(list);
}
@@ -662,8 +666,10 @@ WebKit::WebGraphicsContext3D* Layer::Context3d() {
return NULL;
}
-bool Layer::PrepareTextureMailbox(cc::TextureMailbox* mailbox,
- bool use_shared_memory) {
+bool Layer::PrepareTextureMailbox(
+ cc::TextureMailbox* mailbox,
+ scoped_ptr<cc::SingleReleaseCallback>* release_callback,
+ bool use_shared_memory) {
return false;
}
@@ -675,6 +681,10 @@ void Layer::SetForceRenderSurface(bool force) {
cc_layer_->SetForceRenderSurface(force_render_surface_);
}
+std::string Layer::DebugName() {
+ return name_;
+}
+
void Layer::OnAnimationStarted(const cc::AnimationEvent& event) {
if (animator_.get())
animator_->OnThreadedAnimationStarted(event);
@@ -708,7 +718,7 @@ bool Layer::ConvertPointForAncestor(const Layer* ancestor,
gfx::Transform transform;
bool result = GetTargetTransformRelativeTo(ancestor, &transform);
gfx::Point3F p(*point);
- transform.TransformPoint(p);
+ transform.TransformPoint(&p);
*point = gfx::ToFlooredPoint(p.AsPointF());
return result;
}
@@ -718,7 +728,7 @@ bool Layer::ConvertPointFromAncestor(const Layer* ancestor,
gfx::Transform transform;
bool result = GetTargetTransformRelativeTo(ancestor, &transform);
gfx::Point3F p(*point);
- transform.TransformPointReverse(p);
+ transform.TransformPointReverse(&p);
*point = gfx::ToFlooredPoint(p.AsPointF());
return result;
}
@@ -917,6 +927,7 @@ void Layer::CreateWebLayer() {
cc_layer_->SetContentsOpaque(true);
cc_layer_->SetIsDrawable(type_ != LAYER_NOT_DRAWN);
cc_layer_->AddLayerAnimationEventObserver(this);
+ cc_layer_->SetLayerClient(this);
RecomputePosition();
}
diff --git a/chromium/ui/compositor/layer.h b/chromium/ui/compositor/layer.h
index aa78d93b73e..5b7e2173700 100644
--- a/chromium/ui/compositor/layer.h
+++ b/chromium/ui/compositor/layer.h
@@ -16,6 +16,7 @@
#include "cc/animation/layer_animation_event_observer.h"
#include "cc/base/scoped_ptr_vector.h"
#include "cc/layers/content_layer_client.h"
+#include "cc/layers/layer_client.h"
#include "cc/layers/texture_layer_client.h"
#include "cc/resources/texture_mailbox.h"
#include "third_party/skia/include/core/SkColor.h"
@@ -38,8 +39,8 @@ class Layer;
class ResourceUpdateQueue;
class SolidColorLayer;
class TextureLayer;
-struct TransferableResource;
-typedef std::vector<TransferableResource> TransferableResourceArray;
+struct ReturnedResource;
+typedef std::vector<ReturnedResource> ReturnedResourceArray;
}
namespace ui {
@@ -62,6 +63,7 @@ class COMPOSITOR_EXPORT Layer
: public LayerAnimationDelegate,
NON_EXPORTED_BASE(public cc::ContentLayerClient),
NON_EXPORTED_BASE(public cc::TextureLayerClient),
+ NON_EXPORTED_BASE(public cc::LayerClient),
NON_EXPORTED_BASE(public cc::LayerAnimationEventObserver) {
public:
Layer();
@@ -254,7 +256,9 @@ class COMPOSITOR_EXPORT Layer
// Set new TextureMailbox for this layer. Note that |mailbox| may hold a
// shared memory resource or an actual mailbox for a texture.
- void SetTextureMailbox(const cc::TextureMailbox& mailbox, float scale_factor);
+ void SetTextureMailbox(const cc::TextureMailbox& mailbox,
+ scoped_ptr<cc::SingleReleaseCallback> release_callback,
+ float scale_factor);
cc::TextureMailbox GetTextureMailbox(float* scale_factor);
// Sets a delegated frame, coming from a child compositor.
@@ -267,7 +271,7 @@ class COMPOSITOR_EXPORT Layer
// Gets unused resources to recycle to the child compositor.
void TakeUnusedResourcesForChildCompositor(
- cc::TransferableResourceArray* array);
+ cc::ReturnedResourceArray* array);
// Sets the layer's fill color. May only be called for LAYER_SOLID_COLOR.
void SetColor(SkColor color);
@@ -320,8 +324,10 @@ class COMPOSITOR_EXPORT Layer
// TextureLayerClient
virtual unsigned PrepareTexture() OVERRIDE;
virtual WebKit::WebGraphicsContext3D* Context3d() OVERRIDE;
- virtual bool PrepareTextureMailbox(cc::TextureMailbox* mailbox,
- bool use_shared_memory) OVERRIDE;
+ virtual bool PrepareTextureMailbox(
+ cc::TextureMailbox* mailbox,
+ scoped_ptr<cc::SingleReleaseCallback>* release_callback,
+ bool use_shared_memory) OVERRIDE;
float device_scale_factor() const { return device_scale_factor_; }
@@ -330,6 +336,9 @@ class COMPOSITOR_EXPORT Layer
void SetForceRenderSurface(bool force);
bool force_render_surface() const { return force_render_surface_; }
+ // LayerClient
+ virtual std::string DebugName() OVERRIDE;
+
// LayerAnimationEventObserver
virtual void OnAnimationStarted(const cc::AnimationEvent& event) OVERRIDE;
@@ -471,7 +480,7 @@ class COMPOSITOR_EXPORT Layer
cc::Layer* cc_layer_;
// If true, the layer scales the canvas and the texture with the device scale
- // factor as appropriate. When true, the texture size is in DIP.
+ // factor as apporpriate. When true, the texture size is in DIP.
bool scale_content_;
// A cached copy of |Compositor::device_scale_factor()|.
diff --git a/chromium/ui/compositor/layer_animation_element.cc b/chromium/ui/compositor/layer_animation_element.cc
index f70c1084a1d..1448660240f 100644
--- a/chromium/ui/compositor/layer_animation_element.cc
+++ b/chromium/ui/compositor/layer_animation_element.cc
@@ -7,13 +7,13 @@
#include "base/compiler_specific.h"
#include "cc/animation/animation.h"
#include "cc/animation/animation_id_provider.h"
-#include "ui/base/animation/tween.h"
#include "ui/compositor/float_animation_curve_adapter.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animation_delegate.h"
#include "ui/compositor/layer_animator.h"
#include "ui/compositor/scoped_animation_duration_scale_mode.h"
#include "ui/compositor/transform_animation_curve_adapter.h"
+#include "ui/gfx/animation/tween.h"
#include "ui/gfx/interpolated_transform.h"
namespace ui {
@@ -63,7 +63,7 @@ class TransformTransition : public LayerAnimationElement {
virtual bool OnProgress(double t, LayerAnimationDelegate* delegate) OVERRIDE {
delegate->SetTransformFromAnimation(
- Tween::ValueBetween(t, start_, target_));
+ gfx::Tween::ValueBetween(t, start_, target_));
return true;
}
@@ -141,7 +141,8 @@ class BoundsTransition : public LayerAnimationElement {
}
virtual bool OnProgress(double t, LayerAnimationDelegate* delegate) OVERRIDE {
- delegate->SetBoundsFromAnimation(Tween::ValueBetween(t, start_, target_));
+ delegate->SetBoundsFromAnimation(
+ gfx::Tween::ValueBetween(t, start_, target_));
return true;
}
@@ -181,7 +182,8 @@ class OpacityTransition : public LayerAnimationElement {
}
virtual bool OnProgress(double t, LayerAnimationDelegate* delegate) OVERRIDE {
- delegate->SetOpacityFromAnimation(Tween::ValueBetween(t, start_, target_));
+ delegate->SetOpacityFromAnimation(
+ gfx::Tween::ValueBetween(t, start_, target_));
return true;
}
@@ -262,7 +264,7 @@ class BrightnessTransition : public LayerAnimationElement {
virtual bool OnProgress(double t, LayerAnimationDelegate* delegate) OVERRIDE {
delegate->SetBrightnessFromAnimation(
- Tween::ValueBetween(t, start_, target_));
+ gfx::Tween::ValueBetween(t, start_, target_));
return true;
}
@@ -303,7 +305,7 @@ class GrayscaleTransition : public LayerAnimationElement {
virtual bool OnProgress(double t, LayerAnimationDelegate* delegate) OVERRIDE {
delegate->SetGrayscaleFromAnimation(
- Tween::ValueBetween(t, start_, target_));
+ gfx::Tween::ValueBetween(t, start_, target_));
return true;
}
@@ -345,18 +347,18 @@ class ColorTransition : public LayerAnimationElement {
virtual bool OnProgress(double t, LayerAnimationDelegate* delegate) OVERRIDE {
delegate->SetColorFromAnimation(
SkColorSetARGB(
- Tween::ValueBetween(t,
- static_cast<int>(SkColorGetA(start_)),
- static_cast<int>(SkColorGetA(target_))),
- Tween::ValueBetween(t,
- static_cast<int>(SkColorGetR(start_)),
- static_cast<int>(SkColorGetR(target_))),
- Tween::ValueBetween(t,
- static_cast<int>(SkColorGetG(start_)),
- static_cast<int>(SkColorGetG(target_))),
- Tween::ValueBetween(t,
- static_cast<int>(SkColorGetB(start_)),
- static_cast<int>(SkColorGetB(target_)))));
+ gfx::Tween::ValueBetween(t,
+ static_cast<int>(SkColorGetA(start_)),
+ static_cast<int>(SkColorGetA(target_))),
+ gfx::Tween::ValueBetween(t,
+ static_cast<int>(SkColorGetR(start_)),
+ static_cast<int>(SkColorGetR(target_))),
+ gfx::Tween::ValueBetween(t,
+ static_cast<int>(SkColorGetG(start_)),
+ static_cast<int>(SkColorGetG(target_))),
+ gfx::Tween::ValueBetween(t,
+ static_cast<int>(SkColorGetB(start_)),
+ static_cast<int>(SkColorGetB(target_)))));
return true;
}
@@ -394,6 +396,10 @@ class ThreadedLayerAnimationElement : public LayerAnimationElement {
}
protected:
+ explicit ThreadedLayerAnimationElement(const LayerAnimationElement& element)
+ : LayerAnimationElement(element) {
+ }
+
virtual bool OnProgress(double t,
LayerAnimationDelegate* delegate) OVERRIDE {
if (t < 1.0)
@@ -453,10 +459,10 @@ class ThreadedOpacityTransition : public ThreadedLayerAnimationElement {
virtual void OnAbort(LayerAnimationDelegate* delegate) OVERRIDE {
if (delegate && Started()) {
ThreadedLayerAnimationElement::OnAbort(delegate);
- delegate->SetOpacityFromAnimation(Tween::ValueBetween(
- Tween::CalculateValue(tween_type(), last_progressed_fraction()),
- start_,
- target_));
+ delegate->SetOpacityFromAnimation(gfx::Tween::ValueBetween(
+ gfx::Tween::CalculateValue(tween_type(), last_progressed_fraction()),
+ start_,
+ target_));
}
}
@@ -519,8 +525,8 @@ class ThreadedTransformTransition : public ThreadedLayerAnimationElement {
virtual void OnAbort(LayerAnimationDelegate* delegate) OVERRIDE {
if (delegate && Started()) {
ThreadedLayerAnimationElement::OnAbort(delegate);
- delegate->SetTransformFromAnimation(Tween::ValueBetween(
- Tween::CalculateValue(tween_type(), last_progressed_fraction()),
+ delegate->SetTransformFromAnimation(gfx::Tween::ValueBetween(
+ gfx::Tween::CalculateValue(tween_type(), last_progressed_fraction()),
start_,
target_));
}
@@ -563,6 +569,127 @@ class ThreadedTransformTransition : public ThreadedLayerAnimationElement {
DISALLOW_COPY_AND_ASSIGN(ThreadedTransformTransition);
};
+// InverseTransformTransision --------------------------------------------------
+
+class InverseTransformTransition : public ThreadedLayerAnimationElement {
+ public:
+ InverseTransformTransition(const gfx::Transform& base_transform,
+ const LayerAnimationElement* uninverted_transition)
+ : ThreadedLayerAnimationElement(*uninverted_transition),
+ base_transform_(base_transform),
+ uninverted_transition_(
+ CheckAndCast<const ThreadedTransformTransition*>(
+ uninverted_transition)) {
+ }
+ virtual ~InverseTransformTransition() {}
+
+ static InverseTransformTransition* Clone(const LayerAnimationElement* other) {
+ const InverseTransformTransition* other_inverse =
+ CheckAndCast<const InverseTransformTransition*>(other);
+ return new InverseTransformTransition(
+ other_inverse->base_transform_, other_inverse->uninverted_transition_);
+ }
+
+ protected:
+ virtual void OnStart(LayerAnimationDelegate* delegate) OVERRIDE {
+ gfx::Transform start(delegate->GetTransformForAnimation());
+ effective_start_ = base_transform_ * start;
+
+ TargetValue target;
+ uninverted_transition_->GetTargetValue(&target);
+ base_target_ = target.transform;
+
+ set_tween_type(uninverted_transition_->tween_type());
+
+ float device_scale_factor = delegate->GetDeviceScaleFactor();
+ const gfx::Transform cc_base_start = Layer::ConvertTransformToCCTransform(
+ base_transform_,
+ device_scale_factor);
+ const gfx::Transform cc_base_target = Layer::ConvertTransformToCCTransform(
+ base_target_,
+ device_scale_factor);
+ TransformAnimationCurveAdapter base_curve(tween_type(),
+ cc_base_start,
+ cc_base_target,
+ duration());
+
+ const gfx::Transform cc_start = Layer::ConvertTransformToCCTransform(
+ start, device_scale_factor);
+ animation_curve_.reset(new InverseTransformCurveAdapter(
+ base_curve, cc_start, duration()));
+ computed_target_transform_ = ComputeWithBaseTransform(effective_start_,
+ base_target_);
+ }
+
+ virtual void OnAbort(LayerAnimationDelegate* delegate) OVERRIDE {
+ if (delegate && Started()) {
+ ThreadedLayerAnimationElement::OnAbort(delegate);
+ delegate->SetTransformFromAnimation(ComputeCurrentTransform());
+ }
+ }
+
+ virtual void OnEnd(LayerAnimationDelegate* delegate) OVERRIDE {
+ delegate->SetTransformFromAnimation(computed_target_transform_);
+ }
+
+ virtual scoped_ptr<cc::Animation> CreateCCAnimation() OVERRIDE {
+ scoped_ptr<cc::Animation> animation(
+ cc::Animation::Create(animation_curve_->Clone(),
+ animation_id(),
+ animation_group_id(),
+ cc::Animation::Transform));
+ return animation.Pass();
+ }
+
+ virtual void OnGetTarget(TargetValue* target) const OVERRIDE {
+ target->transform = computed_target_transform_;
+ }
+
+ private:
+ gfx::Transform ComputeCurrentTransform() const {
+ gfx::Transform base_current = gfx::Tween::ValueBetween(
+ gfx::Tween::CalculateValue(tween_type(), last_progressed_fraction()),
+ base_transform_,
+ base_target_);
+ return ComputeWithBaseTransform(effective_start_, base_current);
+ }
+
+ gfx::Transform ComputeWithBaseTransform(gfx::Transform start,
+ gfx::Transform target) const {
+ gfx::Transform to_return(gfx::Transform::kSkipInitialization);
+ bool success = target.GetInverse(&to_return);
+ DCHECK(success) << "Target transform must be invertible.";
+
+ to_return.PreconcatTransform(start);
+ return to_return;
+ }
+
+ static AnimatableProperties GetProperties() {
+ AnimatableProperties properties;
+ properties.insert(LayerAnimationElement::TRANSFORM);
+ return properties;
+ }
+
+ template <typename T>
+ static T CheckAndCast(const LayerAnimationElement* element) {
+ const AnimatableProperties& properties = element->properties();
+ DCHECK(properties.find(TRANSFORM) != properties.end());
+ return static_cast<T>(element);
+ }
+
+ gfx::Transform effective_start_;
+ gfx::Transform computed_target_transform_;
+
+ const gfx::Transform base_transform_;
+ gfx::Transform base_target_;
+
+ scoped_ptr<cc::AnimationCurve> animation_curve_;
+
+ const ThreadedTransformTransition* const uninverted_transition_;
+
+ DISALLOW_COPY_AND_ASSIGN(InverseTransformTransition);
+};
+
} // namespace
// LayerAnimationElement::TargetValue ------------------------------------------
@@ -595,12 +722,23 @@ LayerAnimationElement::LayerAnimationElement(
: first_frame_(true),
properties_(properties),
duration_(GetEffectiveDuration(duration)),
- tween_type_(Tween::LINEAR),
+ tween_type_(gfx::Tween::LINEAR),
animation_id_(cc::AnimationIdProvider::NextAnimationId()),
animation_group_id_(0),
last_progressed_fraction_(0.0) {
}
+LayerAnimationElement::LayerAnimationElement(
+ const LayerAnimationElement &element)
+ : first_frame_(element.first_frame_),
+ properties_(element.properties_),
+ duration_(element.duration_),
+ tween_type_(element.tween_type_),
+ animation_id_(cc::AnimationIdProvider::NextAnimationId()),
+ animation_group_id_(element.animation_group_id_),
+ last_progressed_fraction_(element.last_progressed_fraction_) {
+}
+
LayerAnimationElement::~LayerAnimationElement() {
}
@@ -634,7 +772,7 @@ bool LayerAnimationElement::Progress(base::TimeTicks now,
base::TimeDelta elapsed = now - effective_start_time_;
if ((duration_ > base::TimeDelta()) && (elapsed < duration_))
t = elapsed.InMillisecondsF() / duration_.InMillisecondsF();
- need_draw = OnProgress(Tween::CalculateValue(tween_type_, t), delegate);
+ need_draw = OnProgress(gfx::Tween::CalculateValue(tween_type_, t), delegate);
first_frame_ = t == 1.0;
last_progressed_fraction_ = t;
return need_draw;
@@ -729,6 +867,19 @@ LayerAnimationElement* LayerAnimationElement::CreateTransformElement(
}
// static
+LayerAnimationElement* LayerAnimationElement::CreateInverseTransformElement(
+ const gfx::Transform& base_transform,
+ const LayerAnimationElement* uninverted_transition) {
+ return new InverseTransformTransition(base_transform, uninverted_transition);
+}
+
+// static
+LayerAnimationElement* LayerAnimationElement::CloneInverseTransformElement(
+ const LayerAnimationElement* other) {
+ return InverseTransformTransition::Clone(other);
+}
+
+// static
LayerAnimationElement*
LayerAnimationElement::CreateInterpolatedTransformElement(
InterpolatedTransform* interpolated_transform,
diff --git a/chromium/ui/compositor/layer_animation_element.h b/chromium/ui/compositor/layer_animation_element.h
index c5949d35e21..0c8a075cb0e 100644
--- a/chromium/ui/compositor/layer_animation_element.h
+++ b/chromium/ui/compositor/layer_animation_element.h
@@ -11,8 +11,8 @@
#include "cc/animation/animation.h"
#include "cc/animation/animation_events.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/animation/tween.h"
#include "ui/compositor/compositor_export.h"
+#include "ui/gfx/animation/tween.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/transform.h"
@@ -57,6 +57,7 @@ class COMPOSITOR_EXPORT LayerAnimationElement {
LayerAnimationElement(const AnimatableProperties& properties,
base::TimeDelta duration);
+
virtual ~LayerAnimationElement();
// Creates an element that transitions to the given transform. The caller owns
@@ -65,6 +66,19 @@ class COMPOSITOR_EXPORT LayerAnimationElement {
const gfx::Transform& transform,
base::TimeDelta duration);
+ // Creates an element that counters a transition to the given transform.
+ // This element maintains the invariant uninverted_transition->at(t) *
+ // this->at(t) == base_transform * this->at(t_start) for any t. The caller
+ // owns the return value.
+ static LayerAnimationElement* CreateInverseTransformElement(
+ const gfx::Transform& base_transform,
+ const LayerAnimationElement* uninverted_transition);
+
+
+ // Duplicates elements as created by CreateInverseTransformElement.
+ static LayerAnimationElement* CloneInverseTransformElement(
+ const LayerAnimationElement* other);
+
// Creates an element that transitions to another in a way determined by an
// interpolated transform. The element accepts ownership of the interpolated
// transform. NB: at every step, the interpolated transform clobbers the
@@ -168,8 +182,8 @@ class COMPOSITOR_EXPORT LayerAnimationElement {
// Whether this element animates on the compositor thread.
virtual bool IsThreaded() const;
- Tween::Type tween_type() const { return tween_type_; }
- void set_tween_type(Tween::Type tween_type) { tween_type_ = tween_type; }
+ gfx::Tween::Type tween_type() const { return tween_type_; }
+ void set_tween_type(gfx::Tween::Type tween_type) { tween_type_ = tween_type; }
// Each LayerAnimationElement has a unique animation_id. Elements belonging
// to sequences that are supposed to start together have the same
@@ -178,6 +192,8 @@ class COMPOSITOR_EXPORT LayerAnimationElement {
int animation_group_id() const { return animation_group_id_; }
void set_animation_group_id(int id) { animation_group_id_ = id; }
+ base::TimeDelta duration() const { return duration_; }
+
// The fraction of the animation that has been completed after the last
// call made to {Progress, ProgressToEnd}.
double last_progressed_fraction() const { return last_progressed_fraction_; }
@@ -190,11 +206,11 @@ class COMPOSITOR_EXPORT LayerAnimationElement {
virtual void OnGetTarget(TargetValue* target) const = 0;
virtual void OnAbort(LayerAnimationDelegate* delegate) = 0;
- base::TimeDelta duration() const { return duration_; }
-
// Actually start the animation, dispatching to another thread if needed.
virtual void RequestEffectiveStart(LayerAnimationDelegate* delegate);
+ LayerAnimationElement(const LayerAnimationElement& element);
+
private:
// For debugging purposes, we sometimes alter the duration we actually use.
// For example, during tests we often set duration = 0, and it is sometimes
@@ -208,14 +224,14 @@ class COMPOSITOR_EXPORT LayerAnimationElement {
// When the animation actually started, taking into account queueing delays.
base::TimeTicks effective_start_time_;
const base::TimeDelta duration_;
- Tween::Type tween_type_;
+ gfx::Tween::Type tween_type_;
const int animation_id_;
int animation_group_id_;
double last_progressed_fraction_;
- DISALLOW_COPY_AND_ASSIGN(LayerAnimationElement);
+ DISALLOW_ASSIGN(LayerAnimationElement);
};
} // namespace ui
diff --git a/chromium/ui/compositor/layer_animation_element_unittest.cc b/chromium/ui/compositor/layer_animation_element_unittest.cc
index 2701200c014..8871a2c9f5e 100644
--- a/chromium/ui/compositor/layer_animation_element_unittest.cc
+++ b/chromium/ui/compositor/layer_animation_element_unittest.cc
@@ -10,6 +10,7 @@
#include "base/time/time.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/compositor/layer_animation_delegate.h"
+#include "ui/compositor/scoped_animation_duration_scale_mode.h"
#include "ui/compositor/test/test_layer_animation_delegate.h"
#include "ui/compositor/test/test_utils.h"
#include "ui/gfx/rect.h"
@@ -23,7 +24,7 @@ namespace {
// that the element can be reused after it completes.
TEST(LayerAnimationElementTest, TransformElement) {
TestLayerAnimationDelegate delegate;
- gfx::Transform start_transform, target_transform, middle_transform;
+ gfx::Transform start_transform, target_transform;
start_transform.Rotate(-30.0);
target_transform.Rotate(30.0);
base::TimeTicks start_time;
@@ -65,6 +66,68 @@ TEST(LayerAnimationElementTest, TransformElement) {
CheckApproximatelyEqual(target_transform, target_value.transform);
}
+// Ensures that duration is copied correctly.
+TEST(LayerAnimationElementTest, InverseElementDurationNoScale) {
+ gfx::Transform transform;
+ base::TimeDelta delta;
+
+ scoped_ptr<LayerAnimationElement> base_element(
+ LayerAnimationElement::CreateTransformElement(transform, delta));
+
+ scoped_ptr<LayerAnimationElement> inverse_element(
+ LayerAnimationElement::CreateInverseTransformElement(transform,
+ base_element.get()));
+ EXPECT_EQ(base_element->duration(), inverse_element->duration());
+}
+
+// Ensures that duration is copied correctly and not double scaled.
+TEST(LayerAnimationElementTest, InverseElementDurationScaled) {
+ gfx::Transform transform;
+ base::TimeDelta delta;
+
+ ScopedAnimationDurationScaleMode faster_duration(
+ ScopedAnimationDurationScaleMode::FAST_DURATION);
+ scoped_ptr<LayerAnimationElement> base_element(
+ LayerAnimationElement::CreateTransformElement(transform, delta));
+
+ scoped_ptr<LayerAnimationElement> inverse_element(
+ LayerAnimationElement::CreateInverseTransformElement(transform,
+ base_element.get()));
+ EXPECT_EQ(base_element->duration(), inverse_element->duration());
+}
+
+// Ensures that the GetTargetTransform() method works as intended.
+TEST(LayerAnimationElementTest, InverseElementTargetCalculation) {
+ base::TimeTicks start_time;
+ base::TimeDelta delta = base::TimeDelta::FromSeconds(1);
+ start_time += delta;
+
+ gfx::Transform identity, transform;
+
+ transform.Scale3d(2.0, 2.0, 2.0);
+
+ scoped_ptr<LayerAnimationElement> base_element(
+ LayerAnimationElement::CreateTransformElement(transform, delta));
+ scoped_ptr<LayerAnimationElement> inverse_element(
+ LayerAnimationElement::CreateInverseTransformElement(identity,
+ base_element.get()));
+
+ base_element->set_requested_start_time(start_time);
+ inverse_element->set_requested_start_time(start_time);
+
+ TestLayerAnimationDelegate delegate;
+ delegate.SetTransformFromAnimation(transform);
+
+ base_element->Start(&delegate, 1);
+ inverse_element->Start(&delegate, 1);
+ LayerAnimationElement::TargetValue target;
+ inverse_element->GetTargetValue(&target);
+
+ EXPECT_TRUE(target.transform.IsIdentity())
+ << "Target should be identity such that the initial 2x scale from the start"
+ << " carries over at end when parent is doubled.";
+}
+
// Check that the bounds element progresses the delegate as expected and
// that the element can be reused after it completes.
TEST(LayerAnimationElementTest, BoundsElement) {
@@ -303,7 +366,7 @@ TEST(LayerAnimationElementTest, AbortOpacityElement) {
LayerAnimationElement::CreateOpacityElement(target, delta));
// Choose a non-linear Tween type.
- Tween::Type tween_type = Tween::EASE_IN;
+ gfx::Tween::Type tween_type = gfx::Tween::EASE_IN;
element->set_tween_type(tween_type);
delegate.SetOpacityFromAnimation(start);
@@ -324,7 +387,7 @@ TEST(LayerAnimationElementTest, AbortOpacityElement) {
// Since the element has started, it should update the delegate when
// aborted.
element->Abort(&delegate);
- EXPECT_FLOAT_EQ(Tween::CalculateValue(tween_type, 0.5),
+ EXPECT_FLOAT_EQ(gfx::Tween::CalculateValue(tween_type, 0.5),
delegate.GetOpacityForAnimation());
}
@@ -342,7 +405,7 @@ TEST(LayerAnimationElementTest, AbortTransformElement) {
LayerAnimationElement::CreateTransformElement(target_transform, delta));
// Choose a non-linear Tween type.
- Tween::Type tween_type = Tween::EASE_IN;
+ gfx::Tween::Type tween_type = gfx::Tween::EASE_IN;
element->set_tween_type(tween_type);
delegate.SetTransformFromAnimation(start_transform);
@@ -364,7 +427,7 @@ TEST(LayerAnimationElementTest, AbortTransformElement) {
// aborted.
element->Abort(&delegate);
target_transform.Blend(start_transform,
- Tween::CalculateValue(tween_type, 0.5));
+ gfx::Tween::CalculateValue(tween_type, 0.5));
CheckApproximatelyEqual(target_transform,
delegate.GetTransformForAnimation());
}
diff --git a/chromium/ui/compositor/layer_animation_sequence.cc b/chromium/ui/compositor/layer_animation_sequence.cc
index 371e5409219..f336035851a 100644
--- a/chromium/ui/compositor/layer_animation_sequence.cc
+++ b/chromium/ui/compositor/layer_animation_sequence.cc
@@ -8,6 +8,7 @@
#include <iterator>
#include "base/debug/trace_event.h"
+#include "cc/animation/animation_id_provider.h"
#include "ui/compositor/layer_animation_delegate.h"
#include "ui/compositor/layer_animation_element.h"
#include "ui/compositor/layer_animation_observer.h"
@@ -76,8 +77,10 @@ void LayerAnimationSequence::Progress(base::TimeTicks now,
}
if (is_cyclic_ || last_element_ < elements_.size()) {
- if (!elements_[current_index]->Started())
+ if (!elements_[current_index]->Started()) {
+ animation_group_id_ = cc::AnimationIdProvider::NextGroupId();
elements_[current_index]->Start(delegate, animation_group_id_);
+ }
if (elements_[current_index]->Progress(now, delegate))
redraw_required = true;
last_progressed_fraction_ =
@@ -239,6 +242,18 @@ void LayerAnimationSequence::OnAnimatorDestroyed() {
}
}
+size_t LayerAnimationSequence::size() const {
+ return elements_.size();
+}
+
+LayerAnimationElement* LayerAnimationSequence::FirstElement() const {
+ if (elements_.empty()) {
+ return NULL;
+ }
+
+ return elements_[0].get();
+}
+
void LayerAnimationSequence::NotifyScheduled() {
FOR_EACH_OBSERVER(LayerAnimationObserver,
observers_,
@@ -257,7 +272,7 @@ void LayerAnimationSequence::NotifyAborted() {
OnLayerAnimationAborted(this));
}
-LayerAnimationElement* LayerAnimationSequence::CurrentElement() {
+LayerAnimationElement* LayerAnimationSequence::CurrentElement() const {
if (elements_.empty())
return NULL;
diff --git a/chromium/ui/compositor/layer_animation_sequence.h b/chromium/ui/compositor/layer_animation_sequence.h
index 838c6b98841..854785ae150 100644
--- a/chromium/ui/compositor/layer_animation_sequence.h
+++ b/chromium/ui/compositor/layer_animation_sequence.h
@@ -102,6 +102,8 @@ class COMPOSITOR_EXPORT LayerAnimationSequence
bool IsFirstElementThreaded() const;
// Used to identify groups of sequences that are supposed to start together.
+ // Once started, used to identify the sequence that owns a particular
+ // threaded animation.
int animation_group_id() const { return animation_group_id_; }
void set_animation_group_id(int id) { animation_group_id_ = id; }
@@ -123,6 +125,10 @@ class COMPOSITOR_EXPORT LayerAnimationSequence
// by this sequence. Returns 0.0 if no elements have been progressed.
double last_progressed_fraction() const { return last_progressed_fraction_; }
+ size_t size() const;
+
+ LayerAnimationElement* FirstElement() const;
+
private:
friend class LayerAnimatorTestController;
@@ -141,7 +147,7 @@ class COMPOSITOR_EXPORT LayerAnimationSequence
void NotifyAborted();
// The currently animating element.
- LayerAnimationElement* CurrentElement();
+ LayerAnimationElement* CurrentElement() const;
// The union of all the properties modified by all elements in the sequence.
LayerAnimationElement::AnimatableProperties properties_;
@@ -164,6 +170,9 @@ class COMPOSITOR_EXPORT LayerAnimationSequence
bool waiting_for_group_start_;
// Identifies groups of sequences that are supposed to start together.
+ // Also used to identify the owner of a particular threaded animation; any
+ // in-progress threaded animation owned by this sequence will have this
+ // group id.
int animation_group_id_;
// These parties are notified when layer animations end.
diff --git a/chromium/ui/compositor/layer_animation_sequence_unittest.cc b/chromium/ui/compositor/layer_animation_sequence_unittest.cc
index fe70601f15d..3b4591762b0 100644
--- a/chromium/ui/compositor/layer_animation_sequence_unittest.cc
+++ b/chromium/ui/compositor/layer_animation_sequence_unittest.cc
@@ -82,8 +82,8 @@ TEST(LayerAnimationSequenceTest, SingleThreadedElement) {
LayerAnimationElement::CreateOpacityElement(target, delta));
for (int i = 0; i < 2; ++i) {
- int group_id = 1;
- sequence.set_animation_group_id(group_id);
+ int starting_group_id = 1;
+ sequence.set_animation_group_id(starting_group_id);
start_time = effective_start + delta;
sequence.set_start_time(start_time);
delegate.SetOpacityFromAnimation(start);
@@ -94,7 +94,7 @@ TEST(LayerAnimationSequenceTest, SingleThreadedElement) {
sequence.OnThreadedAnimationStarted(cc::AnimationEvent(
cc::AnimationEvent::Started,
0,
- group_id,
+ sequence.animation_group_id(),
cc::Animation::Opacity,
(effective_start - base::TimeTicks()).InSecondsF()));
sequence.Progress(effective_start + delta/2, &delegate);
@@ -139,8 +139,8 @@ TEST(LayerAnimationSequenceTest, MultipleElement) {
LayerAnimationElement::CreateTransformElement(target_transform, delta));
for (int i = 0; i < 2; ++i) {
- int group_id = 1;
- sequence.set_animation_group_id(group_id);
+ int starting_group_id = 1;
+ sequence.set_animation_group_id(starting_group_id);
start_time = opacity_effective_start + 4 * delta;
sequence.set_start_time(start_time);
delegate.SetOpacityFromAnimation(start_opacity);
@@ -150,10 +150,11 @@ TEST(LayerAnimationSequenceTest, MultipleElement) {
sequence.Progress(start_time, &delegate);
EXPECT_FLOAT_EQ(0.0, sequence.last_progressed_fraction());
opacity_effective_start = start_time + delta;
+ EXPECT_EQ(starting_group_id, sequence.animation_group_id());
sequence.OnThreadedAnimationStarted(cc::AnimationEvent(
cc::AnimationEvent::Started,
0,
- group_id,
+ sequence.animation_group_id(),
cc::Animation::Opacity,
(opacity_effective_start - base::TimeTicks()).InSecondsF()));
sequence.Progress(opacity_effective_start + delta/2, &delegate);
@@ -180,10 +181,11 @@ TEST(LayerAnimationSequenceTest, MultipleElement) {
delegate.GetTransformForAnimation());
EXPECT_FLOAT_EQ(0.0, sequence.last_progressed_fraction());
transform_effective_start = opacity_effective_start + 3 * delta;
+ EXPECT_NE(starting_group_id, sequence.animation_group_id());
sequence.OnThreadedAnimationStarted(cc::AnimationEvent(
cc::AnimationEvent::Started,
0,
- group_id,
+ sequence.animation_group_id(),
cc::Animation::Transform,
(transform_effective_start - base::TimeTicks()).InSecondsF()));
sequence.Progress(transform_effective_start + delta/2, &delegate);
diff --git a/chromium/ui/compositor/layer_animator.cc b/chromium/ui/compositor/layer_animator.cc
index 4b1e9812232..c287574bbb8 100644
--- a/chromium/ui/compositor/layer_animator.cc
+++ b/chromium/ui/compositor/layer_animator.cc
@@ -8,12 +8,12 @@
#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
#include "cc/animation/animation_id_provider.h"
-#include "ui/base/animation/animation_container.h"
#include "ui/compositor/compositor.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animation_delegate.h"
#include "ui/compositor/layer_animation_observer.h"
#include "ui/compositor/layer_animation_sequence.h"
+#include "ui/gfx/animation/animation_container.h"
#define SAFE_INVOKE_VOID(function, running_anim, ...) \
if (running_anim.is_sequence_alive()) \
@@ -37,10 +37,10 @@ const int kDefaultTransitionDurationMs = 120;
const int kTimerIntervalMs = 10;
// Returns the AnimationContainer we're added to.
-ui::AnimationContainer* GetAnimationContainer() {
- static ui::AnimationContainer* container = NULL;
+gfx::AnimationContainer* GetAnimationContainer() {
+ static gfx::AnimationContainer* container = NULL;
if (!container) {
- container = new AnimationContainer();
+ container = new gfx::AnimationContainer();
container->AddRef();
}
return container;
@@ -54,7 +54,7 @@ LayerAnimator::LayerAnimator(base::TimeDelta transition_duration)
: delegate_(NULL),
preemption_strategy_(IMMEDIATELY_SET_NEW_TARGET),
transition_duration_(transition_duration),
- tween_type_(Tween::LINEAR),
+ tween_type_(gfx::Tween::LINEAR),
is_started_(false),
disable_timer_for_test_(false),
adding_animations_(false) {
diff --git a/chromium/ui/compositor/layer_animator.h b/chromium/ui/compositor/layer_animator.h
index 7d6392e940f..5fe0d5c1896 100644
--- a/chromium/ui/compositor/layer_animator.h
+++ b/chromium/ui/compositor/layer_animator.h
@@ -13,18 +13,18 @@
#include "base/memory/ref_counted.h"
#include "base/observer_list.h"
#include "base/time/time.h"
-#include "ui/base/animation/animation_container_element.h"
-#include "ui/base/animation/tween.h"
#include "ui/compositor/compositor_export.h"
#include "ui/compositor/layer_animation_element.h"
+#include "ui/gfx/animation/animation_container_element.h"
+#include "ui/gfx/animation/tween.h"
namespace gfx {
+class Animation;
class Rect;
class Transform;
}
namespace ui {
-class Animation;
class Layer;
class LayerAnimationSequence;
class LayerAnimationDelegate;
@@ -41,7 +41,8 @@ class ScopedLayerAnimationSettings;
// by holding a reference to itself for the duration of methods for which it
// must guarantee that |this| is valid.
class COMPOSITOR_EXPORT LayerAnimator
- : public AnimationContainerElement, public base::RefCounted<LayerAnimator> {
+ : public gfx::AnimationContainerElement,
+ public base::RefCounted<LayerAnimator> {
public:
enum PreemptionStrategy {
IMMEDIATELY_SET_NEW_TARGET,
@@ -171,8 +172,8 @@ class COMPOSITOR_EXPORT LayerAnimator
// This determines how implicit animations will be tweened. This has no
// effect on animations that are explicitly started or scheduled. The default
// is Tween::LINEAR.
- void set_tween_type(Tween::Type tween_type) { tween_type_ = tween_type; }
- Tween::Type tween_type() const { return tween_type_; }
+ void set_tween_type(gfx::Tween::Type tween_type) { tween_type_ = tween_type; }
+ gfx::Tween::Type tween_type() const { return tween_type_; }
// For testing purposes only.
void set_disable_timer_for_test(bool disable_timer) {
@@ -320,7 +321,7 @@ class COMPOSITOR_EXPORT LayerAnimator
base::TimeDelta transition_duration_;
// The default tween type for implicit transitions
- Tween::Type tween_type_;
+ gfx::Tween::Type tween_type_;
// Used for coordinating the starting of animations.
base::TimeTicks last_step_time_;
diff --git a/chromium/ui/compositor/layer_animator_unittest.cc b/chromium/ui/compositor/layer_animator_unittest.cc
index 8b4d792bf7f..b01a1c32165 100644
--- a/chromium/ui/compositor/layer_animator_unittest.cc
+++ b/chromium/ui/compositor/layer_animator_unittest.cc
@@ -10,6 +10,7 @@
#include "base/strings/stringprintf.h"
#include "base/time/time.h"
#include "testing/gtest/include/gtest/gtest.h"
+#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animation_delegate.h"
#include "ui/compositor/layer_animation_element.h"
#include "ui/compositor/layer_animation_sequence.h"
@@ -22,6 +23,8 @@
#include "ui/gfx/rect.h"
#include "ui/gfx/transform.h"
+using gfx::AnimationContainerElement;
+
namespace ui {
namespace {
@@ -112,7 +115,6 @@ class DeletingLayerAnimationObserver : public LayerAnimationObserver {
private:
LayerAnimator* animator_;
- LayerAnimationSequence* sequence_;
DISALLOW_COPY_AND_ASSIGN(DeletingLayerAnimationObserver);
};
@@ -1764,13 +1766,13 @@ TEST(LayerAnimatorTest, ObserverReleasedBeforeAnimationSequenceEnds) {
animator->StartAnimation(sequence);
// |observer| should be attached to |sequence|.
- EXPECT_EQ(static_cast<size_t>(1), sequence->observers_.size());
+ EXPECT_TRUE(sequence->observers_.might_have_observers());
// Now, release |observer|
observer.reset();
// And |sequence| should no longer be attached to |observer|.
- EXPECT_EQ(static_cast<size_t>(0), sequence->observers_.size());
+ EXPECT_FALSE(sequence->observers_.might_have_observers());
}
TEST(LayerAnimatorTest, ObserverAttachedAfterAnimationStarted) {
@@ -2376,4 +2378,33 @@ TEST(LayerAnimatorTest, TestSetterRespectEnqueueStrategy) {
EXPECT_EQ(start_opacity, delegate.GetOpacityForAnimation());
}
+TEST(LayerAnimatorTest, TestScopedCounterAnimation) {
+ Layer parent, child;
+ parent.Add(&child);
+
+ gfx::Transform parent_begin, parent_end;
+
+ parent_end.Scale3d(2.0, 0.5, 1.0);
+
+ // Parent animates from identity to the end value. The counter animation will
+ // start at the end value and animate back to identity.
+ gfx::Transform child_begin(parent_end);
+
+ child.SetTransform(child_begin);
+ parent.SetTransform(parent_begin);
+
+ EXPECT_FALSE(child.GetAnimator()->is_animating());
+
+ ScopedLayerAnimationSettings settings(parent.GetAnimator());
+ settings.SetInverselyAnimatedBaseLayer(&parent);
+ settings.AddInverselyAnimatedLayer(&child);
+
+ parent.SetTransform(parent_end);
+
+ EXPECT_TRUE(child.GetAnimator()->is_animating());
+ EXPECT_TRUE(child.GetTargetTransform().IsIdentity())
+ << child.GetTargetTransform().ToString();
+
+}
+
} // namespace ui
diff --git a/chromium/ui/compositor/run_all_unittests.cc b/chromium/ui/compositor/run_all_unittests.cc
index 52bb2fad611..f2f7251391e 100644
--- a/chromium/ui/compositor/run_all_unittests.cc
+++ b/chromium/ui/compositor/run_all_unittests.cc
@@ -2,8 +2,14 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "base/bind.h"
+#include "base/test/unit_test_launcher.h"
#include "ui/compositor/test/test_suite.h"
int main(int argc, char** argv) {
- return ui::test::CompositorTestSuite(argc, argv).Run();
+ ui::test::CompositorTestSuite test_suite(argc, argv);
+
+ return base::LaunchUnitTests(
+ argc, argv, base::Bind(&ui::test::CompositorTestSuite::Run,
+ base::Unretained(&test_suite)));
}
diff --git a/chromium/ui/compositor/scoped_layer_animation_settings.cc b/chromium/ui/compositor/scoped_layer_animation_settings.cc
index b45d94c65b7..b5bad673f60 100644
--- a/chromium/ui/compositor/scoped_layer_animation_settings.cc
+++ b/chromium/ui/compositor/scoped_layer_animation_settings.cc
@@ -4,7 +4,9 @@
#include "ui/compositor/scoped_layer_animation_settings.h"
+#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animation_observer.h"
+#include "ui/compositor/layer_animation_sequence.h"
#include "ui/compositor/layer_animator.h"
namespace {
@@ -15,12 +17,74 @@ const int kDefaultTransitionDurationMs = 200;
namespace ui {
+// InvertingObserver -----------------------------------------------------------
+class InvertingObserver : public ImplicitAnimationObserver {
+ public:
+ InvertingObserver()
+ : base_layer_(NULL) {
+ }
+
+ virtual ~InvertingObserver() {}
+
+ void SetLayer(Layer* base_layer) { base_layer_ = base_layer; }
+
+ Layer* layer() { return base_layer_; }
+
+ void AddInverselyAnimatedLayer(Layer* inverse_layer) {
+ inverse_layers_.push_back(inverse_layer);
+ }
+
+ virtual void OnImplicitAnimationsCompleted() OVERRIDE {}
+
+ virtual void OnLayerAnimationScheduled(
+ LayerAnimationSequence* sequence) OVERRIDE {
+ DCHECK(base_layer_ != NULL)
+ << "Must set base layer with ScopedLayerAnimationSettings::"
+ << "SetInverslyAnimatedBaseLayer";
+ gfx::Transform base_transform = base_layer_->transform();
+ scoped_ptr<LayerAnimationElement> inverse = GetInverseElement(sequence,
+ base_transform);
+
+ for (std::vector<Layer*>::const_iterator i =
+ inverse_layers_.begin(); i != inverse_layers_.end(); ++i) {
+ (*i)->GetAnimator()->StartAnimation(new LayerAnimationSequence(
+ LayerAnimationElement::CloneInverseTransformElement(
+ inverse.get())));
+ }
+ }
+ private:
+ scoped_ptr<LayerAnimationElement> GetInverseElement(
+ LayerAnimationSequence* sequence,
+ gfx::Transform base) const {
+ const size_t expected_size = 1;
+ DCHECK_EQ(expected_size, sequence->size()) <<
+ "Inverse supported only for single element sequences.";
+
+ LayerAnimationElement* element = sequence->FirstElement();
+ LayerAnimationElement::AnimatableProperties transform_property;
+ transform_property.insert(LayerAnimationElement::TRANSFORM);
+ DCHECK(transform_property == element->properties())
+ << "Only transform animations are currently invertible.";
+
+ scoped_ptr<LayerAnimationElement> to_return(
+ LayerAnimationElement::CreateInverseTransformElement(base, element));
+ return to_return.Pass();
+ }
+
+ Layer* base_layer_;
+ // child layers
+ std::vector<Layer*> inverse_layers_;
+};
+
+
+// ScoperLayerAnimationSettings ------------------------------------------------
ScopedLayerAnimationSettings::ScopedLayerAnimationSettings(
LayerAnimator* animator)
: animator_(animator),
old_transition_duration_(animator->transition_duration_),
old_tween_type_(animator->tween_type()),
- old_preemption_strategy_(animator->preemption_strategy()) {
+ old_preemption_strategy_(animator->preemption_strategy()),
+ inverse_observer_(new InvertingObserver()) {
SetTransitionDuration(
base::TimeDelta::FromMilliseconds(kDefaultTransitionDurationMs));
}
@@ -35,6 +99,10 @@ ScopedLayerAnimationSettings::~ScopedLayerAnimationSettings() {
animator_->observers_.RemoveObserver(*i);
(*i)->SetActive(true);
}
+
+ if (inverse_observer_->layer()) {
+ animator_->observers_.RemoveObserver(inverse_observer_.get());
+ }
}
void ScopedLayerAnimationSettings::AddObserver(
@@ -52,11 +120,11 @@ base::TimeDelta ScopedLayerAnimationSettings::GetTransitionDuration() const {
return animator_->transition_duration_;
}
-void ScopedLayerAnimationSettings::SetTweenType(Tween::Type tween_type) {
+void ScopedLayerAnimationSettings::SetTweenType(gfx::Tween::Type tween_type) {
animator_->set_tween_type(tween_type);
}
-Tween::Type ScopedLayerAnimationSettings::GetTweenType() const {
+gfx::Tween::Type ScopedLayerAnimationSettings::GetTweenType() const {
return animator_->tween_type();
}
@@ -70,4 +138,18 @@ ScopedLayerAnimationSettings::GetPreemptionStrategy() const {
return animator_->preemption_strategy();
}
+void ScopedLayerAnimationSettings::SetInverselyAnimatedBaseLayer(Layer* base) {
+ if (inverse_observer_->layer() && !base) {
+ animator_->RemoveObserver(inverse_observer_.get());
+ } else if (base && !(inverse_observer_->layer())) {
+ animator_->AddObserver(inverse_observer_.get());
+ }
+ inverse_observer_->SetLayer(base);
+}
+
+void ScopedLayerAnimationSettings::AddInverselyAnimatedLayer(
+ Layer* inverse_layer) {
+ inverse_observer_->AddInverselyAnimatedLayer(inverse_layer);
+}
+
} // namespace ui
diff --git a/chromium/ui/compositor/scoped_layer_animation_settings.h b/chromium/ui/compositor/scoped_layer_animation_settings.h
index 7f8e1c76340..e36b8532729 100644
--- a/chromium/ui/compositor/scoped_layer_animation_settings.h
+++ b/chromium/ui/compositor/scoped_layer_animation_settings.h
@@ -7,16 +7,18 @@
#include <set>
+#include "base/memory/scoped_vector.h"
#include "base/time/time.h"
-#include "ui/base/animation/tween.h"
#include "ui/compositor/compositor_export.h"
#include "ui/compositor/layer_animator.h"
+#include "ui/gfx/animation/tween.h"
namespace ui {
class ImplicitAnimationObserver;
class LayerAnimationObserver;
+class InvertingObserver;
// Scoped settings allow you to temporarily change the animator's settings and
// these changes are reverted when the object is destroyed. NOTE: when the
@@ -32,18 +34,27 @@ class COMPOSITOR_EXPORT ScopedLayerAnimationSettings {
void SetTransitionDuration(base::TimeDelta duration);
base::TimeDelta GetTransitionDuration() const;
- void SetTweenType(Tween::Type tween_type);
- Tween::Type GetTweenType() const;
+ void SetTweenType(gfx::Tween::Type tween_type);
+ gfx::Tween::Type GetTweenType() const;
void SetPreemptionStrategy(LayerAnimator::PreemptionStrategy strategy);
LayerAnimator::PreemptionStrategy GetPreemptionStrategy() const;
+ // Sets the base layer whose animation will be countered.
+ void SetInverselyAnimatedBaseLayer(Layer* base);
+
+ // Adds the layer to be counter-animated when a transform animation is
+ // scheduled on the animator_. Must call SetInverselyAnimatedBaseLayer with
+ // the layer associated with animator_ before animating.
+ void AddInverselyAnimatedLayer(Layer* inverse_layer);
+
private:
LayerAnimator* animator_;
base::TimeDelta old_transition_duration_;
- Tween::Type old_tween_type_;
+ gfx::Tween::Type old_tween_type_;
LayerAnimator::PreemptionStrategy old_preemption_strategy_;
std::set<ImplicitAnimationObserver*> observers_;
+ scoped_ptr<InvertingObserver> inverse_observer_;
DISALLOW_COPY_AND_ASSIGN(ScopedLayerAnimationSettings);
};
diff --git a/chromium/ui/compositor/test_web_graphics_context_3d.cc b/chromium/ui/compositor/test_web_graphics_context_3d.cc
deleted file mode 100644
index d8febc9ca08..00000000000
--- a/chromium/ui/compositor/test_web_graphics_context_3d.cc
+++ /dev/null
@@ -1,220 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/compositor/test_web_graphics_context_3d.h"
-
-#include "ui/gl/gl_bindings.h"
-#include "ui/gl/gl_context_stub.h"
-#include "ui/gl/gl_surface_stub.h"
-
-namespace ui {
-
-TestWebGraphicsContext3D::TestWebGraphicsContext3D()
- : next_texture_id_(1) {}
-
-TestWebGraphicsContext3D::~TestWebGraphicsContext3D() {}
-
-void TestWebGraphicsContext3D::Initialize() {
- gl_surface_ = new gfx::GLSurfaceStub;
- gl_context_ = new gfx::GLContextStub;
- gl_context_->MakeCurrent(gl_surface_.get());
-}
-
-bool TestWebGraphicsContext3D::makeContextCurrent() {
- return true;
-}
-
-int TestWebGraphicsContext3D::width() {
- return 0;
-}
-
-int TestWebGraphicsContext3D::height() {
- return 0;
-}
-
-bool TestWebGraphicsContext3D::isContextLost() {
- return false;
-}
-
-void* TestWebGraphicsContext3D::mapBufferSubDataCHROMIUM(
- WebKit::WGC3Denum target,
- WebKit::WGC3Dintptr offset,
- WebKit::WGC3Dsizeiptr size,
- WebKit::WGC3Denum access) {
- return 0;
-}
-
-void* TestWebGraphicsContext3D::mapTexSubImage2DCHROMIUM(
- WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Dint xoffset,
- WebKit::WGC3Dint yoffset,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Denum format,
- WebKit::WGC3Denum type,
- WebKit::WGC3Denum access) {
- return 0;
-}
-
-WebKit::WebString TestWebGraphicsContext3D::getRequestableExtensionsCHROMIUM() {
- return WebKit::WebString();
-}
-
-WebKit::WGC3Denum TestWebGraphicsContext3D::checkFramebufferStatus(
- WebKit::WGC3Denum target) {
- return GL_FRAMEBUFFER_COMPLETE;
-}
-
-bool TestWebGraphicsContext3D::getActiveAttrib(WebKit::WebGLId program,
- WebKit::WGC3Duint index,
- ActiveInfo& info) {
- return false;
-}
-
-bool TestWebGraphicsContext3D::getActiveUniform(WebKit::WebGLId program,
- WebKit::WGC3Duint index,
- ActiveInfo& info) {
- return false;
-}
-
-WebKit::WGC3Dint TestWebGraphicsContext3D::getAttribLocation(
- WebKit::WebGLId program,
- const WebKit::WGC3Dchar* name) {
- return 0;
-}
-
-TestWebGraphicsContext3D::Attributes
-TestWebGraphicsContext3D::getContextAttributes() {
- return Attributes();
-}
-
-WebKit::WGC3Denum TestWebGraphicsContext3D::getError() {
- return 0;
-}
-
-void TestWebGraphicsContext3D::getIntegerv(WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {
- if (pname == GL_MAX_TEXTURE_SIZE)
- *value = 1024;
- else if (pname == GL_ACTIVE_TEXTURE)
- *value = GL_TEXTURE0;
-}
-
-void TestWebGraphicsContext3D::getProgramiv(WebKit::WebGLId program,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {
- if (pname == GL_LINK_STATUS)
- *value = 1;
-}
-
-WebKit::WebString TestWebGraphicsContext3D::getProgramInfoLog(
- WebKit::WebGLId program) {
- return WebKit::WebString();
-}
-
-void TestWebGraphicsContext3D::getShaderiv(WebKit::WebGLId shader,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {
- if (pname == GL_COMPILE_STATUS)
- *value = 1;
-}
-
-WebKit::WebString TestWebGraphicsContext3D::getShaderInfoLog(
- WebKit::WebGLId shader) {
- return WebKit::WebString();
-}
-
-WebKit::WebString TestWebGraphicsContext3D::getShaderSource(
- WebKit::WebGLId shader) {
- return WebKit::WebString();
-}
-
-WebKit::WebString TestWebGraphicsContext3D::getString(WebKit::WGC3Denum name) {
- return WebKit::WebString();
-}
-
-WebKit::WGC3Dint TestWebGraphicsContext3D::getUniformLocation(
- WebKit::WebGLId program,
- const WebKit::WGC3Dchar* name) {
- return 0;
-}
-
-WebKit::WGC3Dsizeiptr TestWebGraphicsContext3D::getVertexAttribOffset(
- WebKit::WGC3Duint index,
- WebKit::WGC3Denum pname) {
- return 0;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isBuffer(
- WebKit::WebGLId buffer) {
- return false;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isEnabled(
- WebKit::WGC3Denum cap) {
- return false;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isFramebuffer(
- WebKit::WebGLId framebuffer) {
- return false;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isProgram(
- WebKit::WebGLId program) {
- return false;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isRenderbuffer(
- WebKit::WebGLId renderbuffer) {
- return false;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isShader(
- WebKit::WebGLId shader) {
- return false;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isTexture(
- WebKit::WebGLId texture) {
- return false;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createBuffer() {
- return 1;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createFramebuffer() {
- return 1;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createProgram() {
- return 1;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createRenderbuffer() {
- return 1;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createShader(
- WebKit::WGC3Denum value) {
- return 1;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createTexture() {
- return next_texture_id_++;
-}
-
-WebKit::WebGLId TestWebGraphicsContext3D::createQueryEXT()
-{
- return 1;
-}
-
-WebKit::WGC3Dboolean TestWebGraphicsContext3D::isQueryEXT(WebKit::WebGLId)
-{
- return true;
-}
-
-} // namespace ui
diff --git a/chromium/ui/compositor/test_web_graphics_context_3d.h b/chromium/ui/compositor/test_web_graphics_context_3d.h
deleted file mode 100644
index f7a96220a47..00000000000
--- a/chromium/ui/compositor/test_web_graphics_context_3d.h
+++ /dev/null
@@ -1,450 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_COMPOSITOR_TEST_WEB_GRAPHICS_CONTEXT_3D_H_
-#define UI_COMPOSITOR_TEST_WEB_GRAPHICS_CONTEXT_3D_H_
-
-#include "base/logging.h"
-#include "base/memory/ref_counted.h"
-#include "third_party/WebKit/public/platform/WebGraphicsContext3D.h"
-#include "third_party/WebKit/public/platform/WebString.h"
-#include "ui/compositor/compositor_export.h"
-
-namespace gfx {
-class GLContext;
-class GLSurface;
-}
-
-namespace ui {
-
-// WebGraphicsContext3D that does nothing. Suitable for testing.
-class COMPOSITOR_EXPORT TestWebGraphicsContext3D :
- public NON_EXPORTED_BASE(WebKit::WebGraphicsContext3D) {
- public:
- TestWebGraphicsContext3D();
- virtual ~TestWebGraphicsContext3D();
-
- void Initialize();
- virtual bool makeContextCurrent();
- virtual int width();
- virtual int height();
- virtual void reshape(int width, int height) {}
- virtual void prepareTexture() {}
- virtual void postSubBufferCHROMIUM(int x, int y, int width, int height) {}
- virtual void synthesizeGLError(WebKit::WGC3Denum value) {}
- virtual bool isContextLost();
- virtual void* mapBufferSubDataCHROMIUM(WebKit::WGC3Denum target,
- WebKit::WGC3Dintptr offset,
- WebKit::WGC3Dsizeiptr size,
- WebKit::WGC3Denum access);
- virtual void unmapBufferSubDataCHROMIUM(const void* data) {}
- virtual void* mapTexSubImage2DCHROMIUM(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Dint xoffset,
- WebKit::WGC3Dint yoffset,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Denum format,
- WebKit::WGC3Denum type,
- WebKit::WGC3Denum access);
- virtual void unmapTexSubImage2DCHROMIUM(const void* data) {}
- virtual void setVisibilityCHROMIUM(bool visible) {}
- virtual void discardFramebufferEXT(WebKit::WGC3Denum target,
- WebKit::WGC3Dsizei numAttachments,
- const WebKit::WGC3Denum* attachments) {}
- virtual void setMemoryAllocationChangedCallbackCHROMIUM(
- WebGraphicsMemoryAllocationChangedCallbackCHROMIUM*) { }
- virtual WebKit::WebString getRequestableExtensionsCHROMIUM();
- virtual void requestExtensionCHROMIUM(const char*) {}
- virtual void blitFramebufferCHROMIUM(WebKit::WGC3Dint src_x0,
- WebKit::WGC3Dint src_y0,
- WebKit::WGC3Dint src_x1,
- WebKit::WGC3Dint src_y1,
- WebKit::WGC3Dint dst_x0,
- WebKit::WGC3Dint dst_y0,
- WebKit::WGC3Dint dst_x1,
- WebKit::WGC3Dint dst_y1,
- WebKit::WGC3Dbitfield mask,
- WebKit::WGC3Denum filter) {}
- virtual void renderbufferStorageMultisampleCHROMIUM(
- WebKit::WGC3Denum target,
- WebKit::WGC3Dsizei samples,
- WebKit::WGC3Denum internalformat,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height) {}
- virtual void activeTexture(WebKit::WGC3Denum texture) {}
- virtual void attachShader(WebKit::WebGLId program, WebKit::WebGLId shader) {}
- virtual void bindAttribLocation(WebKit::WebGLId program,
- WebKit::WGC3Duint index,
- const WebKit::WGC3Dchar* name) {}
- virtual void bindBuffer(WebKit::WGC3Denum target, WebKit::WebGLId buffer) {}
- virtual void bindFramebuffer(WebKit::WGC3Denum target,
- WebKit::WebGLId framebuffer) {}
- virtual void bindRenderbuffer(WebKit::WGC3Denum target,
- WebKit::WebGLId renderbuffer) {}
- virtual void bindTexture(WebKit::WGC3Denum target, WebKit::WebGLId texture) {}
- virtual void blendColor(WebKit::WGC3Dclampf red,
- WebKit::WGC3Dclampf green,
- WebKit::WGC3Dclampf blue,
- WebKit::WGC3Dclampf alpha) {}
- virtual void blendEquation(WebKit::WGC3Denum mode) {}
- virtual void blendEquationSeparate(WebKit::WGC3Denum modeRGB,
- WebKit::WGC3Denum modeAlpha) {}
- virtual void blendFunc(WebKit::WGC3Denum sfactor,
- WebKit::WGC3Denum dfactor) {}
- virtual void blendFuncSeparate(WebKit::WGC3Denum src_rgb,
- WebKit::WGC3Denum dst_rgb,
- WebKit::WGC3Denum src_alpha,
- WebKit::WGC3Denum dst_alpha) {}
- virtual void bufferData(WebKit::WGC3Denum target,
- WebKit::WGC3Dsizeiptr size,
- const void* data,
- WebKit::WGC3Denum usage) {}
- virtual void bufferSubData(WebKit::WGC3Denum target,
- WebKit::WGC3Dintptr offset,
- WebKit::WGC3Dsizeiptr size,
- const void* data) {}
- virtual WebKit::WGC3Denum checkFramebufferStatus(WebKit::WGC3Denum target);
- virtual void clear(WebKit::WGC3Dbitfield mask) {}
- virtual void clearColor(WebKit::WGC3Dclampf red,
- WebKit::WGC3Dclampf green,
- WebKit::WGC3Dclampf blue,
- WebKit::WGC3Dclampf alpha) {}
- virtual void clearDepth(WebKit::WGC3Dclampf depth) {}
- virtual void clearStencil(WebKit::WGC3Dint s) {}
- virtual void colorMask(WebKit::WGC3Dboolean red,
- WebKit::WGC3Dboolean green,
- WebKit::WGC3Dboolean blue,
- WebKit::WGC3Dboolean alpha) {}
- virtual void compileShader(WebKit::WebGLId shader) {}
- virtual void compressedTexImage2D(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Denum internalformat,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Dint border,
- WebKit::WGC3Dsizei imageSize,
- const void* data) {}
- virtual void compressedTexSubImage2D(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Dint xoffset,
- WebKit::WGC3Dint yoffset,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Denum format,
- WebKit::WGC3Dsizei imageSize,
- const void* data) {}
- virtual void copyTexImage2D(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Denum internal_format,
- WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Dint border) {}
- virtual void copyTexSubImage2D(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Dint xoffset,
- WebKit::WGC3Dint yoffset,
- WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height) {}
- virtual void cullFace(WebKit::WGC3Denum mode) {}
- virtual void depthFunc(WebKit::WGC3Denum func) {}
- virtual void depthMask(WebKit::WGC3Dboolean flag) {}
- virtual void depthRange(WebKit::WGC3Dclampf z_near,
- WebKit::WGC3Dclampf z_far) {}
- virtual void detachShader(WebKit::WebGLId program, WebKit::WebGLId shader) {}
- virtual void disable(WebKit::WGC3Denum cap) {}
- virtual void disableVertexAttribArray(WebKit::WGC3Duint index) {}
- virtual void drawArrays(WebKit::WGC3Denum mode, WebKit::WGC3Dint first,
- WebKit::WGC3Dsizei count) {}
- virtual void drawElements(WebKit::WGC3Denum mode,
- WebKit::WGC3Dsizei count,
- WebKit::WGC3Denum type,
- WebKit::WGC3Dintptr offset) {}
- virtual void enable(WebKit::WGC3Denum cap) {}
- virtual void enableVertexAttribArray(WebKit::WGC3Duint index) {}
- virtual void finish() {}
- virtual void flush() {}
- virtual void framebufferRenderbuffer(WebKit::WGC3Denum target,
- WebKit::WGC3Denum attachment,
- WebKit::WGC3Denum renderbuffertarget,
- WebKit::WebGLId renderbuffer) {}
- virtual void framebufferTexture2D(WebKit::WGC3Denum target,
- WebKit::WGC3Denum attachment,
- WebKit::WGC3Denum textarget,
- WebKit::WebGLId texture,
- WebKit::WGC3Dint level) {}
- virtual void frontFace(WebKit::WGC3Denum mode) {}
- virtual void generateMipmap(WebKit::WGC3Denum target) {}
- virtual bool getActiveAttrib(WebKit::WebGLId program,
- WebKit::WGC3Duint index,
- ActiveInfo& info);
- virtual bool getActiveUniform(WebKit::WebGLId program,
- WebKit::WGC3Duint index,
- ActiveInfo& info);
- virtual void getAttachedShaders(WebKit::WebGLId program,
- WebKit::WGC3Dsizei maxCount,
- WebKit::WGC3Dsizei* count,
- WebKit::WebGLId* shaders) {}
- virtual WebKit::WGC3Dint getAttribLocation(WebKit::WebGLId program,
- const WebKit::WGC3Dchar* name);
- virtual void getBooleanv(WebKit::WGC3Denum pname,
- WebKit::WGC3Dboolean* value) {}
- virtual void getBufferParameteriv(WebKit::WGC3Denum target,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {}
- virtual Attributes getContextAttributes();
- virtual WebKit::WGC3Denum getError();
- virtual void getFloatv(WebKit::WGC3Denum pname, WebKit::WGC3Dfloat* value) {}
- virtual void getFramebufferAttachmentParameteriv(WebKit::WGC3Denum target,
- WebKit::WGC3Denum attachment,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {}
- virtual void getIntegerv(WebKit::WGC3Denum pname, WebKit::WGC3Dint* value);
- virtual void getProgramiv(WebKit::WebGLId program,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value);
- virtual WebKit::WebString getProgramInfoLog(WebKit::WebGLId program);
- virtual void getRenderbufferParameteriv(WebKit::WGC3Denum target,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {}
- virtual void getShaderiv(WebKit::WebGLId shader,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value);
- virtual WebKit::WebString getShaderInfoLog(WebKit::WebGLId shader);
- virtual void getShaderPrecisionFormat(WebKit::WGC3Denum shaderType,
- WebKit::WGC3Denum precisionType,
- WebKit::WGC3Dint* range,
- WebKit::WGC3Dint* precision) {}
- virtual WebKit::WebString getShaderSource(WebKit::WebGLId shader);
- virtual WebKit::WebString getString(WebKit::WGC3Denum name);
- virtual void getTexParameterfv(WebKit::WGC3Denum target,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dfloat* value) {}
- virtual void getTexParameteriv(WebKit::WGC3Denum target,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {}
- virtual void getUniformfv(WebKit::WebGLId program,
- WebKit::WGC3Dint location,
- WebKit::WGC3Dfloat* value) {}
- virtual void getUniformiv(WebKit::WebGLId program,
- WebKit::WGC3Dint location,
- WebKit::WGC3Dint* value) {}
- virtual WebKit::WGC3Dint getUniformLocation(WebKit::WebGLId program,
- const WebKit::WGC3Dchar* name);
- virtual void getVertexAttribfv(WebKit::WGC3Duint index,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dfloat* value) {}
- virtual void getVertexAttribiv(WebKit::WGC3Duint index,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint* value) {}
- virtual WebKit::WGC3Dsizeiptr getVertexAttribOffset(WebKit::WGC3Duint index,
- WebKit::WGC3Denum pname);
- virtual void hint(WebKit::WGC3Denum target, WebKit::WGC3Denum mode) {}
- virtual WebKit::WGC3Dboolean isBuffer(WebKit::WebGLId buffer);
- virtual WebKit::WGC3Dboolean isEnabled(WebKit::WGC3Denum cap);
- virtual WebKit::WGC3Dboolean isFramebuffer(WebKit::WebGLId framebuffer);
- virtual WebKit::WGC3Dboolean isProgram(WebKit::WebGLId program);
- virtual WebKit::WGC3Dboolean isRenderbuffer(WebKit::WebGLId renderbuffer);
- virtual WebKit::WGC3Dboolean isShader(WebKit::WebGLId shader);
- virtual WebKit::WGC3Dboolean isTexture(WebKit::WebGLId texture);
- virtual void lineWidth(WebKit::WGC3Dfloat) {}
- virtual void linkProgram(WebKit::WebGLId program) {}
- virtual void pixelStorei(WebKit::WGC3Denum pname, WebKit::WGC3Dint param) {}
- virtual void polygonOffset(WebKit::WGC3Dfloat factor,
- WebKit::WGC3Dfloat units) {}
- virtual void readPixels(WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Denum format,
- WebKit::WGC3Denum type,
- void* pixels) {}
- virtual void releaseShaderCompiler() {}
- virtual void renderbufferStorage(WebKit::WGC3Denum target,
- WebKit::WGC3Denum internalformat,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height) {}
- virtual void sampleCoverage(WebKit::WGC3Dclampf value,
- WebKit::WGC3Dboolean invert) {}
- virtual void scissor(WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height) {}
- virtual void shaderSource(WebKit::WebGLId shader,
- const WebKit::WGC3Dchar* string) {}
- virtual void stencilFunc(WebKit::WGC3Denum func,
- WebKit::WGC3Dint ref,
- WebKit::WGC3Duint mask) {}
- virtual void stencilFuncSeparate(WebKit::WGC3Denum face,
- WebKit::WGC3Denum func,
- WebKit::WGC3Dint ref,
- WebKit::WGC3Duint mask) {}
- virtual void stencilMask(WebKit::WGC3Duint mask) {}
- virtual void stencilMaskSeparate(WebKit::WGC3Denum face,
- WebKit::WGC3Duint mask) {}
- virtual void stencilOp(WebKit::WGC3Denum fail,
- WebKit::WGC3Denum zfail,
- WebKit::WGC3Denum zpass) {}
- virtual void stencilOpSeparate(WebKit::WGC3Denum face,
- WebKit::WGC3Denum fail,
- WebKit::WGC3Denum zfail,
- WebKit::WGC3Denum zpass) {}
- virtual void texImage2D(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Denum internal_format,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Dint border,
- WebKit::WGC3Denum format,
- WebKit::WGC3Denum type,
- const void* pixels) {}
- virtual void texParameterf(WebKit::WGC3Denum target,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dfloat param) {}
- virtual void texParameteri(WebKit::WGC3Denum target,
- WebKit::WGC3Denum pname,
- WebKit::WGC3Dint param) {}
- virtual void texSubImage2D(WebKit::WGC3Denum target,
- WebKit::WGC3Dint level,
- WebKit::WGC3Dint xoffset,
- WebKit::WGC3Dint yoffset,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height,
- WebKit::WGC3Denum format,
- WebKit::WGC3Denum type,
- const void* pixels) {}
- virtual void uniform1f(WebKit::WGC3Dint location, WebKit::WGC3Dfloat x) {}
- virtual void uniform1fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dfloat* v) {}
- virtual void uniform1i(WebKit::WGC3Dint location, WebKit::WGC3Dint x) {}
- virtual void uniform1iv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dint* v) {}
- virtual void uniform2f(WebKit::WGC3Dint location,
- WebKit::WGC3Dfloat x,
- WebKit::WGC3Dfloat y) {}
- virtual void uniform2fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dfloat* v) {}
- virtual void uniform2i(WebKit::WGC3Dint location,
- WebKit::WGC3Dint x,
- WebKit::WGC3Dint y) {}
- virtual void uniform2iv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dint* v) {}
- virtual void uniform3f(WebKit::WGC3Dint location,
- WebKit::WGC3Dfloat x,
- WebKit::WGC3Dfloat y,
- WebKit::WGC3Dfloat z) {}
- virtual void uniform3fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dfloat* v) {}
- virtual void uniform3i(WebKit::WGC3Dint location,
- WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dint z) {}
- virtual void uniform3iv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dint* v) {}
- virtual void uniform4f(WebKit::WGC3Dint location,
- WebKit::WGC3Dfloat x,
- WebKit::WGC3Dfloat y,
- WebKit::WGC3Dfloat z,
- WebKit::WGC3Dfloat w) {}
- virtual void uniform4fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dfloat* v) {}
- virtual void uniform4i(WebKit::WGC3Dint location,
- WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dint z,
- WebKit::WGC3Dint w) {}
- virtual void uniform4iv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- const WebKit::WGC3Dint* v) {}
- virtual void uniformMatrix2fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- WebKit::WGC3Dboolean transpose,
- const WebKit::WGC3Dfloat* value) {}
- virtual void uniformMatrix3fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- WebKit::WGC3Dboolean transpose,
- const WebKit::WGC3Dfloat* value) {}
- virtual void uniformMatrix4fv(WebKit::WGC3Dint location,
- WebKit::WGC3Dsizei count,
- WebKit::WGC3Dboolean transpose,
- const WebKit::WGC3Dfloat* value) {}
- virtual void useProgram(WebKit::WebGLId program) {}
- virtual void validateProgram(WebKit::WebGLId program) {}
- virtual void vertexAttrib1f(WebKit::WGC3Duint index, WebKit::WGC3Dfloat x) {}
- virtual void vertexAttrib1fv(WebKit::WGC3Duint index,
- const WebKit::WGC3Dfloat* values) {}
- virtual void vertexAttrib2f(WebKit::WGC3Duint index,
- WebKit::WGC3Dfloat x,
- WebKit::WGC3Dfloat y) {}
- virtual void vertexAttrib2fv(WebKit::WGC3Duint index,
- const WebKit::WGC3Dfloat* values) {}
- virtual void vertexAttrib3f(WebKit::WGC3Duint index,
- WebKit::WGC3Dfloat x,
- WebKit::WGC3Dfloat y,
- WebKit::WGC3Dfloat z) {}
- virtual void vertexAttrib3fv(WebKit::WGC3Duint index,
- const WebKit::WGC3Dfloat* values) {}
- virtual void vertexAttrib4f(WebKit::WGC3Duint index,
- WebKit::WGC3Dfloat x,
- WebKit::WGC3Dfloat y,
- WebKit::WGC3Dfloat z,
- WebKit::WGC3Dfloat w) {}
- virtual void vertexAttrib4fv(WebKit::WGC3Duint index,
- const WebKit::WGC3Dfloat* values) {}
- virtual void vertexAttribPointer(WebKit::WGC3Duint index,
- WebKit::WGC3Dint size,
- WebKit::WGC3Denum type,
- WebKit::WGC3Dboolean normalized,
- WebKit::WGC3Dsizei stride,
- WebKit::WGC3Dintptr offset) {}
- virtual void viewport(WebKit::WGC3Dint x,
- WebKit::WGC3Dint y,
- WebKit::WGC3Dsizei width,
- WebKit::WGC3Dsizei height) {}
- virtual WebKit::WebGLId createBuffer();
- virtual WebKit::WebGLId createFramebuffer();
- virtual WebKit::WebGLId createProgram();
- virtual WebKit::WebGLId createRenderbuffer();
- virtual WebKit::WebGLId createShader(WebKit::WGC3Denum value);
- virtual WebKit::WebGLId createTexture();
- virtual void deleteBuffer(WebKit::WebGLId) {}
- virtual void deleteFramebuffer(WebKit::WebGLId) {}
- virtual void deleteProgram(WebKit::WebGLId) {}
- virtual void deleteRenderbuffer(WebKit::WebGLId) {}
- virtual void deleteShader(WebKit::WebGLId) {}
- virtual void deleteTexture(WebKit::WebGLId) {}
- virtual WebKit::WebGLId createQueryEXT();
- virtual void deleteQueryEXT(WebKit::WebGLId) {};
- virtual WebKit::WGC3Dboolean isQueryEXT(WebKit::WebGLId query);
- virtual void beginQueryEXT(WebKit::WGC3Denum, WebKit::WebGLId) {}
- virtual void endQueryEXT(WebKit::WGC3Denum) {}
- virtual void getQueryivEXT(WebKit::WGC3Denum,
- WebKit::WGC3Denum,
- WebKit::WGC3Dint*) {}
- virtual void getQueryObjectuivEXT(WebKit::WebGLId,
- WebKit::WGC3Denum,
- WebKit::WGC3Duint*) {}
-
- private:
- scoped_refptr<gfx::GLContext> gl_context_;
- scoped_refptr<gfx::GLSurface> gl_surface_;
- unsigned next_texture_id_;
-
- DISALLOW_COPY_AND_ASSIGN(TestWebGraphicsContext3D);
-};
-
-} // namespace ui
-
-#endif // UI_COMPOSITOR_TEST_WEB_GRAPHICS_CONTEXT_3D_H_
diff --git a/chromium/ui/compositor/transform_animation_curve_adapter.cc b/chromium/ui/compositor/transform_animation_curve_adapter.cc
index 96500b3de52..49feb6af746 100644
--- a/chromium/ui/compositor/transform_animation_curve_adapter.cc
+++ b/chromium/ui/compositor/transform_animation_curve_adapter.cc
@@ -7,7 +7,7 @@
namespace ui {
TransformAnimationCurveAdapter::TransformAnimationCurveAdapter(
- Tween::Type tween_type,
+ gfx::Tween::Type tween_type,
gfx::Transform initial_value,
gfx::Transform target_value,
base::TimeDelta duration)
@@ -47,8 +47,67 @@ gfx::Transform TransformAnimationCurveAdapter::GetValue(
gfx::BlendDecomposedTransforms(&to_return,
decomposed_target_value_,
decomposed_initial_value_,
- Tween::CalculateValue(tween_type_, progress));
+ gfx::Tween::CalculateValue(tween_type_,
+ progress));
return gfx::ComposeTransform(to_return);
}
+bool TransformAnimationCurveAdapter::AnimatedBoundsForBox(
+ const gfx::BoxF& box,
+ gfx::BoxF* bounds) const {
+ // TODO(ajuma): Once cc::TransformOperation::BlendedBoundsForBox supports
+ // computing bounds for TransformOperationMatrix, use that to compute
+ // the bounds we need here.
+ return false;
+}
+
+InverseTransformCurveAdapter::InverseTransformCurveAdapter(
+ TransformAnimationCurveAdapter base_curve,
+ gfx::Transform initial_value,
+ base::TimeDelta duration)
+ : base_curve_(base_curve),
+ initial_value_(initial_value),
+ duration_(duration) {
+ effective_initial_value_ = base_curve_.GetValue(0.0) * initial_value_;
+}
+
+InverseTransformCurveAdapter::~InverseTransformCurveAdapter() {
+}
+
+double InverseTransformCurveAdapter::Duration() const {
+ return duration_.InSeconds();
+}
+
+scoped_ptr<cc::AnimationCurve> InverseTransformCurveAdapter::Clone() const {
+ scoped_ptr<InverseTransformCurveAdapter> to_return(
+ new InverseTransformCurveAdapter(base_curve_,
+ initial_value_,
+ duration_));
+ return to_return.PassAs<cc::AnimationCurve>();
+}
+
+gfx::Transform InverseTransformCurveAdapter::GetValue(
+ double t) const {
+ if (t <= 0.0)
+ return initial_value_;
+
+ gfx::Transform base_transform = base_curve_.GetValue(t);
+ // Invert base
+ gfx::Transform to_return(gfx::Transform::kSkipInitialization);
+ bool is_invertible = base_transform.GetInverse(&to_return);
+ DCHECK(is_invertible);
+
+ to_return.PreconcatTransform(effective_initial_value_);
+ return to_return;
+}
+
+bool InverseTransformCurveAdapter::AnimatedBoundsForBox(
+ const gfx::BoxF& box,
+ gfx::BoxF* bounds) const {
+ // TODO(ajuma): Once cc::TransformOperation::BlendedBoundsForBox supports
+ // computing bounds for TransformOperationMatrix, use that to compute
+ // the bounds we need here.
+ return false;
+}
+
} // namespace ui
diff --git a/chromium/ui/compositor/transform_animation_curve_adapter.h b/chromium/ui/compositor/transform_animation_curve_adapter.h
index 7b6bdcea52b..36861e46008 100644
--- a/chromium/ui/compositor/transform_animation_curve_adapter.h
+++ b/chromium/ui/compositor/transform_animation_curve_adapter.h
@@ -7,15 +7,17 @@
#include "base/time/time.h"
#include "cc/animation/animation_curve.h"
-#include "ui/base/animation/tween.h"
+#include "ui/compositor/compositor_export.h"
+#include "ui/gfx/animation/tween.h"
#include "ui/gfx/transform.h"
#include "ui/gfx/transform_util.h"
namespace ui {
-class TransformAnimationCurveAdapter :public cc::TransformAnimationCurve {
+class COMPOSITOR_EXPORT TransformAnimationCurveAdapter
+ : public cc::TransformAnimationCurve {
public:
- TransformAnimationCurveAdapter(Tween::Type tween_type,
+ TransformAnimationCurveAdapter(gfx::Tween::Type tween_type,
gfx::Transform intial_value,
gfx::Transform target_value,
base::TimeDelta duration);
@@ -26,14 +28,42 @@ class TransformAnimationCurveAdapter :public cc::TransformAnimationCurve {
virtual double Duration() const OVERRIDE;
virtual scoped_ptr<AnimationCurve> Clone() const OVERRIDE;
virtual gfx::Transform GetValue(double t) const OVERRIDE;
+ virtual bool AnimatedBoundsForBox(const gfx::BoxF& box,
+ gfx::BoxF* bounds) const OVERRIDE;
private:
- Tween::Type tween_type_;
+ gfx::Tween::Type tween_type_;
gfx::Transform initial_value_;
gfx::Transform target_value_;
gfx::DecomposedTransform decomposed_initial_value_;
gfx::DecomposedTransform decomposed_target_value_;
base::TimeDelta duration_;
+
+ DISALLOW_ASSIGN(TransformAnimationCurveAdapter);
+};
+
+class COMPOSITOR_EXPORT InverseTransformCurveAdapter
+ : public cc::TransformAnimationCurve {
+ public:
+ InverseTransformCurveAdapter(TransformAnimationCurveAdapter base_curve,
+ gfx::Transform initial_value,
+ base::TimeDelta duration);
+
+ virtual ~InverseTransformCurveAdapter();
+
+ virtual double Duration() const OVERRIDE;
+ virtual scoped_ptr<AnimationCurve> Clone() const OVERRIDE;
+ virtual gfx::Transform GetValue(double t) const OVERRIDE;
+ virtual bool AnimatedBoundsForBox(const gfx::BoxF& box,
+ gfx::BoxF* bounds) const OVERRIDE;
+
+ private:
+ TransformAnimationCurveAdapter base_curve_;
+ gfx::Transform initial_value_;
+ gfx::Transform effective_initial_value_;
+ base::TimeDelta duration_;
+
+ DISALLOW_ASSIGN(InverseTransformCurveAdapter);
};
} // namespace ui
diff --git a/chromium/ui/compositor/transform_animation_curve_adapter_unittest.cc b/chromium/ui/compositor/transform_animation_curve_adapter_unittest.cc
new file mode 100644
index 00000000000..b68e8626891
--- /dev/null
+++ b/chromium/ui/compositor/transform_animation_curve_adapter_unittest.cc
@@ -0,0 +1,59 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/compositor/transform_animation_curve_adapter.h"
+
+#include <sstream>
+
+#include "base/time/time.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "ui/compositor/test/test_utils.h"
+
+namespace ui {
+
+namespace {
+
+// Check that the inverse transform curve gives the gives a transform that when
+// applied on top of the parent transform gives the original transform
+TEST(InverseTransformCurveAdapterTest, InversesTransform) {
+ gfx::Transform parent_start, parent_target;
+ parent_start.Scale(0.5, 3.0);
+ parent_start.Translate(-20.0, 30.0);
+ parent_target.Translate(0, 100);
+
+ gfx::Transform child_transform;
+ child_transform.Rotate(-30.0);
+
+ base::TimeDelta duration = base::TimeDelta::FromSeconds(1);
+
+ const gfx::Transform effective_child_transform =
+ parent_start * child_transform;
+
+ TransformAnimationCurveAdapter parent_curve(gfx::Tween::LINEAR,
+ parent_start,
+ parent_target,
+ duration);
+
+ InverseTransformCurveAdapter child_curve(parent_curve,
+ child_transform,
+ duration);
+ static const int kSteps = 1000;
+ double step = 1.0 / kSteps;
+ for (int i = 0; i <= kSteps ; ++i) {
+ std::ostringstream message;
+ message << "Step " << i << " of " << kSteps;
+ SCOPED_TRACE(message.str());
+ gfx::Transform progress_parent_transform =
+ parent_curve.GetValue(i*step);
+ gfx::Transform progress_child_transform =
+ child_curve.GetValue(i*step);
+ CheckApproximatelyEqual(effective_child_transform,
+ progress_parent_transform *
+ progress_child_transform);
+ }
+}
+
+} // namespace
+
+} // namespace ui
diff --git a/chromium/ui/base/events/OWNERS b/chromium/ui/events/OWNERS
index b8e32c10903..b8e32c10903 100644
--- a/chromium/ui/base/events/OWNERS
+++ b/chromium/ui/events/OWNERS
diff --git a/chromium/ui/base/events/event.cc b/chromium/ui/events/event.cc
index 02813108f7a..7c3e6d5021c 100644
--- a/chromium/ui/base/events/event.cc
+++ b/chromium/ui/events/event.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#if defined(USE_X11)
#include <X11/Xlib.h>
@@ -13,15 +13,15 @@
#include "base/metrics/histogram.h"
#include "base/strings/stringprintf.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_code_conversion.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion.h"
#include "ui/gfx/point3_f.h"
#include "ui/gfx/point_conversions.h"
#include "ui/gfx/transform.h"
#include "ui/gfx/transform_util.h"
#if defined(USE_X11)
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
#endif
namespace {
@@ -36,7 +36,7 @@ base::NativeEvent CopyNativeEvent(const base::NativeEvent& event) {
#elif defined(OS_WIN)
return event;
#elif defined(USE_OZONE)
- return event;
+ return NULL;
#else
NOTREACHED() <<
"Don't know how to copy base::NativeEvent for this platform";
@@ -284,7 +284,7 @@ void LocatedEvent::UpdateForRootTransform(
const gfx::Transform& reversed_root_transform) {
// Transform has to be done at root level.
gfx::Point3F p(location_);
- reversed_root_transform.TransformPoint(p);
+ reversed_root_transform.TransformPoint(&p);
root_location_ = location_ = gfx::ToFlooredPoint(p.AsPointF());
}
@@ -295,7 +295,7 @@ MouseEvent::MouseEvent(const base::NativeEvent& native_event)
: LocatedEvent(native_event),
changed_button_flags_(
GetChangedMouseButtonFlagsFromNative(native_event)) {
- if (type() == ET_MOUSE_PRESSED)
+ if (type() == ET_MOUSE_PRESSED || type() == ET_MOUSE_RELEASED)
SetClickCount(GetRepeatCount(*this));
}
@@ -345,6 +345,8 @@ bool MouseEvent::IsRepeatedClickEvent(
int MouseEvent::GetRepeatCount(const MouseEvent& event) {
int click_count = 1;
if (last_click_event_) {
+ if (event.type() == ui::ET_MOUSE_RELEASED)
+ return last_click_event_->GetClickCount();
if (IsX11SendEventTrue(event.native_event()))
click_count = last_click_event_->GetClickCount();
else if (IsRepeatedClickEvent(*last_click_event_, event))
@@ -362,7 +364,7 @@ int MouseEvent::GetRepeatCount(const MouseEvent& event) {
MouseEvent* MouseEvent::last_click_event_ = NULL;
int MouseEvent::GetClickCount() const {
- if (type() != ET_MOUSE_PRESSED)
+ if (type() != ET_MOUSE_PRESSED && type() != ET_MOUSE_RELEASED)
return 0;
if (flags() & EF_IS_TRIPLE_CLICK)
@@ -374,7 +376,7 @@ int MouseEvent::GetClickCount() const {
}
void MouseEvent::SetClickCount(int click_count) {
- if (type() != ET_MOUSE_PRESSED)
+ if (type() != ET_MOUSE_PRESSED && type() != ET_MOUSE_RELEASED)
return;
DCHECK(click_count > 0);
@@ -600,7 +602,11 @@ uint16 KeyEvent::GetUnmodifiedCharacter() const {
}
KeyEvent* KeyEvent::Copy() const {
+#if defined(USE_OZONE)
+ KeyEvent* copy = new KeyEvent(*this);
+#else
KeyEvent* copy = new KeyEvent(::CopyNativeEvent(native_event()), is_char());
+#endif
#if defined(USE_X11)
copy->set_delete_native_event(true);
#endif
@@ -735,18 +741,6 @@ void ScrollEvent::Scale(const float factor) {
y_offset_ordinal_ *= factor;
}
-void ScrollEvent::UpdateForRootTransform(
- const gfx::Transform& inverted_root_transform) {
- LocatedEvent::UpdateForRootTransform(inverted_root_transform);
- gfx::DecomposedTransform decomp;
- bool success = gfx::DecomposeTransform(&decomp, inverted_root_transform);
- DCHECK(success);
- if (decomp.scale[0])
- x_offset_ordinal_ *= decomp.scale[0];
- if (decomp.scale[1])
- y_offset_ordinal_ *= decomp.scale[1];
-}
-
////////////////////////////////////////////////////////////////////////////////
// GestureEvent
diff --git a/chromium/ui/base/events/event.h b/chromium/ui/events/event.h
index 193e6e6a237..5c7582f7faf 100644
--- a/chromium/ui/base/events/event.h
+++ b/chromium/ui/events/event.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_EVENTS_EVENT_H_
-#define UI_BASE_EVENTS_EVENT_H_
+#ifndef UI_EVENTS_EVENT_H_
+#define UI_EVENTS_EVENT_H_
#include "base/basictypes.h"
#include "base/compiler_specific.h"
@@ -11,11 +11,10 @@
#include "base/logging.h"
#include "base/time/time.h"
#include "ui/base/dragdrop/os_exchange_data.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/gestures/gesture_types.h"
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/latency_info.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/events/latency_info.h"
#include "ui/gfx/point.h"
namespace gfx {
@@ -25,7 +24,7 @@ class Transform;
namespace ui {
class EventTarget;
-class UI_EXPORT Event {
+class EVENTS_EXPORT Event {
public:
virtual ~Event();
@@ -220,8 +219,6 @@ class UI_EXPORT Event {
void InitLatencyInfo();
private:
- void operator=(const Event&);
-
// Safely initializes the native event members of this class.
void Init();
void InitWithNativeEvent(const base::NativeEvent& native_event);
@@ -240,13 +237,13 @@ class UI_EXPORT Event {
EventResult result_;
};
-class UI_EXPORT CancelModeEvent : public Event {
+class EVENTS_EXPORT CancelModeEvent : public Event {
public:
CancelModeEvent();
virtual ~CancelModeEvent();
};
-class UI_EXPORT LocatedEvent : public Event {
+class EVENTS_EXPORT LocatedEvent : public Event {
public:
// For testing.
class TestApi : public Event::TestApi {
@@ -313,7 +310,7 @@ class UI_EXPORT LocatedEvent : public Event {
gfx::Point root_location_;
};
-class UI_EXPORT MouseEvent : public LocatedEvent {
+class EVENTS_EXPORT MouseEvent : public LocatedEvent {
public:
explicit MouseEvent(const base::NativeEvent& native_event);
@@ -410,7 +407,7 @@ class UI_EXPORT MouseEvent : public LocatedEvent {
class ScrollEvent;
-class UI_EXPORT MouseWheelEvent : public MouseEvent {
+class EVENTS_EXPORT MouseWheelEvent : public MouseEvent {
public:
// See |offset| for details.
static const int kWheelDelta;
@@ -444,7 +441,7 @@ class UI_EXPORT MouseWheelEvent : public MouseEvent {
gfx::Vector2d offset_;
};
-class UI_EXPORT TouchEvent : public LocatedEvent {
+class EVENTS_EXPORT TouchEvent : public LocatedEvent {
public:
explicit TouchEvent(const base::NativeEvent& native_event);
@@ -527,7 +524,7 @@ class UI_EXPORT TouchEvent : public LocatedEvent {
float force_;
};
-class UI_EXPORT KeyEvent : public Event {
+class EVENTS_EXPORT KeyEvent : public Event {
public:
KeyEvent(const base::NativeEvent& native_event, bool is_char);
@@ -587,7 +584,7 @@ class UI_EXPORT KeyEvent : public Event {
// TranslatedKeyEvent(VKEY_SPACE) event. If the IME receives a KeyEvent and
// it does consume the event, it might dispatch a
// TranslatedKeyEvent(VKEY_PROCESSKEY) event as defined in the DOM spec.
-class UI_EXPORT TranslatedKeyEvent : public KeyEvent {
+class EVENTS_EXPORT TranslatedKeyEvent : public KeyEvent {
public:
TranslatedKeyEvent(const base::NativeEvent& native_event, bool is_char);
@@ -602,7 +599,7 @@ class UI_EXPORT TranslatedKeyEvent : public KeyEvent {
DISALLOW_COPY_AND_ASSIGN(TranslatedKeyEvent);
};
-class UI_EXPORT DropTargetEvent : public LocatedEvent {
+class EVENTS_EXPORT DropTargetEvent : public LocatedEvent {
public:
DropTargetEvent(const OSExchangeData& data,
const gfx::Point& location,
@@ -622,7 +619,7 @@ class UI_EXPORT DropTargetEvent : public LocatedEvent {
DISALLOW_COPY_AND_ASSIGN(DropTargetEvent);
};
-class UI_EXPORT ScrollEvent : public MouseEvent {
+class EVENTS_EXPORT ScrollEvent : public MouseEvent {
public:
explicit ScrollEvent(const base::NativeEvent& native_event);
template <class T>
@@ -659,10 +656,6 @@ class UI_EXPORT ScrollEvent : public MouseEvent {
float y_offset_ordinal() const { return y_offset_ordinal_; }
int finger_count() const { return finger_count_; }
- // Overridden from LocatedEvent.
- virtual void UpdateForRootTransform(
- const gfx::Transform& inverted_root_transform) OVERRIDE;
-
private:
// Potential accelerated offsets.
float x_offset_;
@@ -674,7 +667,7 @@ class UI_EXPORT ScrollEvent : public MouseEvent {
int finger_count_;
};
-class UI_EXPORT GestureEvent : public LocatedEvent {
+class EVENTS_EXPORT GestureEvent : public LocatedEvent {
public:
GestureEvent(EventType type,
int x,
@@ -710,10 +703,8 @@ class UI_EXPORT GestureEvent : public LocatedEvent {
// This value is stored as a bitfield because the number of touch ids varies,
// but we currently don't need more than 32 touches at a time.
const unsigned int touch_ids_bitfield_;
-
- DISALLOW_COPY_AND_ASSIGN(GestureEvent);
};
} // namespace ui
-#endif // UI_BASE_EVENTS_EVENT_H_
+#endif // UI_EVENTS_EVENT_H_
diff --git a/chromium/ui/base/events/event_constants.h b/chromium/ui/events/event_constants.h
index 2c04770ec88..6c0e9f71bc0 100644
--- a/chromium/ui/base/events/event_constants.h
+++ b/chromium/ui/events/event_constants.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_EVENTS_EVENT_CONSTANTS_H_
-#define UI_BASE_EVENTS_EVENT_CONSTANTS_H_
+#ifndef UI_EVENTS_EVENT_CONSTANTS_H_
+#define UI_EVENTS_EVENT_CONSTANTS_H_
namespace ui {
@@ -113,4 +113,4 @@ enum EventPhase {
} // namespace ui
-#endif // UI_BASE_EVENTS_EVENT_CONSTANTS_H_
+#endif // UI_EVENTS_EVENT_CONSTANTS_H_
diff --git a/chromium/ui/base/events/event_dispatcher.cc b/chromium/ui/events/event_dispatcher.cc
index 06c857c2f29..b774b94dcf6 100644
--- a/chromium/ui/base/events/event_dispatcher.cc
+++ b/chromium/ui/events/event_dispatcher.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event_dispatcher.h"
+#include "ui/events/event_dispatcher.h"
#include <algorithm>
diff --git a/chromium/ui/base/events/event_dispatcher.h b/chromium/ui/events/event_dispatcher.h
index b9fd0dc79cd..ef8d6b1c5bb 100644
--- a/chromium/ui/base/events/event_dispatcher.h
+++ b/chromium/ui/events/event_dispatcher.h
@@ -2,20 +2,20 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_EVENTS_EVENT_DISPATCHER_H_
-#define UI_BASE_EVENTS_EVENT_DISPATCHER_H_
+#ifndef UI_EVENTS_EVENT_DISPATCHER_H_
+#define UI_EVENTS_EVENT_DISPATCHER_H_
#include "base/auto_reset.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_target.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_target.h"
+#include "ui/events/events_export.h"
namespace ui {
class EventDispatcher;
-class UI_EXPORT EventDispatcherDelegate {
+class EVENTS_EXPORT EventDispatcherDelegate {
public:
EventDispatcherDelegate();
virtual ~EventDispatcherDelegate();
@@ -42,7 +42,7 @@ class UI_EXPORT EventDispatcherDelegate {
};
// Dispatches events to appropriate targets.
-class UI_EXPORT EventDispatcher {
+class EVENTS_EXPORT EventDispatcher {
public:
explicit EventDispatcher(EventDispatcherDelegate* delegate);
virtual ~EventDispatcher();
@@ -77,4 +77,4 @@ class UI_EXPORT EventDispatcher {
} // namespace ui
-#endif // UI_BASE_EVENTS_EVENT_DISPATCHER_H_
+#endif // UI_EVENTS_EVENT_DISPATCHER_H_
diff --git a/chromium/ui/base/events/event_dispatcher_unittest.cc b/chromium/ui/events/event_dispatcher_unittest.cc
index 41ab0487ee8..b0b3b8a5e38 100644
--- a/chromium/ui/base/events/event_dispatcher_unittest.cc
+++ b/chromium/ui/events/event_dispatcher_unittest.cc
@@ -2,11 +2,11 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event_dispatcher.h"
+#include "ui/events/event_dispatcher.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
namespace ui {
diff --git a/chromium/ui/base/events/event_handler.cc b/chromium/ui/events/event_handler.cc
index 99295b15c6e..243007a5553 100644
--- a/chromium/ui/base/events/event_handler.cc
+++ b/chromium/ui/events/event_handler.cc
@@ -2,10 +2,10 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event_dispatcher.h"
-#include "ui/base/events/event_handler.h"
+#include "ui/events/event_handler.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
+#include "ui/events/event_dispatcher.h"
namespace ui {
diff --git a/chromium/ui/base/events/event_handler.h b/chromium/ui/events/event_handler.h
index 6ecc3890e8e..088c3f84253 100644
--- a/chromium/ui/base/events/event_handler.h
+++ b/chromium/ui/events/event_handler.h
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_EVENTS_EVENT_HANDLER_H_
-#define UI_BASE_EVENTS_EVENT_HANDLER_H_
+#ifndef UI_EVENTS_EVENT_HANDLER_H_
+#define UI_EVENTS_EVENT_HANDLER_H_
#include <stack>
#include <vector>
#include "base/basictypes.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/events_export.h"
namespace ui {
@@ -26,7 +26,7 @@ class TouchEvent;
// Dispatches events to appropriate targets. The default implementations of
// all of the specific handlers (e.g. OnKeyEvent, OnMouseEvent) do nothing.
-class UI_EXPORT EventHandler {
+class EVENTS_EXPORT EventHandler {
public:
EventHandler();
virtual ~EventHandler();
@@ -63,4 +63,4 @@ typedef std::vector<EventHandler*> EventHandlerList;
} // namespace ui
-#endif // UI_BASE_EVENTS_EVENT_HANDLER_H_
+#endif // UI_EVENTS_EVENT_HANDLER_H_
diff --git a/chromium/ui/base/events/event_target.cc b/chromium/ui/events/event_target.cc
index 7ef69c80bbe..9aa53902ca9 100644
--- a/chromium/ui/base/events/event_target.cc
+++ b/chromium/ui/events/event_target.cc
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event_target.h"
+#include "ui/events/event_target.h"
#include <algorithm>
#include "base/logging.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
namespace ui {
diff --git a/chromium/ui/base/events/event_target.h b/chromium/ui/events/event_target.h
index 6961b73cac6..39671e23bde 100644
--- a/chromium/ui/base/events/event_target.h
+++ b/chromium/ui/events/event_target.h
@@ -2,19 +2,19 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_EVENTS_EVENT_TARGET_H_
-#define UI_BASE_EVENTS_EVENT_TARGET_H_
+#ifndef UI_EVENTS_EVENT_TARGET_H_
+#define UI_EVENTS_EVENT_TARGET_H_
#include "base/basictypes.h"
#include "base/compiler_specific.h"
-#include "ui/base/events/event_handler.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/event_handler.h"
+#include "ui/events/events_export.h"
namespace ui {
class EventDispatcher;
-class UI_EXPORT EventTarget : public EventHandler {
+class EVENTS_EXPORT EventTarget : public EventHandler {
public:
typedef std::vector<EventTarget*> EventTargets;
@@ -105,4 +105,4 @@ class UI_EXPORT EventTarget : public EventHandler {
} // namespace ui
-#endif // UI_BASE_EVENTS_EVENT_TARGET_H_
+#endif // UI_EVENTS_EVENT_TARGET_H_
diff --git a/chromium/ui/base/events/event_unittest.cc b/chromium/ui/events/event_unittest.cc
index d55ac9241cf..418c0695336 100644
--- a/chromium/ui/base/events/event_unittest.cc
+++ b/chromium/ui/events/event_unittest.cc
@@ -3,7 +3,7 @@
// found in the LICENSE file.
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#if defined(USE_X11)
#include <X11/Xlib.h>
diff --git a/chromium/ui/base/events/event_utils.cc b/chromium/ui/events/event_utils.cc
index ac09854bbfb..5504e4cb399 100644
--- a/chromium/ui/base/events/event_utils.cc
+++ b/chromium/ui/events/event_utils.cc
@@ -2,9 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event_utils.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
namespace ui {
diff --git a/chromium/ui/base/events/event_utils.h b/chromium/ui/events/event_utils.h
index d57ced90ac6..bcf1213855e 100644
--- a/chromium/ui/base/events/event_utils.h
+++ b/chromium/ui/events/event_utils.h
@@ -2,13 +2,14 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_EVENTS_EVENT_UTILS_H_
-#define UI_BASE_EVENTS_EVENT_UTILS_H_
+#ifndef UI_EVENTS_EVENT_UTILS_H_
+#define UI_EVENTS_EVENT_UTILS_H_
#include "base/event_types.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/native_widget_types.h"
+#include "ui/events/events_export.h"
#if defined(OS_WIN)
#include <windows.h>
@@ -28,30 +29,31 @@ namespace ui {
class Event;
// Updates the list of devices for cached properties.
-UI_EXPORT void UpdateDeviceList();
+EVENTS_EXPORT void UpdateDeviceList();
// Get the EventType from a native event.
-UI_EXPORT EventType EventTypeFromNative(const base::NativeEvent& native_event);
+EVENTS_EXPORT EventType EventTypeFromNative(
+ const base::NativeEvent& native_event);
// Get the EventFlags from a native event.
-UI_EXPORT int EventFlagsFromNative(const base::NativeEvent& native_event);
+EVENTS_EXPORT int EventFlagsFromNative(const base::NativeEvent& native_event);
// Get the timestamp from a native event.
-UI_EXPORT base::TimeDelta EventTimeFromNative(
+EVENTS_EXPORT base::TimeDelta EventTimeFromNative(
const base::NativeEvent& native_event);
// Create a timestamp based on the current time.
-UI_EXPORT base::TimeDelta EventTimeForNow();
+EVENTS_EXPORT base::TimeDelta EventTimeForNow();
// Get the location from a native event. The coordinate system of the resultant
// |Point| has the origin at top-left of the "root window". The nature of
// this "root window" and how it maps to platform-specific drawing surfaces is
// defined in ui/aura/root_window.* and ui/aura/root_window_host*.
-UI_EXPORT gfx::Point EventLocationFromNative(
+EVENTS_EXPORT gfx::Point EventLocationFromNative(
const base::NativeEvent& native_event);
// Gets the location in native system coordinate space.
-UI_EXPORT gfx::Point EventSystemLocationFromNative(
+EVENTS_EXPORT gfx::Point EventSystemLocationFromNative(
const base::NativeEvent& native_event);
#if defined(USE_X11)
@@ -59,43 +61,44 @@ UI_EXPORT gfx::Point EventSystemLocationFromNative(
// does not take into account any remapping (e.g. using xmodmap), while the
// button reported in master events do. This is a utility function to always
// return the mapped button.
-UI_EXPORT int EventButtonFromNative(const base::NativeEvent& native_event);
+EVENTS_EXPORT int EventButtonFromNative(const base::NativeEvent& native_event);
#endif
// Returns the KeyboardCode from a native event.
-UI_EXPORT KeyboardCode KeyboardCodeFromNative(
+EVENTS_EXPORT KeyboardCode KeyboardCodeFromNative(
const base::NativeEvent& native_event);
// Returns true if the message is a mouse event.
-UI_EXPORT bool IsMouseEvent(const base::NativeEvent& native_event);
+EVENTS_EXPORT bool IsMouseEvent(const base::NativeEvent& native_event);
// Returns the flags of the button that changed during a press/release.
-UI_EXPORT int GetChangedMouseButtonFlagsFromNative(
+EVENTS_EXPORT int GetChangedMouseButtonFlagsFromNative(
const base::NativeEvent& native_event);
// Gets the mouse wheel offsets from a native event.
-UI_EXPORT gfx::Vector2d GetMouseWheelOffset(
+EVENTS_EXPORT gfx::Vector2d GetMouseWheelOffset(
const base::NativeEvent& native_event);
// Gets the touch id from a native event.
-UI_EXPORT int GetTouchId(const base::NativeEvent& native_event);
+EVENTS_EXPORT int GetTouchId(const base::NativeEvent& native_event);
// Clear the touch id from bookkeeping if it is a release/cancel event.
-UI_EXPORT void ClearTouchIdIfReleased(const base::NativeEvent& native_event);
+EVENTS_EXPORT void ClearTouchIdIfReleased(
+ const base::NativeEvent& native_event);
// Gets the radius along the X/Y axis from a native event. Default is 1.0.
-UI_EXPORT float GetTouchRadiusX(const base::NativeEvent& native_event);
-UI_EXPORT float GetTouchRadiusY(const base::NativeEvent& native_event);
+EVENTS_EXPORT float GetTouchRadiusX(const base::NativeEvent& native_event);
+EVENTS_EXPORT float GetTouchRadiusY(const base::NativeEvent& native_event);
// Gets the angle of the major axis away from the X axis. Default is 0.0.
-UI_EXPORT float GetTouchAngle(const base::NativeEvent& native_event);
+EVENTS_EXPORT float GetTouchAngle(const base::NativeEvent& native_event);
// Gets the force from a native_event. Normalized to be [0, 1]. Default is 0.0.
-UI_EXPORT float GetTouchForce(const base::NativeEvent& native_event);
+EVENTS_EXPORT float GetTouchForce(const base::NativeEvent& native_event);
// Gets the fling velocity from a native event. is_cancel is set to true if
// this was a tap down, intended to stop an ongoing fling.
-UI_EXPORT bool GetFlingData(const base::NativeEvent& native_event,
+EVENTS_EXPORT bool GetFlingData(const base::NativeEvent& native_event,
float* vx,
float* vy,
float* vx_ordinal,
@@ -104,50 +107,50 @@ UI_EXPORT bool GetFlingData(const base::NativeEvent& native_event,
// Returns whether this is a scroll event and optionally gets the amount to be
// scrolled. |x_offset|, |y_offset| and |finger_count| can be NULL.
-UI_EXPORT bool GetScrollOffsets(const base::NativeEvent& native_event,
+EVENTS_EXPORT bool GetScrollOffsets(const base::NativeEvent& native_event,
float* x_offset,
float* y_offset,
float* x_offset_ordinal,
float* y_offset_ordinal,
int* finger_count);
-UI_EXPORT bool GetGestureTimes(const base::NativeEvent& native_event,
+EVENTS_EXPORT bool GetGestureTimes(const base::NativeEvent& native_event,
double* start_time,
double* end_time);
// Enable/disable natural scrolling for touchpads.
-UI_EXPORT void SetNaturalScroll(bool enabled);
+EVENTS_EXPORT void SetNaturalScroll(bool enabled);
// In natural scrolling enabled for touchpads?
-UI_EXPORT bool IsNaturalScrollEnabled();
+EVENTS_EXPORT bool IsNaturalScrollEnabled();
// Was this event generated by a touchpad device?
// The caller is responsible for ensuring that this is a mouse/touchpad event
// before calling this function.
-UI_EXPORT bool IsTouchpadEvent(const base::NativeEvent& event);
+EVENTS_EXPORT bool IsTouchpadEvent(const base::NativeEvent& event);
// Returns true if event is noop.
-UI_EXPORT bool IsNoopEvent(const base::NativeEvent& event);
+EVENTS_EXPORT bool IsNoopEvent(const base::NativeEvent& event);
// Creates and returns no-op event.
-UI_EXPORT base::NativeEvent CreateNoopEvent();
+EVENTS_EXPORT base::NativeEvent CreateNoopEvent();
#if defined(OS_WIN)
-UI_EXPORT int GetModifiersFromACCEL(const ACCEL& accel);
-UI_EXPORT int GetModifiersFromKeyState();
+EVENTS_EXPORT int GetModifiersFromACCEL(const ACCEL& accel);
+EVENTS_EXPORT int GetModifiersFromKeyState();
// Returns true if |message| identifies a mouse event that was generated as the
// result of a touch event.
-UI_EXPORT bool IsMouseEventFromTouch(UINT message);
+EVENTS_EXPORT bool IsMouseEventFromTouch(UINT message);
#endif
// Returns true if default post-target handling was canceled for |event| after
// its dispatch to its target.
-UI_EXPORT bool EventCanceledDefaultHandling(const Event& event);
+EVENTS_EXPORT bool EventCanceledDefaultHandling(const Event& event);
// Registers a custom event type.
-UI_EXPORT int RegisterCustomEventType();
+EVENTS_EXPORT int RegisterCustomEventType();
} // namespace ui
-#endif // UI_BASE_EVENTS_EVENT_UTILS_H_
+#endif // UI_EVENTS_EVENT_UTILS_H_
diff --git a/chromium/ui/events/events_export.h b/chromium/ui/events/events_export.h
new file mode 100644
index 00000000000..84d96a6a5f7
--- /dev/null
+++ b/chromium/ui/events/events_export.h
@@ -0,0 +1,33 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_EVENTS_EVENTS_EXPORT_H_
+#define UI_EVENTS_EVENTS_EXPORT_H_
+
+// TODO(beng): remove include once events dependencies have been corrected.
+
+#include "ui/base/ui_export.h"
+
+#if defined(COMPONENT_BUILD)
+#if defined(WIN32)
+
+#if defined(UI_IMPLEMENTATION)
+#define EVENTS_EXPORT __declspec(dllexport)
+#else
+#define EVENTS_EXPORT __declspec(dllimport)
+#endif // defined(UI_IMPLEMENTATION)
+
+#else // defined(WIN32)
+#if defined(UI_IMPLEMENTATION)
+#define EVENTS_EXPORT __attribute__((visibility("default")))
+#else
+#define EVENTS_EXPORT
+#endif
+#endif
+
+#else // defined(COMPONENT_BUILD)
+#define EVENTS_EXPORT
+#endif
+
+#endif // UI_EVENTS_EVENTS_EXPORT_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion.cc b/chromium/ui/events/keycodes/keyboard_code_conversion.cc
index 1a4d92aa4cf..a812b51db3f 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion.cc
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion.cc
@@ -2,9 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/keycodes/keyboard_code_conversion.h"
+#include "ui/events/keycodes/keyboard_code_conversion.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
namespace ui {
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion.h b/chromium/ui/events/keycodes/keyboard_code_conversion.h
index afc7aad2b89..87baf882814 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion.h
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion.h
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_H_
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_H_
#include "base/basictypes.h"
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/events_export.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace ui {
@@ -31,8 +31,8 @@ namespace ui {
// correct character. That's why we can use XLookupString() function to get
// the correct text generated by a X key event (See how is GetCharacter()
// implemented in event_x.cc).
-UI_EXPORT uint16 GetCharacterFromKeyCode(KeyboardCode key_code, int flags);
+EVENTS_EXPORT uint16 GetCharacterFromKeyCode(KeyboardCode key_code, int flags);
} // namespace ui
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_H_
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_android.cc b/chromium/ui/events/keycodes/keyboard_code_conversion_android.cc
index 42f2cc7cbe1..fa0ed31c341 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_android.cc
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_android.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/keycodes/keyboard_code_conversion_android.h"
+#include "ui/events/keycodes/keyboard_code_conversion_android.h"
#include <android/keycodes.h>
diff --git a/chromium/ui/events/keycodes/keyboard_code_conversion_android.h b/chromium/ui/events/keycodes/keyboard_code_conversion_android.h
new file mode 100644
index 00000000000..f064393b760
--- /dev/null
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_android.h
@@ -0,0 +1,17 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_ANDROID_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_ANDROID_H_
+
+#include "ui/events/events_export.h"
+#include "ui/events/keycodes/keyboard_codes_posix.h"
+
+namespace ui {
+
+EVENTS_EXPORT KeyboardCode KeyboardCodeFromAndroidKeyCode(int keycode);
+
+} // namespace ui
+
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_ANDROID_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_gtk.cc b/chromium/ui/events/keycodes/keyboard_code_conversion_gtk.cc
index 0d3fcae60b2..9a396534e20 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_gtk.cc
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_gtk.cc
@@ -33,7 +33,7 @@
// WindowsKeyCodeForGdkKeyCode is copied from platform/gtk/KeyEventGtk.cpp
-#include "ui/base/keycodes/keyboard_code_conversion_gtk.h"
+#include "ui/events/keycodes/keyboard_code_conversion_gtk.h"
#include <gdk/gdk.h>
#include <gdk/gdkkeysyms.h>
@@ -41,8 +41,8 @@
#include "base/basictypes.h"
#include "build/build_config.h"
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
-#include "ui/base/keycodes/keyboard_codes_posix.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
+#include "ui/events/keycodes/keyboard_codes_posix.h"
namespace ui {
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_gtk.h b/chromium/ui/events/keycodes/keyboard_code_conversion_gtk.h
index 3593d0c6c62..c9b6a8dd63b 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_gtk.h
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_gtk.h
@@ -33,25 +33,25 @@
// WindowsKeyCodeForGdkKeyCode is copied from platform/gtk/KeyEventGtk.cpp
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_GTK_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_GTK_H_
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_GTK_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_GTK_H_
-#include "ui/base/keycodes/keyboard_codes_posix.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/events_export.h"
+#include "ui/events/keycodes/keyboard_codes_posix.h"
typedef struct _GdkEventKey GdkEventKey;
namespace ui {
-UI_EXPORT KeyboardCode WindowsKeyCodeForGdkKeyCode(int keycode);
+EVENTS_EXPORT KeyboardCode WindowsKeyCodeForGdkKeyCode(int keycode);
-UI_EXPORT int GdkKeyCodeForWindowsKeyCode(KeyboardCode keycode, bool shift);
+EVENTS_EXPORT int GdkKeyCodeForWindowsKeyCode(KeyboardCode keycode, bool shift);
// For WebKit DRT testing: simulate the native keycode for the given
// input |keycode|. Return the native keycode.
-UI_EXPORT int GdkNativeKeyCodeForWindowsKeyCode(KeyboardCode keycode,
+EVENTS_EXPORT int GdkNativeKeyCodeForWindowsKeyCode(KeyboardCode keycode,
bool shift);
} // namespace ui
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_GTK_H_
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_GTK_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_mac.h b/chromium/ui/events/keycodes/keyboard_code_conversion_mac.h
index b0e97790541..d7c05b0072c 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_mac.h
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_mac.h
@@ -2,14 +2,14 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_MAC_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_MAC_H_
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_MAC_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_MAC_H_
#import <Cocoa/Cocoa.h>
#include "base/basictypes.h"
-#include "ui/base/keycodes/keyboard_codes_posix.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/events_export.h"
+#include "ui/events/keycodes/keyboard_codes_posix.h"
namespace ui {
@@ -25,7 +25,7 @@ namespace ui {
// -1 will be returned if the keycode can't be converted.
// This function is mainly for simulating keyboard events in unit tests.
// See |KeyboardCodeFromNSEvent| for reverse conversion.
-UI_EXPORT int MacKeyCodeForWindowsKeyCode(KeyboardCode keycode,
+EVENTS_EXPORT int MacKeyCodeForWindowsKeyCode(KeyboardCode keycode,
NSUInteger flags,
unichar* character,
unichar* characterIgnoringModifiers);
@@ -34,8 +34,8 @@ UI_EXPORT int MacKeyCodeForWindowsKeyCode(KeyboardCode keycode,
// third_party/WebKit/Source/web/mac/WebInputEventFactory.mm
// Converts |event| into a |KeyboardCode|. The mapping is not direct as the Mac
// has a different notion of key codes.
-UI_EXPORT KeyboardCode KeyboardCodeFromNSEvent(NSEvent* event);
+EVENTS_EXPORT KeyboardCode KeyboardCodeFromNSEvent(NSEvent* event);
} // namespace ui
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODE_CONVERSION_MAC_H_
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_MAC_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_mac.mm b/chromium/ui/events/keycodes/keyboard_code_conversion_mac.mm
index 2f8c2110e92..ed50392f84a 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_mac.mm
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_mac.mm
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#import "ui/base/keycodes/keyboard_code_conversion_mac.h"
+#import "ui/events/keycodes/keyboard_code_conversion_mac.h"
#include <algorithm>
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_win.cc b/chromium/ui/events/keycodes/keyboard_code_conversion_win.cc
index f85cc50b4b5..66eeaa75dc7 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_win.cc
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_win.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
namespace ui {
diff --git a/chromium/ui/events/keycodes/keyboard_code_conversion_win.h b/chromium/ui/events/keycodes/keyboard_code_conversion_win.h
new file mode 100644
index 00000000000..9d1c5d759fb
--- /dev/null
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_win.h
@@ -0,0 +1,19 @@
+// Copyright (c) 2011 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_WIN_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_WIN_H_
+
+#include "ui/events/events_export.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+
+namespace ui {
+
+// Methods to convert ui::KeyboardCode/Windows virtual key type methods.
+EVENTS_EXPORT WORD WindowsKeyCodeForKeyboardCode(KeyboardCode keycode);
+EVENTS_EXPORT KeyboardCode KeyboardCodeForWindowsKeyCode(WORD keycode);
+
+} // namespace ui
+
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_WIN_H_
diff --git a/chromium/ui/base/keycodes/keyboard_code_conversion_x.cc b/chromium/ui/events/keycodes/keyboard_code_conversion_x.cc
index a78354f14e9..8b88e393955 100644
--- a/chromium/ui/base/keycodes/keyboard_code_conversion_x.cc
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_x.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/keycodes/keyboard_code_conversion_x.h"
+#include "ui/events/keycodes/keyboard_code_conversion_x.h"
#define XK_3270 // for XK_3270_BackTab
#include <X11/keysym.h>
diff --git a/chromium/ui/events/keycodes/keyboard_code_conversion_x.h b/chromium/ui/events/keycodes/keyboard_code_conversion_x.h
new file mode 100644
index 00000000000..80b38063fc1
--- /dev/null
+++ b/chromium/ui/events/keycodes/keyboard_code_conversion_x.h
@@ -0,0 +1,31 @@
+// Copyright (c) 2011 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_X_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_X_H_
+
+#include "base/basictypes.h"
+#include "ui/events/events_export.h"
+#include "ui/events/keycodes/keyboard_codes_posix.h"
+
+typedef union _XEvent XEvent;
+
+namespace ui {
+
+EVENTS_EXPORT KeyboardCode KeyboardCodeFromXKeyEvent(XEvent* xev);
+
+EVENTS_EXPORT KeyboardCode KeyboardCodeFromXKeysym(unsigned int keysym);
+
+// Returns a character on a standard US PC keyboard from an XEvent.
+EVENTS_EXPORT uint16 GetCharacterFromXEvent(XEvent* xev);
+
+// Converts a KeyboardCode into an X KeySym.
+EVENTS_EXPORT int XKeysymForWindowsKeyCode(KeyboardCode keycode, bool shift);
+
+// Converts an X keycode into an X KeySym.
+unsigned int DefaultXKeysymFromHardwareKeycode(unsigned int keycode);
+
+} // namespace ui
+
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODE_CONVERSION_X_H_
diff --git a/chromium/ui/base/keycodes/keyboard_codes.h b/chromium/ui/events/keycodes/keyboard_codes.h
index 19d6e389c67..00a7847ae9b 100644
--- a/chromium/ui/base/keycodes/keyboard_codes.h
+++ b/chromium/ui/events/keycodes/keyboard_codes.h
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODES_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODES_H_
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODES_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODES_H_
#include "build/build_config.h"
#if defined(OS_WIN)
-#include "ui/base/keycodes/keyboard_codes_win.h"
+#include "ui/events/keycodes/keyboard_codes_win.h"
#elif defined(OS_POSIX)
-#include "ui/base/keycodes/keyboard_codes_posix.h"
+#include "ui/events/keycodes/keyboard_codes_posix.h"
#endif
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODES_H_
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODES_H_
diff --git a/chromium/ui/base/keycodes/keyboard_codes_posix.h b/chromium/ui/events/keycodes/keyboard_codes_posix.h
index 5879c99897e..1f7e06f96b2 100644
--- a/chromium/ui/base/keycodes/keyboard_codes_posix.h
+++ b/chromium/ui/events/keycodes/keyboard_codes_posix.h
@@ -28,8 +28,8 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODES_POSIX_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODES_POSIX_H_
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODES_POSIX_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODES_POSIX_H_
namespace ui {
@@ -225,4 +225,4 @@ enum KeyboardCode {
} // namespace ui
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODES_POSIX_H_
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODES_POSIX_H_
diff --git a/chromium/ui/base/keycodes/keyboard_codes_win.h b/chromium/ui/events/keycodes/keyboard_codes_win.h
index fb8ac20f90c..396d38bea7e 100644
--- a/chromium/ui/base/keycodes/keyboard_codes_win.h
+++ b/chromium/ui/events/keycodes/keyboard_codes_win.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_KEYCODES_KEYBOARD_CODES_WIN_H_
-#define UI_BASE_KEYCODES_KEYBOARD_CODES_WIN_H_
+#ifndef UI_EVENTS_KEYCODES_KEYBOARD_CODES_WIN_H_
+#define UI_EVENTS_KEYCODES_KEYBOARD_CODES_WIN_H_
#include <windows.h>
#include <ime.h>
@@ -189,4 +189,4 @@ enum KeyboardCode {
} // namespace ui
-#endif // UI_BASE_KEYCODES_KEYBOARD_CODES_WIN_H_
+#endif // UI_EVENTS_KEYCODES_KEYBOARD_CODES_WIN_H_
diff --git a/chromium/ui/base/latency_info.cc b/chromium/ui/events/latency_info.cc
index 9551450fab5..796f442ae6d 100644
--- a/chromium/ui/base/latency_info.cc
+++ b/chromium/ui/events/latency_info.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/latency_info.h"
+#include "ui/events/latency_info.h"
#include <algorithm>
diff --git a/chromium/ui/base/latency_info.h b/chromium/ui/events/latency_info.h
index 3482a500a8d..8bf56100dfd 100644
--- a/chromium/ui/base/latency_info.h
+++ b/chromium/ui/events/latency_info.h
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_LATENCY_INFO_H_
-#define UI_BASE_LATENCY_INFO_H_
+#ifndef UI_EVENTS_LATENCY_INFO_H_
+#define UI_EVENTS_LATENCY_INFO_H_
#include <map>
#include <utility>
#include "base/basictypes.h"
#include "base/time/time.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/events_export.h"
namespace ui {
@@ -35,7 +35,7 @@ enum LatencyComponentType {
INPUT_EVENT_LATENCY_ACKED_COMPONENT
};
-struct UI_EXPORT LatencyInfo {
+struct EVENTS_EXPORT LatencyInfo {
struct LatencyComponent {
// Nondecreasing number that can be used to determine what events happened
// in the component at the time this struct was sent on to the next
@@ -93,4 +93,4 @@ struct UI_EXPORT LatencyInfo {
} // namespace ui
-#endif // UI_BASE_LATENCY_INFO_H_
+#endif // UI_EVENTS_LATENCY_INFO_H_
diff --git a/chromium/ui/base/latency_info_unittest.cc b/chromium/ui/events/latency_info_unittest.cc
index bb834787d30..32bb8695765 100644
--- a/chromium/ui/base/latency_info_unittest.cc
+++ b/chromium/ui/events/latency_info_unittest.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/latency_info.h"
+#include "ui/events/latency_info.h"
#include "testing/gtest/include/gtest/gtest.h"
diff --git a/chromium/ui/base/ozone/OWNERS b/chromium/ui/events/ozone/OWNERS
index 77f21b5cae7..77f21b5cae7 100644
--- a/chromium/ui/base/ozone/OWNERS
+++ b/chromium/ui/events/ozone/OWNERS
diff --git a/chromium/ui/base/ozone/evdev/key_event_converter_ozone.cc b/chromium/ui/events/ozone/evdev/key_event_converter_ozone.cc
index 8766164c8b5..dc949d98366 100644
--- a/chromium/ui/base/ozone/evdev/key_event_converter_ozone.cc
+++ b/chromium/ui/events/ozone/evdev/key_event_converter_ozone.cc
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/ozone/evdev/key_event_converter_ozone.h"
+#include "ui/events/ozone/evdev/key_event_converter_ozone.h"
#include <linux/input.h>
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace {
diff --git a/chromium/ui/base/ozone/evdev/key_event_converter_ozone.h b/chromium/ui/events/ozone/evdev/key_event_converter_ozone.h
index 2ce3c22322b..2fdcb638a86 100644
--- a/chromium/ui/base/ozone/evdev/key_event_converter_ozone.h
+++ b/chromium/ui/events/ozone/evdev/key_event_converter_ozone.h
@@ -2,10 +2,10 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_OZONE_EVDEV_KEY_EVENT_CONVERTER_OZONE_H_
-#define UI_BASE_OZONE_EVDEV_KEY_EVENT_CONVERTER_OZONE_H_
+#ifndef UI_EVENTS_OZONE_EVDEV_KEY_EVENT_CONVERTER_OZONE_H_
+#define UI_EVENTS_OZONE_EVDEV_KEY_EVENT_CONVERTER_OZONE_H_
-#include "ui/base/ozone/event_converter_ozone.h"
+#include "ui/events/ozone/event_converter_ozone.h"
namespace ui {
@@ -24,4 +24,5 @@ class KeyEventConverterOzone : public EventConverterOzone {
} // namspace ui
-#endif // UI_BASE_OZONE_EVDEV_KEY_EVENT_CONVERTER_OZONE_H_
+#endif // UI_EVENTS_OZONE_EVDEV_KEY_EVENT_CONVERTER_OZONE_H_
+
diff --git a/chromium/ui/base/ozone/evdev/touch_event_converter_ozone.cc b/chromium/ui/events/ozone/evdev/touch_event_converter_ozone.cc
index 0e4f560305e..30e94139084 100644
--- a/chromium/ui/base/ozone/evdev/touch_event_converter_ozone.cc
+++ b/chromium/ui/events/ozone/evdev/touch_event_converter_ozone.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/ozone/evdev/touch_event_converter_ozone.h"
+#include "ui/events/ozone/evdev/touch_event_converter_ozone.h"
#include <fcntl.h>
#include <linux/input.h>
@@ -11,15 +11,16 @@
#include <unistd.h>
#include <cmath>
+#include <limits>
#include "base/bind.h"
#include "base/callback.h"
#include "base/logging.h"
#include "base/message_loop/message_loop.h"
#include "base/message_loop/message_pump_ozone.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/ozone/surface_factory_ozone.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/gfx/ozone/surface_factory_ozone.h"
namespace {
@@ -36,6 +37,8 @@ TouchEventConverterOzone::TouchEventConverterOzone(int fd, int id)
pressure_max_(0),
x_scale_(1.),
y_scale_(1.),
+ x_max_(std::numeric_limits<int>::max()),
+ y_max_(std::numeric_limits<int>::max()),
current_slot_(0),
fd_(fd),
id_(id) {
@@ -75,14 +78,16 @@ void TouchEventConverterOzone::Init() {
} else {
LOG(WARNING) << "failed ioctl EVIOCGABS ABS_Y event" << id_;
}
- if (x_max && y_max && SurfaceFactoryOzone::GetInstance()) {
+ if (x_max && y_max && gfx::SurfaceFactoryOzone::GetInstance()) {
const char* display =
- SurfaceFactoryOzone::GetInstance()->DefaultDisplaySpec();
+ gfx::SurfaceFactoryOzone::GetInstance()->DefaultDisplaySpec();
int screen_width, screen_height;
int sc = sscanf(display, "%dx%d", &screen_width, &screen_height);
if (sc == 2) {
x_scale_ = (double)screen_width / (x_max - x_min);
y_scale_ = (double)screen_height / (y_max - y_min);
+ x_max_ = screen_width - 1;
+ y_max_ = screen_height - 1;
LOG(INFO) << "touch input x_scale=" << x_scale_
<< " y_scale=" << y_scale_;
} else {
@@ -151,7 +156,8 @@ void TouchEventConverterOzone::OnFileCanReadWithoutBlocking(int fd) {
// TODO(rjkroege): Support elliptical finger regions.
scoped_ptr<TouchEvent> tev(new TouchEvent(
events_[j].type_,
- gfx::Point(events_[j].x_, events_[j].y_),
+ gfx::Point(std::min(x_max_, events_[j].x_),
+ std::min(y_max_, events_[j].y_)),
/* flags */ 0,
/* touch_id */ j,
base::TimeDelta::FromMicroseconds(
@@ -160,8 +166,11 @@ void TouchEventConverterOzone::OnFileCanReadWithoutBlocking(int fd) {
events_[j].pressure_ * kFingerWidth,
/* angle */ 0.,
events_[j].pressure_));
- events_[j].type_ = ET_TOUCH_MOVED;
DispatchEvent(tev.PassAs<ui::Event>());
+
+ // Subsequent events for this finger will be touch-move until it
+ // is released.
+ events_[j].type_ = ET_TOUCH_MOVED;
}
}
altered_slots_.reset();
diff --git a/chromium/ui/base/ozone/evdev/touch_event_converter_ozone.h b/chromium/ui/events/ozone/evdev/touch_event_converter_ozone.h
index ef96be405b0..730bfaffc19 100644
--- a/chromium/ui/base/ozone/evdev/touch_event_converter_ozone.h
+++ b/chromium/ui/events/ozone/evdev/touch_event_converter_ozone.h
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_OZONE_EVDEV_TOUCH_EVENT_CONVERTER_OZONE_H_
-#define UI_BASE_OZONE_EVDEV_TOUCH_EVENT_CONVERTER_OZONE_H_
+#ifndef UI_EVENTS_OZONE_EVDEV_TOUCH_EVENT_CONVERTER_OZONE_H_
+#define UI_EVENTS_OZONE_EVDEV_TOUCH_EVENT_CONVERTER_OZONE_H_
#include <bitset>
#include "base/compiler_specific.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/ozone/event_converter_ozone.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/events_export.h"
+#include "ui/events/ozone/event_converter_ozone.h"
namespace ui {
@@ -42,6 +42,10 @@ class UI_EXPORT TouchEventConverterOzone : public EventConverterOzone {
float x_scale_;
float y_scale_;
+ // Maximum coordinate-values allowed for the events.
+ int x_max_;
+ int y_max_;
+
// Touch point currently being updated from the /dev/input/event* stream.
int current_slot_;
@@ -74,4 +78,5 @@ class UI_EXPORT TouchEventConverterOzone : public EventConverterOzone {
} // namespace ui
-#endif // UI_BASE_OZONE_EVDEV_TOUCH_EVENT_CONVERTER_OZONE_H_
+#endif // UI_EVENTS_OZONE_EVDEV_TOUCH_EVENT_CONVERTER_OZONE_H_
+
diff --git a/chromium/ui/base/ozone/evdev/touch_event_converter_ozone_unittest.cc b/chromium/ui/events/ozone/evdev/touch_event_converter_ozone_unittest.cc
index 61bf54bda5b..709b5c129d3 100644
--- a/chromium/ui/base/ozone/evdev/touch_event_converter_ozone_unittest.cc
+++ b/chromium/ui/events/ozone/evdev/touch_event_converter_ozone_unittest.cc
@@ -16,8 +16,8 @@
#include "base/run_loop.h"
#include "base/time/time.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event.h"
-#include "ui/base/ozone/evdev/touch_event_converter_ozone.h"
+#include "ui/events/event.h"
+#include "ui/events/ozone/evdev/touch_event_converter_ozone.h"
namespace {
diff --git a/chromium/ui/base/ozone/event_converter_ozone.cc b/chromium/ui/events/ozone/event_converter_ozone.cc
index 485ea22bc0e..2bb6164e80b 100644
--- a/chromium/ui/base/ozone/event_converter_ozone.cc
+++ b/chromium/ui/events/ozone/event_converter_ozone.cc
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/ozone/event_converter_ozone.h"
+#include "ui/events/ozone/event_converter_ozone.h"
#include "base/bind.h"
#include "base/message_loop/message_loop.h"
#include "base/message_loop/message_pump_ozone.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
namespace {
diff --git a/chromium/ui/base/ozone/event_converter_ozone.h b/chromium/ui/events/ozone/event_converter_ozone.h
index 58db8363bc5..b28df34fb6b 100644
--- a/chromium/ui/base/ozone/event_converter_ozone.h
+++ b/chromium/ui/events/ozone/event_converter_ozone.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_OZONE_EVENT_CONVERTER_OZONE_H_
-#define UI_BASE_OZONE_EVENT_CONVERTER_OZONE_H_
+#ifndef UI_EVENTS_OZONE_EVENT_CONVERTER_OZONE_H_
+#define UI_EVENTS_OZONE_EVENT_CONVERTER_OZONE_H_
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_pump_libevent.h"
@@ -35,4 +35,4 @@ class EventConverterOzone : public base::MessagePumpLibevent::Watcher {
} // namespace ui
-#endif // UI_BASE_OZONE_EVENT_CONVERTER_OZONE_H_
+#endif // UI_EVENTS_OZONE_EVENT_CONVERTER_OZONE_H_
diff --git a/chromium/ui/base/ozone/event_factory_delegate_ozone.h b/chromium/ui/events/ozone/event_factory_delegate_ozone.h
index 04d427dd8fc..e16adc81985 100644
--- a/chromium/ui/base/ozone/event_factory_delegate_ozone.h
+++ b/chromium/ui/events/ozone/event_factory_delegate_ozone.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_OZONE_EVENT_FACTORY_DELEGATE_OZONE_H_
-#define UI_BASE_OZONE_EVENT_FACTORY_DELEGATE_OZONE_H_
+#ifndef UI_EVENTS_OZONE_EVENT_FACTORY_DELEGATE_OZONE_H_
+#define UI_EVENTS_OZONE_EVENT_FACTORY_DELEGATE_OZONE_H_
namespace ui {
class Event;
@@ -26,4 +26,4 @@ class UI_EXPORT EventFactoryDelegateOzone {
} // namespace ui
-#endif // UI_BASE_OZONE_EVENT_FACTORY_DELEGATE_OZONE_H_
+#endif // UI_EVENTS_OZONE_EVENT_FACTORY_DELEGATE_OZONE_H_
diff --git a/chromium/ui/base/ozone/event_factory_ozone.cc b/chromium/ui/events/ozone/event_factory_ozone.cc
index afeff2b7a19..acdf9958b55 100644
--- a/chromium/ui/base/ozone/event_factory_ozone.cc
+++ b/chromium/ui/events/ozone/event_factory_ozone.cc
@@ -2,8 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/ozone/event_factory_ozone.h"
+#include "ui/events/ozone/event_factory_ozone.h"
+#include <errno.h>
#include <fcntl.h>
#include <linux/input.h>
#include <poll.h>
@@ -12,9 +13,9 @@
#include "base/message_loop/message_pump_ozone.h"
#include "base/stl_util.h"
#include "base/strings/stringprintf.h"
-#include "ui/base/ozone/evdev/key_event_converter_ozone.h"
-#include "ui/base/ozone/evdev/touch_event_converter_ozone.h"
-#include "ui/base/ozone/event_factory_delegate_ozone.h"
+#include "ui/events/ozone/evdev/key_event_converter_ozone.h"
+#include "ui/events/ozone/evdev/touch_event_converter_ozone.h"
+#include "ui/events/ozone/event_factory_delegate_ozone.h"
namespace ui {
@@ -45,8 +46,10 @@ void EventFactoryOzone::CreateStartupEventConverters() {
for (int id = 0; true; id++) {
std::string path = base::StringPrintf("/dev/input/event%d", id);
int fd = open(path.c_str(), O_RDONLY | O_NONBLOCK);
- if (fd < 0)
+ if (fd < 0) {
+ DLOG(ERROR) << "Cannot open '" << path << "': " << strerror(errno);
break;
+ }
size_t evtype = 0;
COMPILE_ASSERT(sizeof(evtype) * 8 >= EV_MAX, evtype_wide_enough);
if (ioctl(fd, EVIOCGBIT(0, sizeof(evtype)), &evtype) == -1) {
diff --git a/chromium/ui/base/ozone/event_factory_ozone.h b/chromium/ui/events/ozone/event_factory_ozone.h
index b88654e5264..489d4aebce1 100644
--- a/chromium/ui/base/ozone/event_factory_ozone.h
+++ b/chromium/ui/events/ozone/event_factory_ozone.h
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_OZONE_EVENT_FACTORY_OZONE_H_
-#define UI_BASE_OZONE_EVENT_FACTORY_OZONE_H_
+#ifndef UI_EVENTS_OZONE_EVENT_FACTORY_OZONE_H_
+#define UI_EVENTS_OZONE_EVENT_FACTORY_OZONE_H_
#include <map>
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_pump_libevent.h"
-#include "ui/base/ozone/event_converter_ozone.h"
-#include "ui/base/ui_export.h"
+#include "ui/events/events_export.h"
+#include "ui/events/ozone/event_converter_ozone.h"
namespace ui {
@@ -57,4 +57,4 @@ class UI_EXPORT EventFactoryOzone {
} // namespace ui
-#endif // UI_BASE_OZONE_EVENT_FACTORY_OZONE_H_
+#endif // UI_EVENTS_OZONE_EVENT_FACTORY_OZONE_H_
diff --git a/chromium/ui/base/ozone/events_ozone.cc b/chromium/ui/events/ozone/events_ozone.cc
index cad17f69728..0db40f48a2c 100644
--- a/chromium/ui/base/ozone/events_ozone.cc
+++ b/chromium/ui/events/ozone/events_ozone.cc
@@ -2,9 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
namespace ui {
diff --git a/chromium/ui/gfx/android/device_display_info.h b/chromium/ui/gfx/android/device_display_info.h
index af7bb622b25..9f90f897b6a 100644
--- a/chromium/ui/gfx/android/device_display_info.h
+++ b/chromium/ui/gfx/android/device_display_info.h
@@ -10,7 +10,7 @@
#include "base/android/scoped_java_ref.h"
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/android/java_bitmap.cc b/chromium/ui/gfx/android/java_bitmap.cc
index e292b385aa1..6c2eaa845a2 100644
--- a/chromium/ui/gfx/android/java_bitmap.cc
+++ b/chromium/ui/gfx/android/java_bitmap.cc
@@ -6,6 +6,7 @@
#include <android/bitmap.h>
+#include "base/android/jni_string.h"
#include "base/logging.h"
#include "jni/BitmapHelper_jni.h"
#include "skia/ext/image_operations.h"
@@ -61,32 +62,20 @@ ScopedJavaLocalRef<jobject> ConvertToJavaBitmap(const SkBitmap* skbitmap) {
return jbitmap;
}
-static ScopedJavaLocalRef<jobject> CreateJavaBitmapFromResource(
- const char* name, gfx::Size requested_size) {
- JNIEnv* env = AttachCurrentThread();
- ScopedJavaLocalRef<jstring> jname(env, env->NewStringUTF(name));
- return ui::Java_BitmapHelper_decodeDrawableResource(env,
- jname.obj(),
- requested_size.width(),
- requested_size.height());
-}
-
-static SkBitmap ConvertToSkBitmap(ScopedJavaLocalRef<jobject> jbitmap) {
- if (jbitmap.is_null())
- return SkBitmap();
+SkBitmap CreateSkBitmapFromJavaBitmap(JavaBitmap& jbitmap) {
+ DCHECK_EQ(jbitmap.format(), ANDROID_BITMAP_FORMAT_RGBA_8888);
- JavaBitmap src_lock(jbitmap.obj());
- DCHECK_EQ(src_lock.format(), ANDROID_BITMAP_FORMAT_RGBA_8888);
-
- gfx::Size src_size = src_lock.size();
+ gfx::Size src_size = jbitmap.size();
SkBitmap skbitmap;
skbitmap.setConfig(SkBitmap::kARGB_8888_Config,
- src_size.width(), src_size.height(), src_lock.stride());
+ src_size.width(),
+ src_size.height(),
+ jbitmap.stride());
skbitmap.allocPixels();
SkAutoLockPixels dst_lock(skbitmap);
- void* src_pixels = src_lock.pixels();
+ void* src_pixels = jbitmap.pixels();
void* dst_pixels = skbitmap.getPixels();
memcpy(dst_pixels, src_pixels, skbitmap.getSize());
@@ -96,13 +85,17 @@ static SkBitmap ConvertToSkBitmap(ScopedJavaLocalRef<jobject> jbitmap) {
SkBitmap CreateSkBitmapFromResource(const char* name, gfx::Size size) {
DCHECK(!size.IsEmpty());
- SkBitmap bitmap =
- ConvertToSkBitmap(CreateJavaBitmapFromResource(name, size));
- if (bitmap.isNull())
- return bitmap;
- return skia::ImageOperations::Resize(bitmap,
- skia::ImageOperations::RESIZE_GOOD,
- size.width(), size.height());
+ JNIEnv* env = AttachCurrentThread();
+ ScopedJavaLocalRef<jstring> jname(env, env->NewStringUTF(name));
+ ScopedJavaLocalRef<jobject> jobj(ui::Java_BitmapHelper_decodeDrawableResource(
+ env, jname.obj(), size.width(), size.height()));
+ if (jobj.is_null())
+ return SkBitmap();
+
+ JavaBitmap jbitmap(jobj.obj());
+ SkBitmap bitmap = CreateSkBitmapFromJavaBitmap(jbitmap);
+ return skia::ImageOperations::Resize(
+ bitmap, skia::ImageOperations::RESIZE_BOX, size.width(), size.height());
}
} // namespace gfx
diff --git a/chromium/ui/gfx/android/java_bitmap.h b/chromium/ui/gfx/android/java_bitmap.h
index 9dd49fb8a38..319ad79eb1e 100644
--- a/chromium/ui/gfx/android/java_bitmap.h
+++ b/chromium/ui/gfx/android/java_bitmap.h
@@ -44,7 +44,10 @@ class UI_EXPORT JavaBitmap {
UI_EXPORT base::android::ScopedJavaLocalRef<jobject> ConvertToJavaBitmap(
const SkBitmap* skbitmap);
+UI_EXPORT SkBitmap CreateSkBitmapFromJavaBitmap(JavaBitmap& jbitmap);
+
// If the resource loads successfully, it will be resized to |size|.
+// Note: If the source resource is smaller than |size|, quality may suffer.
UI_EXPORT SkBitmap CreateSkBitmapFromResource(const char* name, gfx::Size size);
} // namespace gfx
diff --git a/chromium/ui/base/animation/animation.cc b/chromium/ui/gfx/animation/animation.cc
index 78ee4d9c213..ba0bac822cc 100644
--- a/chromium/ui/base/animation/animation.cc
+++ b/chromium/ui/gfx/animation/animation.cc
@@ -2,18 +2,18 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/animation.h"
+#include "ui/gfx/animation/animation.h"
-#include "ui/base/animation/animation_container.h"
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/animation_container.h"
+#include "ui/gfx/animation/animation_delegate.h"
+#include "ui/gfx/animation/tween.h"
#include "ui/gfx/rect.h"
#if defined(OS_WIN)
#include "base/win/windows_version.h"
#endif
-namespace ui {
+namespace gfx {
Animation::Animation(base::TimeDelta timer_interval)
: timer_interval_(timer_interval),
@@ -121,4 +121,4 @@ base::TimeDelta Animation::GetTimerInterval() const {
return timer_interval_;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/animation.h b/chromium/ui/gfx/animation/animation.h
index 361ab15dbbd..32d297e2939 100644
--- a/chromium/ui/base/animation/animation.h
+++ b/chromium/ui/gfx/animation/animation.h
@@ -2,19 +2,19 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_ANIMATION_H_
-#define UI_BASE_ANIMATION_ANIMATION_H_
+#ifndef UI_GFX_ANIMATION_ANIMATION_H_
+#define UI_GFX_ANIMATION_ANIMATION_H_
#include "base/compiler_specific.h"
#include "base/memory/ref_counted.h"
#include "base/time/time.h"
-#include "ui/base/animation/animation_container_element.h"
+#include "ui/gfx/animation/animation_container_element.h"
namespace gfx {
class Rect;
}
-namespace ui {
+namespace gfx {
class AnimationContainer;
class AnimationDelegate;
@@ -25,7 +25,7 @@ class AnimationDelegate;
//
// To subclass override Step, which is invoked as the animation progresses and
// GetCurrentValue() to return the value appropriate to the animation.
-class UI_EXPORT Animation : public AnimationContainerElement {
+class GFX_EXPORT Animation : public AnimationContainerElement {
public:
explicit Animation(base::TimeDelta timer_interval);
virtual ~Animation();
@@ -104,6 +104,6 @@ class UI_EXPORT Animation : public AnimationContainerElement {
DISALLOW_COPY_AND_ASSIGN(Animation);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_ANIMATION_H_
+#endif // UI_GFX_ANIMATION_ANIMATION_H_
diff --git a/chromium/ui/base/animation/animation_container.cc b/chromium/ui/gfx/animation/animation_container.cc
index c82d26b9aa5..c76f1bb7797 100644
--- a/chromium/ui/base/animation/animation_container.cc
+++ b/chromium/ui/gfx/animation/animation_container.cc
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/animation_container.h"
+#include "ui/gfx/animation/animation_container.h"
-#include "ui/base/animation/animation_container_element.h"
-#include "ui/base/animation/animation_container_observer.h"
+#include "ui/gfx/animation/animation_container_element.h"
+#include "ui/gfx/animation/animation_container_observer.h"
using base::TimeDelta;
using base::TimeTicks;
-namespace ui {
+namespace gfx {
AnimationContainer::AnimationContainer()
: last_tick_time_(TimeTicks::Now()),
@@ -101,4 +101,4 @@ TimeDelta AnimationContainer::GetMinInterval() {
return min;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/animation_container.h b/chromium/ui/gfx/animation/animation_container.h
index e1631f082e4..bb59f8f0cc7 100644
--- a/chromium/ui/base/animation/animation_container.h
+++ b/chromium/ui/gfx/animation/animation_container.h
@@ -2,17 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_ANIMATION_CONTAINER_H_
-#define UI_BASE_ANIMATION_ANIMATION_CONTAINER_H_
+#ifndef UI_GFX_ANIMATION_ANIMATION_CONTAINER_H_
+#define UI_GFX_ANIMATION_ANIMATION_CONTAINER_H_
#include <set>
#include "base/memory/ref_counted.h"
#include "base/time/time.h"
#include "base/timer/timer.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
-namespace ui {
+namespace gfx {
class AnimationContainerElement;
class AnimationContainerObserver;
@@ -25,7 +25,7 @@ class AnimationContainerObserver;
//
// AnimationContainer is ref counted. Each Animation contained within the
// AnimationContainer own it.
-class UI_EXPORT AnimationContainer
+class GFX_EXPORT AnimationContainer
: public base::RefCounted<AnimationContainer> {
public:
AnimationContainer();
@@ -86,6 +86,6 @@ class UI_EXPORT AnimationContainer
DISALLOW_COPY_AND_ASSIGN(AnimationContainer);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_ANIMATION_CONTAINER_H_
+#endif // UI_GFX_ANIMATION_ANIMATION_CONTAINER_H_
diff --git a/chromium/ui/base/animation/animation_container_element.h b/chromium/ui/gfx/animation/animation_container_element.h
index 1afa2b8b0c2..224655eb318 100644
--- a/chromium/ui/base/animation/animation_container_element.h
+++ b/chromium/ui/gfx/animation/animation_container_element.h
@@ -2,17 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_ANIMATION_CONTAINER_ELEMENT_H_
-#define UI_BASE_ANIMATION_ANIMATION_CONTAINER_ELEMENT_H_
+#ifndef UI_GFX_ANIMATION_ANIMATION_CONTAINER_ELEMENT_H_
+#define UI_GFX_ANIMATION_ANIMATION_CONTAINER_ELEMENT_H_
#include "base/time/time.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
-namespace ui {
+namespace gfx {
// Interface for the elements the AnimationContainer contains. This is
// implemented by Animation.
-class UI_EXPORT AnimationContainerElement {
+class GFX_EXPORT AnimationContainerElement {
public:
// Sets the start of the animation. This is invoked from
// AnimationContainer::Start.
@@ -29,6 +29,6 @@ class UI_EXPORT AnimationContainerElement {
virtual ~AnimationContainerElement() {}
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_ANIMATION_CONTAINER_ELEMENT_H_
+#endif // UI_GFX_ANIMATION_ANIMATION_CONTAINER_ELEMENT_H_
diff --git a/chromium/ui/base/animation/animation_container_observer.h b/chromium/ui/gfx/animation/animation_container_observer.h
index 06948ef3449..a5051679626 100644
--- a/chromium/ui/base/animation/animation_container_observer.h
+++ b/chromium/ui/gfx/animation/animation_container_observer.h
@@ -2,18 +2,18 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_ANIMATION_CONTAINER_OBSERVER_H_
-#define UI_BASE_ANIMATION_ANIMATION_CONTAINER_OBSERVER_H_
+#ifndef UI_GFX_ANIMATION_ANIMATION_CONTAINER_OBSERVER_H_
+#define UI_GFX_ANIMATION_ANIMATION_CONTAINER_OBSERVER_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
-namespace ui {
+namespace gfx {
class AnimationContainer;
// The observer is notified after every update of the animations managed by
// the container.
-class UI_EXPORT AnimationContainerObserver {
+class GFX_EXPORT AnimationContainerObserver {
public:
// Invoked on every tick of the timer managed by the container and after
// all the animations have updated.
@@ -27,6 +27,6 @@ class UI_EXPORT AnimationContainerObserver {
virtual ~AnimationContainerObserver() {}
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_ANIMATION_CONTAINER_OBSERVER_H_
+#endif // UI_GFX_ANIMATION_ANIMATION_CONTAINER_OBSERVER_H_
diff --git a/chromium/ui/base/animation/animation_container_unittest.cc b/chromium/ui/gfx/animation/animation_container_unittest.cc
index c516cf325f8..25977c26161 100644
--- a/chromium/ui/base/animation/animation_container_unittest.cc
+++ b/chromium/ui/gfx/animation/animation_container_unittest.cc
@@ -2,17 +2,18 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "ui/gfx/animation/animation_container.h"
+
#include "base/memory/scoped_ptr.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/animation/animation_container.h"
-#include "ui/base/animation/animation_container_observer.h"
-#include "ui/base/animation/linear_animation.h"
-#include "ui/base/animation/test_animation_delegate.h"
+#include "ui/gfx/animation/animation_container_observer.h"
+#include "ui/gfx/animation/linear_animation.h"
+#include "ui/gfx/animation/test_animation_delegate.h"
using testing::AtLeast;
-namespace ui {
+namespace gfx {
namespace {
@@ -123,4 +124,4 @@ TEST_F(AnimationContainerTest, Observer) {
container->set_observer(NULL);
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/animation_delegate.h b/chromium/ui/gfx/animation/animation_delegate.h
index 9a7edbcd1af..94303ddd93a 100644
--- a/chromium/ui/base/animation/animation_delegate.h
+++ b/chromium/ui/gfx/animation/animation_delegate.h
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_ANIMATION_DELEGATE_H_
-#define UI_BASE_ANIMATION_ANIMATION_DELEGATE_H_
+#ifndef UI_GFX_ANIMATION_ANIMATION_DELEGATE_H_
+#define UI_GFX_ANIMATION_ANIMATION_DELEGATE_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
-namespace ui {
+namespace gfx {
class Animation;
@@ -15,7 +15,7 @@ class Animation;
//
// Implement this interface when you want to receive notifications about the
// state of an animation.
-class UI_EXPORT AnimationDelegate {
+class GFX_EXPORT AnimationDelegate {
public:
// Called when an animation has completed.
virtual void AnimationEnded(const Animation* animation) {}
@@ -30,6 +30,6 @@ class UI_EXPORT AnimationDelegate {
virtual ~AnimationDelegate() {}
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_ANIMATION_DELEGATE_H_
+#endif // UI_GFX_ANIMATION_ANIMATION_DELEGATE_H_
diff --git a/chromium/ui/base/animation/animation_unittest.cc b/chromium/ui/gfx/animation/animation_unittest.cc
index 007f92d07d4..00f1e2626c1 100644
--- a/chromium/ui/base/animation/animation_unittest.cc
+++ b/chromium/ui/gfx/animation/animation_unittest.cc
@@ -3,15 +3,15 @@
// found in the LICENSE file.
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/animation/linear_animation.h"
-#include "ui/base/animation/test_animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
+#include "ui/gfx/animation/linear_animation.h"
+#include "ui/gfx/animation/test_animation_delegate.h"
#if defined(OS_WIN)
#include "base/win/windows_version.h"
#endif
-namespace ui {
+namespace gfx {
class AnimationTest: public testing::Test {
private:
@@ -155,4 +155,4 @@ TEST_F(AnimationTest, StartState) {
EXPECT_EQ(0.0, animation.GetCurrentValue());
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/linear_animation.cc b/chromium/ui/gfx/animation/linear_animation.cc
index 33bd1d1a481..b3f3df0e0c9 100644
--- a/chromium/ui/base/animation/linear_animation.cc
+++ b/chromium/ui/gfx/animation/linear_animation.cc
@@ -2,17 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/linear_animation.h"
+#include "ui/gfx/animation/linear_animation.h"
#include <math.h>
-#include "ui/base/animation/animation_container.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_container.h"
+#include "ui/gfx/animation/animation_delegate.h"
using base::Time;
using base::TimeDelta;
-namespace ui {
+namespace gfx {
static TimeDelta CalculateInterval(int frame_rate) {
int timer_interval = 1000000 / frame_rate;
@@ -105,4 +105,4 @@ bool LinearAnimation::ShouldSendCanceledFromStop() {
return state_ != 1;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/linear_animation.h b/chromium/ui/gfx/animation/linear_animation.h
index 307a9fbe111..401f1be18bb 100644
--- a/chromium/ui/base/animation/linear_animation.h
+++ b/chromium/ui/gfx/animation/linear_animation.h
@@ -2,19 +2,19 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_LINEAR_ANIMATION_H_
-#define UI_BASE_ANIMATION_LINEAR_ANIMATION_H_
+#ifndef UI_GFX_ANIMATION_LINEAR_ANIMATION_H_
+#define UI_GFX_ANIMATION_LINEAR_ANIMATION_H_
#include "base/time/time.h"
-#include "ui/base/animation/animation.h"
+#include "ui/gfx/animation/animation.h"
-namespace ui {
+namespace gfx {
class AnimationDelegate;
// Linear time bounded animation. As the animation progresses AnimateToState is
// invoked.
-class UI_EXPORT LinearAnimation : public Animation {
+class GFX_EXPORT LinearAnimation : public Animation {
public:
// Initializes everything except the duration.
//
@@ -74,6 +74,6 @@ class UI_EXPORT LinearAnimation : public Animation {
DISALLOW_COPY_AND_ASSIGN(LinearAnimation);
};
-} // namespace ui
+} // namespace gfx
#endif // APP_LINEAR_ANIMATION_H_
diff --git a/chromium/ui/base/animation/multi_animation.cc b/chromium/ui/gfx/animation/multi_animation.cc
index 2e9e4772db6..4ecc73c805a 100644
--- a/chromium/ui/base/animation/multi_animation.cc
+++ b/chromium/ui/gfx/animation/multi_animation.cc
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/multi_animation.h"
+#include "ui/gfx/animation/multi_animation.h"
#include "base/logging.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
-namespace ui {
+namespace gfx {
// Default interval, in ms.
static const int kDefaultTimerInterval = 20;
@@ -91,4 +91,4 @@ const MultiAnimation::Part& MultiAnimation::GetPart(int* time_ms,
return parts_[0];
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/multi_animation.h b/chromium/ui/gfx/animation/multi_animation.h
index cbe36c4c752..f0480980576 100644
--- a/chromium/ui/base/animation/multi_animation.h
+++ b/chromium/ui/gfx/animation/multi_animation.h
@@ -2,21 +2,21 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_MULTI_ANIMATION_H_
-#define UI_BASE_ANIMATION_MULTI_ANIMATION_H_
+#ifndef UI_GFX_ANIMATION_MULTI_ANIMATION_H_
+#define UI_GFX_ANIMATION_MULTI_ANIMATION_H_
#include <vector>
-#include "ui/base/animation/animation.h"
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/animation.h"
+#include "ui/gfx/animation/tween.h"
-namespace ui {
+namespace gfx {
// MultiAnimation is an animation that consists of a number of sub animations.
// To create a MultiAnimation pass in the parts, invoke Start() and the delegate
// is notified as the animation progresses. By default MultiAnimation runs until
// Stop is invoked, see |set_continuous()| for details.
-class UI_EXPORT MultiAnimation : public Animation {
+class GFX_EXPORT MultiAnimation : public Animation {
public:
// Defines part of the animation. Each part consists of the following:
//
@@ -91,6 +91,6 @@ class UI_EXPORT MultiAnimation : public Animation {
DISALLOW_COPY_AND_ASSIGN(MultiAnimation);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_MULTI_ANIMATION_H_
+#endif // UI_GFX_ANIMATION_MULTI_ANIMATION_H_
diff --git a/chromium/ui/base/animation/multi_animation_unittest.cc b/chromium/ui/gfx/animation/multi_animation_unittest.cc
index 0c21939c7f0..b8a11fdacf2 100644
--- a/chromium/ui/base/animation/multi_animation_unittest.cc
+++ b/chromium/ui/gfx/animation/multi_animation_unittest.cc
@@ -2,11 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "ui/gfx/animation/multi_animation.h"
+
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/animation/animation_container_element.h"
-#include "ui/base/animation/multi_animation.h"
+#include "ui/gfx/animation/animation_container_element.h"
-namespace ui {
+namespace gfx {
TEST(MultiAnimationTest, Basic) {
// Create a MultiAnimation with two parts.
@@ -88,4 +89,4 @@ TEST(MultiAnimationTest, Cycle) {
EXPECT_EQ(.5, animation.GetCurrentValue());
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/slide_animation.cc b/chromium/ui/gfx/animation/slide_animation.cc
index e73474cbaaa..d08ac41d9af 100644
--- a/chromium/ui/base/animation/slide_animation.cc
+++ b/chromium/ui/gfx/animation/slide_animation.cc
@@ -2,11 +2,11 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
#include <math.h>
-namespace ui {
+namespace gfx {
// How many frames per second to target.
static const int kDefaultFrameRateHz = 60;
@@ -111,4 +111,4 @@ void SlideAnimation::AnimateToState(double state) {
}
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/slide_animation.h b/chromium/ui/gfx/animation/slide_animation.h
index 709633b7642..8fdf8f86970 100644
--- a/chromium/ui/base/animation/slide_animation.h
+++ b/chromium/ui/gfx/animation/slide_animation.h
@@ -2,19 +2,19 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_SLIDE_ANIMATION_H_
-#define UI_BASE_ANIMATION_SLIDE_ANIMATION_H_
+#ifndef UI_GFX_ANIMATION_SLIDE_ANIMATION_H_
+#define UI_GFX_ANIMATION_SLIDE_ANIMATION_H_
-#include "ui/base/animation/linear_animation.h"
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/linear_animation.h"
+#include "ui/gfx/animation/tween.h"
-namespace ui {
+namespace gfx {
// Slide Animation
//
// Used for reversible animations and as a general helper class. Typical usage:
//
-// #include "ui/base/animation/slide_animation.h"
+// #include "ui/gfx/animation/slide_animation.h"
//
// class MyClass : public AnimationDelegate {
// public:
@@ -44,7 +44,7 @@ namespace ui {
// private:
// scoped_ptr<SlideAnimation> animation_;
// }
-class UI_EXPORT SlideAnimation : public LinearAnimation {
+class GFX_EXPORT SlideAnimation : public LinearAnimation {
public:
explicit SlideAnimation(AnimationDelegate* target);
virtual ~SlideAnimation();
@@ -96,6 +96,6 @@ class UI_EXPORT SlideAnimation : public LinearAnimation {
DISALLOW_COPY_AND_ASSIGN(SlideAnimation);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_SLIDE_ANIMATION_H_
+#endif // UI_GFX_ANIMATION_SLIDE_ANIMATION_H_
diff --git a/chromium/ui/base/animation/slide_animation_unittest.cc b/chromium/ui/gfx/animation/slide_animation_unittest.cc
index afd32b750aa..9d4f5343db1 100644
--- a/chromium/ui/base/animation/slide_animation_unittest.cc
+++ b/chromium/ui/gfx/animation/slide_animation_unittest.cc
@@ -2,13 +2,14 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "ui/gfx/animation/slide_animation.h"
+
#include "base/memory/scoped_ptr.h"
#include "base/time/time.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/animation/slide_animation.h"
-#include "ui/base/animation/test_animation_delegate.h"
+#include "ui/gfx/animation/test_animation_delegate.h"
-namespace ui {
+namespace gfx {
// Class to provide access to SlideAnimation internals for testing.
class SlideAnimation::TestApi {
@@ -101,4 +102,4 @@ TEST_F(SlideAnimationTest, DontNotifyOnDelete) {
EXPECT_FALSE(delegate.canceled());
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/test_animation_delegate.h b/chromium/ui/gfx/animation/test_animation_delegate.h
index 3cdaf8c414f..5bf6ea0a43b 100644
--- a/chromium/ui/base/animation/test_animation_delegate.h
+++ b/chromium/ui/gfx/animation/test_animation_delegate.h
@@ -2,13 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_TEST_ANIMATION_DELEGATE_H_
-#define UI_BASE_ANIMATION_TEST_ANIMATION_DELEGATE_H_
+#ifndef UI_GFX_ANIMATION_TEST_ANIMATION_DELEGATE_H_
+#define UI_GFX_ANIMATION_TEST_ANIMATION_DELEGATE_H_
#include "base/message_loop/message_loop.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
-namespace ui {
+namespace gfx {
// Trivial AnimationDelegate implementation. AnimationEnded/Canceled quit the
// message loop.
@@ -43,6 +43,6 @@ class TestAnimationDelegate : public AnimationDelegate {
DISALLOW_COPY_AND_ASSIGN(TestAnimationDelegate);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_TEST_ANIMATION_DELEGATE_H_
+#endif // UI_GFX_ANIMATION_TEST_ANIMATION_DELEGATE_H_
diff --git a/chromium/ui/base/animation/throb_animation.cc b/chromium/ui/gfx/animation/throb_animation.cc
index 72392a09161..0a88aa7d9c4 100644
--- a/chromium/ui/base/animation/throb_animation.cc
+++ b/chromium/ui/gfx/animation/throb_animation.cc
@@ -2,11 +2,11 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/throb_animation.h"
+#include "ui/gfx/animation/throb_animation.h"
#include <limits>
-namespace ui {
+namespace gfx {
static const int kDefaultThrobDurationMS = 400;
@@ -82,4 +82,4 @@ void ThrobAnimation::ResetForSlide() {
throbbing_ = false;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/throb_animation.h b/chromium/ui/gfx/animation/throb_animation.h
index 4292eee81f1..8bea7f8799c 100644
--- a/chromium/ui/base/animation/throb_animation.h
+++ b/chromium/ui/gfx/animation/throb_animation.h
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_THROB_ANIMATION_H_
-#define UI_BASE_ANIMATION_THROB_ANIMATION_H_
+#ifndef UI_GFX_ANIMATION_THROB_ANIMATION_H_
+#define UI_GFX_ANIMATION_THROB_ANIMATION_H_
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
-namespace ui {
+namespace gfx {
// A subclass of SlideAnimation that can continually slide. All of the Animation
// methods behave like that of SlideAnimation: transition to the next state.
@@ -16,7 +16,7 @@ namespace ui {
//
// A ThrobAnimation has two durations: the duration used when behavior like
// a SlideAnimation, and the duration used when throbbing.
-class UI_EXPORT ThrobAnimation : public SlideAnimation {
+class GFX_EXPORT ThrobAnimation : public SlideAnimation {
public:
explicit ThrobAnimation(AnimationDelegate* target);
virtual ~ThrobAnimation() {}
@@ -64,6 +64,6 @@ class UI_EXPORT ThrobAnimation : public SlideAnimation {
DISALLOW_COPY_AND_ASSIGN(ThrobAnimation);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_THROB_ANIMATION_H_
+#endif // UI_GFX_ANIMATION_THROB_ANIMATION_H_
diff --git a/chromium/ui/base/animation/tween.cc b/chromium/ui/gfx/animation/tween.cc
index ac6fa261fd5..4d1a6b3b260 100644
--- a/chromium/ui/base/animation/tween.cc
+++ b/chromium/ui/gfx/animation/tween.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/tween.h"
#include <math.h>
@@ -12,7 +12,7 @@
#include "base/logging.h"
-namespace ui {
+namespace gfx {
// static
double Tween::CalculateValue(Tween::Type type, double state) {
@@ -103,4 +103,4 @@ gfx::Transform Tween::ValueBetween(double value,
return to_return;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/animation/tween.h b/chromium/ui/gfx/animation/tween.h
index 6e2f17977bc..0c1f7585ecf 100644
--- a/chromium/ui/base/animation/tween.h
+++ b/chromium/ui/gfx/animation/tween.h
@@ -2,17 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_ANIMATION_TWEEN_H_
-#define UI_BASE_ANIMATION_TWEEN_H_
+#ifndef UI_GFX_ANIMATION_TWEEN_H_
+#define UI_GFX_ANIMATION_TWEEN_H_
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/transform.h"
-namespace ui {
+namespace gfx {
-class UI_EXPORT Tween {
+class GFX_EXPORT Tween {
public:
enum Type {
LINEAR, // Linear.
@@ -46,6 +46,6 @@ class UI_EXPORT Tween {
DISALLOW_COPY_AND_ASSIGN(Tween);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_ANIMATION_TWEEN_H_
+#endif // UI_GFX_ANIMATION_TWEEN_H_
diff --git a/chromium/ui/gfx/blit.h b/chromium/ui/gfx/blit.h
index 616fda3c18d..f0668172c05 100644
--- a/chromium/ui/gfx/blit.h
+++ b/chromium/ui/gfx/blit.h
@@ -5,8 +5,8 @@
#ifndef UI_GFX_BLIT_H_
#define UI_GFX_BLIT_H_
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
-#include "ui/base/ui_export.h"
class SkCanvas;
diff --git a/chromium/ui/gfx/box_f.cc b/chromium/ui/gfx/box_f.cc
index 107c5d691bf..efb57967145 100644
--- a/chromium/ui/gfx/box_f.cc
+++ b/chromium/ui/gfx/box_f.cc
@@ -4,6 +4,8 @@
#include "ui/gfx/box_f.h"
+#include <algorithm>
+
#include "base/strings/stringprintf.h"
namespace gfx {
diff --git a/chromium/ui/gfx/break_list.h b/chromium/ui/gfx/break_list.h
index 770386e9020..b55debf9688 100644
--- a/chromium/ui/gfx/break_list.h
+++ b/chromium/ui/gfx/break_list.h
@@ -10,7 +10,7 @@
#include "base/basictypes.h"
#include "base/logging.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
namespace gfx {
@@ -40,10 +40,11 @@ class BreakList {
void SetValue(T value);
// Adjust the breaks to apply |value| over the supplied |range|.
- void ApplyValue(T value, const ui::Range& range);
+ void ApplyValue(T value, const Range& range);
// Set the max position and trim any breaks at or beyond that position.
void SetMax(size_t max);
+ size_t max() const { return max_; }
// Get the break applicable to |position| (at or preceeding |position|).
typename std::vector<Break>::iterator GetBreak(size_t position);
@@ -51,7 +52,7 @@ class BreakList {
// Get the range of the supplied break; returns the break's start position and
// the next break's start position (or |max_| for the terminal break).
- ui::Range GetRange(const typename BreakList<T>::const_iterator& i) const;
+ Range GetRange(const typename BreakList<T>::const_iterator& i) const;
// Comparison functions for testing purposes.
bool EqualsValueForTesting(T value) const;
@@ -82,12 +83,12 @@ void BreakList<T>::SetValue(T value) {
}
template<class T>
-void BreakList<T>::ApplyValue(T value, const ui::Range& range) {
+void BreakList<T>::ApplyValue(T value, const Range& range) {
if (!range.IsValid() || range.is_empty())
return;
DCHECK(!breaks_.empty());
DCHECK(!range.is_reversed());
- DCHECK(ui::Range(0, max_).Contains(range));
+ DCHECK(Range(0, max_).Contains(range));
// Erase any breaks in |range|, then add start and end breaks as needed.
typename std::vector<Break>::iterator start = GetBreak(range.start());
@@ -135,10 +136,10 @@ typename std::vector<std::pair<size_t, T> >::const_iterator
}
template<class T>
-ui::Range BreakList<T>::GetRange(
+Range BreakList<T>::GetRange(
const typename BreakList<T>::const_iterator& i) const {
const typename BreakList<T>::const_iterator next = i + 1;
- return ui::Range(i->first, next == breaks_.end() ? max_ : next->first);
+ return Range(i->first, next == breaks_.end() ? max_ : next->first);
}
template<class T>
diff --git a/chromium/ui/gfx/break_list_unittest.cc b/chromium/ui/gfx/break_list_unittest.cc
index 4acb0d264eb..5d4e39bbc05 100644
--- a/chromium/ui/gfx/break_list_unittest.cc
+++ b/chromium/ui/gfx/break_list_unittest.cc
@@ -6,7 +6,7 @@
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
namespace gfx {
@@ -32,10 +32,10 @@ TEST_F(BreakListTest, ApplyValue) {
breaks.SetMax(max);
// Ensure ApplyValue is a no-op on invalid and empty ranges.
- breaks.ApplyValue(true, ui::Range::InvalidRange());
+ breaks.ApplyValue(true, Range::InvalidRange());
EXPECT_TRUE(breaks.EqualsValueForTesting(false));
for (size_t i = 0; i < 3; ++i) {
- breaks.ApplyValue(true, ui::Range(i, i));
+ breaks.ApplyValue(true, Range(i, i));
EXPECT_TRUE(breaks.EqualsValueForTesting(false));
}
@@ -45,7 +45,7 @@ TEST_F(BreakListTest, ApplyValue) {
expected.push_back(std::pair<size_t, bool>(2, true));
expected.push_back(std::pair<size_t, bool>(3, false));
for (size_t i = 0; i < 2; ++i) {
- breaks.ApplyValue(true, ui::Range(2, 3));
+ breaks.ApplyValue(true, Range(2, 3));
EXPECT_TRUE(breaks.EqualsForTesting(expected));
}
@@ -54,43 +54,43 @@ TEST_F(BreakListTest, ApplyValue) {
EXPECT_TRUE(breaks.EqualsValueForTesting(true));
// Ensure applying a value over [0, |max|) is the same as setting a value.
- breaks.ApplyValue(false, ui::Range(0, max));
+ breaks.ApplyValue(false, Range(0, max));
EXPECT_TRUE(breaks.EqualsValueForTesting(false));
// Ensure applying a value that is already applied has no effect.
- breaks.ApplyValue(false, ui::Range(0, 2));
- breaks.ApplyValue(false, ui::Range(3, 6));
- breaks.ApplyValue(false, ui::Range(7, max));
+ breaks.ApplyValue(false, Range(0, 2));
+ breaks.ApplyValue(false, Range(3, 6));
+ breaks.ApplyValue(false, Range(7, max));
EXPECT_TRUE(breaks.EqualsValueForTesting(false));
// Ensure applying an identical neighboring value merges the ranges.
- breaks.ApplyValue(true, ui::Range(0, 3));
- breaks.ApplyValue(true, ui::Range(3, 6));
- breaks.ApplyValue(true, ui::Range(6, max));
+ breaks.ApplyValue(true, Range(0, 3));
+ breaks.ApplyValue(true, Range(3, 6));
+ breaks.ApplyValue(true, Range(6, max));
EXPECT_TRUE(breaks.EqualsValueForTesting(true));
// Ensure applying a value with the same range overrides the ranged value.
- breaks.ApplyValue(false, ui::Range(2, 3));
- breaks.ApplyValue(true, ui::Range(2, 3));
+ breaks.ApplyValue(false, Range(2, 3));
+ breaks.ApplyValue(true, Range(2, 3));
EXPECT_TRUE(breaks.EqualsValueForTesting(true));
// Ensure applying a value with a containing range overrides contained values.
- breaks.ApplyValue(false, ui::Range(0, 1));
- breaks.ApplyValue(false, ui::Range(2, 3));
- breaks.ApplyValue(true, ui::Range(0, 3));
+ breaks.ApplyValue(false, Range(0, 1));
+ breaks.ApplyValue(false, Range(2, 3));
+ breaks.ApplyValue(true, Range(0, 3));
EXPECT_TRUE(breaks.EqualsValueForTesting(true));
- breaks.ApplyValue(false, ui::Range(4, 5));
- breaks.ApplyValue(false, ui::Range(6, 7));
- breaks.ApplyValue(false, ui::Range(8, 9));
- breaks.ApplyValue(true, ui::Range(4, 9));
+ breaks.ApplyValue(false, Range(4, 5));
+ breaks.ApplyValue(false, Range(6, 7));
+ breaks.ApplyValue(false, Range(8, 9));
+ breaks.ApplyValue(true, Range(4, 9));
EXPECT_TRUE(breaks.EqualsValueForTesting(true));
// Ensure applying various overlapping values yields the intended results.
- breaks.ApplyValue(false, ui::Range(1, 4));
- breaks.ApplyValue(false, ui::Range(5, 8));
- breaks.ApplyValue(true, ui::Range(0, 2));
- breaks.ApplyValue(true, ui::Range(3, 6));
- breaks.ApplyValue(true, ui::Range(7, max));
+ breaks.ApplyValue(false, Range(1, 4));
+ breaks.ApplyValue(false, Range(5, 8));
+ breaks.ApplyValue(true, Range(0, 2));
+ breaks.ApplyValue(true, Range(3, 6));
+ breaks.ApplyValue(true, Range(7, max));
std::vector<std::pair<size_t, bool> > overlap;
overlap.push_back(std::pair<size_t, bool>(0, true));
overlap.push_back(std::pair<size_t, bool>(2, false));
@@ -104,9 +104,9 @@ TEST_F(BreakListTest, SetMax) {
// Ensure values adjust to accommodate max position changes.
BreakList<bool> breaks(false);
breaks.SetMax(9);
- breaks.ApplyValue(true, ui::Range(0, 2));
- breaks.ApplyValue(true, ui::Range(3, 6));
- breaks.ApplyValue(true, ui::Range(7, 9));
+ breaks.ApplyValue(true, Range(0, 2));
+ breaks.ApplyValue(true, Range(3, 6));
+ breaks.ApplyValue(true, Range(7, 9));
std::vector<std::pair<size_t, bool> > expected;
expected.push_back(std::pair<size_t, bool>(0, true));
@@ -134,25 +134,25 @@ TEST_F(BreakListTest, SetMax) {
TEST_F(BreakListTest, GetBreakAndRange) {
BreakList<bool> breaks(false);
breaks.SetMax(8);
- breaks.ApplyValue(true, ui::Range(1, 2));
- breaks.ApplyValue(true, ui::Range(4, 6));
+ breaks.ApplyValue(true, Range(1, 2));
+ breaks.ApplyValue(true, Range(4, 6));
struct {
size_t position;
size_t break_index;
- ui::Range range;
+ Range range;
} cases[] = {
- { 0, 0, ui::Range(0, 1) },
- { 1, 1, ui::Range(1, 2) },
- { 2, 2, ui::Range(2, 4) },
- { 3, 2, ui::Range(2, 4) },
- { 4, 3, ui::Range(4, 6) },
- { 5, 3, ui::Range(4, 6) },
- { 6, 4, ui::Range(6, 8) },
- { 7, 4, ui::Range(6, 8) },
+ { 0, 0, Range(0, 1) },
+ { 1, 1, Range(1, 2) },
+ { 2, 2, Range(2, 4) },
+ { 3, 2, Range(2, 4) },
+ { 4, 3, Range(4, 6) },
+ { 5, 3, Range(4, 6) },
+ { 6, 4, Range(6, 8) },
+ { 7, 4, Range(6, 8) },
// Positions at or beyond the max simply return the last break and range.
- { 8, 4, ui::Range(6, 8) },
- { 9, 4, ui::Range(6, 8) },
+ { 8, 4, Range(6, 8) },
+ { 9, 4, Range(6, 8) },
};
diff --git a/chromium/ui/gfx/canvas.cc b/chromium/ui/gfx/canvas.cc
index 2b0f5046cf0..b59d2a0d888 100644
--- a/chromium/ui/gfx/canvas.cc
+++ b/chromium/ui/gfx/canvas.cc
@@ -11,7 +11,7 @@
#include "third_party/skia/include/core/SkBitmap.h"
#include "third_party/skia/include/effects/SkGradientShader.h"
#include "ui/gfx/canvas.h"
-#include "ui/gfx/font.h"
+#include "ui/gfx/font_list.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/size_conversions.h"
#include "ui/gfx/skia_util.h"
@@ -23,13 +23,11 @@
namespace gfx {
-Canvas::Canvas(const gfx::Size& size,
- ui::ScaleFactor scale_factor,
- bool is_opaque)
- : scale_factor_(scale_factor),
- canvas_(NULL) {
- gfx::Size pixel_size = gfx::ToCeiledSize(
- gfx::ScaleSize(size, ui::GetScaleFactorScale(scale_factor)));
+Canvas::Canvas(const Size& size, ui::ScaleFactor scale_factor, bool is_opaque)
+ : scale_factor_(scale_factor),
+ canvas_(NULL) {
+ Size pixel_size = ToCeiledSize(
+ ScaleSize(size, ui::GetScaleFactorScale(scale_factor)));
owned_canvas_ = skia::AdoptRef(skia::CreatePlatformCanvas(pixel_size.width(),
pixel_size.height(),
is_opaque));
@@ -45,7 +43,7 @@ Canvas::Canvas(const gfx::Size& size,
canvas_->scale(scale, scale);
}
-Canvas::Canvas(const gfx::ImageSkiaRep& image_rep, bool is_opaque)
+Canvas::Canvas(const ImageSkiaRep& image_rep, bool is_opaque)
: scale_factor_(image_rep.scale_factor()),
owned_canvas_(skia::AdoptRef(
skia::CreatePlatformCanvas(image_rep.pixel_width(),
@@ -54,7 +52,7 @@ Canvas::Canvas(const gfx::ImageSkiaRep& image_rep, bool is_opaque)
canvas_(owned_canvas_.get()) {
SkScalar scale = SkFloatToScalar(ui::GetScaleFactorScale(scale_factor_));
canvas_->scale(scale, scale);
- DrawImageInt(gfx::ImageSkia(image_rep), 0, 0);
+ DrawImageInt(ImageSkia(image_rep), 0, 0);
}
Canvas::Canvas()
@@ -72,12 +70,12 @@ Canvas* Canvas::CreateCanvasWithoutScaling(SkCanvas* canvas,
return new Canvas(canvas, scale_factor);
}
-void Canvas::RecreateBackingCanvas(const gfx::Size& size,
+void Canvas::RecreateBackingCanvas(const Size& size,
ui::ScaleFactor scale_factor,
bool is_opaque) {
scale_factor_ = scale_factor;
- gfx::Size pixel_size = gfx::ToFlooredSize(
- gfx::ScaleSize(size, ui::GetScaleFactorScale(scale_factor)));
+ Size pixel_size = ToFlooredSize(
+ ScaleSize(size, ui::GetScaleFactorScale(scale_factor)));
owned_canvas_ = skia::AdoptRef(skia::CreatePlatformCanvas(pixel_size.width(),
pixel_size.height(),
is_opaque));
@@ -87,9 +85,27 @@ void Canvas::RecreateBackingCanvas(const gfx::Size& size,
}
// static
-int Canvas::GetStringWidth(const base::string16& text, const gfx::Font& font) {
+void Canvas::SizeStringInt(const base::string16& text,
+ const Font& font,
+ int* width,
+ int* height,
+ int line_height,
+ int flags) {
+ SizeStringInt(text, FontList(font), width, height, line_height, flags);
+}
+
+// static
+int Canvas::GetStringWidth(const base::string16& text,
+ const FontList& font_list) {
+ int width = 0, height = 0;
+ SizeStringInt(text, font_list, &width, &height, 0, NO_ELLIPSIS);
+ return width;
+}
+
+// static
+int Canvas::GetStringWidth(const base::string16& text, const Font& font) {
int width = 0, height = 0;
- Canvas::SizeStringInt(text, font, &width, &height, 0, NO_ELLIPSIS);
+ SizeStringInt(text, FontList(font), &width, &height, 0, NO_ELLIPSIS);
return width;
}
@@ -98,7 +114,20 @@ int Canvas::DefaultCanvasTextAlignment() {
return base::i18n::IsRTL() ? TEXT_ALIGN_RIGHT : TEXT_ALIGN_LEFT;
}
-gfx::ImageSkiaRep Canvas::ExtractImageRep() const {
+void Canvas::DrawStringWithHalo(const base::string16& text,
+ const Font& font,
+ SkColor text_color,
+ SkColor halo_color_in,
+ int x,
+ int y,
+ int w,
+ int h,
+ int flags) {
+ DrawStringRectWithHalo(text, FontList(font), text_color, halo_color_in,
+ Rect(x, y, w, h), flags);
+}
+
+ImageSkiaRep Canvas::ExtractImageRep() const {
const SkBitmap& device_bitmap = canvas_->getDevice()->accessBitmap(false);
// Make a bitmap to return, and a canvas to draw into it. We don't just want
@@ -107,10 +136,10 @@ gfx::ImageSkiaRep Canvas::ExtractImageRep() const {
SkBitmap result;
device_bitmap.copyTo(&result, SkBitmap::kARGB_8888_Config);
- return gfx::ImageSkiaRep(result, scale_factor_);
+ return ImageSkiaRep(result, scale_factor_);
}
-void Canvas::DrawDashedRect(const gfx::Rect& rect, SkColor color) {
+void Canvas::DrawDashedRect(const Rect& rect, SkColor color) {
// Create a 2D bitmap containing alternating on/off pixels - we do this
// so that you never get two pixels of the same color around the edges
// of the focus rect (this may mean that opposing edges of the rect may
@@ -149,11 +178,11 @@ void Canvas::DrawDashedRect(const gfx::Rect& rect, SkColor color) {
SkPaint paint;
paint.setShader(shader.get());
- DrawRect(gfx::Rect(rect.x(), rect.y(), rect.width(), 1), paint);
- DrawRect(gfx::Rect(rect.x(), rect.y() + rect.height() - 1, rect.width(), 1),
+ DrawRect(Rect(rect.x(), rect.y(), rect.width(), 1), paint);
+ DrawRect(Rect(rect.x(), rect.y() + rect.height() - 1, rect.width(), 1),
paint);
- DrawRect(gfx::Rect(rect.x(), rect.y(), 1, rect.height()), paint);
- DrawRect(gfx::Rect(rect.x() + rect.width() - 1, rect.y(), 1, rect.height()),
+ DrawRect(Rect(rect.x(), rect.y(), 1, rect.height()), paint);
+ DrawRect(Rect(rect.x() + rect.width() - 1, rect.y(), 1, rect.height()),
paint);
}
@@ -166,8 +195,8 @@ void Canvas::SaveLayerAlpha(uint8 alpha) {
}
-void Canvas::SaveLayerAlpha(uint8 alpha, const gfx::Rect& layer_bounds) {
- SkRect bounds(gfx::RectToSkRect(layer_bounds));
+void Canvas::SaveLayerAlpha(uint8 alpha, const Rect& layer_bounds) {
+ SkRect bounds(RectToSkRect(layer_bounds));
canvas_->saveLayerAlpha(&bounds, alpha);
}
@@ -175,22 +204,22 @@ void Canvas::Restore() {
canvas_->restore();
}
-bool Canvas::ClipRect(const gfx::Rect& rect) {
- return canvas_->clipRect(gfx::RectToSkRect(rect));
+bool Canvas::ClipRect(const Rect& rect) {
+ return canvas_->clipRect(RectToSkRect(rect));
}
bool Canvas::ClipPath(const SkPath& path) {
return canvas_->clipPath(path);
}
-bool Canvas::GetClipBounds(gfx::Rect* bounds) {
+bool Canvas::GetClipBounds(Rect* bounds) {
SkRect out;
bool has_non_empty_clip = canvas_->getClipBounds(&out);
bounds->SetRect(out.left(), out.top(), out.width(), out.height());
return has_non_empty_clip;
}
-void Canvas::Translate(const gfx::Vector2d& offset) {
+void Canvas::Translate(const Vector2d& offset) {
canvas_->translate(SkIntToScalar(offset.x()), SkIntToScalar(offset.y()));
}
@@ -206,11 +235,11 @@ void Canvas::DrawColor(SkColor color, SkXfermode::Mode mode) {
canvas_->drawColor(color, mode);
}
-void Canvas::FillRect(const gfx::Rect& rect, SkColor color) {
+void Canvas::FillRect(const Rect& rect, SkColor color) {
FillRect(rect, color, SkXfermode::kSrcOver_Mode);
}
-void Canvas::FillRect(const gfx::Rect& rect,
+void Canvas::FillRect(const Rect& rect,
SkColor color,
SkXfermode::Mode mode) {
SkPaint paint;
@@ -220,11 +249,11 @@ void Canvas::FillRect(const gfx::Rect& rect,
DrawRect(rect, paint);
}
-void Canvas::DrawRect(const gfx::Rect& rect, SkColor color) {
+void Canvas::DrawRect(const Rect& rect, SkColor color) {
DrawRect(rect, color, SkXfermode::kSrcOver_Mode);
}
-void Canvas::DrawRect(const gfx::Rect& rect,
+void Canvas::DrawRect(const Rect& rect,
SkColor color,
SkXfermode::Mode mode) {
SkPaint paint;
@@ -239,38 +268,34 @@ void Canvas::DrawRect(const gfx::Rect& rect,
DrawRect(rect, paint);
}
-void Canvas::DrawRect(const gfx::Rect& rect, const SkPaint& paint) {
+void Canvas::DrawRect(const Rect& rect, const SkPaint& paint) {
canvas_->drawIRect(RectToSkIRect(rect), paint);
}
-void Canvas::DrawPoint(const gfx::Point& p1, const SkPaint& paint) {
+void Canvas::DrawPoint(const Point& p1, const SkPaint& paint) {
canvas_->drawPoint(SkIntToScalar(p1.x()), SkIntToScalar(p1.y()), paint);
}
-void Canvas::DrawLine(const gfx::Point& p1,
- const gfx::Point& p2,
- SkColor color) {
+void Canvas::DrawLine(const Point& p1, const Point& p2, SkColor color) {
SkPaint paint;
paint.setColor(color);
paint.setStrokeWidth(SkIntToScalar(1));
DrawLine(p1, p2, paint);
}
-void Canvas::DrawLine(const gfx::Point& p1,
- const gfx::Point& p2,
- const SkPaint& paint) {
+void Canvas::DrawLine(const Point& p1, const Point& p2, const SkPaint& paint) {
canvas_->drawLine(SkIntToScalar(p1.x()), SkIntToScalar(p1.y()),
SkIntToScalar(p2.x()), SkIntToScalar(p2.y()), paint);
}
-void Canvas::DrawCircle(const gfx::Point& center_point,
+void Canvas::DrawCircle(const Point& center_point,
int radius,
const SkPaint& paint) {
canvas_->drawCircle(SkIntToScalar(center_point.x()),
SkIntToScalar(center_point.y()), SkIntToScalar(radius), paint);
}
-void Canvas::DrawRoundRect(const gfx::Rect& rect,
+void Canvas::DrawRoundRect(const Rect& rect,
int radius,
const SkPaint& paint) {
canvas_->drawRoundRect(RectToSkRect(rect), SkIntToScalar(radius),
@@ -281,25 +306,26 @@ void Canvas::DrawPath(const SkPath& path, const SkPaint& paint) {
canvas_->drawPath(path, paint);
}
-void Canvas::DrawFocusRect(const gfx::Rect& rect) {
+void Canvas::DrawFocusRect(const Rect& rect) {
DrawDashedRect(rect, SK_ColorGRAY);
}
-void Canvas::DrawImageInt(const gfx::ImageSkia& image, int x, int y) {
+void Canvas::DrawImageInt(const ImageSkia& image, int x, int y) {
SkPaint paint;
DrawImageInt(image, x, y, paint);
}
-void Canvas::DrawImageInt(const gfx::ImageSkia& image, int x, int y, uint8 a) {
+void Canvas::DrawImageInt(const ImageSkia& image, int x, int y, uint8 a) {
SkPaint paint;
paint.setAlpha(a);
DrawImageInt(image, x, y, paint);
}
-void Canvas::DrawImageInt(const gfx::ImageSkia& image,
- int x, int y,
+void Canvas::DrawImageInt(const ImageSkia& image,
+ int x,
+ int y,
const SkPaint& paint) {
- const gfx::ImageSkiaRep& image_rep = GetImageRepToPaint(image);
+ const ImageSkiaRep& image_rep = GetImageRepToPaint(image);
if (image_rep.is_null())
return;
const SkBitmap& bitmap = image_rep.sk_bitmap();
@@ -315,18 +341,30 @@ void Canvas::DrawImageInt(const gfx::ImageSkia& image,
canvas_->restore();
}
-void Canvas::DrawImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y, int src_w, int src_h,
- int dest_x, int dest_y, int dest_w, int dest_h,
+void Canvas::DrawImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ int src_w,
+ int src_h,
+ int dest_x,
+ int dest_y,
+ int dest_w,
+ int dest_h,
bool filter) {
SkPaint p;
DrawImageInt(image, src_x, src_y, src_w, src_h, dest_x, dest_y,
dest_w, dest_h, filter, p);
}
-void Canvas::DrawImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y, int src_w, int src_h,
- int dest_x, int dest_y, int dest_w, int dest_h,
+void Canvas::DrawImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ int src_w,
+ int src_h,
+ int dest_x,
+ int dest_y,
+ int dest_w,
+ int dest_h,
bool filter,
const SkPaint& paint) {
DLOG_ASSERT(src_x + src_w < std::numeric_limits<int16_t>::max() &&
@@ -342,7 +380,7 @@ void Canvas::DrawImageInt(const gfx::ImageSkia& image,
float user_scale_x = static_cast<float>(dest_w) / src_w;
float user_scale_y = static_cast<float>(dest_h) / src_h;
- const gfx::ImageSkiaRep& image_rep = GetImageRepToPaint(image,
+ const ImageSkiaRep& image_rep = GetImageRepToPaint(image,
user_scale_x, user_scale_y);
if (image_rep.is_null())
return;
@@ -373,7 +411,7 @@ void Canvas::DrawImageInt(const gfx::ImageSkia& image,
shader_scale.preTranslate(SkIntToScalar(-src_x), SkIntToScalar(-src_y));
shader_scale.postTranslate(SkIntToScalar(dest_x), SkIntToScalar(dest_y));
- skia::RefPtr<SkShader> shader = gfx::CreateImageRepShader(
+ skia::RefPtr<SkShader> shader = CreateImageRepShader(
image_rep,
SkShader::kRepeat_TileMode,
shader_scale);
@@ -388,18 +426,18 @@ void Canvas::DrawImageInt(const gfx::ImageSkia& image,
canvas_->drawRect(dest_rect, p);
}
-void Canvas::DrawImageInPath(const gfx::ImageSkia& image,
+void Canvas::DrawImageInPath(const ImageSkia& image,
int x,
int y,
const SkPath& path,
const SkPaint& paint) {
- const gfx::ImageSkiaRep& image_rep = GetImageRepToPaint(image);
+ const ImageSkiaRep& image_rep = GetImageRepToPaint(image);
if (image_rep.is_null())
return;
SkMatrix matrix;
matrix.setTranslate(SkIntToScalar(x), SkIntToScalar(y));
- skia::RefPtr<SkShader> shader = gfx::CreateImageRepShader(
+ skia::RefPtr<SkShader> shader = CreateImageRepShader(
image_rep,
SkShader::kRepeat_TileMode,
matrix);
@@ -409,55 +447,96 @@ void Canvas::DrawImageInPath(const gfx::ImageSkia& image,
canvas_->drawPath(path, p);
}
+void Canvas::DrawStringRect(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& display_rect) {
+ DrawStringRectWithFlags(text, font_list, color, display_rect,
+ DefaultCanvasTextAlignment());
+}
+
+void Canvas::DrawStringRectWithFlags(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& display_rect,
+ int flags) {
+ DrawStringRectWithShadows(text, font_list, color, display_rect, 0, flags,
+ ShadowValues());
+}
+
void Canvas::DrawStringInt(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- int x, int y, int w, int h) {
+ int x,
+ int y,
+ int w,
+ int h) {
DrawStringInt(text, font, color, x, y, w, h, DefaultCanvasTextAlignment());
}
void Canvas::DrawStringInt(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- const gfx::Rect& display_rect) {
+ const Rect& display_rect) {
DrawStringInt(text, font, color, display_rect.x(), display_rect.y(),
display_rect.width(), display_rect.height());
}
void Canvas::DrawStringInt(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- int x, int y, int w, int h,
+ int x,
+ int y,
+ int w,
+ int h,
int flags) {
- DrawStringWithShadows(text,
- font,
- color,
- gfx::Rect(x, y, w, h),
- 0,
- flags,
+ DrawStringWithShadows(text, font, color, Rect(x, y, w, h), 0, flags,
ShadowValues());
}
-void Canvas::TileImageInt(const gfx::ImageSkia& image,
- int x, int y, int w, int h) {
+void Canvas::DrawStringWithShadows(const base::string16& text,
+ const Font& font,
+ SkColor color,
+ const Rect& text_bounds,
+ int line_height,
+ int flags,
+ const ShadowValues& shadows) {
+ DrawStringRectWithShadows(text, FontList(font), color, text_bounds,
+ line_height, flags, shadows);
+}
+
+void Canvas::TileImageInt(const ImageSkia& image,
+ int x,
+ int y,
+ int w,
+ int h) {
TileImageInt(image, 0, 0, x, y, w, h);
}
-void Canvas::TileImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y,
- int dest_x, int dest_y, int w, int h) {
+void Canvas::TileImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ int dest_x,
+ int dest_y,
+ int w,
+ int h) {
TileImageInt(image, src_x, src_y, 1.0f, 1.0f, dest_x, dest_y, w, h);
}
-void Canvas::TileImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y,
- float tile_scale_x, float tile_scale_y,
- int dest_x, int dest_y, int w, int h) {
+void Canvas::TileImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ float tile_scale_x,
+ float tile_scale_y,
+ int dest_x,
+ int dest_y,
+ int w,
+ int h) {
if (!IntersectsClipRectInt(dest_x, dest_y, w, h))
return;
- const gfx::ImageSkiaRep& image_rep = GetImageRepToPaint(image,
- tile_scale_x, tile_scale_y);
+ const ImageSkiaRep& image_rep = GetImageRepToPaint(
+ image, tile_scale_x, tile_scale_y);
if (image_rep.is_null())
return;
@@ -467,7 +546,7 @@ void Canvas::TileImageInt(const gfx::ImageSkia& image,
shader_scale.preTranslate(SkIntToScalar(-src_x), SkIntToScalar(-src_y));
shader_scale.postTranslate(SkIntToScalar(dest_x), SkIntToScalar(dest_y));
- skia::RefPtr<SkShader> shader = gfx::CreateImageRepShader(
+ skia::RefPtr<SkShader> shader = CreateImageRepShader(
image_rep,
SkShader::kRepeat_TileMode,
shader_scale);
@@ -483,7 +562,7 @@ void Canvas::TileImageInt(const gfx::ImageSkia& image,
canvas_->drawRect(dest_rect, paint);
}
-gfx::NativeDrawingContext Canvas::BeginPlatformPaint() {
+NativeDrawingContext Canvas::BeginPlatformPaint() {
return skia::BeginPlatformPaint(canvas_);
}
@@ -509,21 +588,20 @@ bool Canvas::IntersectsClipRectInt(int x, int y, int w, int h) {
SkIntToScalar(y + h));
}
-bool Canvas::IntersectsClipRect(const gfx::Rect& rect) {
+bool Canvas::IntersectsClipRect(const Rect& rect) {
return IntersectsClipRectInt(rect.x(), rect.y(),
rect.width(), rect.height());
}
-const gfx::ImageSkiaRep& Canvas::GetImageRepToPaint(
- const gfx::ImageSkia& image) const {
+const ImageSkiaRep& Canvas::GetImageRepToPaint(const ImageSkia& image) const {
return GetImageRepToPaint(image, 1.0f, 1.0f);
}
-const gfx::ImageSkiaRep& Canvas::GetImageRepToPaint(
- const gfx::ImageSkia& image,
+const ImageSkiaRep& Canvas::GetImageRepToPaint(
+ const ImageSkia& image,
float user_additional_scale_x,
float user_additional_scale_y) const {
- const gfx::ImageSkiaRep& image_rep = image.GetRepresentation(scale_factor_);
+ const ImageSkiaRep& image_rep = image.GetRepresentation(scale_factor_);
if (!image_rep.is_null()) {
SkMatrix m = canvas_->getTotalMatrix();
diff --git a/chromium/ui/gfx/canvas.h b/chromium/ui/gfx/canvas.h
index 8baa45c11e3..c8996a234a8 100644
--- a/chromium/ui/gfx/canvas.h
+++ b/chromium/ui/gfx/canvas.h
@@ -20,6 +20,7 @@ namespace gfx {
class Rect;
class Font;
+class FontList;
class Point;
class Size;
class Transform;
@@ -95,17 +96,15 @@ class UI_EXPORT Canvas {
// Creates canvas with provided DIP |size| and |scale_factor|.
// If this canvas is not opaque, it's explicitly cleared to transparent before
// being returned.
- Canvas(const gfx::Size& size,
- ui::ScaleFactor scale_factor,
- bool is_opaque);
+ Canvas(const Size& size, ui::ScaleFactor scale_factor, bool is_opaque);
// Constructs a canvas with the size and the scale factor of the
// provided |image_rep|, and draws the |image_rep| into it.
- Canvas(const gfx::ImageSkiaRep& image_rep, bool is_opaque);
+ Canvas(const ImageSkiaRep& image_rep, bool is_opaque);
virtual ~Canvas();
- // Creates a gfx::Canvas backed by an |sk_canvas| with |scale_factor|.
+ // Creates a Canvas backed by an |sk_canvas| with |scale_factor|.
// |sk_canvas| is assumed to be already scaled based on |scale_factor|
// so no additional scaling is applied.
static Canvas* CreateCanvasWithoutScaling(SkCanvas* sk_canvas,
@@ -117,36 +116,47 @@ class UI_EXPORT Canvas {
// canvas after having initialized the canvas.
// TODO(pkotwicz): Push the scale factor into skia::PlatformCanvas such that
// this method can be private.
- void RecreateBackingCanvas(const gfx::Size& size,
+ void RecreateBackingCanvas(const Size& size,
ui::ScaleFactor scale_factor,
bool is_opaque);
- // Compute the size required to draw some text with the provided font.
+ // Compute the size required to draw some text with the provided fonts.
// Attempts to fit the text with the provided width and height. Increases
// height and then width as needed to make the text fit. This method
// supports multiple lines. On Skia only a line_height can be specified and
// specifying a 0 value for it will cause the default height to be used.
static void SizeStringInt(const base::string16& text,
- const gfx::Font& font,
- int* width, int* height,
+ const FontList& font_list,
+ int* width,
+ int* height,
+ int line_height,
+ int flags);
+ // Obsolete version. Use the above version which takes FontList.
+ static void SizeStringInt(const base::string16& text,
+ const Font& font,
+ int* width,
+ int* height,
int line_height,
int flags);
// Returns the number of horizontal pixels needed to display the specified
- // |text| with |font|.
- static int GetStringWidth(const base::string16& text, const gfx::Font& font);
+ // |text| with |font_list|.
+ static int GetStringWidth(const base::string16& text,
+ const FontList& font_list);
+ // Obsolete version. Use the above version which takes FontList.
+ static int GetStringWidth(const base::string16& text, const Font& font);
// Returns the default text alignment to be used when drawing text on a
- // gfx::Canvas based on the directionality of the system locale language.
- // This function is used by gfx::Canvas::DrawStringInt when the text alignment
+ // Canvas based on the directionality of the system locale language.
+ // This function is used by Canvas::DrawStringInt when the text alignment
// is not specified.
//
- // This function returns either gfx::Canvas::TEXT_ALIGN_LEFT or
- // gfx::Canvas::TEXT_ALIGN_RIGHT.
+ // This function returns either Canvas::TEXT_ALIGN_LEFT or
+ // Canvas::TEXT_ALIGN_RIGHT.
static int DefaultCanvasTextAlignment();
// Draws text with a 1-pixel halo around it of the given color.
- // On Windows, it allows ClearType to be drawn to an otherwise transparenct
+ // On Windows, it allows ClearType to be drawn to an otherwise transparent
// bitmap for drag images. Drag images have only 1-bit of transparency, so
// we don't do any fancy blurring.
// On Linux, text with halo is created by stroking it with 2px |halo_color|
@@ -154,18 +164,28 @@ class UI_EXPORT Canvas {
// On Mac, NOTIMPLEMENTED.
// TODO(dhollowa): Skia-native implementation is underway. Cut over to
// that when ready. http::/crbug.com/109946
+ void DrawStringRectWithHalo(const base::string16& text,
+ const FontList& font_list,
+ SkColor text_color,
+ SkColor halo_color,
+ const Rect& display_rect,
+ int flags);
+ // Obsolete version. Use the above version which takes FontList.
void DrawStringWithHalo(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor text_color,
SkColor halo_color,
- int x, int y, int w, int h,
+ int x,
+ int y,
+ int w,
+ int h,
int flags);
// Extracts an ImageSkiaRep from the contents of this canvas.
- gfx::ImageSkiaRep ExtractImageRep() const;
+ ImageSkiaRep ExtractImageRep() const;
// Draws a dashed rectangle of the specified color.
- void DrawDashedRect(const gfx::Rect& rect, SkColor color);
+ void DrawDashedRect(const Rect& rect, SkColor color);
// Saves a copy of the drawing state onto a stack, operating on this copy
// until a balanced call to Restore() is made.
@@ -176,7 +196,7 @@ class UI_EXPORT Canvas {
// |layer_bounds| are the bounds of the layer relative to the current
// transform.
void SaveLayerAlpha(uint8 alpha);
- void SaveLayerAlpha(uint8 alpha, const gfx::Rect& layer_bounds);
+ void SaveLayerAlpha(uint8 alpha, const Rect& layer_bounds);
// Restores the drawing state after a call to Save*(). It is an error to
// call Restore() more times than Save*().
@@ -184,7 +204,7 @@ class UI_EXPORT Canvas {
// Adds |rect| to the current clip. Returns true if the resulting clip is
// non-empty.
- bool ClipRect(const gfx::Rect& rect);
+ bool ClipRect(const Rect& rect);
// Adds |path| to the current clip. Returns true if the resulting clip is
// non-empty.
@@ -192,9 +212,9 @@ class UI_EXPORT Canvas {
// Returns the bounds of the current clip (in local coordinates) in the
// |bounds| parameter, and returns true if it is non empty.
- bool GetClipBounds(gfx::Rect* bounds);
+ bool GetClipBounds(Rect* bounds);
- void Translate(const gfx::Vector2d& offset);
+ void Translate(const Vector2d& offset);
void Scale(int x_scale, int y_scale);
@@ -208,45 +228,43 @@ class UI_EXPORT Canvas {
// Fills |rect| with |color| using a transfer mode of
// SkXfermode::kSrcOver_Mode.
- void FillRect(const gfx::Rect& rect, SkColor color);
+ void FillRect(const Rect& rect, SkColor color);
// Fills |rect| with the specified |color| and |mode|.
- void FillRect(const gfx::Rect& rect, SkColor color, SkXfermode::Mode mode);
+ void FillRect(const Rect& rect, SkColor color, SkXfermode::Mode mode);
// Draws a single pixel rect in the specified region with the specified
// color, using a transfer mode of SkXfermode::kSrcOver_Mode.
//
// NOTE: if you need a single pixel line, use DrawLine.
- void DrawRect(const gfx::Rect& rect, SkColor color);
+ void DrawRect(const Rect& rect, SkColor color);
// Draws a single pixel rect in the specified region with the specified
// color and transfer mode.
//
// NOTE: if you need a single pixel line, use DrawLine.
- void DrawRect(const gfx::Rect& rect, SkColor color, SkXfermode::Mode mode);
+ void DrawRect(const Rect& rect, SkColor color, SkXfermode::Mode mode);
// Draws the given rectangle with the given |paint| parameters.
- void DrawRect(const gfx::Rect& rect, const SkPaint& paint);
+ void DrawRect(const Rect& rect, const SkPaint& paint);
// Draw the given point with the given |paint| parameters.
- void DrawPoint(const gfx::Point& p, const SkPaint& paint);
+ void DrawPoint(const Point& p, const SkPaint& paint);
// Draws a single pixel line with the specified color.
- void DrawLine(const gfx::Point& p1, const gfx::Point& p2, SkColor color);
+ void DrawLine(const Point& p1, const Point& p2, SkColor color);
// Draws a line with the given |paint| parameters.
- void DrawLine(const gfx::Point& p1,
- const gfx::Point& p2,
- const SkPaint& paint);
+ void DrawLine(const Point& p1, const Point& p2, const SkPaint& paint);
// Draws a circle with the given |paint| parameters.
- void DrawCircle(const gfx::Point& center_point,
+ void DrawCircle(const Point& center_point,
int radius,
const SkPaint& paint);
// Draws the given rectangle with rounded corners of |radius| using the
// given |paint| parameters.
- void DrawRoundRect(const gfx::Rect& rect, int radius, const SkPaint& paint);
+ void DrawRoundRect(const Rect& rect, int radius, const SkPaint& paint);
// Draws the given path using the given |paint| parameters.
void DrawPath(const SkPath& path, const SkPaint& paint);
@@ -255,19 +273,20 @@ class UI_EXPORT Canvas {
// corner of the bitmap is rendered at the specified location.
// Parameters are specified relative to current canvas scale not in pixels.
// Thus, x is 2 pixels if canvas scale = 2 & |x| = 1.
- void DrawImageInt(const gfx::ImageSkia&, int x, int y);
+ void DrawImageInt(const ImageSkia&, int x, int y);
// Helper for DrawImageInt(..., paint) that constructs a temporary paint and
// calls paint.setAlpha(alpha).
- void DrawImageInt(const gfx::ImageSkia&, int x, int y, uint8 alpha);
+ void DrawImageInt(const ImageSkia&, int x, int y, uint8 alpha);
// Draws an image with the origin at the specified location, using the
// specified paint. The upper left corner of the bitmap is rendered at the
// specified location.
// Parameters are specified relative to current canvas scale not in pixels.
// Thus, |x| is 2 pixels if canvas scale = 2 & |x| = 1.
- void DrawImageInt(const gfx::ImageSkia& image,
- int x, int y,
+ void DrawImageInt(const ImageSkia& image,
+ int x,
+ int y,
const SkPaint& paint);
// Draws a portion of an image in the specified location. The src parameters
@@ -282,13 +301,25 @@ class UI_EXPORT Canvas {
// An optional custom SkPaint can be provided.
// Parameters are specified relative to current canvas scale not in pixels.
// Thus, |x| is 2 pixels if canvas scale = 2 & |x| = 1.
- void DrawImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y, int src_w, int src_h,
- int dest_x, int dest_y, int dest_w, int dest_h,
+ void DrawImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ int src_w,
+ int src_h,
+ int dest_x,
+ int dest_y,
+ int dest_w,
+ int dest_h,
bool filter);
- void DrawImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y, int src_w, int src_h,
- int dest_x, int dest_y, int dest_w, int dest_h,
+ void DrawImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ int src_w,
+ int src_h,
+ int dest_x,
+ int dest_y,
+ int dest_w,
+ int dest_h,
bool filter,
const SkPaint& paint);
@@ -296,59 +327,96 @@ class UI_EXPORT Canvas {
// |path|.
// Parameters are specified relative to current canvas scale not in pixels.
// Thus, x is 2 pixels if canvas scale = 2 & |x| = 1.
- void DrawImageInPath(const gfx::ImageSkia& image,
+ void DrawImageInPath(const ImageSkia& image,
int x,
int y,
const SkPath& path,
const SkPaint& paint);
- // Draws text with the specified color, font and location. The text is
+ // Draws text with the specified color, fonts and location. The text is
// aligned to the left, vertically centered, clipped to the region. If the
// text is too big, it is truncated and '...' is added to the end.
+ void DrawStringRect(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& display_rect);
+ // Obsolete versions. Use the above versions which take FontList.
void DrawStringInt(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- int x, int y, int w, int h);
+ int x,
+ int y,
+ int w,
+ int h);
void DrawStringInt(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- const gfx::Rect& display_rect);
+ const Rect& display_rect);
- // Draws text with the specified color, font and location. The last argument
+ // Draws text with the specified color, fonts and location. The last argument
// specifies flags for how the text should be rendered. It can be one of
// TEXT_ALIGN_CENTER, TEXT_ALIGN_RIGHT or TEXT_ALIGN_LEFT.
+ void DrawStringRectWithFlags(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& display_rect,
+ int flags);
+ // Obsolete version. Use the above version which takes FontList.
void DrawStringInt(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- int x, int y, int w, int h,
+ int x,
+ int y,
+ int w,
+ int h,
int flags);
// Similar to above DrawStringInt method but with text shadows support.
// Currently it's only implemented for canvas skia. Specifying a 0 line_height
// will cause the default height to be used.
+ void DrawStringRectWithShadows(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& text_bounds,
+ int line_height,
+ int flags,
+ const ShadowValues& shadows);
+ // Obsolete version. Use the above version which takes FontList.
void DrawStringWithShadows(const base::string16& text,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- const gfx::Rect& text_bounds,
+ const Rect& text_bounds,
int line_height,
int flags,
const ShadowValues& shadows);
// Draws a dotted gray rectangle used for focus purposes.
- void DrawFocusRect(const gfx::Rect& rect);
+ void DrawFocusRect(const Rect& rect);
// Tiles the image in the specified region.
// Parameters are specified relative to current canvas scale not in pixels.
// Thus, |x| is 2 pixels if canvas scale = 2 & |x| = 1.
- void TileImageInt(const gfx::ImageSkia& image,
- int x, int y, int w, int h);
- void TileImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y,
- int dest_x, int dest_y, int w, int h);
- void TileImageInt(const gfx::ImageSkia& image,
- int src_x, int src_y,
- float tile_scale_x, float tile_scale_y,
- int dest_x, int dest_y, int w, int h);
+ void TileImageInt(const ImageSkia& image,
+ int x,
+ int y,
+ int w,
+ int h);
+ void TileImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ int dest_x,
+ int dest_y,
+ int w,
+ int h);
+ void TileImageInt(const ImageSkia& image,
+ int src_x,
+ int src_y,
+ float tile_scale_x,
+ float tile_scale_y,
+ int dest_x,
+ int dest_y,
+ int w,
+ int h);
// Returns a native drawing context for platform specific drawing routines to
// use. Must be balanced by a call to EndPlatformPaint().
@@ -359,19 +427,27 @@ class UI_EXPORT Canvas {
void EndPlatformPaint();
// Apply transformation on the canvas.
- void Transform(const gfx::Transform& transform);
+ void Transform(const Transform& transform);
// Draws the given string with the beginning and/or the end using a fade
// gradient. When truncating the head
// |desired_characters_to_truncate_from_head| specifies the maximum number of
// characters that can be truncated.
+ void DrawFadeTruncatingStringRect(
+ const base::string16& text,
+ TruncateFadeMode truncate_mode,
+ size_t desired_characters_to_truncate_from_head,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& display_rect);
+ // Obsolete version. Use the above version which takes FontList.
void DrawFadeTruncatingString(
const base::string16& text,
TruncateFadeMode truncate_mode,
size_t desired_characters_to_truncate_from_head,
- const gfx::Font& font,
+ const Font& font,
SkColor color,
- const gfx::Rect& display_rect);
+ const Rect& display_rect);
skia::PlatformCanvas* platform_canvas() const { return owned_canvas_.get(); }
SkCanvas* sk_canvas() const { return canvas_; }
@@ -382,19 +458,18 @@ class UI_EXPORT Canvas {
// Test whether the provided rectangle intersects the current clip rect.
bool IntersectsClipRectInt(int x, int y, int w, int h);
- bool IntersectsClipRect(const gfx::Rect& rect);
+ bool IntersectsClipRect(const Rect& rect);
// Returns the image rep which best matches the canvas |scale_factor_|.
// Returns a null image rep if |image| contains no image reps.
// Builds mip map for returned image rep if necessary.
//
// An optional additional user defined scale can be provided.
- const gfx::ImageSkiaRep& GetImageRepToPaint(
- const gfx::ImageSkia& image) const;
- const gfx::ImageSkiaRep& GetImageRepToPaint(
- const gfx::ImageSkia& image,
+ const ImageSkiaRep& GetImageRepToPaint(const ImageSkia& image) const;
+ const ImageSkiaRep& GetImageRepToPaint(
+ const ImageSkia& image,
float user_defined_scale_factor_x,
- float user_defined_scale_factor_y) const;
+ float user_defined_scale_factor_y) const;
// The device scale factor at which drawing on this canvas occurs.
// An additional scale can be applied via Canvas::Scale(). However,
diff --git a/chromium/ui/gfx/canvas_android.cc b/chromium/ui/gfx/canvas_android.cc
index c26a668f1d4..54e45f7653a 100644
--- a/chromium/ui/gfx/canvas_android.cc
+++ b/chromium/ui/gfx/canvas_android.cc
@@ -5,13 +5,12 @@
#include "ui/gfx/canvas.h"
#include "base/logging.h"
-#include "ui/gfx/font.h"
namespace gfx {
// static
void Canvas::SizeStringInt(const base::string16& text,
- const gfx::Font& font,
+ const FontList& font_list,
int* width,
int* height,
int line_height,
@@ -19,13 +18,22 @@ void Canvas::SizeStringInt(const base::string16& text,
NOTIMPLEMENTED();
}
-void Canvas::DrawStringWithShadows(const base::string16& text,
- const gfx::Font& font,
- SkColor color,
- const gfx::Rect& text_bounds,
- int line_height,
- int flags,
- const ShadowValues& shadows) {
+void Canvas::DrawStringRectWithHalo(const base::string16& text,
+ const FontList& font_list,
+ SkColor text_color,
+ SkColor halo_color_in,
+ const Rect& display_rect,
+ int flags) {
+ NOTIMPLEMENTED();
+}
+
+void Canvas::DrawStringRectWithShadows(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& text_bounds,
+ int line_height,
+ int flags,
+ const ShadowValues& shadows) {
NOTIMPLEMENTED();
}
diff --git a/chromium/ui/gfx/canvas_mac.mm b/chromium/ui/gfx/canvas_mac.mm
deleted file mode 100644
index a906873d4e5..00000000000
--- a/chromium/ui/gfx/canvas_mac.mm
+++ /dev/null
@@ -1,89 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#import <Cocoa/Cocoa.h>
-
-#include "ui/gfx/canvas.h"
-
-#include "base/logging.h"
-#include "base/strings/sys_string_conversions.h"
-#include "third_party/skia/include/core/SkTypeface.h"
-#include "ui/gfx/font.h"
-#include "ui/gfx/rect.h"
-
-// Note: This is a temporary Skia-based implementation of the ui/gfx text
-// rendering routines for views/aura. It replaces the stale Cocoa-based
-// implementation. A future |canvas_skia.cc| implementation will supersede
-// this and the other platform-specific implmenentations. Most drawing options,
-// such as alignment, multi-line, and line heights are not implemented here.
-
-namespace {
-
-SkTypeface::Style FontTypefaceStyle(const gfx::Font& font) {
- int style = 0;
- if (font.GetStyle() & gfx::Font::BOLD)
- style |= SkTypeface::kBold;
- if (font.GetStyle() & gfx::Font::ITALIC)
- style |= SkTypeface::kItalic;
-
- return static_cast<SkTypeface::Style>(style);
-}
-
-} // namespace
-
-namespace gfx {
-
-// static
-void Canvas::SizeStringInt(const base::string16& text,
- const gfx::Font& font,
- int* width,
- int* height,
- int line_height,
- int flags) {
- DLOG_IF(WARNING, line_height != 0) << "Line heights not implemented.";
- DLOG_IF(WARNING, flags & Canvas::MULTI_LINE) << "Multi-line not implemented.";
-
- NSFont* native_font = font.GetNativeFont();
- NSString* ns_string = base::SysUTF16ToNSString(text);
- NSDictionary* attributes =
- [NSDictionary dictionaryWithObject:native_font
- forKey:NSFontAttributeName];
- NSSize string_size = [ns_string sizeWithAttributes:attributes];
- *width = string_size.width;
- *height = font.GetHeight();
-}
-
-void Canvas::DrawStringWithShadows(const base::string16& text,
- const gfx::Font& font,
- SkColor color,
- const gfx::Rect& text_bounds,
- int line_height,
- int flags,
- const ShadowValues& shadows) {
- DLOG_IF(WARNING, line_height != 0) << "Line heights not implemented.";
- DLOG_IF(WARNING, flags & Canvas::MULTI_LINE) << "Multi-line not implemented.";
- DLOG_IF(WARNING, !shadows.empty()) << "Text shadows not implemented.";
-
- skia::RefPtr<SkTypeface> typeface = skia::AdoptRef(
- SkTypeface::CreateFromName(
- font.GetFontName().c_str(), FontTypefaceStyle(font)));
- SkPaint paint;
- paint.setTypeface(typeface.get());
- paint.setColor(color);
- canvas_->drawText(text.c_str(),
- text.size() * sizeof(base::string16::value_type),
- text_bounds.x(),
- text_bounds.bottom(),
- paint);
-}
-
-void Canvas::DrawStringWithHalo(const base::string16& text,
- const gfx::Font& font,
- SkColor text_color,
- SkColor halo_color,
- int x, int y, int w, int h,
- int flags) {
-}
-
-} // namespace gfx
diff --git a/chromium/ui/gfx/canvas_paint.h b/chromium/ui/gfx/canvas_paint.h
index 1db5341adae..4ae8b7c0229 100644
--- a/chromium/ui/gfx/canvas_paint.h
+++ b/chromium/ui/gfx/canvas_paint.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_CANVAS_PAINT_H_
#define UI_GFX_CANVAS_PAINT_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
diff --git a/chromium/ui/gfx/canvas_paint_win.cc b/chromium/ui/gfx/canvas_paint_win.cc
index 661b2976fd7..71c836724a2 100644
--- a/chromium/ui/gfx/canvas_paint_win.cc
+++ b/chromium/ui/gfx/canvas_paint_win.cc
@@ -56,7 +56,7 @@ void CanvasSkiaPaint::Init(bool opaque) {
const int height = ps_.rcPaint.bottom - ps_.rcPaint.top;
RecreateBackingCanvas(gfx::Size(width, height),
- ui::GetScaleFactorFromScale(ui::win::GetDeviceScaleFactor()),
+ ui::GetScaleFactorFromScale(gfx::win::GetDeviceScaleFactor()),
opaque);
skia::PlatformCanvas* canvas = platform_canvas();
@@ -65,8 +65,8 @@ void CanvasSkiaPaint::Init(bool opaque) {
// This will bring the canvas into the screen coordinate system for the
// dirty rect
canvas->translate(
- -ps_.rcPaint.left / ui::win::GetDeviceScaleFactor(),
- -ps_.rcPaint.top / ui::win::GetDeviceScaleFactor());
+ -ps_.rcPaint.left / gfx::win::GetDeviceScaleFactor(),
+ -ps_.rcPaint.top / gfx::win::GetDeviceScaleFactor());
}
} // namespace gfx
diff --git a/chromium/ui/gfx/canvas_paint_win.h b/chromium/ui/gfx/canvas_paint_win.h
index d9326e30c07..c5d3aee3211 100644
--- a/chromium/ui/gfx/canvas_paint_win.h
+++ b/chromium/ui/gfx/canvas_paint_win.h
@@ -6,9 +6,9 @@
#define UI_GFX_CANVAS_PAINT_WIN_H_
#include "skia/ext/platform_canvas.h"
-#include "ui/base/win/dpi.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/size.h"
+#include "ui/gfx/win/dpi.h"
namespace gfx {
diff --git a/chromium/ui/gfx/canvas_skia.cc b/chromium/ui/gfx/canvas_skia.cc
index bb8ce7db5e5..ef8ee3625a7 100644
--- a/chromium/ui/gfx/canvas_skia.cc
+++ b/chromium/ui/gfx/canvas_skia.cc
@@ -7,14 +7,13 @@
#include "base/i18n/rtl.h"
#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/range/range.h"
-#include "ui/base/text/text_elider.h"
-#include "ui/gfx/font.h"
#include "ui/gfx/font_list.h"
#include "ui/gfx/insets.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/render_text.h"
#include "ui/gfx/shadow_value.h"
+#include "ui/gfx/text_elider.h"
#include "ui/gfx/text_utils.h"
namespace gfx {
@@ -57,9 +56,9 @@ bool AdjustStringDirection(int flags, base::string16* text) {
// Checks each pixel immediately adjacent to the given pixel in the bitmap. If
// any of them are not the halo color, returns true. This defines the halo of
// pixels that will appear around the text. Note that we have to check each
-// pixel against both the halo color and transparent since |DrawStringWithHalo|
-// will modify the bitmap as it goes, and cleared pixels shouldn't count as
-// changed.
+// pixel against both the halo color and transparent since
+// |DrawStringRectWithHalo| will modify the bitmap as it goes, and cleared
+// pixels shouldn't count as changed.
bool PixelShouldGetHalo(const SkBitmap& bitmap,
int x, int y,
SkColor halo_color) {
@@ -83,49 +82,49 @@ bool PixelShouldGetHalo(const SkBitmap& bitmap,
}
// Strips accelerator character prefixes in |text| if needed, based on |flags|.
-// Returns a range in |text| to underline or ui::Range::InvalidRange() if
+// Returns a range in |text| to underline or gfx::Range::InvalidRange() if
// underlining is not needed.
-ui::Range StripAcceleratorChars(int flags, base::string16* text) {
+Range StripAcceleratorChars(int flags, base::string16* text) {
if (flags & (Canvas::SHOW_PREFIX | Canvas::HIDE_PREFIX)) {
int char_pos = -1;
int char_span = 0;
*text = RemoveAcceleratorChar(*text, '&', &char_pos, &char_span);
if ((flags & Canvas::SHOW_PREFIX) && char_pos != -1)
- return ui::Range(char_pos, char_pos + char_span);
+ return Range(char_pos, char_pos + char_span);
}
- return ui::Range::InvalidRange();
+ return Range::InvalidRange();
}
// Elides |text| and adjusts |range| appropriately. If eliding causes |range|
// to no longer point to the same character in |text|, |range| is made invalid.
-void ElideTextAndAdjustRange(const Font& font,
+void ElideTextAndAdjustRange(const FontList& font_list,
int width,
base::string16* text,
- ui::Range* range) {
+ Range* range) {
const base::char16 start_char =
(range->IsValid() ? text->at(range->start()) : 0);
- *text = ui::ElideText(*text, font, width, ui::ELIDE_AT_END);
+ *text = gfx::ElideText(*text, font_list, width, gfx::ELIDE_AT_END);
if (!range->IsValid())
return;
if (range->start() >= text->length() ||
text->at(range->start()) != start_char) {
- *range = ui::Range::InvalidRange();
+ *range = Range::InvalidRange();
}
}
// Updates |render_text| from the specified parameters.
void UpdateRenderText(const Rect& rect,
const base::string16& text,
- const Font& font,
+ const FontList& font_list,
int flags,
SkColor color,
RenderText* render_text) {
- render_text->SetFont(font);
+ render_text->SetFontList(font_list);
render_text->SetText(text);
render_text->SetCursorEnabled(false);
Rect display_rect = rect;
- display_rect.set_height(font.GetHeight());
+ display_rect.set_height(font_list.GetHeight());
render_text->SetDisplayRect(display_rect);
// Set the text alignment explicitly based on the directionality of the UI,
@@ -147,9 +146,10 @@ void UpdateRenderText(const Rect& rect,
render_text->set_background_is_transparent(true);
render_text->SetColor(color);
- render_text->SetStyle(BOLD, (font.GetStyle() & Font::BOLD) != 0);
- render_text->SetStyle(ITALIC, (font.GetStyle() & Font::ITALIC) != 0);
- render_text->SetStyle(UNDERLINE, (font.GetStyle() & Font::UNDERLINE) != 0);
+ const int font_style = font_list.GetFontStyle();
+ render_text->SetStyle(BOLD, (font_style & Font::BOLD) != 0);
+ render_text->SetStyle(ITALIC, (font_style & Font::ITALIC) != 0);
+ render_text->SetStyle(UNDERLINE, (font_style & Font::UNDERLINE) != 0);
}
// Returns updated |flags| to match platform-specific expected behavior.
@@ -168,7 +168,7 @@ int AdjustPlatformSpecificFlags(const base::string16& text, int flags) {
// static
void Canvas::SizeStringInt(const base::string16& text,
- const Font& font,
+ const FontList& font_list,
int* width, int* height,
int line_height,
int flags) {
@@ -183,25 +183,27 @@ void Canvas::SizeStringInt(const base::string16& text,
#endif
if ((flags & MULTI_LINE) && *width != 0) {
- ui::WordWrapBehavior wrap_behavior = ui::TRUNCATE_LONG_WORDS;
+ gfx::WordWrapBehavior wrap_behavior = gfx::TRUNCATE_LONG_WORDS;
if (flags & CHARACTER_BREAK)
- wrap_behavior = ui::WRAP_LONG_WORDS;
+ wrap_behavior = gfx::WRAP_LONG_WORDS;
else if (!(flags & NO_ELLIPSIS))
- wrap_behavior = ui::ELIDE_LONG_WORDS;
+ wrap_behavior = gfx::ELIDE_LONG_WORDS;
Rect rect(*width, INT_MAX);
std::vector<base::string16> strings;
- ui::ElideRectangleText(adjusted_text, font, rect.width(), rect.height(),
+ gfx::ElideRectangleText(adjusted_text, font_list,
+ rect.width(), rect.height(),
wrap_behavior, &strings);
scoped_ptr<RenderText> render_text(RenderText::CreateInstance());
- UpdateRenderText(rect, base::string16(), font, flags, 0, render_text.get());
+ UpdateRenderText(rect, base::string16(), font_list, flags, 0,
+ render_text.get());
int h = 0;
int w = 0;
for (size_t i = 0; i < strings.size(); ++i) {
StripAcceleratorChars(flags, &strings[i]);
render_text->SetText(strings[i]);
- const Size string_size = render_text->GetStringSize();
+ const Size& string_size = render_text->GetStringSize();
w = std::max(w, string_size.width());
h += (i > 0 && line_height > 0) ? line_height : string_size.height();
}
@@ -212,27 +214,28 @@ void Canvas::SizeStringInt(const base::string16& text,
// will inexplicably fail with result E_INVALIDARG. Guard against this.
const size_t kMaxRenderTextLength = 5000;
if (adjusted_text.length() >= kMaxRenderTextLength) {
- *width = adjusted_text.length() * font.GetAverageCharacterWidth();
- *height = font.GetHeight();
+ *width = font_list.GetExpectedTextWidth(adjusted_text.length());
+ *height = font_list.GetHeight();
} else {
scoped_ptr<RenderText> render_text(RenderText::CreateInstance());
Rect rect(*width, *height);
StripAcceleratorChars(flags, &adjusted_text);
- UpdateRenderText(rect, adjusted_text, font, flags, 0, render_text.get());
- const Size string_size = render_text->GetStringSize();
+ UpdateRenderText(rect, adjusted_text, font_list, flags, 0,
+ render_text.get());
+ const Size& string_size = render_text->GetStringSize();
*width = string_size.width();
*height = string_size.height();
}
}
}
-void Canvas::DrawStringWithShadows(const base::string16& text,
- const Font& font,
- SkColor color,
- const Rect& text_bounds,
- int line_height,
- int flags,
- const ShadowValues& shadows) {
+void Canvas::DrawStringRectWithShadows(const base::string16& text,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& text_bounds,
+ int line_height,
+ int flags,
+ const ShadowValues& shadows) {
if (!IntersectsClipRect(text_bounds))
return;
@@ -255,22 +258,23 @@ void Canvas::DrawStringWithShadows(const base::string16& text,
render_text->SetTextShadows(shadows);
if (flags & MULTI_LINE) {
- ui::WordWrapBehavior wrap_behavior = ui::IGNORE_LONG_WORDS;
+ gfx::WordWrapBehavior wrap_behavior = gfx::IGNORE_LONG_WORDS;
if (flags & CHARACTER_BREAK)
- wrap_behavior = ui::WRAP_LONG_WORDS;
+ wrap_behavior = gfx::WRAP_LONG_WORDS;
else if (!(flags & NO_ELLIPSIS))
- wrap_behavior = ui::ELIDE_LONG_WORDS;
+ wrap_behavior = gfx::ELIDE_LONG_WORDS;
std::vector<base::string16> strings;
- ui::ElideRectangleText(adjusted_text,
- font,
+ gfx::ElideRectangleText(adjusted_text,
+ font_list,
text_bounds.width(), text_bounds.height(),
wrap_behavior,
&strings);
for (size_t i = 0; i < strings.size(); i++) {
- ui::Range range = StripAcceleratorChars(flags, &strings[i]);
- UpdateRenderText(rect, strings[i], font, flags, color, render_text.get());
+ Range range = StripAcceleratorChars(flags, &strings[i]);
+ UpdateRenderText(rect, strings[i], font_list, flags, color,
+ render_text.get());
int line_padding = 0;
if (line_height > 0)
line_padding = line_height - render_text->GetStringSize().height();
@@ -295,7 +299,7 @@ void Canvas::DrawStringWithShadows(const base::string16& text,
rect += Vector2d(0, line_height);
}
} else {
- ui::Range range = StripAcceleratorChars(flags, &adjusted_text);
+ Range range = StripAcceleratorChars(flags, &adjusted_text);
bool elide_text = ((flags & NO_ELLIPSIS) == 0);
#if defined(OS_LINUX)
@@ -311,13 +315,13 @@ void Canvas::DrawStringWithShadows(const base::string16& text,
#endif
if (elide_text) {
- ElideTextAndAdjustRange(font,
+ ElideTextAndAdjustRange(font_list,
text_bounds.width(),
&adjusted_text,
&range);
}
- UpdateRenderText(rect, adjusted_text, font, flags, color,
+ UpdateRenderText(rect, adjusted_text, font_list, flags, color,
render_text.get());
const int text_height = render_text->GetStringSize().height();
@@ -333,19 +337,19 @@ void Canvas::DrawStringWithShadows(const base::string16& text,
canvas_->restore();
}
-void Canvas::DrawStringWithHalo(const base::string16& text,
- const Font& font,
- SkColor text_color,
- SkColor halo_color_in,
- int x, int y, int w, int h,
- int flags) {
+void Canvas::DrawStringRectWithHalo(const base::string16& text,
+ const FontList& font_list,
+ SkColor text_color,
+ SkColor halo_color_in,
+ const Rect& display_rect,
+ int flags) {
// Some callers will have semitransparent halo colors, which we don't handle
// (since the resulting image can have 1-bit transparency only).
SkColor halo_color = SkColorSetA(halo_color_in, 0xFF);
// Create a temporary buffer filled with the halo color. It must leave room
// for the 1-pixel border around the text.
- Size size(w + 2, h + 2);
+ Size size(display_rect.width() + 2, display_rect.height() + 2);
Canvas text_canvas(size, scale_factor(), true);
SkPaint bkgnd_paint;
bkgnd_paint.setColor(halo_color);
@@ -353,7 +357,9 @@ void Canvas::DrawStringWithHalo(const base::string16& text,
// Draw the text into the temporary buffer. This will have correct
// ClearType since the background color is the same as the halo color.
- text_canvas.DrawStringInt(text, font, text_color, 1, 1, w, h, flags);
+ text_canvas.DrawStringRectWithFlags(
+ text, font_list, text_color,
+ Rect(1, 1, display_rect.width(), display_rect.height()), flags);
uint32_t halo_premul = SkPreMultiplyColor(halo_color);
SkBitmap& text_bitmap = const_cast<SkBitmap&>(
@@ -376,22 +382,21 @@ void Canvas::DrawStringWithHalo(const base::string16& text,
// Draw the halo bitmap with blur.
ImageSkia text_image = ImageSkia(ImageSkiaRep(text_bitmap,
text_canvas.scale_factor()));
- DrawImageInt(text_image, x - 1, y - 1);
+ DrawImageInt(text_image, display_rect.x() - 1, display_rect.y() - 1);
}
-void Canvas::DrawFadeTruncatingString(
- const base::string16& text,
- TruncateFadeMode truncate_mode,
- size_t desired_characters_to_truncate_from_head,
- const Font& font,
- SkColor color,
- const Rect& display_rect) {
+void Canvas::DrawFadeTruncatingStringRect(
+ const base::string16& text,
+ TruncateFadeMode truncate_mode,
+ size_t desired_characters_to_truncate_from_head,
+ const FontList& font_list,
+ SkColor color,
+ const Rect& display_rect) {
int flags = NO_ELLIPSIS;
// If the whole string fits in the destination then just draw it directly.
- if (GetStringWidth(text, font) <= display_rect.width()) {
- DrawStringInt(text, font, color, display_rect.x(), display_rect.y(),
- display_rect.width(), display_rect.height(), flags);
+ if (GetStringWidth(text, font_list) <= display_rect.width()) {
+ DrawStringRectWithFlags(text, font_list, color, display_rect, flags);
return;
}
@@ -437,7 +442,8 @@ void Canvas::DrawFadeTruncatingString(
flags |= TEXT_ALIGN_LEFT;
Rect rect = display_rect;
- UpdateRenderText(rect, clipped_text, font, flags, color, render_text.get());
+ UpdateRenderText(rect, clipped_text, font_list, flags, color,
+ render_text.get());
const int line_height = render_text->GetStringSize().height();
// Center the text vertically.
@@ -451,4 +457,16 @@ void Canvas::DrawFadeTruncatingString(
canvas_->restore();
}
+void Canvas::DrawFadeTruncatingString(
+ const base::string16& text,
+ TruncateFadeMode truncate_mode,
+ size_t desired_characters_to_truncate_from_head,
+ const Font& font,
+ SkColor color,
+ const Rect& display_rect) {
+ DrawFadeTruncatingStringRect(text, truncate_mode,
+ desired_characters_to_truncate_from_head,
+ FontList(font), color, display_rect);
+}
+
} // namespace gfx
diff --git a/chromium/ui/gfx/canvas_unittest_mac.mm b/chromium/ui/gfx/canvas_unittest_mac.mm
new file mode 100644
index 00000000000..d607218c64f
--- /dev/null
+++ b/chromium/ui/gfx/canvas_unittest_mac.mm
@@ -0,0 +1,84 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gfx/canvas.h"
+
+#include <cmath>
+
+#import <Cocoa/Cocoa.h>
+
+#include "base/strings/utf_string_conversions.h"
+#include "base/strings/sys_string_conversions.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "ui/gfx/font.h"
+#include "ui/gfx/font_list.h"
+
+namespace gfx {
+
+namespace {
+
+// Mac-specific code for string size computations. This is a verbatim copy
+// of the old implementation that used to be in canvas_mac.mm.
+void CanvasMac_SizeStringInt(const base::string16& text,
+ const FontList& font_list,
+ int* width,
+ int* height,
+ int line_height,
+ int flags) {
+ DLOG_IF(WARNING, line_height != 0) << "Line heights not implemented.";
+ DLOG_IF(WARNING, flags & Canvas::MULTI_LINE) << "Multi-line not implemented.";
+
+ NSFont* native_font = font_list.GetPrimaryFont().GetNativeFont();
+ NSString* ns_string = base::SysUTF16ToNSString(text);
+ NSDictionary* attributes =
+ [NSDictionary dictionaryWithObject:native_font
+ forKey:NSFontAttributeName];
+ NSSize string_size = [ns_string sizeWithAttributes:attributes];
+ *width = std::ceil(string_size.width);
+ *height = font_list.GetHeight();
+}
+
+} // namespace
+
+class CanvasTestMac : public testing::Test {
+ protected:
+ // Compare the size returned by Canvas::SizeStringInt to the size generated
+ // by the platform-specific version in CanvasMac_SizeStringInt. Will generate
+ // expectation failure on any mismatch. Only works for single-line text
+ // without specified line height, since that is all the platform
+ // implementation supports.
+ void CompareSizes(const char* text) {
+ const int kReallyLargeNumber = 12345678;
+ FontList font_list(font_);
+ base::string16 text16 = base::UTF8ToUTF16(text);
+
+ int mac_width = kReallyLargeNumber;
+ int mac_height = kReallyLargeNumber;
+ CanvasMac_SizeStringInt(text16, font_list, &mac_width, &mac_height, 0, 0);
+
+ int canvas_width = kReallyLargeNumber;
+ int canvas_height = kReallyLargeNumber;
+ Canvas::SizeStringInt(
+ text16, font_list, &canvas_width, &canvas_height, 0, 0);
+
+ EXPECT_NE(kReallyLargeNumber, mac_width) << "no width for " << text;
+ EXPECT_NE(kReallyLargeNumber, mac_height) << "no height for " << text;
+ EXPECT_EQ(mac_width, canvas_width) << " width for " << text;
+ EXPECT_EQ(mac_height, canvas_height) << " height for " << text;
+ }
+
+ private:
+ Font font_;
+};
+
+ // Tests that Canvas' SizeStringInt yields result consistent with a native
+ // implementation.
+ TEST_F(CanvasTestMac, StringSizeIdenticalForSkia) {
+ CompareSizes("");
+ CompareSizes("Foo");
+ CompareSizes("Longword");
+ CompareSizes("This is a complete sentence.");
+}
+
+} // namespace gfx
diff --git a/chromium/ui/gfx/codec/OWNERS b/chromium/ui/gfx/codec/OWNERS
new file mode 100644
index 00000000000..44aa7e470f9
--- /dev/null
+++ b/chromium/ui/gfx/codec/OWNERS
@@ -0,0 +1,2 @@
+erg@chromium.org
+dcheng@chromium.org
diff --git a/chromium/ui/gfx/codec/jpeg_codec.h b/chromium/ui/gfx/codec/jpeg_codec.h
index e4edeee2236..b6b7088c361 100644
--- a/chromium/ui/gfx/codec/jpeg_codec.h
+++ b/chromium/ui/gfx/codec/jpeg_codec.h
@@ -8,7 +8,7 @@
#include <stddef.h>
#include <vector>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
class SkBitmap;
diff --git a/chromium/ui/gfx/codec/png_codec.cc b/chromium/ui/gfx/codec/png_codec.cc
index 360526b3436..30e4eb6d653 100644
--- a/chromium/ui/gfx/codec/png_codec.cc
+++ b/chromium/ui/gfx/codec/png_codec.cc
@@ -472,7 +472,7 @@ bool PNGCodec::Decode(const unsigned char* input, size_t input_size,
// static
SkBitmap* PNGCodec::CreateSkBitmapFromBGRAFormat(
- std::vector<unsigned char>& bgra, int width, int height) {
+ const std::vector<unsigned char>& bgra, int width, int height) {
SkBitmap* bitmap = new SkBitmap();
bitmap->setConfig(SkBitmap::kARGB_8888_Config, width, height);
bitmap->allocPixels();
@@ -654,29 +654,14 @@ bool DoLibpngWrite(png_struct* png_ptr, png_info* info_ptr,
return true;
}
-} // namespace
-
-// static
-bool PNGCodec::Encode(const unsigned char* input, ColorFormat format,
- const Size& size, int row_byte_width,
- bool discard_transparency,
- const std::vector<Comment>& comments,
- std::vector<unsigned char>* output) {
- return PNGCodec::EncodeWithCompressionLevel(input, format, size,
- row_byte_width,
- discard_transparency,
- comments, Z_DEFAULT_COMPRESSION,
- output);
-}
-
-// static
-bool PNGCodec::EncodeWithCompressionLevel(const unsigned char* input,
- ColorFormat format, const Size& size,
- int row_byte_width,
- bool discard_transparency,
- const std::vector<Comment>& comments,
- int compression_level,
- std::vector<unsigned char>* output) {
+bool EncodeWithCompressionLevel(const unsigned char* input,
+ PNGCodec::ColorFormat format,
+ const Size& size,
+ int row_byte_width,
+ bool discard_transparency,
+ const std::vector<PNGCodec::Comment>& comments,
+ int compression_level,
+ std::vector<unsigned char>* output) {
// Run to convert an input row into the output row format, NULL means no
// conversion is necessary.
FormatConverter converter = NULL;
@@ -684,13 +669,13 @@ bool PNGCodec::EncodeWithCompressionLevel(const unsigned char* input,
int input_color_components, output_color_components;
int png_output_color_type;
switch (format) {
- case FORMAT_RGB:
+ case PNGCodec::FORMAT_RGB:
input_color_components = 3;
output_color_components = 3;
png_output_color_type = PNG_COLOR_TYPE_RGB;
break;
- case FORMAT_RGBA:
+ case PNGCodec::FORMAT_RGBA:
input_color_components = 4;
if (discard_transparency) {
output_color_components = 3;
@@ -703,7 +688,7 @@ bool PNGCodec::EncodeWithCompressionLevel(const unsigned char* input,
}
break;
- case FORMAT_BGRA:
+ case PNGCodec::FORMAT_BGRA:
input_color_components = 4;
if (discard_transparency) {
output_color_components = 3;
@@ -716,7 +701,7 @@ bool PNGCodec::EncodeWithCompressionLevel(const unsigned char* input,
}
break;
- case FORMAT_SkBitmap:
+ case PNGCodec::FORMAT_SkBitmap:
input_color_components = 4;
if (discard_transparency) {
output_color_components = 3;
@@ -758,24 +743,62 @@ bool PNGCodec::EncodeWithCompressionLevel(const unsigned char* input,
return success;
}
+
+} // namespace
+
+// static
+bool PNGCodec::Encode(const unsigned char* input, ColorFormat format,
+ const Size& size, int row_byte_width,
+ bool discard_transparency,
+ const std::vector<Comment>& comments,
+ std::vector<unsigned char>* output) {
+ return EncodeWithCompressionLevel(input,
+ format,
+ size,
+ row_byte_width,
+ discard_transparency,
+ comments,
+ Z_DEFAULT_COMPRESSION,
+ output);
+}
+
// static
bool PNGCodec::EncodeBGRASkBitmap(const SkBitmap& input,
bool discard_transparency,
std::vector<unsigned char>* output) {
static const int bbp = 4;
- SkAutoLockPixels lock_input(input);
if (input.empty())
return false;
- DCHECK(input.bytesPerPixel() == bbp);
- DCHECK(static_cast<int>(input.rowBytes()) >= input.width() * bbp);
+ DCHECK_EQ(input.bytesPerPixel(), bbp);
+ DCHECK_GE(static_cast<int>(input.rowBytes()), input.width() * bbp);
+ SkAutoLockPixels lock_input(input);
return Encode(reinterpret_cast<unsigned char*>(input.getAddr32(0, 0)),
FORMAT_SkBitmap, Size(input.width(), input.height()),
static_cast<int>(input.rowBytes()), discard_transparency,
std::vector<Comment>(), output);
}
+// static
+bool PNGCodec::FastEncodeBGRASkBitmap(const SkBitmap& input,
+ bool discard_transparency,
+ std::vector<unsigned char>* output) {
+ static const int bbp = 4;
+
+ if (input.empty())
+ return false;
+ DCHECK_EQ(input.bytesPerPixel(), bbp);
+ DCHECK_GE(static_cast<int>(input.rowBytes()), input.width() * bbp);
+
+ SkAutoLockPixels lock_input(input);
+ return EncodeWithCompressionLevel(
+ reinterpret_cast<unsigned char*>(input.getAddr32(0, 0)),
+ FORMAT_SkBitmap, Size(input.width(), input.height()),
+ static_cast<int>(input.rowBytes()), discard_transparency,
+ std::vector<Comment>(), Z_BEST_SPEED, output);
+}
+
PNGCodec::Comment::Comment(const std::string& k, const std::string& t)
: key(k), text(t) {
}
diff --git a/chromium/ui/gfx/codec/png_codec.h b/chromium/ui/gfx/codec/png_codec.h
index 3a6d295dbdf..86f170d359f 100644
--- a/chromium/ui/gfx/codec/png_codec.h
+++ b/chromium/ui/gfx/codec/png_codec.h
@@ -9,7 +9,7 @@
#include <vector>
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
class SkBitmap;
@@ -51,16 +51,6 @@ class UI_EXPORT PNGCodec {
std::string text;
};
- // Calls PNGCodec::EncodeWithCompressionLevel with the default compression
- // level.
- static bool Encode(const unsigned char* input,
- ColorFormat format,
- const Size& size,
- int row_byte_width,
- bool discard_transparency,
- const std::vector<Comment>& comments,
- std::vector<unsigned char>* output);
-
// Encodes the given raw 'input' data, with each pixel being represented as
// given in 'format'. The encoded PNG data will be written into the supplied
// vector and true will be returned on success. On failure (false), the
@@ -78,16 +68,13 @@ class UI_EXPORT PNGCodec {
// written to the resulting file. Otherwise, alpha values in the input
// will be preserved.
// comments: comments to be written in the png's metadata.
- // compression_level: An integer between -1 and 9, corresponding to zlib's
- // compression levels. -1 is the default.
- static bool EncodeWithCompressionLevel(const unsigned char* input,
- ColorFormat format,
- const Size& size,
- int row_byte_width,
- bool discard_transparency,
- const std::vector<Comment>& comments,
- int compression_level,
- std::vector<unsigned char>* output);
+ static bool Encode(const unsigned char* input,
+ ColorFormat format,
+ const Size& size,
+ int row_byte_width,
+ bool discard_transparency,
+ const std::vector<Comment>& comments,
+ std::vector<unsigned char>* output);
// Call PNGCodec::Encode on the supplied SkBitmap |input|, which is assumed
// to be BGRA, 32 bits per pixel. The params |discard_transparency| and
@@ -97,6 +84,13 @@ class UI_EXPORT PNGCodec {
bool discard_transparency,
std::vector<unsigned char>* output);
+ // Call PNGCodec::Encode on the supplied SkBitmap |input|. The difference
+ // between this and the previous method is that this restricts compression to
+ // zlib q1, which is just rle encoding.
+ static bool FastEncodeBGRASkBitmap(const SkBitmap& input,
+ bool discard_transparency,
+ std::vector<unsigned char>* output);
+
// Decodes the PNG data contained in input of length input_size. The
// decoded data will be placed in *output with the dimensions in *w and *h
// on success (returns true). This data will be written in the 'format'
@@ -123,7 +117,7 @@ class UI_EXPORT PNGCodec {
// Create a SkBitmap from a decoded BGRA DIB. The caller owns the returned
// SkBitmap.
static SkBitmap* CreateSkBitmapFromBGRAFormat(
- std::vector<unsigned char>& bgra, int width, int height);
+ const std::vector<unsigned char>& bgra, int width, int height);
private:
DISALLOW_COPY_AND_ASSIGN(PNGCodec);
diff --git a/chromium/ui/gfx/codec/png_codec_unittest.cc b/chromium/ui/gfx/codec/png_codec_unittest.cc
index e3540a27114..f1654d9d363 100644
--- a/chromium/ui/gfx/codec/png_codec_unittest.cc
+++ b/chromium/ui/gfx/codec/png_codec_unittest.cc
@@ -14,6 +14,7 @@
#include "third_party/zlib/zlib.h"
#include "ui/gfx/codec/png_codec.h"
#include "ui/gfx/size.h"
+#include "ui/gfx/skia_util.h"
namespace gfx {
@@ -1119,43 +1120,31 @@ TEST(PNGCodec, EncodeDecodeWithVaryingCompressionLevels) {
// create an image with known values, a must be opaque because it will be
// lost during encoding
- std::vector<unsigned char> original;
- MakeRGBAImage(w, h, true, &original);
+ SkBitmap original_bitmap;
+ MakeTestSkBitmap(w, h, &original_bitmap);
// encode
- std::vector<unsigned char> encoded_fast;
- EXPECT_TRUE(PNGCodec::EncodeWithCompressionLevel(
- &original[0], PNGCodec::FORMAT_RGBA, Size(w, h), w * 4, false,
- std::vector<PNGCodec::Comment>(), Z_BEST_SPEED, &encoded_fast));
+ std::vector<unsigned char> encoded_normal;
+ EXPECT_TRUE(
+ PNGCodec::EncodeBGRASkBitmap(original_bitmap, false, &encoded_normal));
- std::vector<unsigned char> encoded_best;
- EXPECT_TRUE(PNGCodec::EncodeWithCompressionLevel(
- &original[0], PNGCodec::FORMAT_RGBA, Size(w, h), w * 4, false,
- std::vector<PNGCodec::Comment>(), Z_BEST_COMPRESSION, &encoded_best));
+ std::vector<unsigned char> encoded_fast;
+ EXPECT_TRUE(
+ PNGCodec::FastEncodeBGRASkBitmap(original_bitmap, false, &encoded_fast));
// Make sure the different compression settings actually do something; the
// sizes should be different.
- EXPECT_NE(encoded_fast.size(), encoded_best.size());
-
- // decode, it should have the same size as the original
- std::vector<unsigned char> decoded;
- int outw, outh;
- EXPECT_TRUE(PNGCodec::Decode(&encoded_fast[0], encoded_fast.size(),
- PNGCodec::FORMAT_RGBA, &decoded,
- &outw, &outh));
- ASSERT_EQ(w, outw);
- ASSERT_EQ(h, outh);
- ASSERT_EQ(original.size(), decoded.size());
+ EXPECT_NE(encoded_normal.size(), encoded_fast.size());
- EXPECT_TRUE(PNGCodec::Decode(&encoded_best[0], encoded_best.size(),
- PNGCodec::FORMAT_RGBA, &decoded,
- &outw, &outh));
- ASSERT_EQ(w, outw);
- ASSERT_EQ(h, outh);
- ASSERT_EQ(original.size(), decoded.size());
+ // decode, they should be identical to the original.
+ SkBitmap decoded;
+ EXPECT_TRUE(
+ PNGCodec::Decode(&encoded_normal[0], encoded_normal.size(), &decoded));
+ EXPECT_TRUE(BitmapsAreEqual(decoded, original_bitmap));
- // Images must be exactly equal
- ASSERT_TRUE(original == decoded);
+ EXPECT_TRUE(
+ PNGCodec::Decode(&encoded_fast[0], encoded_fast.size(), &decoded));
+ EXPECT_TRUE(BitmapsAreEqual(decoded, original_bitmap));
}
diff --git a/chromium/ui/gfx/color_analysis.h b/chromium/ui/gfx/color_analysis.h
index 1d0b1a51409..797b4f94663 100644
--- a/chromium/ui/gfx/color_analysis.h
+++ b/chromium/ui/gfx/color_analysis.h
@@ -10,7 +10,7 @@
#include "base/memory/ref_counted.h"
#include "base/memory/ref_counted_memory.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/matrix3_f.h"
class SkBitmap;
diff --git a/chromium/ui/gfx/color_profile.h b/chromium/ui/gfx/color_profile.h
index 5e50f6b88a2..3a3f5b2ce04 100644
--- a/chromium/ui/gfx/color_profile.h
+++ b/chromium/ui/gfx/color_profile.h
@@ -9,7 +9,7 @@
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/color_profile_win.cc b/chromium/ui/gfx/color_profile_win.cc
index 51b1b312d08..2e08a36d4b6 100644
--- a/chromium/ui/gfx/color_profile_win.cc
+++ b/chromium/ui/gfx/color_profile_win.cc
@@ -21,7 +21,7 @@ void ReadColorProfile(std::vector<char>* profile) {
if (!res)
return;
std::string profileData;
- if (!file_util::ReadFileToString(base::FilePath(path), &profileData))
+ if (!base::ReadFileToString(base::FilePath(path), &profileData))
return;
size_t length = profileData.size();
if (length > gfx::kMaxProfileLength)
diff --git a/chromium/ui/gfx/color_utils.h b/chromium/ui/gfx/color_utils.h
index c9f62066427..440e3825c31 100644
--- a/chromium/ui/gfx/color_utils.h
+++ b/chromium/ui/gfx/color_utils.h
@@ -7,7 +7,7 @@
#include "base/basictypes.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
class SkBitmap;
diff --git a/chromium/ui/gfx/display.cc b/chromium/ui/gfx/display.cc
index 02d97a903fc..ee650d8964f 100644
--- a/chromium/ui/gfx/display.cc
+++ b/chromium/ui/gfx/display.cc
@@ -4,15 +4,17 @@
#include "ui/gfx/display.h"
+#include <algorithm>
+
#include "base/command_line.h"
#include "base/logging.h"
#include "base/strings/string_number_conversions.h"
#include "base/strings/stringprintf.h"
-#include "ui/base/ui_base_switches.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/point_conversions.h"
#include "ui/gfx/point_f.h"
#include "ui/gfx/size_conversions.h"
+#include "ui/gfx/switches.h"
namespace gfx {
namespace {
diff --git a/chromium/ui/gfx/display.h b/chromium/ui/gfx/display.h
index 2282cb0a568..17cedfe38fe 100644
--- a/chromium/ui/gfx/display.h
+++ b/chromium/ui/gfx/display.h
@@ -7,11 +7,15 @@
#include "base/basictypes.h"
#include "base/compiler_specific.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/rect.h"
namespace gfx {
+// This class typically, but does not always, correspond to a physical display
+// connected to the system. A fake Display may exist on a headless system, or a
+// Display may correspond to a remote, virtual display.
+//
// Note: The screen and display currently uses pixel coordinate
// system. For platforms that support DIP (density independent pixel),
// |bounds()| and |work_area| will return values in DIP coordinate
diff --git a/chromium/ui/gfx/display_observer.h b/chromium/ui/gfx/display_observer.h
index 85a4086bb5a..1e7cd8cb899 100644
--- a/chromium/ui/gfx/display_observer.h
+++ b/chromium/ui/gfx/display_observer.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_DISPLAY_OBSERVER_H_
#define UI_GFX_DISPLAY_OBSERVER_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
class Display;
diff --git a/chromium/ui/gfx/favicon_size.h b/chromium/ui/gfx/favicon_size.h
index 6b2c6a14f4f..ecab851dc1a 100644
--- a/chromium/ui/gfx/favicon_size.h
+++ b/chromium/ui/gfx/favicon_size.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_FAVICON_SIZE_H_
#define UI_GFX_FAVICON_SIZE_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/font.h b/chromium/ui/gfx/font.h
index bd6e4650767..dfbf410f30c 100644
--- a/chromium/ui/gfx/font.h
+++ b/chromium/ui/gfx/font.h
@@ -9,7 +9,7 @@
#include "base/memory/ref_counted.h"
#include "base/strings/string16.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
diff --git a/chromium/ui/gfx/font_list.h b/chromium/ui/gfx/font_list.h
index 22be9121cc0..ae96251cce8 100644
--- a/chromium/ui/gfx/font_list.h
+++ b/chromium/ui/gfx/font_list.h
@@ -8,8 +8,8 @@
#include <string>
#include <vector>
-#include "ui/base/ui_export.h"
#include "ui/gfx/font.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/font_render_params_linux.h b/chromium/ui/gfx/font_render_params_linux.h
index ec39302dccc..9ba6ca971b2 100644
--- a/chromium/ui/gfx/font_render_params_linux.h
+++ b/chromium/ui/gfx/font_render_params_linux.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_FONT_RENDER_PARAMS_LINUX_H_
#define UI_GFX_FONT_RENDER_PARAMS_LINUX_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/font_smoothing_win.cc b/chromium/ui/gfx/font_smoothing_win.cc
index a4be72930a4..b181fb564e8 100644
--- a/chromium/ui/gfx/font_smoothing_win.cc
+++ b/chromium/ui/gfx/font_smoothing_win.cc
@@ -5,13 +5,13 @@
#include "ui/gfx/font_smoothing_win.h"
#include "base/memory/singleton.h"
-#include "ui/base/win/singleton_hwnd.h"
+#include "ui/gfx/win/singleton_hwnd.h"
namespace {
// Helper class to cache font smoothing settings and listen for notifications
// to re-query them from the system.
-class CachedFontSmoothingSettings : public ui::SingletonHwnd::Observer {
+class CachedFontSmoothingSettings : public gfx::SingletonHwnd::Observer {
public:
static CachedFontSmoothingSettings* GetInstance();
@@ -66,7 +66,7 @@ void CachedFontSmoothingSettings::GetFontSmoothingSettings(
need_to_query_settings_ = false;
}
if (!observer_added_) {
- ui::SingletonHwnd::GetInstance()->AddObserver(this);
+ gfx::SingletonHwnd::GetInstance()->AddObserver(this);
observer_added_ = true;
}
*smoothing_enabled = smoothing_enabled_;
diff --git a/chromium/ui/gfx/gdi_util.h b/chromium/ui/gfx/gdi_util.h
index fdf6a67bf20..53b6e91a897 100644
--- a/chromium/ui/gfx/gdi_util.h
+++ b/chromium/ui/gfx/gdi_util.h
@@ -8,7 +8,7 @@
#include <vector>
#include <windows.h>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/path.h"
diff --git a/chromium/ui/base/gtk/gdk_x_compat.h b/chromium/ui/gfx/gdk_compat.h
index fd395c78f6a..b11d7795831 100644
--- a/chromium/ui/base/gtk/gdk_x_compat.h
+++ b/chromium/ui/gfx/gdk_compat.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_GTK_GDK_X_COMPAT_H_
-#define UI_BASE_GTK_GDK_X_COMPAT_H_
+#ifndef UI_GFX_GDK_COMPAT_H_
+#define UI_GFX_GDK_COMPAT_H_
#include <gtk/gtk.h>
#include <gdk/gdkx.h>
@@ -24,4 +24,4 @@ inline GdkWindow* gdk_x11_window_lookup_for_display(GdkDisplay* display,
}
#endif
-#endif // UI_BASE_GTK_GDK_X_COMPAT_H_
+#endif // UI_GFX_GDK_COMPAT_H_
diff --git a/chromium/ui/gfx/gfx_export.h b/chromium/ui/gfx/gfx_export.h
new file mode 100644
index 00000000000..f610d98d82d
--- /dev/null
+++ b/chromium/ui/gfx/gfx_export.h
@@ -0,0 +1,33 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_GFX_GFX_EXPORT_H_
+#define UI_GFX_GFX_EXPORT_H_
+
+// TODO(beng): remove include once gfx dependencies have been corrected.
+
+#include "ui/base/ui_export.h"
+
+#if defined(COMPONENT_BUILD)
+#if defined(WIN32)
+
+#if defined(UI_IMPLEMENTATION)
+#define GFX_EXPORT __declspec(dllexport)
+#else
+#define GFX_EXPORT __declspec(dllimport)
+#endif // defined(UI_IMPLEMENTATION)
+
+#else // defined(WIN32)
+#if defined(UI_IMPLEMENTATION)
+#define GFX_EXPORT __attribute__((visibility("default")))
+#else
+#define GFX_EXPORT
+#endif
+#endif
+
+#else // defined(COMPONENT_BUILD)
+#define GFX_EXPORT
+#endif
+
+#endif // UI_GFX_GFX_EXPORT_H_
diff --git a/chromium/ui/gfx/gfx_paths.h b/chromium/ui/gfx/gfx_paths.h
index 24fad8b4cb1..d5eec96fd74 100644
--- a/chromium/ui/gfx/gfx_paths.h
+++ b/chromium/ui/gfx/gfx_paths.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_GFX_PATHS_H_
#define UI_GFX_GFX_PATHS_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
// This file declares path keys for the app module. These can be used with
// the PathService to access various special directories and files.
diff --git a/chromium/ui/gfx/gpu_memory_buffer.h b/chromium/ui/gfx/gpu_memory_buffer.h
index ff94979ff01..c600527f022 100644
--- a/chromium/ui/gfx/gpu_memory_buffer.h
+++ b/chromium/ui/gfx/gpu_memory_buffer.h
@@ -7,7 +7,7 @@
#include "base/memory/shared_memory.h"
#include "build/build_config.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#if defined(OS_ANDROID)
#include <third_party/khronos/EGL/egl.h>
diff --git a/chromium/ui/base/gtk/gtk_compat.h b/chromium/ui/gfx/gtk_compat.h
index 0518fad23f2..ca14a27627a 100644
--- a/chromium/ui/base/gtk/gtk_compat.h
+++ b/chromium/ui/gfx/gtk_compat.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_GTK_GTK_COMPAT_H_
-#define UI_BASE_GTK_GTK_COMPAT_H_
+#ifndef UI_GFX_GTK_COMPAT_H_
+#define UI_GFX_GTK_COMPAT_H_
#include <gtk/gtk.h>
@@ -94,4 +94,4 @@ inline int gdk_window_get_width(GdkWindow* window) {
}
#endif // !GTK_CHECK_VERSION(2, 24, 0)
-#endif // UI_BASE_GTK_GTK_COMPAT_H_
+#endif // UI_GFX_GTK_COMPAT_H_
diff --git a/chromium/ui/gfx/gtk_native_view_id_manager.cc b/chromium/ui/gfx/gtk_native_view_id_manager.cc
index 07e1ed4c81d..0844b190dd9 100644
--- a/chromium/ui/gfx/gtk_native_view_id_manager.cc
+++ b/chromium/ui/gfx/gtk_native_view_id_manager.cc
@@ -10,8 +10,8 @@
#include "base/logging.h"
#include "base/memory/singleton.h"
#include "base/rand_util.h"
-#include "ui/base/gtk/gdk_x_compat.h"
-#include "ui/base/gtk/gtk_compat.h"
+#include "ui/gfx/gdk_compat.h"
+#include "ui/gfx/gtk_compat.h"
#include "ui/gfx/gtk_preserve_window.h"
// -----------------------------------------------------------------------------
diff --git a/chromium/ui/gfx/gtk_native_view_id_manager.h b/chromium/ui/gfx/gtk_native_view_id_manager.h
index 7c8afcc0f9d..242cf0939e3 100644
--- a/chromium/ui/gfx/gtk_native_view_id_manager.h
+++ b/chromium/ui/gfx/gtk_native_view_id_manager.h
@@ -8,7 +8,7 @@
#include <map>
#include "base/synchronization/lock.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
template <typename T> struct DefaultSingletonTraits;
diff --git a/chromium/ui/gfx/gtk_preserve_window.cc b/chromium/ui/gfx/gtk_preserve_window.cc
index 8ea1c431650..78a49c28510 100644
--- a/chromium/ui/gfx/gtk_preserve_window.cc
+++ b/chromium/ui/gfx/gtk_preserve_window.cc
@@ -7,7 +7,7 @@
#include <gdk/gdk.h>
#include <gtk/gtk.h>
-#include "ui/base/gtk/gtk_compat.h"
+#include "ui/gfx/gtk_compat.h"
G_BEGIN_DECLS
diff --git a/chromium/ui/gfx/gtk_preserve_window.h b/chromium/ui/gfx/gtk_preserve_window.h
index 53a821e44dd..f48be3f2bdb 100644
--- a/chromium/ui/gfx/gtk_preserve_window.h
+++ b/chromium/ui/gfx/gtk_preserve_window.h
@@ -9,7 +9,7 @@
#include <gdk/gdk.h>
#include <gtk/gtk.h>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
// GtkFixed creates an X window when realized and destroys an X window
// when unrealized. GtkPreserveWindow allows overrides this
diff --git a/chromium/ui/gfx/gtk_util.h b/chromium/ui/gfx/gtk_util.h
index 5fe0c081fca..5672bbd8f12 100644
--- a/chromium/ui/gfx/gtk_util.h
+++ b/chromium/ui/gfx/gtk_util.h
@@ -8,7 +8,7 @@
#include <vector>
#include "base/time/time.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
typedef struct _GdkPixbuf GdkPixbuf;
typedef struct _GdkRegion GdkRegion;
diff --git a/chromium/ui/gfx/icon_util.h b/chromium/ui/gfx/icon_util.h
index 7ce5606f525..d56f5a10df3 100644
--- a/chromium/ui/gfx/icon_util.h
+++ b/chromium/ui/gfx/icon_util.h
@@ -12,7 +12,7 @@
#include "base/basictypes.h"
#include "base/gtest_prod_util.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point.h"
#include "ui/gfx/size.h"
diff --git a/chromium/ui/gfx/icon_util_unittest.cc b/chromium/ui/gfx/icon_util_unittest.cc
index b1548cee447..641422a24ef 100644
--- a/chromium/ui/gfx/icon_util_unittest.cc
+++ b/chromium/ui/gfx/icon_util_unittest.cc
@@ -92,7 +92,7 @@ void IconUtilTest::CheckAllIconSizes(const base::FilePath& icon_filename,
// Read the file completely into memory.
std::string icon_data;
- ASSERT_TRUE(file_util::ReadFileToString(icon_filename, &icon_data));
+ ASSERT_TRUE(base::ReadFileToString(icon_filename, &icon_data));
ASSERT_GE(icon_data.length(), sizeof(IconUtil::ICONDIR));
// Ensure that it has exactly the expected number and sizes of icons, in the
diff --git a/chromium/ui/gfx/image/cairo_cached_surface.h b/chromium/ui/gfx/image/cairo_cached_surface.h
index d29d9befd8c..7c0204aa81b 100644
--- a/chromium/ui/gfx/image/cairo_cached_surface.h
+++ b/chromium/ui/gfx/image/cairo_cached_surface.h
@@ -7,7 +7,7 @@
#include <vector>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
typedef struct _GdkDisplay GdkDisplay;
typedef struct _GdkPixbuf GdkPixbuf;
diff --git a/chromium/ui/gfx/image/canvas_image_source.h b/chromium/ui/gfx/image/canvas_image_source.h
index a713b95ce8d..8373387326c 100644
--- a/chromium/ui/gfx/image/canvas_image_source.h
+++ b/chromium/ui/gfx/image/canvas_image_source.h
@@ -7,7 +7,7 @@
#include "base/basictypes.h"
#include "base/compiler_specific.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/image/image_skia_source.h"
#include "ui/gfx/size.h"
diff --git a/chromium/ui/gfx/image/image.cc b/chromium/ui/gfx/image/image.cc
index b0733b7ccda..f089c837504 100644
--- a/chromium/ui/gfx/image/image.cc
+++ b/chromium/ui/gfx/image/image.cc
@@ -22,10 +22,10 @@
#include <gdk-pixbuf/gdk-pixbuf.h>
#include <gdk/gdk.h>
#include <glib-object.h>
-#include "ui/base/gtk/scoped_gobject.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/gtk_util.h"
#include "ui/gfx/image/cairo_cached_surface.h"
+#include "ui/gfx/scoped_gobject.h"
#elif defined(OS_IOS)
#include "base/mac/foundation_util.h"
#include "ui/gfx/image/image_skia_util_ios.h"
diff --git a/chromium/ui/gfx/image/image.h b/chromium/ui/gfx/image/image.h
index e9619dca21e..00b5baa194b 100644
--- a/chromium/ui/gfx/image/image.h
+++ b/chromium/ui/gfx/image/image.h
@@ -25,7 +25,7 @@
#include "base/basictypes.h"
#include "base/gtest_prod_util.h"
#include "base/memory/ref_counted_memory.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
#if defined(OS_MACOSX) && !defined(OS_IOS)
diff --git a/chromium/ui/gfx/image/image_family.h b/chromium/ui/gfx/image/image_family.h
index 902dedeb419..c7943713676 100644
--- a/chromium/ui/gfx/image/image_family.h
+++ b/chromium/ui/gfx/image/image_family.h
@@ -9,7 +9,7 @@
#include <map>
#include <utility>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/image/image.h"
namespace gfx {
diff --git a/chromium/ui/gfx/image/image_png_rep.h b/chromium/ui/gfx/image/image_png_rep.h
index 466e37c1ac9..7e5ce5b4e41 100644
--- a/chromium/ui/gfx/image/image_png_rep.h
+++ b/chromium/ui/gfx/image/image_png_rep.h
@@ -7,7 +7,7 @@
#include "base/memory/ref_counted_memory.h"
#include "ui/base/layout.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
class Size;
diff --git a/chromium/ui/gfx/image/image_skia.h b/chromium/ui/gfx/image/image_skia.h
index 9d0e9afa88f..4bc21f877cd 100644
--- a/chromium/ui/gfx/image/image_skia.h
+++ b/chromium/ui/gfx/image/image_skia.h
@@ -11,7 +11,7 @@
#include "base/gtest_prod_util.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/image/image_skia_rep.h"
namespace gfx {
diff --git a/chromium/ui/gfx/image/image_skia_operations.h b/chromium/ui/gfx/image/image_skia_operations.h
index 9e397df7e0f..92da50ca1a9 100644
--- a/chromium/ui/gfx/image/image_skia_operations.h
+++ b/chromium/ui/gfx/image/image_skia_operations.h
@@ -7,8 +7,8 @@
#include "base/gtest_prod_util.h"
#include "skia/ext/image_operations.h"
-#include "ui/base/ui_export.h"
#include "ui/gfx/color_utils.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/shadow_value.h"
#include "ui/gfx/skbitmap_operations.h"
diff --git a/chromium/ui/gfx/image/image_skia_rep.h b/chromium/ui/gfx/image/image_skia_rep.h
index 1314215d242..6fca4111597 100644
--- a/chromium/ui/gfx/image/image_skia_rep.h
+++ b/chromium/ui/gfx/image/image_skia_rep.h
@@ -7,7 +7,7 @@
#include "third_party/skia/include/core/SkBitmap.h"
#include "ui/base/layout.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/size.h"
namespace gfx {
diff --git a/chromium/ui/gfx/image/image_skia_source.h b/chromium/ui/gfx/image/image_skia_source.h
index 1fff1358717..ed38e1c9389 100644
--- a/chromium/ui/gfx/image/image_skia_source.h
+++ b/chromium/ui/gfx/image/image_skia_source.h
@@ -6,7 +6,7 @@
#define UI_GFX_IMAGE_IMAGE_SKIA_SOURCE_H_
#include "ui/base/layout.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/image/image_skia_util_ios.h b/chromium/ui/gfx/image/image_skia_util_ios.h
index ff4468d94ce..57c9698b955 100644
--- a/chromium/ui/gfx/image/image_skia_util_ios.h
+++ b/chromium/ui/gfx/image/image_skia_util_ios.h
@@ -6,7 +6,7 @@
#define UI_GFX_IMAGE_IMAGE_SKIA_UTIL_IOS_H_
#include "ui/base/layout.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#ifdef __OBJC__
@class UIImage;
diff --git a/chromium/ui/gfx/image/image_skia_util_mac.h b/chromium/ui/gfx/image/image_skia_util_mac.h
index 1a4427da89f..10d05b045d4 100644
--- a/chromium/ui/gfx/image/image_skia_util_mac.h
+++ b/chromium/ui/gfx/image/image_skia_util_mac.h
@@ -7,7 +7,7 @@
#include <ApplicationServices/ApplicationServices.h>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#ifdef __LP64__
typedef CGSize NSSize;
diff --git a/chromium/ui/gfx/image/image_util.h b/chromium/ui/gfx/image/image_util.h
index 9ada2fe74ff..a039557a8f0 100644
--- a/chromium/ui/gfx/image/image_util.h
+++ b/chromium/ui/gfx/image/image_util.h
@@ -8,7 +8,7 @@
#include <vector>
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
class Image;
diff --git a/chromium/ui/gfx/insets.h b/chromium/ui/gfx/insets.h
index f9ef4ffc314..571751d937e 100644
--- a/chromium/ui/gfx/insets.h
+++ b/chromium/ui/gfx/insets.h
@@ -8,7 +8,7 @@
#include <string>
#include "build/build_config.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/insets_base.h"
#if defined(TOOLKIT_GTK)
diff --git a/chromium/ui/gfx/insets_base.h b/chromium/ui/gfx/insets_base.h
index bf0b48309bc..ab105bccfb8 100644
--- a/chromium/ui/gfx/insets_base.h
+++ b/chromium/ui/gfx/insets_base.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_INSETS_BASE_H_
#define UI_GFX_INSETS_BASE_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/insets_f.h b/chromium/ui/gfx/insets_f.h
index d447d941682..045b8a02e8e 100644
--- a/chromium/ui/gfx/insets_f.h
+++ b/chromium/ui/gfx/insets_f.h
@@ -8,7 +8,7 @@
#include <string>
#include "build/build_config.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/insets_base.h"
namespace gfx {
diff --git a/chromium/ui/gfx/interpolated_transform.cc b/chromium/ui/gfx/interpolated_transform.cc
index 583c27f05b9..b9698b160cd 100644
--- a/chromium/ui/gfx/interpolated_transform.cc
+++ b/chromium/ui/gfx/interpolated_transform.cc
@@ -11,7 +11,7 @@
#endif
#include "base/logging.h"
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/tween.h"
namespace {
@@ -125,7 +125,8 @@ inline float InterpolatedTransform::ValueBetween(float time,
return end_value;
float t = (time - start_time_) / (end_time_ - start_time_);
- return static_cast<float>(Tween::ValueBetween(t, start_value, end_value));
+ return static_cast<float>(
+ gfx::Tween::ValueBetween(t, start_value, end_value));
}
///////////////////////////////////////////////////////////////////////////////
diff --git a/chromium/ui/gfx/interpolated_transform_unittest.cc b/chromium/ui/gfx/interpolated_transform_unittest.cc
index dd31b8b5e2f..acea465d59a 100644
--- a/chromium/ui/gfx/interpolated_transform_unittest.cc
+++ b/chromium/ui/gfx/interpolated_transform_unittest.cc
@@ -90,10 +90,10 @@ TEST(InterpolatedTransformTest, InterpolatedRotationAboutPivot) {
CheckApproximatelyEqual(gfx::Transform(), result);
result = interpolated_xform.Interpolate(1.0f);
gfx::Point expected_result = pivot;
- result.TransformPoint(pivot);
+ result.TransformPoint(&pivot);
EXPECT_EQ(expected_result, pivot);
expected_result = gfx::Point(0, 100);
- result.TransformPoint(above_pivot);
+ result.TransformPoint(&above_pivot);
EXPECT_EQ(expected_result, above_pivot);
}
@@ -107,10 +107,10 @@ TEST(InterpolatedTransformTest, InterpolatedScaleAboutPivot) {
CheckApproximatelyEqual(gfx::Transform(), result);
result = interpolated_xform.Interpolate(1.0f);
gfx::Point expected_result = pivot;
- result.TransformPoint(pivot);
+ result.TransformPoint(&pivot);
EXPECT_EQ(expected_result, pivot);
expected_result = gfx::Point(100, 300);
- result.TransformPoint(above_pivot);
+ result.TransformPoint(&above_pivot);
EXPECT_EQ(expected_result, above_pivot);
}
diff --git a/chromium/ui/gfx/native_widget_types.h b/chromium/ui/gfx/native_widget_types.h
index faf3607db92..3d7b9d1cd3b 100644
--- a/chromium/ui/gfx/native_widget_types.h
+++ b/chromium/ui/gfx/native_widget_types.h
@@ -13,7 +13,7 @@
#include "base/basictypes.h"
#include "base/logging.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
// This file provides cross platform typedefs for native widget types.
// NativeWindow: this is a handle to a native, top-level window
@@ -43,13 +43,12 @@
// 'views'.
#if defined(USE_AURA)
-#include "ui/base/cursor/cursor.h"
-
class SkRegion;
namespace aura {
class Window;
}
namespace ui {
+class Cursor;
class Event;
}
#endif // defined(USE_AURA)
diff --git a/chromium/ui/gfx/ozone/OWNERS b/chromium/ui/gfx/ozone/OWNERS
new file mode 100644
index 00000000000..77f21b5cae7
--- /dev/null
+++ b/chromium/ui/gfx/ozone/OWNERS
@@ -0,0 +1 @@
+rjkroege@chromium.org
diff --git a/chromium/ui/base/ozone/surface_factory_ozone.cc b/chromium/ui/gfx/ozone/surface_factory_ozone.cc
index f082e7dc416..9be61f42877 100644
--- a/chromium/ui/base/ozone/surface_factory_ozone.cc
+++ b/chromium/ui/gfx/ozone/surface_factory_ozone.cc
@@ -2,11 +2,11 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/ozone/surface_factory_ozone.h"
+#include "ui/gfx/ozone/surface_factory_ozone.h"
#include <stdlib.h>
-namespace ui {
+namespace gfx {
// static
SurfaceFactoryOzone* SurfaceFactoryOzone::impl_ = NULL;
@@ -16,7 +16,7 @@ class SurfaceFactoryOzoneStub : public SurfaceFactoryOzone {
SurfaceFactoryOzoneStub() {}
virtual ~SurfaceFactoryOzoneStub() {}
- virtual void InitializeHardware() OVERRIDE {}
+ virtual HardwareState InitializeHardware() OVERRIDE { return INITIALIZED; }
virtual void ShutdownHardware() OVERRIDE {}
virtual gfx::AcceleratedWidget GetAcceleratedWidget() OVERRIDE { return 0; }
virtual gfx::AcceleratedWidget RealizeAcceleratedWidget(
@@ -57,9 +57,21 @@ const char* SurfaceFactoryOzone::DefaultDisplaySpec() {
return "720x1280*2";
}
+gfx::Screen* SurfaceFactoryOzone::CreateDesktopScreen() {
+ return NULL;
+}
+
+intptr_t SurfaceFactoryOzone::GetNativeDisplay() {
+ return 0;
+}
+
+bool SurfaceFactoryOzone::SchedulePageFlip(gfx::AcceleratedWidget) {
+ return true;
+}
+
// static
SurfaceFactoryOzone* SurfaceFactoryOzone::CreateTestHelper() {
return new SurfaceFactoryOzoneStub;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/ozone/surface_factory_ozone.h b/chromium/ui/gfx/ozone/surface_factory_ozone.h
index 50a9b4bdf59..9c5eac23b4f 100644
--- a/chromium/ui/base/ozone/surface_factory_ozone.h
+++ b/chromium/ui/gfx/ozone/surface_factory_ozone.h
@@ -2,43 +2,54 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_OZONE_SURFACE_LNUX_FACTORY_OZONE_H_
-#define UI_BASE_OZONE_SURFACE_LNUX_FACTORY_OZONE_H_
+#ifndef UI_GFX_OZONE_SURFACE_LNUX_FACTORY_OZONE_H_
+#define UI_GFX_OZONE_SURFACE_LNUX_FACTORY_OZONE_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/rect.h"
namespace gfx {
+class Screen;
class VSyncProvider;
-} // namespace gfx
-namespace ui {
-
-class SurfaceFactoryOzone {
+class GFX_EXPORT SurfaceFactoryOzone {
public:
+ // Describes the state of the hardware after initialization.
+ enum HardwareState {
+ INITIALIZED,
+ FAILED,
+ };
+
SurfaceFactoryOzone();
virtual ~SurfaceFactoryOzone();
// Returns the instance
- UI_EXPORT static SurfaceFactoryOzone* GetInstance();
+ static SurfaceFactoryOzone* GetInstance();
// Returns a display spec as in |CreateDisplayFromSpec| for the default
// native surface.
virtual const char* DefaultDisplaySpec();
// Sets the implementation delegate. Ownership is retained by the caller.
- UI_EXPORT static void SetInstance(SurfaceFactoryOzone* impl);
+ static void SetInstance(SurfaceFactoryOzone* impl);
+
+ // TODO(rjkroege): decide how to separate screen/display stuff from SFOz
+ // This method implements gfx::Screen, particularly useful in Desktop Aura.
+ virtual gfx::Screen* CreateDesktopScreen();
- // TODO(rjkroege): Add a status code if necessary.
// Configures the display hardware. Must be called from within the GPU
// process before the sandbox has been activated.
- virtual void InitializeHardware() = 0;
+ virtual HardwareState InitializeHardware() = 0;
// Cleans up display hardware state. Call this from within the GPU process.
// This method must be safe to run inside of the sandbox.
virtual void ShutdownHardware() = 0;
+ // Returns the native EGL display. This is generally needed in creating
+ // EGL windows.
+ virtual intptr_t GetNativeDisplay();
+
// Obtains an AcceleratedWidget backed by a native Linux framebuffer.
// The returned AcceleratedWidget is an opaque token that must realized
// before it can be used to create a GL surface.
@@ -60,6 +71,10 @@ class SurfaceFactoryOzone {
gfx::AcceleratedWidget w,
const gfx::Rect& bounds) = 0;
+ // Called after the appropriate GL swap buffers command. Used if extra work
+ // is needed to perform the actual buffer swap.
+ virtual bool SchedulePageFlip(gfx::AcceleratedWidget w);
+
// Returns a gfx::VsyncProvider for the provided AcceleratedWidget. Note
// that this may be called after we have entered the sandbox so if there are
// operations (e.g. opening a file descriptor providing vsync events) that
@@ -68,13 +83,12 @@ class SurfaceFactoryOzone {
virtual gfx::VSyncProvider* GetVSyncProvider(gfx::AcceleratedWidget w) = 0;
// Create a default SufaceFactoryOzone implementation useful for tests.
- UI_EXPORT static SurfaceFactoryOzone* CreateTestHelper();
+ static SurfaceFactoryOzone* CreateTestHelper();
private:
static SurfaceFactoryOzone* impl_; // not owned
};
-} // namespace ui
-
+} // namespace gfx
-#endif // UI_BASE_OZONE_SURFACE_LNUX_FACTORY_OZONE_H_
+#endif // UI_GFX_OZONE_SURFACE_LNUX_FACTORY_OZONE_H_
diff --git a/chromium/ui/gfx/pango_util.cc b/chromium/ui/gfx/pango_util.cc
index 3f96d4b140d..10bd2538742 100644
--- a/chromium/ui/gfx/pango_util.cc
+++ b/chromium/ui/gfx/pango_util.cc
@@ -34,13 +34,6 @@ namespace {
// Marker for accelerators in the text.
const gunichar kAcceleratorChar = '&';
-// Multiply by the text height to determine how much text should be faded
-// when elliding.
-const double kFadeWidthFactor = 1.5;
-
-// End state of the elliding fade.
-const double kFadeFinalAlpha = 0.15;
-
// Return |cairo_font_options|. If needed, allocate and update it.
// TODO(derat): Return font-specific options: http://crbug.com/125235
cairo_font_options_t* GetCairoFontOptions() {
@@ -321,28 +314,10 @@ void DrawPangoLayout(cairo_t* cr,
cairo_save(cr);
- // If we're not eliding, use a fixed color.
- // Otherwise, create a gradient pattern to use as the source.
- if (text_direction == base::i18n::RIGHT_TO_LEFT ||
- (flags & gfx::Canvas::NO_ELLIPSIS) ||
- text_rect.width() <= bounds.width()) {
- cairo_set_source_rgba(cr, r, g, b, a);
- } else {
- // Fade to semi-transparent to elide.
- int fade_width = static_cast<double>(text_rect.height()) * kFadeWidthFactor;
- if (fade_width > bounds.width() / 2) {
- // Don't fade more than half the text.
- fade_width = bounds.width() / 2;
- }
- int fade_x = bounds.x() + bounds.width() - fade_width;
-
- pattern = cairo_pattern_create_linear(
- fade_x, bounds.y(), bounds.x() + bounds.width(), bounds.y());
- cairo_pattern_add_color_stop_rgba(pattern, 0, r, g, b, a);
- cairo_pattern_add_color_stop_rgba(pattern, 1, r, g, b, kFadeFinalAlpha);
- cairo_set_source(cr, pattern);
- }
-
+ // Use a fixed color.
+ // Note: We do not elide (fade out the text) here, due to a bug in certain
+ // Linux environments (http://crbug.com/123104).
+ cairo_set_source_rgba(cr, r, g, b, a);
cairo_move_to(cr, text_rect.x(), text_rect.y());
pango_cairo_show_layout(cr, layout);
diff --git a/chromium/ui/gfx/pango_util.h b/chromium/ui/gfx/pango_util.h
index abb0a7d550e..840163825cd 100644
--- a/chromium/ui/gfx/pango_util.h
+++ b/chromium/ui/gfx/pango_util.h
@@ -13,7 +13,7 @@
#include "base/logging.h"
#include "base/strings/string16.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
typedef struct _PangoContext PangoContext;
diff --git a/chromium/ui/gfx/path.h b/chromium/ui/gfx/path.h
index 1e8662921c5..f1c7718f9a3 100644
--- a/chromium/ui/gfx/path.h
+++ b/chromium/ui/gfx/path.h
@@ -7,7 +7,7 @@
#include "base/basictypes.h"
#include "third_party/skia/include/core/SkPath.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
diff --git a/chromium/ui/gfx/path_win.h b/chromium/ui/gfx/path_win.h
index 6df025b1bfc..f64bc80a5ef 100644
--- a/chromium/ui/gfx/path_win.h
+++ b/chromium/ui/gfx/path_win.h
@@ -7,7 +7,7 @@
#include <windows.h>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
class SkPath;
diff --git a/chromium/ui/gfx/path_x11.h b/chromium/ui/gfx/path_x11.h
index df3ad623d33..e5a309209cc 100644
--- a/chromium/ui/gfx/path_x11.h
+++ b/chromium/ui/gfx/path_x11.h
@@ -8,7 +8,7 @@
#include <X11/Xlib.h>
#include <X11/Xregion.h>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
class SkPath;
diff --git a/chromium/ui/gfx/platform_font.h b/chromium/ui/gfx/platform_font.h
index c5f71202356..09bf8be0b3d 100644
--- a/chromium/ui/gfx/platform_font.h
+++ b/chromium/ui/gfx/platform_font.h
@@ -9,7 +9,7 @@
#include "base/memory/ref_counted.h"
#include "base/strings/string16.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
namespace gfx {
diff --git a/chromium/ui/gfx/platform_font_pango.cc b/chromium/ui/gfx/platform_font_pango.cc
index b950d23aac1..0ddf363c3f7 100644
--- a/chromium/ui/gfx/platform_font_pango.cc
+++ b/chromium/ui/gfx/platform_font_pango.cc
@@ -14,10 +14,8 @@
#include "base/strings/string_piece.h"
#include "base/strings/string_split.h"
#include "base/strings/utf_string_conversions.h"
-#include "grit/app_locale_settings.h"
#include "third_party/skia/include/core/SkPaint.h"
#include "third_party/skia/include/core/SkTypeface.h"
-#include "ui/base/l10n/l10n_util.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/gfx/pango_util.h"
@@ -60,37 +58,18 @@ std::string FindBestMatchFontFamilyName(
return font_family;
}
-// Returns a Pango font description (suitable for parsing by
-// pango_font_description_from_string()) for the default UI font.
-std::string GetDefaultFont() {
-#if !defined(TOOLKIT_GTK)
-#if defined(OS_CHROMEOS)
- return l10n_util::GetStringUTF8(IDS_UI_FONT_FAMILY_CROS);
-#else
- return "sans 10";
-#endif // defined(OS_CHROMEOS)
-#else
- GtkSettings* settings = gtk_settings_get_default();
-
- gchar* font_name = NULL;
- g_object_get(settings, "gtk-font-name", &font_name, NULL);
-
- // Temporary CHECK for helping track down
- // http://code.google.com/p/chromium/issues/detail?id=12530
- CHECK(font_name) << " Unable to get gtk-font-name for default font.";
-
- std::string default_font = std::string(font_name);
- g_free(font_name);
- return default_font;
-#endif // !defined(TOOLKIT_GTK)
-}
-
} // namespace
namespace gfx {
+// static
Font* PlatformFontPango::default_font_ = NULL;
+#if defined(OS_CHROMEOS)
+// static
+std::string* PlatformFontPango::default_font_description_ = NULL;
+#endif
+
////////////////////////////////////////////////////////////////////////////////
// PlatformFontPango, public:
@@ -154,6 +133,16 @@ void PlatformFontPango::ReloadDefaultFont() {
default_font_ = NULL;
}
+#if defined(OS_CHROMEOS)
+// static
+void PlatformFontPango::SetDefaultFontDescription(
+ const std::string& font_description) {
+ delete default_font_description_;
+ default_font_description_ = new std::string(font_description);
+}
+
+#endif
+
Font PlatformFontPango::DeriveFont(int size_delta, int style) const {
// If the delta is negative, if must not push the size below 1
if (size_delta < 0)
@@ -261,6 +250,33 @@ PlatformFontPango::PlatformFontPango(const skia::RefPtr<SkTypeface>& typeface,
PlatformFontPango::~PlatformFontPango() {}
+// static
+std::string PlatformFontPango::GetDefaultFont() {
+#if !defined(TOOLKIT_GTK)
+#if defined(OS_CHROMEOS)
+ // Font name must have been provided by way of SetDefaultFontDescription().
+ CHECK(default_font_description_);
+ return *default_font_description_;
+#else
+ return "sans 10";
+#endif // defined(OS_CHROMEOS)
+#else
+ GtkSettings* settings = gtk_settings_get_default();
+
+ gchar* font_name = NULL;
+ g_object_get(settings, "gtk-font-name", &font_name, NULL);
+
+ // Temporary CHECK for helping track down
+ // http://code.google.com/p/chromium/issues/detail?id=12530
+ CHECK(font_name) << " Unable to get gtk-font-name for default font.";
+
+ std::string default_font = std::string(font_name);
+ g_free(font_name);
+ return default_font;
+#endif // !defined(TOOLKIT_GTK)
+}
+
+
void PlatformFontPango::InitWithNameAndSize(const std::string& font_name,
int font_size) {
DCHECK_GT(font_size, 0);
diff --git a/chromium/ui/gfx/platform_font_pango.h b/chromium/ui/gfx/platform_font_pango.h
index 2fce305a1b7..1804f37ddd3 100644
--- a/chromium/ui/gfx/platform_font_pango.h
+++ b/chromium/ui/gfx/platform_font_pango.h
@@ -5,6 +5,8 @@
#ifndef UI_GFX_PLATFORM_FONT_PANGO_H_
#define UI_GFX_PLATFORM_FONT_PANGO_H_
+#include <string>
+
#include "base/compiler_specific.h"
#include "base/memory/scoped_ptr.h"
#include "skia/ext/refptr.h"
@@ -31,6 +33,11 @@ class UI_EXPORT PlatformFontPango : public PlatformFont {
// the locale has changed.
static void ReloadDefaultFont();
+#if defined(OS_CHROMEOS)
+ // Sets the default font.
+ static void SetDefaultFontDescription(const std::string& font_description);
+#endif
+
// Position as an offset from the height of the drawn text, used to draw
// an underline. This is a negative number, so the underline would be
// drawn at y + height + underline_position.
@@ -59,6 +66,10 @@ class UI_EXPORT PlatformFontPango : public PlatformFont {
int style);
virtual ~PlatformFontPango();
+ // Returns a Pango font description (suitable for parsing by
+ // pango_font_description_from_string()) for the default UI font.
+ static std::string GetDefaultFont();
+
// Initialize this object.
void InitWithNameAndSize(const std::string& font_name, int font_size);
void InitWithTypefaceNameSizeAndStyle(
@@ -102,6 +113,10 @@ class UI_EXPORT PlatformFontPango : public PlatformFont {
// The default font, used for the default constructor.
static Font* default_font_;
+#if defined(OS_CHROMEOS)
+ static std::string* default_font_description_;
+#endif
+
DISALLOW_COPY_AND_ASSIGN(PlatformFontPango);
};
diff --git a/chromium/ui/gfx/platform_font_pango_unittest.cc b/chromium/ui/gfx/platform_font_pango_unittest.cc
index 228c66b0201..f30e584c9b2 100644
--- a/chromium/ui/gfx/platform_font_pango_unittest.cc
+++ b/chromium/ui/gfx/platform_font_pango_unittest.cc
@@ -21,8 +21,10 @@ namespace gfx {
// Test that PlatformFontPango is able to cope with PangoFontDescriptions
// containing multiple font families. The first family should be preferred.
TEST(PlatformFontPangoTest, FamilyList) {
- // Needed for GLib versions prior to 2.36.
+ // Needed for GLib versions prior to 2.36, but deprecated starting 2.35.
+#if !GLIB_CHECK_VERSION(2, 35, 0)
g_type_init();
+#endif
ScopedPangoFontDescription desc(
pango_font_description_from_string("Arial,Times New Roman, 13px"));
diff --git a/chromium/ui/gfx/platform_font_win.cc b/chromium/ui/gfx/platform_font_win.cc
index 4a792f6ad86..2d4c006f268 100644
--- a/chromium/ui/gfx/platform_font_win.cc
+++ b/chromium/ui/gfx/platform_font_win.cc
@@ -17,9 +17,9 @@
#include "base/win/scoped_hdc.h"
#include "base/win/scoped_select_object.h"
#include "base/win/win_util.h"
-#include "ui/base/win/scoped_set_map_mode.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
+#include "ui/gfx/win/scoped_set_map_mode.h"
namespace {
@@ -229,7 +229,7 @@ PlatformFontWin::HFontRef* PlatformFontWin::CreateHFontRef(HFONT font) {
{
base::win::ScopedGetDC screen_dc(NULL);
base::win::ScopedSelectObject scoped_font(screen_dc, font);
- ui::ScopedSetMapMode mode(screen_dc, MM_TEXT);
+ gfx::ScopedSetMapMode mode(screen_dc, MM_TEXT);
GetTextMetrics(screen_dc, &font_metrics);
}
@@ -284,7 +284,7 @@ int PlatformFontWin::HFontRef::GetDluBaseX() {
base::win::ScopedGetDC screen_dc(NULL);
base::win::ScopedSelectObject font(screen_dc, hfont_);
- ui::ScopedSetMapMode mode(screen_dc, MM_TEXT);
+ gfx::ScopedSetMapMode mode(screen_dc, MM_TEXT);
// Yes, this is how Microsoft recommends calculating the dialog unit
// conversions. See: http://support.microsoft.com/kb/125681
diff --git a/chromium/ui/gfx/platform_font_win.h b/chromium/ui/gfx/platform_font_win.h
index 568bf952b35..ffa82499d45 100644
--- a/chromium/ui/gfx/platform_font_win.h
+++ b/chromium/ui/gfx/platform_font_win.h
@@ -9,7 +9,7 @@
#include "base/compiler_specific.h"
#include "base/memory/ref_counted.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/platform_font.h"
namespace gfx {
diff --git a/chromium/ui/gfx/point.h b/chromium/ui/gfx/point.h
index 0f8a327c5c8..cb233da5274 100644
--- a/chromium/ui/gfx/point.h
+++ b/chromium/ui/gfx/point.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_POINT_H_
#define UI_GFX_POINT_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point_base.h"
#include "ui/gfx/point_f.h"
#include "ui/gfx/vector2d.h"
diff --git a/chromium/ui/gfx/point3_f.h b/chromium/ui/gfx/point3_f.h
index 8c700df47a7..5ea0c3181f0 100644
--- a/chromium/ui/gfx/point3_f.h
+++ b/chromium/ui/gfx/point3_f.h
@@ -7,7 +7,7 @@
#include <string>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point_f.h"
#include "ui/gfx/vector3d_f.h"
diff --git a/chromium/ui/gfx/point_base.h b/chromium/ui/gfx/point_base.h
index 048b0930b2d..17f1d5183c4 100644
--- a/chromium/ui/gfx/point_base.h
+++ b/chromium/ui/gfx/point_base.h
@@ -9,7 +9,7 @@
#include "base/compiler_specific.h"
#include "build/build_config.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/point_f.h b/chromium/ui/gfx/point_f.h
index a7b841f23db..d9fc18cbbcc 100644
--- a/chromium/ui/gfx/point_f.h
+++ b/chromium/ui/gfx/point_f.h
@@ -7,7 +7,7 @@
#include <string>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point_base.h"
#include "ui/gfx/vector2d_f.h"
diff --git a/chromium/ui/gfx/quad_f.h b/chromium/ui/gfx/quad_f.h
index 4173dbe0f2f..5bbc3cd40dd 100644
--- a/chromium/ui/gfx/quad_f.h
+++ b/chromium/ui/gfx/quad_f.h
@@ -5,10 +5,11 @@
#ifndef UI_GFX_QUAD_F_H_
#define UI_GFX_QUAD_F_H_
+#include <algorithm>
#include <cmath>
#include <string>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point_f.h"
#include "ui/gfx/rect_f.h"
diff --git a/chromium/ui/base/range/OWNERS b/chromium/ui/gfx/range/OWNERS
index 14fce2ae686..14fce2ae686 100644
--- a/chromium/ui/base/range/OWNERS
+++ b/chromium/ui/gfx/range/OWNERS
diff --git a/chromium/ui/base/range/range.cc b/chromium/ui/gfx/range/range.cc
index 75325646a73..1c3968aa6e2 100644
--- a/chromium/ui/base/range/range.cc
+++ b/chromium/ui/gfx/range/range.cc
@@ -2,15 +2,16 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
+#include <algorithm>
#include <limits>
#include "base/format_macros.h"
#include "base/logging.h"
#include "base/strings/stringprintf.h"
-namespace ui {
+namespace gfx {
Range::Range()
: start_(0),
@@ -80,4 +81,8 @@ std::string Range::ToString() const {
return base::StringPrintf("{%" PRIuS ",%" PRIuS "}", start(), end());
}
+std::ostream& operator<<(std::ostream& os, const Range& range) {
+ return os << range.ToString();
+}
+
} // namespace gfx
diff --git a/chromium/ui/base/range/range.h b/chromium/ui/gfx/range/range.h
index b8bf4786824..c41c98c8d03 100644
--- a/chromium/ui/base/range/range.h
+++ b/chromium/ui/gfx/range/range.h
@@ -2,13 +2,14 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_RANGE_RANGE_H_
-#define UI_BASE_RANGE_RANGE_H_
+#ifndef UI_GFX_RANGE_RANGE_H_
+#define UI_GFX_RANGE_RANGE_H_
+#include <ostream>
#include <string>
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#if defined(OS_MACOSX)
#if __OBJC__
@@ -23,7 +24,7 @@ typedef struct _NSRange NSRange;
#include <richedit.h>
#endif
-namespace ui {
+namespace gfx {
// A Range contains two integer values that represent a numeric range, like the
// range of characters in a text selection. A range is made of a start and end
@@ -109,6 +110,8 @@ class UI_EXPORT Range {
size_t end_;
};
-} // namespace ui
+UI_EXPORT std::ostream& operator<<(std::ostream& os, const Range& range);
-#endif // UI_BASE_RANGE_RANGE_H_
+} // namespace gfx
+
+#endif // UI_GFX_RANGE_RANGE_H_
diff --git a/chromium/ui/base/range/range_mac.mm b/chromium/ui/gfx/range/range_mac.mm
index e99db374c90..3f78fb618e3 100644
--- a/chromium/ui/base/range/range_mac.mm
+++ b/chromium/ui/gfx/range/range_mac.mm
@@ -2,13 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
#include <limits>
#include "base/logging.h"
-namespace ui {
+namespace gfx {
Range::Range(const NSRange& range) {
*this = range;
diff --git a/chromium/ui/base/range/range_mac_unittest.mm b/chromium/ui/gfx/range/range_mac_unittest.mm
index 3142540f04b..c04cbfe9503 100644
--- a/chromium/ui/base/range/range_mac_unittest.mm
+++ b/chromium/ui/gfx/range/range_mac_unittest.mm
@@ -3,11 +3,11 @@
// found in the LICENSE file.
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
TEST(RangeTest, FromNSRange) {
NSRange nsr = NSMakeRange(10, 3);
- ui::Range r(nsr);
+ gfx::Range r(nsr);
EXPECT_EQ(nsr.location, r.start());
EXPECT_EQ(13U, r.end());
EXPECT_EQ(nsr.length, r.length());
@@ -16,14 +16,14 @@ TEST(RangeTest, FromNSRange) {
}
TEST(RangeTest, ToNSRange) {
- ui::Range r(10, 12);
+ gfx::Range r(10, 12);
NSRange nsr = r.ToNSRange();
EXPECT_EQ(10U, nsr.location);
EXPECT_EQ(2U, nsr.length);
}
TEST(RangeTest, ReversedToNSRange) {
- ui::Range r(20, 10);
+ gfx::Range r(20, 10);
NSRange nsr = r.ToNSRange();
EXPECT_EQ(10U, nsr.location);
EXPECT_EQ(10U, nsr.length);
@@ -31,12 +31,12 @@ TEST(RangeTest, ReversedToNSRange) {
TEST(RangeTest, FromNSRangeInvalid) {
NSRange nsr = NSMakeRange(NSNotFound, 0);
- ui::Range r(nsr);
+ gfx::Range r(nsr);
EXPECT_FALSE(r.IsValid());
}
TEST(RangeTest, ToNSRangeInvalid) {
- ui::Range r(ui::Range::InvalidRange());
+ gfx::Range r(gfx::Range::InvalidRange());
NSRange nsr = r.ToNSRange();
EXPECT_EQ(NSNotFound, nsr.location);
EXPECT_EQ(0U, nsr.length);
diff --git a/chromium/ui/base/range/range_unittest.cc b/chromium/ui/gfx/range/range_unittest.cc
index 95bc54eb843..0afaa405ca4 100644
--- a/chromium/ui/base/range/range_unittest.cc
+++ b/chromium/ui/gfx/range/range_unittest.cc
@@ -3,10 +3,10 @@
// found in the LICENSE file.
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
TEST(RangeTest, EmptyInit) {
- ui::Range r;
+ gfx::Range r;
EXPECT_EQ(0U, r.start());
EXPECT_EQ(0U, r.end());
EXPECT_EQ(0U, r.length());
@@ -18,7 +18,7 @@ TEST(RangeTest, EmptyInit) {
}
TEST(RangeTest, StartEndInit) {
- ui::Range r(10, 15);
+ gfx::Range r(10, 15);
EXPECT_EQ(10U, r.start());
EXPECT_EQ(15U, r.end());
EXPECT_EQ(5U, r.length());
@@ -30,7 +30,7 @@ TEST(RangeTest, StartEndInit) {
}
TEST(RangeTest, StartEndReversedInit) {
- ui::Range r(10, 5);
+ gfx::Range r(10, 5);
EXPECT_EQ(10U, r.start());
EXPECT_EQ(5U, r.end());
EXPECT_EQ(5U, r.length());
@@ -42,7 +42,7 @@ TEST(RangeTest, StartEndReversedInit) {
}
TEST(RangeTest, PositionInit) {
- ui::Range r(12);
+ gfx::Range r(12);
EXPECT_EQ(12U, r.start());
EXPECT_EQ(12U, r.end());
EXPECT_EQ(0U, r.length());
@@ -54,7 +54,7 @@ TEST(RangeTest, PositionInit) {
}
TEST(RangeTest, InvalidRange) {
- ui::Range r(ui::Range::InvalidRange());
+ gfx::Range r(gfx::Range::InvalidRange());
EXPECT_EQ(0U, r.length());
EXPECT_EQ(r.start(), r.end());
EXPECT_FALSE(r.is_reversed());
@@ -63,32 +63,32 @@ TEST(RangeTest, InvalidRange) {
}
TEST(RangeTest, Equality) {
- ui::Range r1(10, 4);
- ui::Range r2(10, 4);
- ui::Range r3(10, 2);
+ gfx::Range r1(10, 4);
+ gfx::Range r2(10, 4);
+ gfx::Range r3(10, 2);
EXPECT_EQ(r1, r2);
EXPECT_NE(r1, r3);
EXPECT_NE(r2, r3);
- ui::Range r4(11, 4);
+ gfx::Range r4(11, 4);
EXPECT_NE(r1, r4);
EXPECT_NE(r2, r4);
EXPECT_NE(r3, r4);
- ui::Range r5(12, 5);
+ gfx::Range r5(12, 5);
EXPECT_NE(r1, r5);
EXPECT_NE(r2, r5);
EXPECT_NE(r3, r5);
}
TEST(RangeTest, EqualsIgnoringDirection) {
- ui::Range r1(10, 5);
- ui::Range r2(5, 10);
+ gfx::Range r1(10, 5);
+ gfx::Range r2(5, 10);
EXPECT_TRUE(r1.EqualsIgnoringDirection(r2));
}
TEST(RangeTest, SetStart) {
- ui::Range r(10, 20);
+ gfx::Range r(10, 20);
EXPECT_EQ(10U, r.start());
EXPECT_EQ(10U, r.length());
@@ -100,7 +100,7 @@ TEST(RangeTest, SetStart) {
}
TEST(RangeTest, SetEnd) {
- ui::Range r(10, 13);
+ gfx::Range r(10, 13);
EXPECT_EQ(10U, r.start());
EXPECT_EQ(3U, r.length());
@@ -111,7 +111,7 @@ TEST(RangeTest, SetEnd) {
}
TEST(RangeTest, SetStartAndEnd) {
- ui::Range r;
+ gfx::Range r;
r.set_end(5);
r.set_start(1);
EXPECT_EQ(1U, r.start());
@@ -122,7 +122,7 @@ TEST(RangeTest, SetStartAndEnd) {
}
TEST(RangeTest, ReversedRange) {
- ui::Range r(10, 5);
+ gfx::Range r(10, 5);
EXPECT_EQ(10U, r.start());
EXPECT_EQ(5U, r.end());
EXPECT_EQ(5U, r.length());
@@ -133,7 +133,7 @@ TEST(RangeTest, ReversedRange) {
}
TEST(RangeTest, SetReversedRange) {
- ui::Range r(10, 20);
+ gfx::Range r(10, 20);
r.set_start(25);
EXPECT_EQ(25U, r.start());
EXPECT_EQ(20U, r.end());
@@ -150,12 +150,12 @@ TEST(RangeTest, SetReversedRange) {
EXPECT_EQ(25U, r.GetMax());
}
-void TestContainsAndIntersects(const ui::Range& r1,
- const ui::Range& r2,
- const ui::Range& r3) {
+void TestContainsAndIntersects(const gfx::Range& r1,
+ const gfx::Range& r2,
+ const gfx::Range& r3) {
EXPECT_TRUE(r1.Intersects(r1));
EXPECT_TRUE(r1.Contains(r1));
- EXPECT_EQ(ui::Range(10, 12), r1.Intersect(r1));
+ EXPECT_EQ(gfx::Range(10, 12), r1.Intersect(r1));
EXPECT_FALSE(r1.Intersects(r2));
EXPECT_FALSE(r1.Contains(r2));
@@ -168,36 +168,36 @@ void TestContainsAndIntersects(const ui::Range& r1,
EXPECT_TRUE(r3.Intersects(r1));
EXPECT_TRUE(r3.Contains(r1));
EXPECT_FALSE(r1.Contains(r3));
- EXPECT_EQ(ui::Range(10, 12), r1.Intersect(r3));
- EXPECT_EQ(ui::Range(10, 12), r3.Intersect(r1));
+ EXPECT_EQ(gfx::Range(10, 12), r1.Intersect(r3));
+ EXPECT_EQ(gfx::Range(10, 12), r3.Intersect(r1));
EXPECT_TRUE(r2.Intersects(r3));
EXPECT_TRUE(r3.Intersects(r2));
EXPECT_FALSE(r3.Contains(r2));
EXPECT_FALSE(r2.Contains(r3));
- EXPECT_EQ(ui::Range(5, 8), r2.Intersect(r3));
- EXPECT_EQ(ui::Range(5, 8), r3.Intersect(r2));
+ EXPECT_EQ(gfx::Range(5, 8), r2.Intersect(r3));
+ EXPECT_EQ(gfx::Range(5, 8), r3.Intersect(r2));
}
TEST(RangeTest, ContainAndIntersect) {
{
SCOPED_TRACE("contain and intersect");
- ui::Range r1(10, 12);
- ui::Range r2(1, 8);
- ui::Range r3(5, 12);
+ gfx::Range r1(10, 12);
+ gfx::Range r2(1, 8);
+ gfx::Range r3(5, 12);
TestContainsAndIntersects(r1, r2, r3);
}
{
SCOPED_TRACE("contain and intersect: reversed");
- ui::Range r1(12, 10);
- ui::Range r2(8, 1);
- ui::Range r3(12, 5);
+ gfx::Range r1(12, 10);
+ gfx::Range r2(8, 1);
+ gfx::Range r3(12, 5);
TestContainsAndIntersects(r1, r2, r3);
}
// Invalid rect tests
- ui::Range r1(10, 12);
- ui::Range r2(8, 1);
- ui::Range invalid = r1.Intersect(r2);
+ gfx::Range r1(10, 12);
+ gfx::Range r2(8, 1);
+ gfx::Range invalid = r1.Intersect(r2);
EXPECT_FALSE(invalid.IsValid());
EXPECT_FALSE(invalid.Contains(invalid));
EXPECT_FALSE(invalid.Contains(r1));
diff --git a/chromium/ui/base/range/range_win.cc b/chromium/ui/gfx/range/range_win.cc
index 29178b347c3..1180e1bf7a8 100644
--- a/chromium/ui/base/range/range_win.cc
+++ b/chromium/ui/gfx/range/range_win.cc
@@ -2,13 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
#include <limits>
#include "base/logging.h"
-namespace ui {
+namespace gfx {
Range::Range(const CHARRANGE& range, LONG total_length) {
// Check if this is an invalid range.
diff --git a/chromium/ui/base/range/range_win_unittest.cc b/chromium/ui/gfx/range/range_win_unittest.cc
index 4122d0668dd..f7a442c5bbf 100644
--- a/chromium/ui/base/range/range_win_unittest.cc
+++ b/chromium/ui/gfx/range/range_win_unittest.cc
@@ -3,11 +3,11 @@
// found in the LICENSE file.
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
TEST(RangeTest, FromCHARRANGE) {
CHARRANGE cr = { 10, 32 };
- ui::Range r(cr, 50);
+ gfx::Range r(cr, 50);
EXPECT_EQ(10U, r.start());
EXPECT_EQ(32U, r.end());
EXPECT_EQ(22U, r.length());
@@ -17,7 +17,7 @@ TEST(RangeTest, FromCHARRANGE) {
TEST(RangeTest, FromReversedCHARRANGE) {
CHARRANGE cr = { 20, 10 };
- ui::Range r(cr, 40);
+ gfx::Range r(cr, 40);
EXPECT_EQ(20U, r.start());
EXPECT_EQ(10U, r.end());
EXPECT_EQ(10U, r.length());
@@ -27,7 +27,7 @@ TEST(RangeTest, FromReversedCHARRANGE) {
TEST(RangeTest, FromCHARRANGETotal) {
CHARRANGE cr = { 0, -1 };
- ui::Range r(cr, 20);
+ gfx::Range r(cr, 20);
EXPECT_EQ(0U, r.start());
EXPECT_EQ(20U, r.end());
EXPECT_EQ(20U, r.length());
@@ -36,14 +36,14 @@ TEST(RangeTest, FromCHARRANGETotal) {
}
TEST(RangeTest, ToCHARRANGE) {
- ui::Range r(10, 30);
+ gfx::Range r(10, 30);
CHARRANGE cr = r.ToCHARRANGE();
EXPECT_EQ(10, cr.cpMin);
EXPECT_EQ(30, cr.cpMax);
}
TEST(RangeTest, ReversedToCHARRANGE) {
- ui::Range r(20, 10);
+ gfx::Range r(20, 10);
CHARRANGE cr = r.ToCHARRANGE();
EXPECT_EQ(20U, cr.cpMin);
EXPECT_EQ(10U, cr.cpMax);
@@ -51,12 +51,12 @@ TEST(RangeTest, ReversedToCHARRANGE) {
TEST(RangeTest, FromCHARRANGEInvalid) {
CHARRANGE cr = { -1, -1 };
- ui::Range r(cr, 30);
+ gfx::Range r(cr, 30);
EXPECT_FALSE(r.IsValid());
}
TEST(RangeTest, ToCHARRANGEInvalid) {
- ui::Range r(ui::Range::InvalidRange());
+ gfx::Range r(gfx::Range::InvalidRange());
CHARRANGE cr = r.ToCHARRANGE();
EXPECT_EQ(-1, cr.cpMin);
EXPECT_EQ(-1, cr.cpMax);
diff --git a/chromium/ui/gfx/rect_conversions.cc b/chromium/ui/gfx/rect_conversions.cc
index ac7767b3204..a54a49a23d6 100644
--- a/chromium/ui/gfx/rect_conversions.cc
+++ b/chromium/ui/gfx/rect_conversions.cc
@@ -4,6 +4,7 @@
#include "ui/gfx/rect_conversions.h"
+#include <algorithm>
#include <cmath>
#include "base/logging.h"
diff --git a/chromium/ui/gfx/render_text.cc b/chromium/ui/gfx/render_text.cc
index 1fcf18cede4..47f42e37cb6 100644
--- a/chromium/ui/gfx/render_text.cc
+++ b/chromium/ui/gfx/render_text.cc
@@ -13,12 +13,12 @@
#include "third_party/icu/source/common/unicode/utf16.h"
#include "third_party/skia/include/core/SkTypeface.h"
#include "third_party/skia/include/effects/SkGradientShader.h"
-#include "ui/base/text/text_elider.h"
-#include "ui/base/text/utf16_indexing.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/skia_util.h"
#include "ui/gfx/text_constants.h"
+#include "ui/gfx/text_elider.h"
+#include "ui/gfx/utf16_indexing.h"
namespace gfx {
@@ -288,8 +288,8 @@ StyleIterator::StyleIterator(const BreakList<SkColor>& colors,
StyleIterator::~StyleIterator() {}
-ui::Range StyleIterator::GetRange() const {
- ui::Range range(colors_.GetRange(color_));
+Range StyleIterator::GetRange() const {
+ Range range(colors_.GetRange(color_));
for (size_t i = 0; i < NUM_TEXT_STYLES; ++i)
range = range.Intersect(styles_[i].GetRange(style_[i]));
return range;
@@ -301,6 +301,14 @@ void StyleIterator::UpdatePosition(size_t position) {
style_[i] = styles_[i].GetBreak(position);
}
+LineSegment::LineSegment() : run(0) {}
+
+LineSegment::~LineSegment() {}
+
+Line::Line() : preceding_heights(0), baseline(0) {}
+
+Line::~Line() {}
+
} // namespace internal
RenderText::~RenderText() {
@@ -308,6 +316,8 @@ RenderText::~RenderText() {
void RenderText::SetText(const base::string16& text) {
DCHECK(!composition_range_.IsValid());
+ if (text_ == text)
+ return;
text_ = text;
// Adjust ranged styles and colors to accommodate a new text length.
@@ -394,9 +404,18 @@ void RenderText::SetObscuredRevealIndex(int index) {
ResetLayout();
}
+void RenderText::SetMultiline(bool multiline) {
+ if (multiline != multiline_) {
+ multiline_ = multiline;
+ cached_bounds_and_offset_valid_ = false;
+ lines_.clear();
+ }
+}
+
void RenderText::SetDisplayRect(const Rect& r) {
display_rect_ = r;
cached_bounds_and_offset_valid_ = false;
+ lines_.clear();
}
void RenderText::SetCursorPosition(size_t position) {
@@ -431,8 +450,8 @@ void RenderText::MoveCursor(BreakType break_type,
bool RenderText::MoveCursorTo(const SelectionModel& model) {
// Enforce valid selection model components.
size_t text_length = text().length();
- ui::Range range(std::min(model.selection().start(), text_length),
- std::min(model.caret_pos(), text_length));
+ Range range(std::min(model.selection().start(), text_length),
+ std::min(model.caret_pos(), text_length));
// The current model only supports caret positions at valid character indices.
if (!IsCursorablePosition(range.start()) ||
!IsCursorablePosition(range.end()))
@@ -450,9 +469,9 @@ bool RenderText::MoveCursorTo(const Point& point, bool select) {
return MoveCursorTo(position);
}
-bool RenderText::SelectRange(const ui::Range& range) {
- ui::Range sel(std::min(range.start(), text().length()),
- std::min(range.end(), text().length()));
+bool RenderText::SelectRange(const Range& range) {
+ Range sel(std::min(range.start(), text().length()),
+ std::min(range.end(), text().length()));
if (!IsCursorablePosition(sel.start()) || !IsCursorablePosition(sel.end()))
return false;
LogicalCursorDirection affinity =
@@ -476,7 +495,7 @@ void RenderText::ClearSelection() {
void RenderText::SelectAll(bool reversed) {
const size_t length = text().length();
- const ui::Range all = reversed ? ui::Range(length, 0) : ui::Range(0, length);
+ const Range all = reversed ? Range(length, 0) : Range(0, length);
const bool success = SelectRange(all);
DCHECK(success);
}
@@ -517,13 +536,13 @@ void RenderText::SelectWord() {
MoveCursorTo(reversed ? selection_min : selection_max, true);
}
-const ui::Range& RenderText::GetCompositionRange() const {
+const Range& RenderText::GetCompositionRange() const {
return composition_range_;
}
-void RenderText::SetCompositionRange(const ui::Range& composition_range) {
+void RenderText::SetCompositionRange(const Range& composition_range) {
CHECK(!composition_range.IsValid() ||
- ui::Range(0, text_.length()).Contains(composition_range));
+ Range(0, text_.length()).Contains(composition_range));
composition_range_.set_end(composition_range.end());
composition_range_.set_start(composition_range.start());
ResetLayout();
@@ -539,7 +558,7 @@ void RenderText::SetColor(SkColor value) {
#endif
}
-void RenderText::ApplyColor(SkColor value, const ui::Range& range) {
+void RenderText::ApplyColor(SkColor value, const Range& range) {
colors_.ApplyValue(value, range);
#if defined(OS_WIN)
@@ -564,9 +583,7 @@ void RenderText::SetStyle(TextStyle style, bool value) {
}
}
-void RenderText::ApplyStyle(TextStyle style,
- bool value,
- const ui::Range& range) {
+void RenderText::ApplyStyle(TextStyle style, bool value, const Range& range) {
styles_[style].ApplyValue(value, range);
// Only invalidate the layout on font changes; not for colors or decorations.
@@ -686,6 +703,10 @@ void RenderText::DrawSelectedTextForDrag(Canvas* canvas) {
Rect RenderText::GetCursorBounds(const SelectionModel& caret,
bool insert_mode) {
+ // TODO(ckocagil): Support multiline. This function should return the height
+ // of the line the cursor is on. |GetStringSize()| now returns
+ // the multiline size, eliminate its use here.
+
EnsureLayout();
size_t caret_pos = caret.caret_pos();
@@ -704,7 +725,7 @@ Rect RenderText::GetCursorBounds(const SelectionModel& caret,
} else {
size_t grapheme_start = (caret_affinity == CURSOR_FORWARD) ?
caret_pos : IndexOfAdjacentGrapheme(caret_pos, CURSOR_BACKWARD);
- ui::Range xspan(GetGlyphBounds(grapheme_start));
+ Range xspan(GetGlyphBounds(grapheme_start));
if (insert_mode) {
x = (caret_affinity == CURSOR_BACKWARD) ? xspan.end() : xspan.start();
} else { // overtype mode
@@ -745,7 +766,7 @@ size_t RenderText::IndexOfAdjacentGrapheme(size_t index,
}
SelectionModel RenderText::GetSelectionModelForSelectionStart() {
- const ui::Range& sel = selection();
+ const Range& sel = selection();
if (sel.is_empty())
return selection_model_;
return SelectionModel(sel.start(),
@@ -768,13 +789,14 @@ RenderText::RenderText()
selection_color_(kDefaultColor),
selection_background_focused_color_(kDefaultSelectionBackgroundColor),
focused_(false),
- composition_range_(ui::Range::InvalidRange()),
+ composition_range_(Range::InvalidRange()),
colors_(kDefaultColor),
styles_(NUM_TEXT_STYLES),
composition_and_selection_styles_applied_(false),
obscured_(false),
obscured_reveal_index_(-1),
truncate_length_(0),
+ multiline_(false),
fade_head_(false),
fade_tail_(false),
background_is_transparent_(false),
@@ -818,6 +840,26 @@ const base::string16& RenderText::GetLayoutText() const {
return layout_text_.empty() ? text_ : layout_text_;
}
+const BreakList<size_t>& RenderText::GetLineBreaks() {
+ if (line_breaks_.max() != 0)
+ return line_breaks_;
+
+ const string16& layout_text = GetLayoutText();
+ const size_t text_length = layout_text.length();
+ line_breaks_.SetValue(0);
+ line_breaks_.SetMax(text_length);
+ base::i18n::BreakIterator iter(layout_text,
+ base::i18n::BreakIterator::BREAK_LINE);
+ const bool success = iter.Init();
+ DCHECK(success);
+ if (success) {
+ do {
+ line_breaks_.ApplyValue(iter.pos(), Range(iter.pos(), text_length));
+ } while (iter.Advance());
+ }
+ return line_breaks_;
+}
+
void RenderText::ApplyCompositionAndSelectionStyles() {
// Save the underline and color breaks to undo the temporary styles later.
DCHECK(!composition_and_selection_styles_applied_);
@@ -830,7 +872,7 @@ void RenderText::ApplyCompositionAndSelectionStyles() {
// Apply the selected text color to the [un-reversed] selection range.
if (!selection().is_empty()) {
- const ui::Range range(selection().GetMin(), selection().GetMax());
+ const Range range(selection().GetMin(), selection().GetMax());
colors_.ApplyValue(selection_color_, range);
}
composition_and_selection_styles_applied_ = true;
@@ -844,25 +886,81 @@ void RenderText::UndoCompositionAndSelectionStyles() {
composition_and_selection_styles_applied_ = false;
}
-Vector2d RenderText::GetTextOffset() {
+Vector2d RenderText::GetLineOffset(size_t line_number) {
Vector2d offset = display_rect().OffsetFromOrigin();
- offset.Add(GetUpdatedDisplayOffset());
- offset.Add(GetAlignmentOffset());
+ // TODO(ckocagil): Apply the display offset for multiline scrolling.
+ if (!multiline())
+ offset.Add(GetUpdatedDisplayOffset());
+ else
+ offset.Add(Vector2d(0, lines_[line_number].preceding_heights));
+ offset.Add(GetAlignmentOffset(line_number));
return offset;
}
Point RenderText::ToTextPoint(const Point& point) {
- return point - GetTextOffset();
+ return point - GetLineOffset(0);
+ // TODO(ckocagil): Convert multiline view space points to text space.
}
Point RenderText::ToViewPoint(const Point& point) {
- return point + GetTextOffset();
+ if (!multiline())
+ return point + GetLineOffset(0);
+
+ // TODO(ckocagil): Traverse individual line segments for RTL support.
+ DCHECK(!lines_.empty());
+ int x = point.x();
+ size_t line = 0;
+ for (; line < lines_.size() && x > lines_[line].size.width(); ++line)
+ x -= lines_[line].size.width();
+ return Point(x, point.y()) + GetLineOffset(line);
}
-Vector2d RenderText::GetAlignmentOffset() {
+std::vector<Rect> RenderText::TextBoundsToViewBounds(const Range& x) {
+ std::vector<Rect> rects;
+
+ if (!multiline()) {
+ rects.push_back(Rect(ToViewPoint(Point(x.GetMin(), 0)),
+ Size(x.length(), GetStringSize().height())));
+ return rects;
+ }
+
+ EnsureLayout();
+
+ // Each line segment keeps its position in text coordinates. Traverse all line
+ // segments and if the segment intersects with the given range, add the view
+ // rect corresponding to the intersection to |rects|.
+ for (size_t line = 0; line < lines_.size(); ++line) {
+ int line_x = 0;
+ const Vector2d offset = GetLineOffset(line);
+ for (size_t i = 0; i < lines_[line].segments.size(); ++i) {
+ const internal::LineSegment* segment = &lines_[line].segments[i];
+ const Range intersection = segment->x_range.Intersect(x);
+ if (!intersection.is_empty()) {
+ Rect rect(line_x + intersection.start() - segment->x_range.start(),
+ 0, intersection.length(), lines_[line].size.height());
+ rects.push_back(rect + offset);
+ }
+ line_x += segment->x_range.length();
+ }
+ }
+
+ return rects;
+}
+
+Vector2d RenderText::GetAlignmentOffset(size_t line_number) {
+ // TODO(ckocagil): Enable |lines_| usage in other platforms.
+#if defined(OS_WIN)
+ DCHECK_LT(line_number, lines_.size());
+#endif
Vector2d offset;
if (horizontal_alignment_ != ALIGN_LEFT) {
- offset.set_x(display_rect().width() - GetContentWidth());
+#if defined(OS_WIN)
+ const int width = lines_[line_number].size.width() +
+ (cursor_enabled_ ? 1 : 0);
+#else
+ const int width = GetContentWidth();
+#endif
+ offset.set_x(display_rect().width() - width);
if (horizontal_alignment_ == ALIGN_CENTER)
offset.set_x(offset.x() / 2);
}
@@ -875,14 +973,13 @@ Vector2d RenderText::GetAlignmentOffset() {
}
void RenderText::ApplyFadeEffects(internal::SkiaTextRenderer* renderer) {
- if (!fade_head() && !fade_tail())
+ if (multiline() || (!fade_head() && !fade_tail()))
return;
- const int text_width = GetStringSize().width();
const int display_width = display_rect().width();
// If the text fits as-is, no need to fade.
- if (text_width <= display_width)
+ if (GetStringSize().width() <= display_width)
return;
int gradient_width = CalculateFadeGradientWidth(GetPrimaryFont(),
@@ -914,7 +1011,7 @@ void RenderText::ApplyFadeEffects(internal::SkiaTextRenderer* renderer) {
}
Rect text_rect = display_rect();
- text_rect.Inset(GetAlignmentOffset().x(), 0, 0, 0);
+ text_rect.Inset(GetAlignmentOffset(0).x(), 0, 0, 0);
// TODO(msw): Use the actual text colors corresponding to each faded part.
skia::RefPtr<SkShader> shader = CreateFadeShader(
@@ -929,29 +1026,30 @@ void RenderText::ApplyTextShadows(internal::SkiaTextRenderer* renderer) {
}
// static
-bool RenderText::RangeContainsCaret(const ui::Range& range,
+bool RenderText::RangeContainsCaret(const Range& range,
size_t caret_pos,
LogicalCursorDirection caret_affinity) {
// NB: exploits unsigned wraparound (WG14/N1124 section 6.2.5 paragraph 9).
size_t adjacent = (caret_affinity == CURSOR_BACKWARD) ?
caret_pos - 1 : caret_pos + 1;
- return range.Contains(ui::Range(caret_pos, adjacent));
+ return range.Contains(Range(caret_pos, adjacent));
}
void RenderText::MoveCursorTo(size_t position, bool select) {
size_t cursor = std::min(position, text().length());
if (IsCursorablePosition(cursor))
SetSelectionModel(SelectionModel(
- ui::Range(select ? selection().start() : cursor, cursor),
+ Range(select ? selection().start() : cursor, cursor),
(cursor == 0) ? CURSOR_FORWARD : CURSOR_BACKWARD));
}
void RenderText::UpdateLayoutText() {
layout_text_.clear();
+ line_breaks_.SetMax(0);
if (obscured_) {
size_t obscured_text_length =
- static_cast<size_t>(ui::UTF16IndexToOffset(text_, 0, text_.length()));
+ static_cast<size_t>(gfx::UTF16IndexToOffset(text_, 0, text_.length()));
layout_text_.assign(obscured_text_length, kPasswordReplacementChar);
if (obscured_reveal_index_ >= 0 &&
@@ -965,7 +1063,7 @@ void RenderText::UpdateLayoutText() {
// Gets the index in |layout_text_| to be replaced.
const size_t cp_start =
- static_cast<size_t>(ui::UTF16IndexToOffset(text_, 0, start));
+ static_cast<size_t>(gfx::UTF16IndexToOffset(text_, 0, start));
if (layout_text_.length() > cp_start)
layout_text_.replace(cp_start, 1, text_.substr(start, end - start));
}
@@ -976,7 +1074,7 @@ void RenderText::UpdateLayoutText() {
// Truncate the text at a valid character break and append an ellipsis.
icu::StringCharacterIterator iter(text.c_str());
iter.setIndex32(truncate_length_ - 1);
- layout_text_.assign(text.substr(0, iter.getIndex()) + ui::kEllipsisUTF16);
+ layout_text_.assign(text.substr(0, iter.getIndex()) + gfx::kEllipsisUTF16);
}
}
@@ -984,6 +1082,8 @@ void RenderText::UpdateCachedBoundsAndOffset() {
if (cached_bounds_and_offset_valid_)
return;
+ // TODO(ckocagil): Add support for scrolling multiline text.
+
// First, set the valid flag true to calculate the current cursor bounds using
// the stale |display_offset_|. Applying |delta_offset| at the end of this
// function will set |cursor_bounds_| and |display_offset_| to correct values.
diff --git a/chromium/ui/gfx/render_text.h b/chromium/ui/gfx/render_text.h
index 34277400b73..598f4e1d181 100644
--- a/chromium/ui/gfx/render_text.h
+++ b/chromium/ui/gfx/render_text.h
@@ -18,10 +18,10 @@
#include "third_party/skia/include/core/SkColor.h"
#include "third_party/skia/include/core/SkPaint.h"
#include "third_party/skia/include/core/SkRect.h"
-#include "ui/base/range/range.h"
#include "ui/gfx/break_list.h"
#include "ui/gfx/font_list.h"
#include "ui/gfx/point.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/selection_model.h"
#include "ui/gfx/shadow_value.h"
@@ -96,7 +96,7 @@ class StyleIterator {
bool style(TextStyle s) const { return style_[s]->second; }
// Get the intersecting range of the current iterator set.
- ui::Range GetRange() const;
+ Range GetRange() const;
// Update the iterator to point to colors and styles applicable at |position|.
void UpdatePosition(size_t position);
@@ -111,6 +111,40 @@ class StyleIterator {
DISALLOW_COPY_AND_ASSIGN(StyleIterator);
};
+// Line segments are slices of the layout text to be rendered on a single line.
+struct LineSegment {
+ LineSegment();
+ ~LineSegment();
+
+ // X coordinates of this line segment in text space.
+ Range x_range;
+
+ // The character range this segment corresponds to.
+ Range char_range;
+
+ // Index of the text run that generated this segment.
+ size_t run;
+};
+
+// A line of layout text, comprised of a line segment list and some metrics.
+struct Line {
+ Line();
+ ~Line();
+
+ // Segments that make up this line in visual order.
+ std::vector<LineSegment> segments;
+
+ // A line size is the sum of segment widths and the maximum of segment
+ // heights.
+ Size size;
+
+ // Sum of preceding lines' heights.
+ int preceding_heights;
+
+ // Maximum baseline of all segments on this line.
+ int baseline;
+};
+
} // namespace internal
// RenderText represents an abstract model of styled text and its corresponding
@@ -186,6 +220,11 @@ class UI_EXPORT RenderText {
// cleared when SetText or SetObscured is called.
void SetObscuredRevealIndex(int index);
+ // TODO(ckocagil): Multiline text rendering is currently only supported on
+ // Windows. Support other platforms.
+ bool multiline() const { return multiline_; }
+ void SetMultiline(bool multiline);
+
// Set the maximum length of the displayed layout text, not the actual text.
// A |length| of 0 forgoes a hard limit, but does not guarantee proper
// functionality of very long strings. Applies to subsequent SetText calls.
@@ -207,7 +246,7 @@ class UI_EXPORT RenderText {
const SelectionModel& selection_model() const { return selection_model_; }
- const ui::Range& selection() const { return selection_model_.selection(); }
+ const Range& selection() const { return selection_model_.selection(); }
size_t cursor_position() const { return selection_model_.caret_pos(); }
void SetCursorPosition(size_t position);
@@ -236,7 +275,7 @@ class UI_EXPORT RenderText {
// to be the text length.
// If the |range| start or end is not a cursorable position (not on grapheme
// boundary), it is a NO-OP and returns false. Otherwise, returns true.
- bool SelectRange(const ui::Range& range);
+ bool SelectRange(const Range& range);
// Returns true if the local point is over selected text.
bool IsPointInSelection(const Point& point);
@@ -254,19 +293,19 @@ class UI_EXPORT RenderText {
// boundaries.
void SelectWord();
- const ui::Range& GetCompositionRange() const;
- void SetCompositionRange(const ui::Range& composition_range);
+ const Range& GetCompositionRange() const;
+ void SetCompositionRange(const Range& composition_range);
// Set the text color over the entire text or a logical character range.
// The |range| should be valid, non-reversed, and within [0, text().length()].
void SetColor(SkColor value);
- void ApplyColor(SkColor value, const ui::Range& range);
+ void ApplyColor(SkColor value, const Range& range);
// Set various text styles over the entire text or a logical character range.
// The respective |style| is applied if |value| is true, or removed if false.
// The |range| should be valid, non-reversed, and within [0, text().length()].
void SetStyle(TextStyle style, bool value);
- void ApplyStyle(TextStyle style, bool value, const ui::Range& range);
+ void ApplyStyle(TextStyle style, bool value, const Range& range);
// Returns whether this style is enabled consistently across the entire
// RenderText.
@@ -281,14 +320,14 @@ class UI_EXPORT RenderText {
// |GetTextDirection()|, not the direction of a particular run.
VisualCursorDirection GetVisualDirectionOfLogicalEnd();
- // Returns the size in pixels of the entire string. For the height, this will
- // return the maximum height among the different fonts in the text runs.
- // Note that this returns the raw size of the string, which does not include
- // the margin area of text shadows.
+ // Returns the size required to display the current string (which is the
+ // wrapped size in multiline mode). Note that this returns the raw size of the
+ // string, which does not include the cursor or the margin area of text
+ // shadows.
virtual Size GetStringSize() = 0;
- // Returns the width of content, which reserves room for the cursor if
- // |cursor_enabled_| is true.
+ // Returns the width of the content (which is the wrapped width in multiline
+ // mode). Reserves room for the cursor if |cursor_enabled_| is true.
int GetContentWidth();
// Returns the common baseline of the text. The returned value is the vertical
@@ -335,7 +374,7 @@ class UI_EXPORT RenderText {
// Sets shadows to drawn with text.
void SetTextShadows(const ShadowValues& shadows);
- typedef std::pair<Font, ui::Range> FontSpan;
+ typedef std::pair<Font, Range> FontSpan;
// For testing purposes, returns which fonts were chosen for which parts of
// the text by returning a vector of Font and Range pairs, where each range
// specifies the character range for which the corresponding font has been
@@ -348,6 +387,9 @@ class UI_EXPORT RenderText {
const BreakList<SkColor>& colors() const { return colors_; }
const std::vector<BreakList<bool> >& styles() const { return styles_; }
+ const std::vector<internal::Line>& lines() const { return lines_; }
+ void set_lines(std::vector<internal::Line>* lines) { lines_.swap(*lines); }
+
const Vector2d& GetUpdatedDisplayOffset();
void set_cached_bounds_and_offset_valid(bool valid) {
@@ -383,7 +425,7 @@ class UI_EXPORT RenderText {
// of the glyph starting at |index|. If the glyph is RTL then the returned
// Range will have is_reversed() true. (This does not return a Rect because a
// Rect can't have a negative width.)
- virtual ui::Range GetGlyphBounds(size_t index) = 0;
+ virtual Range GetGlyphBounds(size_t index) = 0;
// Get the visual bounds containing the logical substring within the |range|.
// If |range| is empty, the result is empty. These bounds could be visually
@@ -391,7 +433,7 @@ class UI_EXPORT RenderText {
// These bounds are in local coordinates, but may be outside the visible
// region if the text is longer than the textfield. Subsequent text, cursor,
// or bounds changes may invalidate returned values.
- virtual std::vector<Rect> GetSubstringBounds(const ui::Range& range) = 0;
+ virtual std::vector<Rect> GetSubstringBounds(const Range& range) = 0;
// Convert between indices into |text_| and indices into |obscured_text_|,
// which differ when the text is obscured. Regardless of whether or not the
@@ -406,7 +448,7 @@ class UI_EXPORT RenderText {
// Reset the layout to be invalid.
virtual void ResetLayout() = 0;
- // Ensure the text is laid out.
+ // Ensure the text is laid out, lines are computed, and |lines_| is valid.
virtual void EnsureLayout() = 0;
// Draw the text.
@@ -415,22 +457,29 @@ class UI_EXPORT RenderText {
// Returns the text used for layout, which may be obscured or truncated.
const base::string16& GetLayoutText() const;
+ // Returns layout text positions that are suitable for breaking lines.
+ const BreakList<size_t>& GetLineBreaks();
+
// Apply (and undo) temporary composition underlines and selection colors.
void ApplyCompositionAndSelectionStyles();
void UndoCompositionAndSelectionStyles();
- // Returns the text offset from the origin after applying text alignment and
- // display offset.
- Vector2d GetTextOffset();
+ // Returns the line offset from the origin after applying the text alignment
+ // and the display offset.
+ Vector2d GetLineOffset(size_t line_number);
- // Convert points from the text space to the view space and back.
- // Handles the display area, display offset, and the application LTR/RTL mode.
+ // Convert points from the text space to the view space and back. Handles the
+ // display area, display offset, application LTR/RTL mode and multiline.
Point ToTextPoint(const Point& point);
Point ToViewPoint(const Point& point);
- // Returns the text offset from the origin, taking into account text alignment
+ // Convert a text space x-coordinate range to corresponding rects in view
+ // space.
+ std::vector<Rect> TextBoundsToViewBounds(const Range& x);
+
+ // Returns the line offset from the origin, accounting for text alignment
// only.
- Vector2d GetAlignmentOffset();
+ Vector2d GetAlignmentOffset(size_t line_number);
// Applies fade effects to |renderer|.
void ApplyFadeEffects(internal::SkiaTextRenderer* renderer);
@@ -440,7 +489,7 @@ class UI_EXPORT RenderText {
// A convenience function to check whether the glyph attached to the caret
// is within the given range.
- static bool RangeContainsCaret(const ui::Range& range,
+ static bool RangeContainsCaret(const Range& range,
size_t caret_pos,
LogicalCursorDirection caret_affinity);
@@ -457,6 +506,9 @@ class UI_EXPORT RenderText {
FRIEND_TEST_ALL_PREFIXES(RenderTextTest, EdgeSelectionModels);
FRIEND_TEST_ALL_PREFIXES(RenderTextTest, GetTextOffset);
FRIEND_TEST_ALL_PREFIXES(RenderTextTest, GetTextOffsetHorizontalDefaultInRTL);
+ FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Multiline_MinWidth);
+ FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Multiline_NormalWidth);
+ FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Multiline_SufficientWidth);
// Set the cursor to |position|, with the caret trailing the previous
// grapheme, or if there is no previous grapheme, leading the cursor position.
@@ -523,7 +575,7 @@ class UI_EXPORT RenderText {
bool focused_;
// Composition text range.
- ui::Range composition_range_;
+ Range composition_range_;
// Color and style breaks, used to color and stylize ranges of text.
// BreakList positions are stored with text indices, not layout indices.
@@ -547,6 +599,10 @@ class UI_EXPORT RenderText {
// The obscured and/or truncated text that will be displayed.
base::string16 layout_text_;
+ // Whether the text should be broken into multiple lines. Uses the width of
+ // |display_rect_| as the width cap.
+ bool multiline_;
+
// Fade text head and/or tail, if text doesn't fit into |display_rect_|.
bool fade_head_;
bool fade_tail_;
@@ -574,6 +630,13 @@ class UI_EXPORT RenderText {
// Text shadows to be drawn.
ShadowValues text_shadows_;
+ // A list of valid layout text line break positions.
+ BreakList<size_t> line_breaks_;
+
+ // Lines computed by EnsureLayout. These should be invalidated with
+ // ResetLayout and on |display_rect_| changes.
+ std::vector<internal::Line> lines_;
+
DISALLOW_COPY_AND_ASSIGN(RenderText);
};
diff --git a/chromium/ui/gfx/render_text_linux.cc b/chromium/ui/gfx/render_text_linux.cc
index 0178cf8368b..4b7b93474ae 100644
--- a/chromium/ui/gfx/render_text_linux.cc
+++ b/chromium/ui/gfx/render_text_linux.cc
@@ -12,11 +12,11 @@
#include "base/i18n/break_iterator.h"
#include "base/logging.h"
#include "third_party/skia/include/core/SkTypeface.h"
-#include "ui/base/text/utf16_indexing.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/gfx/font_render_params_linux.h"
#include "ui/gfx/pango_util.h"
+#include "ui/gfx/utf16_indexing.h"
namespace gfx {
@@ -40,9 +40,9 @@ bool IsForwardMotion(VisualCursorDirection direction, const PangoItem* item) {
}
// Checks whether |range| contains |index|. This is not the same as calling
-// |range.Contains(ui::Range(index))| - as that would return true when
+// |range.Contains(gfx::Range(index))| - as that would return true when
// |index| == |range.end()|.
-bool IndexInRange(const ui::Range& range, size_t index) {
+bool IndexInRange(const Range& range, size_t index) {
return index >= range.start() && index < range.end();
}
@@ -137,7 +137,7 @@ std::vector<RenderText::FontSpan> RenderTextLinux::GetFontSpansForTesting() {
PangoItem* item = reinterpret_cast<PangoLayoutRun*>(it->data)->item;
const int start = LayoutIndexToTextIndex(item->offset);
const int end = LayoutIndexToTextIndex(item->offset + item->length);
- const ui::Range range(start, end);
+ const Range range(start, end);
ScopedPangoFontDescription desc(pango_font_describe(item->analysis.font));
spans.push_back(RenderText::FontSpan(Font(desc.get()), range));
@@ -214,14 +214,14 @@ SelectionModel RenderTextLinux::AdjacentWordSelectionModel(
return cur;
}
-ui::Range RenderTextLinux::GetGlyphBounds(size_t index) {
+Range RenderTextLinux::GetGlyphBounds(size_t index) {
PangoRectangle pos;
pango_layout_index_to_pos(layout_, TextIndexToLayoutIndex(index), &pos);
// TODO(derat): Support fractional ranges for subpixel positioning?
- return ui::Range(PANGO_PIXELS(pos.x), PANGO_PIXELS(pos.x + pos.width));
+ return Range(PANGO_PIXELS(pos.x), PANGO_PIXELS(pos.x + pos.width));
}
-std::vector<Rect> RenderTextLinux::GetSubstringBounds(const ui::Range& range) {
+std::vector<Rect> RenderTextLinux::GetSubstringBounds(const Range& range) {
DCHECK_LE(range.GetMax(), text().length());
if (range.is_empty())
return std::vector<Rect>();
@@ -252,7 +252,7 @@ std::vector<Rect> RenderTextLinux::GetSubstringBounds(const ui::Range& range) {
size_t RenderTextLinux::TextIndexToLayoutIndex(size_t index) const {
DCHECK(layout_);
- ptrdiff_t offset = ui::UTF16IndexToOffset(text(), 0, index);
+ ptrdiff_t offset = gfx::UTF16IndexToOffset(text(), 0, index);
// Clamp layout indices to the length of the text actually used for layout.
offset = std::min<size_t>(offset, g_utf8_strlen(layout_text_, -1));
const char* layout_pointer = g_utf8_offset_to_pointer(layout_text_, offset);
@@ -263,7 +263,7 @@ size_t RenderTextLinux::LayoutIndexToTextIndex(size_t index) const {
DCHECK(layout_);
const char* layout_pointer = layout_text_ + index;
const long offset = g_utf8_pointer_to_offset(layout_text_, layout_pointer);
- return ui::UTF16OffsetToIndex(text(), 0, offset);
+ return gfx::UTF16OffsetToIndex(text(), 0, offset);
}
bool RenderTextLinux::IsCursorablePosition(size_t position) {
@@ -271,11 +271,11 @@ bool RenderTextLinux::IsCursorablePosition(size_t position) {
return true;
if (position >= text().length())
return position == text().length();
- if (!ui::IsValidCodePointIndex(text(), position))
+ if (!gfx::IsValidCodePointIndex(text(), position))
return false;
EnsureLayout();
- ptrdiff_t offset = ui::UTF16IndexToOffset(text(), 0, position);
+ ptrdiff_t offset = gfx::UTF16IndexToOffset(text(), 0, position);
// Check that the index corresponds with a valid text code point, that it is
// marked as a legitimate cursor position by Pango, and that it is not
// truncated from layout text (its glyph is shown on screen).
@@ -287,6 +287,7 @@ void RenderTextLinux::ResetLayout() {
// set_cached_bounds_and_offset_valid(false) is done in RenderText for every
// operation that triggers ResetLayout().
if (layout_) {
+ // TODO(msw): Keep |layout_| across text changes, etc.; it can be re-used.
g_object_unref(layout_);
layout_ = NULL;
}
@@ -306,9 +307,12 @@ void RenderTextLinux::EnsureLayout() {
if (layout_ == NULL) {
cairo_surface_t* surface =
cairo_image_surface_create(CAIRO_FORMAT_ARGB32, 0, 0);
+ CHECK_EQ(CAIRO_STATUS_SUCCESS, cairo_surface_status(surface));
cairo_t* cr = cairo_create(surface);
+ CHECK_EQ(CAIRO_STATUS_SUCCESS, cairo_status(cr));
layout_ = pango_cairo_create_layout(cr);
+ CHECK_NE(static_cast<PangoLayout*>(NULL), layout_);
cairo_destroy(cr);
cairo_surface_destroy(surface);
@@ -331,6 +335,7 @@ void RenderTextLinux::EnsureLayout() {
SetupPangoAttributes(layout_);
current_line_ = pango_layout_get_line_readonly(layout_, 0);
+ CHECK_NE(static_cast<PangoLayoutLine*>(NULL), current_line_);
pango_layout_line_ref(current_line_);
pango_layout_get_log_attrs(layout_, &log_attrs_, &num_log_attrs_);
@@ -376,7 +381,7 @@ void RenderTextLinux::DrawVisualText(Canvas* canvas) {
DCHECK(layout_);
// Skia will draw glyphs with respect to the baseline.
- Vector2d offset(GetTextOffset() + Vector2d(0, GetBaseline()));
+ Vector2d offset(GetLineOffset(0) + Vector2d(0, GetBaseline()));
SkScalar x = SkIntToScalar(offset.x());
SkScalar y = SkIntToScalar(offset.y());
@@ -428,7 +433,7 @@ void RenderTextLinux::DrawVisualText(Canvas* canvas) {
// Track the current style and its text (not layout) index range.
style.UpdatePosition(GetGlyphTextIndex(run, style_start_glyph_index));
- ui::Range style_range = style.GetRange();
+ Range style_range = style.GetRange();
do {
const PangoGlyphInfo& glyph = run->glyphs->glyphs[glyph_index];
@@ -478,7 +483,7 @@ GSList* RenderTextLinux::GetRunContainingCaret(
GSList* run = current_line_->runs;
while (run) {
PangoItem* item = reinterpret_cast<PangoLayoutRun*>(run->data)->item;
- ui::Range item_range(item->offset, item->offset + item->length);
+ Range item_range(item->offset, item->offset + item->length);
if (RangeContainsCaret(item_range, position, affinity))
return run;
run = run->next;
diff --git a/chromium/ui/gfx/render_text_linux.h b/chromium/ui/gfx/render_text_linux.h
index a2b1e665ae7..1500fc0adef 100644
--- a/chromium/ui/gfx/render_text_linux.h
+++ b/chromium/ui/gfx/render_text_linux.h
@@ -32,8 +32,8 @@ class RenderTextLinux : public RenderText {
virtual SelectionModel AdjacentWordSelectionModel(
const SelectionModel& selection,
VisualCursorDirection direction) OVERRIDE;
- virtual ui::Range GetGlyphBounds(size_t index) OVERRIDE;
- virtual std::vector<Rect> GetSubstringBounds(const ui::Range& range) OVERRIDE;
+ virtual Range GetGlyphBounds(size_t index) OVERRIDE;
+ virtual std::vector<Rect> GetSubstringBounds(const Range& range) OVERRIDE;
virtual size_t TextIndexToLayoutIndex(size_t index) const OVERRIDE;
virtual size_t LayoutIndexToTextIndex(size_t index) const OVERRIDE;
virtual bool IsCursorablePosition(size_t position) OVERRIDE;
diff --git a/chromium/ui/gfx/render_text_mac.cc b/chromium/ui/gfx/render_text_mac.cc
index c56c62638f7..2fcea01b157 100644
--- a/chromium/ui/gfx/render_text_mac.cc
+++ b/chromium/ui/gfx/render_text_mac.cc
@@ -47,8 +47,7 @@ std::vector<RenderText::FontSpan> RenderTextMac::GetFontSpansForTesting() {
for (size_t i = 0; i < runs_.size(); ++i) {
gfx::Font font(runs_[i].font_name, runs_[i].text_size);
const CFRange cf_range = CTRunGetStringRange(runs_[i].ct_run);
- const ui::Range range(cf_range.location,
- cf_range.location + cf_range.length);
+ const Range range(cf_range.location, cf_range.location + cf_range.length);
spans.push_back(RenderText::FontSpan(font, range));
}
@@ -69,12 +68,12 @@ SelectionModel RenderTextMac::AdjacentWordSelectionModel(
return SelectionModel();
}
-ui::Range RenderTextMac::GetGlyphBounds(size_t index) {
+Range RenderTextMac::GetGlyphBounds(size_t index) {
// TODO(asvitkine): Implement this. http://crbug.com/131618
- return ui::Range();
+ return Range();
}
-std::vector<Rect> RenderTextMac::GetSubstringBounds(const ui::Range& range) {
+std::vector<Rect> RenderTextMac::GetSubstringBounds(const Range& range) {
// TODO(asvitkine): Implement this. http://crbug.com/131618
return std::vector<Rect>();
}
@@ -150,7 +149,7 @@ void RenderTextMac::EnsureLayout() {
CGFloat font_list_baseline = font_list().GetBaseline();
ascent = std::max(ascent, font_list_baseline);
descent = std::max(descent, font_list_height - font_list_baseline);
- string_size_ = Size(width, ascent + descent + leading);
+ string_size_ = Size(std::ceil(width), ascent + descent + leading);
common_baseline_ = ascent;
}
@@ -249,9 +248,9 @@ void RenderTextMac::ComputeRuns() {
CFArrayRef ct_runs = CTLineGetGlyphRuns(line_);
const CFIndex ct_runs_count = CFArrayGetCount(ct_runs);
- // TODO(asvitkine): Don't use GetTextOffset() until draw time, since it may be
+ // TODO(asvitkine): Don't use GetLineOffset() until draw time, since it may be
// updated based on alignment changes without resetting the layout.
- gfx::Vector2d text_offset = GetTextOffset();
+ gfx::Vector2d text_offset = GetLineOffset(0);
// Skia will draw glyphs with respect to the baseline.
text_offset += gfx::Vector2d(0, common_baseline_);
diff --git a/chromium/ui/gfx/render_text_mac.h b/chromium/ui/gfx/render_text_mac.h
index 345fef0e98d..be5f12865c0 100644
--- a/chromium/ui/gfx/render_text_mac.h
+++ b/chromium/ui/gfx/render_text_mac.h
@@ -39,8 +39,8 @@ class RenderTextMac : public RenderText {
virtual SelectionModel AdjacentWordSelectionModel(
const SelectionModel& selection,
VisualCursorDirection direction) OVERRIDE;
- virtual ui::Range GetGlyphBounds(size_t index) OVERRIDE;
- virtual std::vector<Rect> GetSubstringBounds(const ui::Range& range) OVERRIDE;
+ virtual Range GetGlyphBounds(size_t index) OVERRIDE;
+ virtual std::vector<Rect> GetSubstringBounds(const Range& range) OVERRIDE;
virtual size_t TextIndexToLayoutIndex(size_t index) const OVERRIDE;
virtual size_t LayoutIndexToTextIndex(size_t index) const OVERRIDE;
virtual bool IsCursorablePosition(size_t position) OVERRIDE;
diff --git a/chromium/ui/gfx/render_text_unittest.cc b/chromium/ui/gfx/render_text_unittest.cc
index 263ef92d815..52cb8344b37 100644
--- a/chromium/ui/gfx/render_text_unittest.cc
+++ b/chromium/ui/gfx/render_text_unittest.cc
@@ -6,6 +6,7 @@
#include <algorithm>
+#include "base/format_macros.h"
#include "base/memory/scoped_ptr.h"
#include "base/strings/stringprintf.h"
#include "base/strings/utf_string_conversions.h"
@@ -40,9 +41,9 @@ const wchar_t kRtlLtr[] = L"\x5d0\x5d1" L"a";
const wchar_t kRtlLtrRtl[] = L"\x5d0" L"a" L"\x5d1";
// Checks whether |range| contains |index|. This is not the same as calling
-// |range.Contains(ui::Range(index))| - as that would return true when
+// |range.Contains(gfx::Range(index))| - as that would return true when
// |index| == |range.end()|.
-bool IndexInRange(const ui::Range& range, size_t index) {
+bool IndexInRange(const Range& range, size_t index) {
return index >= range.start() && index < range.end();
}
@@ -124,8 +125,8 @@ TEST_F(RenderTextTest, ApplyColorAndStyle) {
render_text->SetText(ASCIIToUTF16("012345678"));
// Apply a ranged color and style and check the resulting breaks.
- render_text->ApplyColor(SK_ColorRED, ui::Range(1, 4));
- render_text->ApplyStyle(BOLD, true, ui::Range(2, 5));
+ render_text->ApplyColor(SK_ColorRED, Range(1, 4));
+ render_text->ApplyStyle(BOLD, true, Range(2, 5));
std::vector<std::pair<size_t, SkColor> > expected_color;
expected_color.push_back(std::pair<size_t, SkColor>(0, SK_ColorBLACK));
expected_color.push_back(std::pair<size_t, SkColor>(1, SK_ColorRED));
@@ -146,8 +147,8 @@ TEST_F(RenderTextTest, ApplyColorAndStyle) {
// Apply a color and style over the text end and check the resulting breaks.
// (INT_MAX should be used instead of the text length for the range end)
const size_t text_length = render_text->text().length();
- render_text->ApplyColor(SK_ColorRED, ui::Range(0, text_length));
- render_text->ApplyStyle(BOLD, true, ui::Range(2, text_length));
+ render_text->ApplyColor(SK_ColorRED, Range(0, text_length));
+ render_text->ApplyStyle(BOLD, true, Range(2, text_length));
std::vector<std::pair<size_t, SkColor> > expected_color_end;
expected_color_end.push_back(std::pair<size_t, SkColor>(0, SK_ColorRED));
EXPECT_TRUE(render_text->colors().EqualsForTesting(expected_color_end));
@@ -157,9 +158,9 @@ TEST_F(RenderTextTest, ApplyColorAndStyle) {
EXPECT_TRUE(render_text->styles()[BOLD].EqualsForTesting(expected_style_end));
// Ensure ranged values adjust to accommodate text length changes.
- render_text->ApplyStyle(ITALIC, true, ui::Range(0, 2));
- render_text->ApplyStyle(ITALIC, true, ui::Range(3, 6));
- render_text->ApplyStyle(ITALIC, true, ui::Range(7, text_length));
+ render_text->ApplyStyle(ITALIC, true, Range(0, 2));
+ render_text->ApplyStyle(ITALIC, true, Range(3, 6));
+ render_text->ApplyStyle(ITALIC, true, Range(7, text_length));
std::vector<std::pair<size_t, bool> > expected_italic;
expected_italic.push_back(std::pair<size_t, bool>(0, true));
expected_italic.push_back(std::pair<size_t, bool>(2, false));
@@ -187,8 +188,8 @@ TEST_F(RenderTextTest, PangoAttributes) {
render_text->SetText(ASCIIToUTF16("012345678"));
// Apply ranged BOLD/ITALIC styles and check the resulting Pango attributes.
- render_text->ApplyStyle(BOLD, true, ui::Range(2, 4));
- render_text->ApplyStyle(ITALIC, true, ui::Range(1, 3));
+ render_text->ApplyStyle(BOLD, true, Range(2, 4));
+ render_text->ApplyStyle(ITALIC, true, Range(1, 3));
struct {
int start;
@@ -239,22 +240,22 @@ void TestVisualCursorMotionInObscuredField(RenderText* render_text,
render_text->SetText(text);
int len = text.length();
render_text->MoveCursor(LINE_BREAK, CURSOR_RIGHT, select);
- EXPECT_EQ(SelectionModel(ui::Range(select ? 0 : len, len), CURSOR_FORWARD),
+ EXPECT_EQ(SelectionModel(Range(select ? 0 : len, len), CURSOR_FORWARD),
render_text->selection_model());
render_text->MoveCursor(LINE_BREAK, CURSOR_LEFT, select);
EXPECT_EQ(SelectionModel(0, CURSOR_BACKWARD), render_text->selection_model());
for (int j = 1; j <= len; ++j) {
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, select);
- EXPECT_EQ(SelectionModel(ui::Range(select ? 0 : j, j), CURSOR_BACKWARD),
+ EXPECT_EQ(SelectionModel(Range(select ? 0 : j, j), CURSOR_BACKWARD),
render_text->selection_model());
}
for (int j = len - 1; j >= 0; --j) {
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, select);
- EXPECT_EQ(SelectionModel(ui::Range(select ? 0 : j, j), CURSOR_FORWARD),
+ EXPECT_EQ(SelectionModel(Range(select ? 0 : j, j), CURSOR_FORWARD),
render_text->selection_model());
}
render_text->MoveCursor(WORD_BREAK, CURSOR_RIGHT, select);
- EXPECT_EQ(SelectionModel(ui::Range(select ? 0 : len, len), CURSOR_FORWARD),
+ EXPECT_EQ(SelectionModel(Range(select ? 0 : len, len), CURSOR_FORWARD),
render_text->selection_model());
render_text->MoveCursor(WORD_BREAK, CURSOR_LEFT, select);
EXPECT_EQ(SelectionModel(0, CURSOR_BACKWARD), render_text->selection_model());
@@ -878,8 +879,8 @@ TEST_F(RenderTextTest, SelectAll) {
// Ensure that SelectAll respects the |reversed| argument regardless of
// application locale and text content directionality.
scoped_ptr<RenderText> render_text(RenderText::CreateInstance());
- const SelectionModel expected_reversed(ui::Range(3, 0), CURSOR_FORWARD);
- const SelectionModel expected_forwards(ui::Range(0, 3), CURSOR_BACKWARD);
+ const SelectionModel expected_reversed(Range(3, 0), CURSOR_FORWARD);
+ const SelectionModel expected_forwards(Range(0, 3), CURSOR_BACKWARD);
const bool was_rtl = base::i18n::IsRTL();
for (size_t i = 0; i < 2; ++i) {
@@ -906,39 +907,39 @@ TEST_F(RenderTextTest, SelectAll) {
render_text->SetText(WideToUTF16(L"abc\x05d0\x05d1\x05d2"));
// Left arrow on select ranging (6, 4).
render_text->MoveCursor(LINE_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(6), render_text->selection());
+ EXPECT_EQ(Range(6), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, false);
- EXPECT_EQ(ui::Range(4), render_text->selection());
+ EXPECT_EQ(Range(4), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, false);
- EXPECT_EQ(ui::Range(5), render_text->selection());
+ EXPECT_EQ(Range(5), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, false);
- EXPECT_EQ(ui::Range(6), render_text->selection());
+ EXPECT_EQ(Range(6), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, true);
- EXPECT_EQ(ui::Range(6, 5), render_text->selection());
+ EXPECT_EQ(Range(6, 5), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, true);
- EXPECT_EQ(ui::Range(6, 4), render_text->selection());
+ EXPECT_EQ(Range(6, 4), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, false);
- EXPECT_EQ(ui::Range(6), render_text->selection());
+ EXPECT_EQ(Range(6), render_text->selection());
// Right arrow on select ranging (4, 6).
render_text->MoveCursor(LINE_BREAK, CURSOR_LEFT, false);
- EXPECT_EQ(ui::Range(0), render_text->selection());
+ EXPECT_EQ(Range(0), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(1), render_text->selection());
+ EXPECT_EQ(Range(1), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(2), render_text->selection());
+ EXPECT_EQ(Range(2), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(3), render_text->selection());
+ EXPECT_EQ(Range(3), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(5), render_text->selection());
+ EXPECT_EQ(Range(5), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(4), render_text->selection());
+ EXPECT_EQ(Range(4), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, true);
- EXPECT_EQ(ui::Range(4, 5), render_text->selection());
+ EXPECT_EQ(Range(4, 5), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_LEFT, true);
- EXPECT_EQ(ui::Range(4, 6), render_text->selection());
+ EXPECT_EQ(Range(4, 6), render_text->selection());
render_text->MoveCursor(CHARACTER_BREAK, CURSOR_RIGHT, false);
- EXPECT_EQ(ui::Range(4), render_text->selection());
+ EXPECT_EQ(Range(4), render_text->selection());
}
#endif // !defined(OS_MACOSX)
@@ -1225,7 +1226,7 @@ TEST_F(RenderTextTest, StringSizeBoldWidth) {
EXPECT_GT(bold_width, plain_width);
// Now, apply a plain style over the first word only.
- render_text->ApplyStyle(BOLD, false, ui::Range(0, 5));
+ render_text->ApplyStyle(BOLD, false, Range(0, 5));
const int plain_bold_width = render_text->GetStringSize().width();
EXPECT_GT(plain_bold_width, plain_width);
EXPECT_LT(plain_bold_width, bold_width);
@@ -1294,7 +1295,7 @@ TEST_F(RenderTextTest, GetTextOffset) {
Rect display_rect(font_size);
render_text->SetDisplayRect(display_rect);
- Vector2d offset = render_text->GetTextOffset();
+ Vector2d offset = render_text->GetLineOffset(0);
EXPECT_TRUE(offset.IsZero());
// Set display area's size greater than font size.
@@ -1303,30 +1304,30 @@ TEST_F(RenderTextTest, GetTextOffset) {
render_text->SetDisplayRect(display_rect);
// Check the default horizontal and vertical alignment.
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(kEnlargement / 2, offset.y());
EXPECT_EQ(0, offset.x());
// Check explicitly setting the horizontal alignment.
render_text->SetHorizontalAlignment(ALIGN_LEFT);
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(0, offset.x());
render_text->SetHorizontalAlignment(ALIGN_CENTER);
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(kEnlargement / 2, offset.x());
render_text->SetHorizontalAlignment(ALIGN_RIGHT);
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(kEnlargement, offset.x());
// Check explicitly setting the vertical alignment.
render_text->SetVerticalAlignment(ALIGN_TOP);
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(0, offset.y());
render_text->SetVerticalAlignment(ALIGN_VCENTER);
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(kEnlargement / 2, offset.y());
render_text->SetVerticalAlignment(ALIGN_BOTTOM);
- offset = render_text->GetTextOffset();
+ offset = render_text->GetLineOffset(0);
EXPECT_EQ(kEnlargement, offset.y());
SetRTL(was_rtl);
@@ -1334,7 +1335,7 @@ TEST_F(RenderTextTest, GetTextOffset) {
TEST_F(RenderTextTest, GetTextOffsetHorizontalDefaultInRTL) {
// This only checks the default horizontal alignment in RTL mode; all other
- // GetTextOffset() attributes are checked by the test above.
+ // GetLineOffset(0) attributes are checked by the test above.
const bool was_rtl = base::i18n::IsRTL();
SetRTL(true);
scoped_ptr<RenderText> render_text(RenderText::CreateInstance());
@@ -1345,7 +1346,7 @@ TEST_F(RenderTextTest, GetTextOffsetHorizontalDefaultInRTL) {
render_text->GetStringSize().height());
Rect display_rect(font_size);
render_text->SetDisplayRect(display_rect);
- Vector2d offset = render_text->GetTextOffset();
+ Vector2d offset = render_text->GetLineOffset(0);
EXPECT_EQ(kEnlargement, offset.x());
SetRTL(was_rtl);
}
@@ -1464,7 +1465,7 @@ TEST_F(RenderTextTest, SelectWord) {
for (size_t i = 0; i < ARRAYSIZE_UNSAFE(cases); ++i) {
render_text->SetCursorPosition(cases[i].cursor);
render_text->SelectWord();
- EXPECT_EQ(ui::Range(cases[i].selection_start, cases[i].selection_end),
+ EXPECT_EQ(Range(cases[i].selection_start, cases[i].selection_end),
render_text->selection());
}
}
@@ -1497,13 +1498,13 @@ TEST_F(RenderTextTest, SelectMultipleWords) {
scoped_ptr<RenderText> render_text(RenderText::CreateInstance());
render_text->SetText(ASCIIToUTF16(kTestURL));
- render_text->SelectRange(ui::Range(16, 20));
+ render_text->SelectRange(Range(16, 20));
render_text->SelectWord();
EXPECT_EQ(ASCIIToUTF16("google.com"), GetSelectedText(render_text.get()));
EXPECT_FALSE(render_text->selection().is_reversed());
// SelectWord should preserve the selection direction.
- render_text->SelectRange(ui::Range(20, 16));
+ render_text->SelectRange(Range(20, 16));
render_text->SelectWord();
EXPECT_EQ(ASCIIToUTF16("google.com"), GetSelectedText(render_text.get()));
EXPECT_TRUE(render_text->selection().is_reversed());
@@ -1642,7 +1643,7 @@ TEST_F(RenderTextTest, SelectionKeepsLigatures) {
for (size_t i = 0; i < arraysize(kTestStrings); ++i) {
render_text->SetText(WideToUTF16(kTestStrings[i]));
const int expected_width = render_text->GetStringSize().width();
- render_text->MoveCursorTo(SelectionModel(ui::Range(0, 1), CURSOR_FORWARD));
+ render_text->MoveCursorTo(SelectionModel(Range(0, 1), CURSOR_FORWARD));
EXPECT_EQ(expected_width, render_text->GetStringSize().width());
// Draw the text. It shouldn't hit any DCHECKs or crash.
// See http://crbug.com/214150
@@ -1651,4 +1652,106 @@ TEST_F(RenderTextTest, SelectionKeepsLigatures) {
}
}
+#if defined(OS_WIN)
+// Ensure strings wrap onto multiple lines for a small available width.
+TEST_F(RenderTextTest, Multiline_MinWidth) {
+ const wchar_t* kTestStrings[] = { kWeak, kLtr, kLtrRtl, kLtrRtlLtr, kRtl,
+ kRtlLtr, kRtlLtrRtl };
+
+ scoped_ptr<RenderTextWin> render_text(
+ static_cast<RenderTextWin*>(RenderText::CreateInstance()));
+ render_text->SetDisplayRect(Rect(1, 1000));
+ render_text->SetMultiline(true);
+ Canvas canvas;
+
+ for (size_t i = 0; i < arraysize(kTestStrings); ++i) {
+ SCOPED_TRACE(base::StringPrintf("kTestStrings[%" PRIuS "]", i));
+ render_text->SetText(WideToUTF16(kTestStrings[i]));
+ render_text->Draw(&canvas);
+ EXPECT_GT(render_text->lines_.size(), 1U);
+ }
+}
+
+// Ensure strings wrap onto multiple lines for a normal available width.
+TEST_F(RenderTextTest, Multiline_NormalWidth) {
+ // TODO(ckocagil): Enable this test on XP.
+#if defined(OS_WIN)
+ if (base::win::GetVersion() < base::win::VERSION_VISTA)
+ return;
+#endif
+
+ const struct {
+ const wchar_t* const text;
+ const Range first_line_char_range;
+ const Range second_line_char_range;
+ } kTestStrings[] = {
+ { L"abc defg hijkl", Range(0, 9), Range(9, 14) },
+ { L"qwertyuiop", Range(0, 8), Range(8, 10) },
+ { L"\x062A\x0641\x0627\x062D\x05EA\x05E4\x05D5\x05D6\x05D9\x05DD",
+ Range(4, 10), Range(0, 4) }
+ };
+
+ scoped_ptr<RenderTextWin> render_text(
+ static_cast<RenderTextWin*>(RenderText::CreateInstance()));
+ render_text->SetDisplayRect(Rect(50, 1000));
+ render_text->SetMultiline(true);
+ Canvas canvas;
+
+ for (size_t i = 0; i < ARRAYSIZE_UNSAFE(kTestStrings); ++i) {
+ SCOPED_TRACE(base::StringPrintf("kTestStrings[%" PRIuS "]", i));
+ render_text->SetText(WideToUTF16(kTestStrings[i].text));
+ render_text->Draw(&canvas);
+ ASSERT_EQ(2U, render_text->lines_.size());
+ ASSERT_EQ(1U, render_text->lines_[0].segments.size());
+ EXPECT_EQ(kTestStrings[i].first_line_char_range,
+ render_text->lines_[0].segments[0].char_range);
+ ASSERT_EQ(1U, render_text->lines_[1].segments.size());
+ EXPECT_EQ(kTestStrings[i].second_line_char_range,
+ render_text->lines_[1].segments[0].char_range);
+ }
+}
+
+// Ensure strings don't wrap onto multiple lines for a sufficient available
+// width.
+TEST_F(RenderTextTest, Multiline_SufficientWidth) {
+ const wchar_t* kTestStrings[] = { L"", L" ", L".", L" . ", L"abc", L"a b c",
+ L"\x62E\x628\x632", L"\x62E \x628 \x632" };
+
+ scoped_ptr<RenderTextWin> render_text(
+ static_cast<RenderTextWin*>(RenderText::CreateInstance()));
+ render_text->SetDisplayRect(Rect(30, 1000));
+ render_text->SetMultiline(true);
+ Canvas canvas;
+
+ for (size_t i = 0; i < arraysize(kTestStrings); ++i) {
+ SCOPED_TRACE(base::StringPrintf("kTestStrings[%" PRIuS "]", i));
+ render_text->SetText(WideToUTF16(kTestStrings[i]));
+ render_text->Draw(&canvas);
+ EXPECT_EQ(1U, render_text->lines_.size());
+ }
+}
+#endif // defined(OS_WIN)
+
+#if defined(OS_WIN)
+TEST_F(RenderTextTest, Win_BreakRunsByUnicodeBlocks) {
+ scoped_ptr<RenderTextWin> render_text(
+ static_cast<RenderTextWin*>(RenderText::CreateInstance()));
+
+ render_text->SetText(WideToUTF16(L"x\x25B6y"));
+ render_text->EnsureLayout();
+ ASSERT_EQ(3U, render_text->runs_.size());
+ EXPECT_EQ(Range(0, 1), render_text->runs_[0]->range);
+ EXPECT_EQ(Range(1, 2), render_text->runs_[1]->range);
+ EXPECT_EQ(Range(2, 3), render_text->runs_[2]->range);
+
+ render_text->SetText(WideToUTF16(L"x \x25B6 y"));
+ render_text->EnsureLayout();
+ ASSERT_EQ(3U, render_text->runs_.size());
+ EXPECT_EQ(Range(0, 2), render_text->runs_[0]->range);
+ EXPECT_EQ(Range(2, 3), render_text->runs_[1]->range);
+ EXPECT_EQ(Range(3, 5), render_text->runs_[2]->range);
+
+}
+#endif // !defined(OS_WIN)
+
} // namespace gfx
diff --git a/chromium/ui/gfx/render_text_win.cc b/chromium/ui/gfx/render_text_win.cc
index ac018de3f44..e283de319ef 100644
--- a/chromium/ui/gfx/render_text_win.cc
+++ b/chromium/ui/gfx/render_text_win.cc
@@ -7,16 +7,18 @@
#include <algorithm>
#include "base/i18n/break_iterator.h"
+#include "base/i18n/char_iterator.h"
#include "base/i18n/rtl.h"
#include "base/logging.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "base/win/windows_version.h"
-#include "ui/base/text/utf16_indexing.h"
+#include "third_party/icu/source/common/unicode/uchar.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font_fallback_win.h"
#include "ui/gfx/font_smoothing_win.h"
#include "ui/gfx/platform_font_win.h"
+#include "ui/gfx/utf16_indexing.h"
namespace gfx {
@@ -132,28 +134,118 @@ bool IsUnicodeBidiControlCharacter(char16 c) {
// Returns the corresponding glyph range of the given character range.
// |range| is in text-space (0 corresponds to |GetLayoutText()[0]|).
// Returned value is in run-space (0 corresponds to the first glyph in the run).
-ui::Range CharRangeToGlyphRange(const internal::TextRun& run,
- const ui::Range& range) {
+Range CharRangeToGlyphRange(const internal::TextRun& run,
+ const Range& range) {
DCHECK(run.range.Contains(range));
DCHECK(!range.is_reversed());
DCHECK(!range.is_empty());
- const ui::Range run_range = ui::Range(range.start() - run.range.start(),
- range.end() - run.range.start());
- ui::Range result;
+ const Range run_range(range.start() - run.range.start(),
+ range.end() - run.range.start());
+ Range result;
if (run.script_analysis.fRTL) {
- result = ui::Range(run.logical_clusters[run_range.end() - 1],
+ result = Range(run.logical_clusters[run_range.end() - 1],
run_range.start() > 0 ? run.logical_clusters[run_range.start() - 1]
: run.glyph_count);
} else {
- result = ui::Range(run.logical_clusters[run_range.start()],
+ result = Range(run.logical_clusters[run_range.start()],
run_range.end() < run.range.length() ?
run.logical_clusters[run_range.end()] : run.glyph_count);
}
DCHECK(!result.is_reversed());
- DCHECK(ui::Range(0, run.glyph_count).Contains(result));
+ DCHECK(Range(0, run.glyph_count).Contains(result));
return result;
}
+// Starting from |start_char|, finds a suitable line break position at or before
+// |available_width| using word break info from |breaks|. If |empty_line| is
+// true, this function will not roll back to |start_char| and |*next_char| will
+// be greater than |start_char| (to avoid constructing empty lines).
+// TODO(ckocagil): Do not break ligatures and diacritics.
+// TextRun::logical_clusters might help.
+// TODO(ckocagil): We might have to reshape after breaking at ligatures.
+// See whether resolving the TODO above resolves this too.
+// TODO(ckocagil): Do not reserve width for whitespace at the end of lines.
+void BreakRunAtWidth(const internal::TextRun& run,
+ const BreakList<size_t>& breaks,
+ size_t start_char,
+ int available_width,
+ bool empty_line,
+ int* width,
+ size_t* next_char) {
+ DCHECK(run.range.Contains(Range(start_char, start_char + 1)));
+ BreakList<size_t>::const_iterator word = breaks.GetBreak(start_char);
+ BreakList<size_t>::const_iterator next_word = word + 1;
+ // Width from |std::max(word->first, start_char)| to the current character.
+ int word_width = 0;
+ *width = 0;
+
+ for (size_t i = start_char; i < run.range.end(); ++i) {
+ // |word| holds the word boundary at or before |i|, and |next_word| holds
+ // the word boundary right after |i|. Advance both |word| and |next_word|
+ // when |i| reaches |next_word|.
+ if (next_word != breaks.breaks().end() && i >= next_word->first) {
+ word = next_word++;
+ word_width = 0;
+ }
+
+ Range glyph_range = CharRangeToGlyphRange(run, Range(i, i + 1));
+ int char_width = 0;
+ for (size_t j = glyph_range.start(); j < glyph_range.end(); ++j)
+ char_width += run.advance_widths[j];
+
+ *width += char_width;
+ word_width += char_width;
+
+ if (*width > available_width) {
+ if (!empty_line || word_width < *width) {
+ *width -= word_width;
+ *next_char = std::max(word->first, start_char);
+ } else if (char_width < *width) {
+ *width -= char_width;
+ *next_char = i;
+ } else {
+ *next_char = i + 1;
+ }
+
+ return;
+ }
+ }
+
+ *next_char = run.range.end();
+}
+
+// For segments in the same run, checks the continuity and order of |x_range|
+// and |char_range| fields.
+void CheckLineIntegrity(const std::vector<internal::Line>& lines,
+ const ScopedVector<internal::TextRun>& runs) {
+ size_t previous_segment_line = 0;
+ const internal::LineSegment* previous_segment = NULL;
+
+ for (size_t i = 0; i < lines.size(); ++i) {
+ for (size_t j = 0; j < lines[i].segments.size(); ++j) {
+ const internal::LineSegment* segment = &lines[i].segments[j];
+ internal::TextRun* run = runs[segment->run];
+
+ if (!previous_segment) {
+ previous_segment = segment;
+ } else if (runs[previous_segment->run] != run) {
+ previous_segment = NULL;
+ } else {
+ DCHECK_EQ(previous_segment->char_range.end(),
+ segment->char_range.start());
+ if (!run->script_analysis.fRTL) {
+ DCHECK_EQ(previous_segment->x_range.end(), segment->x_range.start());
+ } else {
+ DCHECK_EQ(segment->x_range.end(), previous_segment->x_range.start());
+ }
+
+ previous_segment = segment;
+ previous_segment_line = i;
+ }
+ }
+ }
+}
+
} // namespace
namespace internal {
@@ -197,6 +289,183 @@ int GetGlyphXBoundary(const internal::TextRun* run,
return run->preceding_run_widths + x;
}
+// Internal class to generate Line structures. If |multiline| is true, the text
+// is broken into lines at |words| boundaries such that each line is no longer
+// than |max_width|. If |multiline| is false, only outputs a single Line from
+// the given runs. |min_baseline| and |min_height| are the minimum baseline and
+// height for each line.
+// TODO(ckocagil): Expose the interface of this class in the header and test
+// this class directly.
+class LineBreaker {
+ public:
+ LineBreaker(int max_width,
+ int min_baseline,
+ int min_height,
+ bool multiline,
+ const BreakList<size_t>* words,
+ const ScopedVector<TextRun>& runs)
+ : max_width_(max_width),
+ min_baseline_(min_baseline),
+ min_height_(min_height),
+ multiline_(multiline),
+ words_(words),
+ runs_(runs),
+ text_x_(0),
+ line_x_(0),
+ line_ascent_(0),
+ line_descent_(0) {
+ AdvanceLine();
+ }
+
+ // Breaks the run at given |run_index| into Line structs.
+ void AddRun(int run_index) {
+ const TextRun* run = runs_[run_index];
+ if (multiline_ && line_x_ + run->width > max_width_)
+ BreakRun(run_index);
+ else
+ AddSegment(run_index, run->range, run->width);
+ }
+
+ // Finishes line breaking and outputs the results. Can be called at most once.
+ void Finalize(std::vector<Line>* lines, Size* size) {
+ DCHECK(!lines_.empty());
+ // Add an empty line to finish the line size calculation and remove it.
+ AdvanceLine();
+ lines_.pop_back();
+ *size = total_size_;
+ lines->swap(lines_);
+ }
+
+ private:
+ // A (line index, segment index) pair that specifies a segment in |lines_|.
+ typedef std::pair<size_t, size_t> SegmentHandle;
+
+ LineSegment* SegmentFromHandle(const SegmentHandle& handle) {
+ return &lines_[handle.first].segments[handle.second];
+ }
+
+ // Breaks a run into segments that fit in the last line in |lines_| and adds
+ // them. Adds a new Line to the back of |lines_| whenever a new segment can't
+ // be added without the Line's width exceeding |max_width_|.
+ void BreakRun(int run_index) {
+ DCHECK(words_);
+ const TextRun* const run = runs_[run_index];
+ int width = 0;
+ size_t next_char = run->range.start();
+
+ // Break the run until it fits the current line.
+ while (next_char < run->range.end()) {
+ const size_t current_char = next_char;
+ BreakRunAtWidth(*run, *words_, current_char, max_width_ - line_x_,
+ line_x_ == 0, &width, &next_char);
+ AddSegment(run_index, Range(current_char, next_char), width);
+ if (next_char < run->range.end())
+ AdvanceLine();
+ }
+ }
+
+ // RTL runs are broken in logical order but displayed in visual order. To find
+ // the text-space coordinate (where it would fall in a single-line text)
+ // |x_range| of RTL segments, segment widths are applied in reverse order.
+ // e.g. {[5, 10], [10, 40]} will become {[35, 40], [5, 35]}.
+ void UpdateRTLSegmentRanges() {
+ if (rtl_segments_.empty())
+ return;
+ int x = SegmentFromHandle(rtl_segments_[0])->x_range.start();
+ for (size_t i = rtl_segments_.size(); i > 0; --i) {
+ LineSegment* segment = SegmentFromHandle(rtl_segments_[i - 1]);
+ const size_t segment_width = segment->x_range.length();
+ segment->x_range = Range(x, x + segment_width);
+ x += segment_width;
+ }
+ rtl_segments_.clear();
+ }
+
+ // Finishes the size calculations of the last Line in |lines_|. Adds a new
+ // Line to the back of |lines_|.
+ void AdvanceLine() {
+ if (!lines_.empty()) {
+ Line* line = &lines_.back();
+ // TODO(ckocagil): Determine optimal multiline height behavior.
+ if (line_ascent_ + line_descent_ == 0) {
+ line_ascent_ = min_baseline_;
+ line_descent_ = min_height_ - min_baseline_;
+ }
+ // Set the single-line mode Line's metrics to be at least
+ // |RenderText::font_list()| to not break the current single-line code.
+ line_ascent_ = std::max(line_ascent_, min_baseline_);
+ line_descent_ = std::max(line_descent_, min_height_ - min_baseline_);
+
+ line->baseline = line_ascent_;
+ line->size.set_height(line_ascent_ + line_descent_);
+ line->preceding_heights = total_size_.height();
+ total_size_.set_height(total_size_.height() + line->size.height());
+ total_size_.set_width(std::max(total_size_.width(), line->size.width()));
+ }
+ line_x_ = 0;
+ line_ascent_ = 0;
+ line_descent_ = 0;
+ lines_.push_back(Line());
+ }
+
+ // Adds a new segment with the given properties to |lines_.back()|.
+ void AddSegment(int run_index, Range char_range, int width) {
+ if (char_range.is_empty()) {
+ DCHECK_EQ(width, 0);
+ return;
+ }
+ const TextRun* run = runs_[run_index];
+ line_ascent_ = std::max(line_ascent_, run->font.GetBaseline());
+ line_descent_ = std::max(line_descent_,
+ run->font.GetHeight() - run->font.GetBaseline());
+
+ LineSegment segment;
+ segment.run = run_index;
+ segment.char_range = char_range;
+ segment.x_range = Range(text_x_, text_x_ + width);
+
+ Line* line = &lines_.back();
+ line->segments.push_back(segment);
+ line->size.set_width(line->size.width() + segment.x_range.length());
+ if (run->script_analysis.fRTL) {
+ rtl_segments_.push_back(SegmentHandle(lines_.size() - 1,
+ line->segments.size() - 1));
+ // If this is the last segment of an RTL run, reprocess the text-space x
+ // ranges of all segments from the run.
+ if (char_range.end() == run->range.end())
+ UpdateRTLSegmentRanges();
+ }
+ text_x_ += width;
+ line_x_ += width;
+ }
+
+ const int max_width_;
+ const int min_baseline_;
+ const int min_height_;
+ const bool multiline_;
+ const BreakList<size_t>* const words_;
+ const ScopedVector<TextRun>& runs_;
+
+ // Stores the resulting lines.
+ std::vector<Line> lines_;
+
+ // Text space and line space x coordinates of the next segment to be added.
+ int text_x_;
+ int line_x_;
+
+ // Size of the multiline text, not including the currently processed line.
+ Size total_size_;
+
+ // Ascent and descent values of the current line, |lines_.back()|.
+ int line_ascent_;
+ int line_descent_;
+
+ // The current RTL run segments, to be applied by |UpdateRTLSegmentRanges()|.
+ std::vector<SegmentHandle> rtl_segments_;
+
+ DISALLOW_COPY_AND_ASSIGN(LineBreaker);
+};
+
} // namespace internal
// static
@@ -207,7 +476,6 @@ std::map<std::string, Font> RenderTextWin::successful_substitute_fonts_;
RenderTextWin::RenderTextWin()
: RenderText(),
- common_baseline_(0),
needs_layout_(false) {
set_truncate_length(kMaxUniscribeTextLength);
@@ -222,12 +490,12 @@ RenderTextWin::~RenderTextWin() {
Size RenderTextWin::GetStringSize() {
EnsureLayout();
- return string_size_;
+ return multiline_string_size_;
}
int RenderTextWin::GetBaseline() {
EnsureLayout();
- return common_baseline_;
+ return lines()[0].baseline;
}
SelectionModel RenderTextWin::FindCursorPosition(const Point& point) {
@@ -266,8 +534,8 @@ std::vector<RenderText::FontSpan> RenderTextWin::GetFontSpansForTesting() {
std::vector<RenderText::FontSpan> spans;
for (size_t i = 0; i < runs_.size(); ++i) {
spans.push_back(RenderText::FontSpan(runs_[i]->font,
- ui::Range(LayoutIndexToTextIndex(runs_[i]->range.start()),
- LayoutIndexToTextIndex(runs_[i]->range.end()))));
+ Range(LayoutIndexToTextIndex(runs_[i]->range.start()),
+ LayoutIndexToTextIndex(runs_[i]->range.end()))));
}
return spans;
@@ -364,54 +632,61 @@ SelectionModel RenderTextWin::AdjacentWordSelectionModel(
return SelectionModel(pos, CURSOR_FORWARD);
}
-ui::Range RenderTextWin::GetGlyphBounds(size_t index) {
+Range RenderTextWin::GetGlyphBounds(size_t index) {
const size_t run_index =
GetRunContainingCaret(SelectionModel(index, CURSOR_FORWARD));
// Return edge bounds if the index is invalid or beyond the layout text size.
if (run_index >= runs_.size())
- return ui::Range(string_size_.width());
+ return Range(string_width_);
internal::TextRun* run = runs_[run_index];
const size_t layout_index = TextIndexToLayoutIndex(index);
- return ui::Range(GetGlyphXBoundary(run, layout_index, false),
- GetGlyphXBoundary(run, layout_index, true));
+ return Range(GetGlyphXBoundary(run, layout_index, false),
+ GetGlyphXBoundary(run, layout_index, true));
}
-std::vector<Rect> RenderTextWin::GetSubstringBounds(const ui::Range& range) {
+std::vector<Rect> RenderTextWin::GetSubstringBounds(const Range& range) {
DCHECK(!needs_layout_);
- DCHECK(ui::Range(0, text().length()).Contains(range));
- ui::Range layout_range(TextIndexToLayoutIndex(range.start()),
- TextIndexToLayoutIndex(range.end()));
- DCHECK(ui::Range(0, GetLayoutText().length()).Contains(layout_range));
+ DCHECK(Range(0, text().length()).Contains(range));
+ Range layout_range(TextIndexToLayoutIndex(range.start()),
+ TextIndexToLayoutIndex(range.end()));
+ DCHECK(Range(0, GetLayoutText().length()).Contains(layout_range));
- std::vector<Rect> bounds;
+ std::vector<Rect> rects;
if (layout_range.is_empty())
- return bounds;
+ return rects;
+ std::vector<Range> bounds;
- // Add a Rect for each run/selection intersection.
+ // Add a Range for each run/selection intersection.
// TODO(msw): The bounds should probably not always be leading the range ends.
for (size_t i = 0; i < runs_.size(); ++i) {
const internal::TextRun* run = runs_[visual_to_logical_[i]];
- ui::Range intersection = run->range.Intersect(layout_range);
+ Range intersection = run->range.Intersect(layout_range);
if (intersection.IsValid()) {
DCHECK(!intersection.is_reversed());
- ui::Range range_x(GetGlyphXBoundary(run, intersection.start(), false),
- GetGlyphXBoundary(run, intersection.end(), false));
- Rect rect(range_x.GetMin(), 0, range_x.length(), run->font.GetHeight());
- rect.set_origin(ToViewPoint(rect.origin()));
- // Union this with the last rect if they're adjacent.
- if (!bounds.empty() && rect.SharesEdgeWith(bounds.back())) {
- rect.Union(bounds.back());
+ Range range_x(GetGlyphXBoundary(run, intersection.start(), false),
+ GetGlyphXBoundary(run, intersection.end(), false));
+ if (range_x.is_empty())
+ continue;
+ range_x = Range(range_x.GetMin(), range_x.GetMax());
+ // Union this with the last range if they're adjacent.
+ DCHECK(bounds.empty() || bounds.back().GetMax() <= range_x.GetMin());
+ if (!bounds.empty() && bounds.back().GetMax() == range_x.GetMin()) {
+ range_x = Range(bounds.back().GetMin(), range_x.GetMax());
bounds.pop_back();
}
- bounds.push_back(rect);
+ bounds.push_back(range_x);
}
}
- return bounds;
+ for (size_t i = 0; i < bounds.size(); ++i) {
+ std::vector<Rect> current_rects = TextBoundsToViewBounds(bounds[i]);
+ rects.insert(rects.end(), current_rects.begin(), current_rects.end());
+ }
+ return rects;
}
size_t RenderTextWin::TextIndexToLayoutIndex(size_t index) const {
DCHECK_LE(index, text().length());
- ptrdiff_t i = obscured() ? ui::UTF16IndexToOffset(text(), 0, index) : index;
+ ptrdiff_t i = obscured() ? gfx::UTF16IndexToOffset(text(), 0, index) : index;
CHECK_GE(i, 0);
// Clamp layout indices to the length of the text actually used for layout.
return std::min<size_t>(GetLayoutText().length(), i);
@@ -422,7 +697,7 @@ size_t RenderTextWin::LayoutIndexToTextIndex(size_t index) const {
return index;
DCHECK_LE(index, GetLayoutText().length());
- const size_t text_index = ui::UTF16OffsetToIndex(text(), 0, index);
+ const size_t text_index = gfx::UTF16OffsetToIndex(text(), 0, index);
DCHECK_LE(text_index, text().length());
return text_index;
}
@@ -437,7 +712,7 @@ bool RenderTextWin::IsCursorablePosition(size_t position) {
// and that its glyph has distinct bounds (not mid-multi-character-grapheme).
// An example of a multi-character-grapheme that is not a surrogate-pair is:
// \x0915\x093f - (ki) - one of many Devanagari biconsonantal conjuncts.
- return ui::IsValidCodePointIndex(text(), position) &&
+ return gfx::IsValidCodePointIndex(text(), position) &&
position < LayoutIndexToTextIndex(GetLayoutText().length()) &&
GetGlyphBounds(position) != GetGlyphBounds(position - 1);
}
@@ -448,23 +723,40 @@ void RenderTextWin::ResetLayout() {
}
void RenderTextWin::EnsureLayout() {
- if (!needs_layout_)
- return;
- // TODO(msw): Skip complex processing if ScriptIsComplex returns false.
- ItemizeLogicalText();
- if (!runs_.empty())
- LayoutVisualText();
- needs_layout_ = false;
+ if (needs_layout_) {
+ // TODO(msw): Skip complex processing if ScriptIsComplex returns false.
+ ItemizeLogicalText();
+ if (!runs_.empty())
+ LayoutVisualText();
+ needs_layout_ = false;
+ std::vector<internal::Line> lines;
+ set_lines(&lines);
+ }
+
+ // Compute lines if they're not valid. This is separate from the layout steps
+ // above to avoid text layout and shaping when we resize |display_rect_|.
+ if (lines().empty()) {
+ DCHECK(!needs_layout_);
+ std::vector<internal::Line> lines;
+ internal::LineBreaker line_breaker(display_rect().width() - 1,
+ font_list().GetBaseline(),
+ font_list().GetHeight(), multiline(),
+ multiline() ? &GetLineBreaks() : NULL,
+ runs_);
+ for (size_t i = 0; i < runs_.size(); ++i)
+ line_breaker.AddRun(visual_to_logical_[i]);
+ line_breaker.Finalize(&lines, &multiline_string_size_);
+ DCHECK(!lines.empty());
+#ifndef NDEBUG
+ CheckLineIntegrity(lines, runs_);
+#endif
+ set_lines(&lines);
+ }
}
void RenderTextWin::DrawVisualText(Canvas* canvas) {
DCHECK(!needs_layout_);
-
- // Skia will draw glyphs with respect to the baseline.
- Vector2d offset(GetTextOffset() + Vector2d(0, common_baseline_));
-
- SkScalar x = SkIntToScalar(offset.x());
- SkScalar y = SkIntToScalar(offset.y());
+ DCHECK(!lines().empty());
std::vector<SkPoint> pos;
@@ -481,52 +773,79 @@ void RenderTextWin::DrawVisualText(Canvas* canvas) {
ApplyCompositionAndSelectionStyles();
- for (size_t i = 0; i < runs_.size(); ++i) {
- // Get the run specified by the visual-to-logical map.
- internal::TextRun* run = runs_[visual_to_logical_[i]];
+ for (size_t i = 0; i < lines().size(); ++i) {
+ const internal::Line& line = lines()[i];
+ const Vector2d line_offset = GetLineOffset(i);
- // Skip painting empty runs and runs outside the display rect area.
- if ((run->glyph_count == 0) || (x >= display_rect().right()) ||
- (x + run->width <= display_rect().x())) {
- x += run->width;
+ // Skip painting empty lines or lines outside the display rect area.
+ if (!display_rect().Intersects(Rect(PointAtOffsetFromOrigin(line_offset),
+ line.size)))
continue;
- }
- // Based on WebCore::skiaDrawText. |pos| contains the positions of glyphs.
- // An extra terminal |pos| entry is added to simplify width calculations.
- pos.resize(run->glyph_count + 1);
- SkScalar glyph_x = x;
- for (int glyph = 0; glyph < run->glyph_count; glyph++) {
- pos[glyph].set(glyph_x + run->offsets[glyph].du,
- y + run->offsets[glyph].dv);
- glyph_x += SkIntToScalar(run->advance_widths[glyph]);
- }
- pos.back().set(glyph_x, y);
-
- renderer.SetTextSize(run->font.GetFontSize());
- renderer.SetFontFamilyWithStyle(run->font.GetFontName(), run->font_style);
-
- for (BreakList<SkColor>::const_iterator it =
- colors().GetBreak(run->range.start());
- it != colors().breaks().end() && it->first < run->range.end();
- ++it) {
- const ui::Range glyph_range = CharRangeToGlyphRange(*run,
- colors().GetRange(it).Intersect(run->range));
- if (glyph_range.is_empty())
- continue;
- renderer.SetForegroundColor(it->second);
- renderer.DrawPosText(&pos[glyph_range.start()],
- &run->glyphs[glyph_range.start()],
- glyph_range.length());
- const SkScalar width = pos[glyph_range.end()].x() -
- pos[glyph_range.start()].x();
- renderer.DrawDecorations(pos[glyph_range.start()].x(), y,
- SkScalarCeilToInt(width), run->underline,
- run->strike, run->diagonal_strike);
- }
+ const Vector2d text_offset = line_offset + Vector2d(0, line.baseline);
+ int preceding_segment_widths = 0;
+
+ for (size_t j = 0; j < line.segments.size(); ++j) {
+ const internal::LineSegment* segment = &line.segments[j];
+ const int segment_width = segment->x_range.length();
+ const internal::TextRun* run = runs_[segment->run];
+ DCHECK(!segment->char_range.is_empty());
+ DCHECK(run->range.Contains(segment->char_range));
+ Range glyph_range = CharRangeToGlyphRange(*run, segment->char_range);
+ DCHECK(!glyph_range.is_empty());
+ // Skip painting segments outside the display rect area.
+ if (!multiline()) {
+ const Rect segment_bounds(PointAtOffsetFromOrigin(line_offset) +
+ Vector2d(preceding_segment_widths, 0),
+ Size(segment_width, line.size.height()));
+ if (!display_rect().Intersects(segment_bounds)) {
+ preceding_segment_widths += segment_width;
+ continue;
+ }
+ }
- DCHECK_EQ(glyph_x - x, run->width);
- x = glyph_x;
+ // |pos| contains the positions of glyphs. An extra terminal |pos| entry
+ // is added to simplify width calculations.
+ int segment_x = preceding_segment_widths;
+ pos.resize(glyph_range.length() + 1);
+ for (size_t k = glyph_range.start(); k < glyph_range.end(); ++k) {
+ pos[k - glyph_range.start()].set(
+ SkIntToScalar(text_offset.x() + run->offsets[k].du + segment_x),
+ SkIntToScalar(text_offset.y() + run->offsets[k].dv));
+ segment_x += run->advance_widths[k];
+ }
+ pos.back().set(SkIntToScalar(text_offset.x() + segment_x),
+ SkIntToScalar(text_offset.y()));
+
+ renderer.SetTextSize(run->font.GetFontSize());
+ renderer.SetFontFamilyWithStyle(run->font.GetFontName(), run->font_style);
+
+ for (BreakList<SkColor>::const_iterator it =
+ colors().GetBreak(segment->char_range.start());
+ it != colors().breaks().end() &&
+ it->first < segment->char_range.end();
+ ++it) {
+ const Range intersection =
+ colors().GetRange(it).Intersect(segment->char_range);
+ const Range colored_glyphs = CharRangeToGlyphRange(*run, intersection);
+ DCHECK(glyph_range.Contains(colored_glyphs));
+ DCHECK(!colored_glyphs.is_empty());
+ const SkPoint& start_pos =
+ pos[colored_glyphs.start() - glyph_range.start()];
+ const SkPoint& end_pos =
+ pos[colored_glyphs.end() - glyph_range.start()];
+
+ renderer.SetForegroundColor(it->second);
+ renderer.DrawPosText(&start_pos, &run->glyphs[colored_glyphs.start()],
+ colored_glyphs.length());
+ renderer.DrawDecorations(start_pos.x(), text_offset.y(),
+ SkScalarCeilToInt(end_pos.x() - start_pos.x()),
+ run->underline, run->strike,
+ run->diagonal_strike);
+ }
+
+ preceding_segment_widths += segment_width;
+ }
}
UndoCompositionAndSelectionStyles();
@@ -534,22 +853,21 @@ void RenderTextWin::DrawVisualText(Canvas* canvas) {
void RenderTextWin::ItemizeLogicalText() {
runs_.clear();
- // Make |string_size_|'s height and |common_baseline_| tall enough to draw
- // often-used characters which are rendered with fonts in the font list.
- string_size_ = Size(0, font_list().GetHeight());
- common_baseline_ = font_list().GetBaseline();
+ string_width_ = 0;
+ multiline_string_size_ = Size();
// Set Uniscribe's base text direction.
script_state_.uBidiLevel =
(GetTextDirection() == base::i18n::RIGHT_TO_LEFT) ? 1 : 0;
- if (text().empty())
+ const base::string16& layout_text = GetLayoutText();
+ if (layout_text.empty())
return;
HRESULT hr = E_OUTOFMEMORY;
int script_items_count = 0;
std::vector<SCRIPT_ITEM> script_items;
- const size_t layout_text_length = GetLayoutText().length();
+ const size_t layout_text_length = layout_text.length();
// Ensure that |kMaxRuns| is attempted and the loop terminates afterward.
for (size_t runs = kGuessRuns; hr == E_OUTOFMEMORY && runs <= kMaxRuns;
runs = std::max(runs + 1, std::min(runs * 2, kMaxRuns))) {
@@ -557,9 +875,9 @@ void RenderTextWin::ItemizeLogicalText() {
// ScriptItemize always adds a terminal array item so that the length of
// the last item can be derived from the terminal SCRIPT_ITEM::iCharPos.
script_items.resize(runs);
- hr = ScriptItemize(GetLayoutText().c_str(), layout_text_length,
- runs - 1, &script_control_, &script_state_,
- &script_items[0], &script_items_count);
+ hr = ScriptItemize(layout_text.c_str(), layout_text_length, runs - 1,
+ &script_control_, &script_state_, &script_items[0],
+ &script_items_count);
}
DCHECK(SUCCEEDED(hr));
if (!SUCCEEDED(hr) || script_items_count <= 0)
@@ -571,7 +889,7 @@ void RenderTextWin::ItemizeLogicalText() {
// Build the list of runs from the script items and ranged styles. Use an
// empty color BreakList to avoid breaking runs at color boundaries.
BreakList<SkColor> empty_colors;
- empty_colors.SetMax(text().length());
+ empty_colors.SetMax(layout_text_length);
internal::StyleIterator style(empty_colors, styles());
SCRIPT_ITEM* script_item = &script_items[0];
const size_t max_run_length = kMaxGlyphs / 2;
@@ -592,9 +910,32 @@ void RenderTextWin::ItemizeLogicalText() {
const size_t script_item_break = (script_item + 1)->iCharPos;
run_break = std::min(script_item_break,
TextIndexToLayoutIndex(style.GetRange().end()));
+
// Clamp run lengths to avoid exceeding the maximum supported glyph count.
- if ((run_break - run->range.start()) > max_run_length)
+ if ((run_break - run->range.start()) > max_run_length) {
run_break = run->range.start() + max_run_length;
+ if (!gfx::IsValidCodePointIndex(layout_text, run_break))
+ --run_break;
+ }
+
+ // Break runs between characters in different code blocks. This avoids using
+ // fallback fonts for more characters than needed. http://crbug.com/278913
+ if (run_break > run->range.start()) {
+ const size_t run_start = run->range.start();
+ const int32 run_length = static_cast<int32>(run_break - run_start);
+ base::i18n::UTF16CharIterator iter(layout_text.c_str() + run_start,
+ run_length);
+ const UBlockCode first_block_code = ublock_getCode(iter.get());
+ while (iter.Advance() && iter.array_pos() < run_length) {
+ if (ublock_getCode(iter.get()) != first_block_code) {
+ run_break = run_start + iter.array_pos();
+ break;
+ }
+ }
+ }
+
+ DCHECK(gfx::IsValidCodePointIndex(layout_text, run_break));
+
style.UpdatePosition(LayoutIndexToTextIndex(run_break));
if (script_item_break == run_break)
script_item++;
@@ -643,8 +984,6 @@ void RenderTextWin::LayoutVisualText() {
DCHECK(SUCCEEDED(hr));
}
}
- string_size_.set_height(ascent + descent);
- common_baseline_ = ascent;
// Build the array of bidirectional embedding levels.
scoped_ptr<BYTE[]> levels(new BYTE[runs_.size()]);
@@ -669,7 +1008,7 @@ void RenderTextWin::LayoutVisualText() {
run->width = abc.abcA + abc.abcB + abc.abcC;
preceding_run_widths += run->width;
}
- string_size_.set_width(preceding_run_widths);
+ string_width_ = preceding_run_widths;
}
void RenderTextWin::LayoutTextRun(internal::TextRun* run) {
@@ -684,7 +1023,6 @@ void RenderTextWin::LayoutTextRun(internal::TextRun* run) {
// in the case where no font is able to display the entire run.
int best_partial_font_missing_char_count = INT_MAX;
Font best_partial_font = original_font;
- bool using_best_partial_font = false;
Font current_font;
run->logical_clusters.reset(new WORD[run_length]);
diff --git a/chromium/ui/gfx/render_text_win.h b/chromium/ui/gfx/render_text_win.h
index 620ef092dff..423e31fcad5 100644
--- a/chromium/ui/gfx/render_text_win.h
+++ b/chromium/ui/gfx/render_text_win.h
@@ -23,7 +23,7 @@ struct TextRun {
TextRun();
~TextRun();
- ui::Range range;
+ Range range;
Font font;
// A gfx::Font::FontStyle flag to specify bold and italic styles.
// Supersedes |font.GetFontStyle()|. Stored separately to avoid calling
@@ -76,8 +76,8 @@ class RenderTextWin : public RenderText {
virtual SelectionModel AdjacentWordSelectionModel(
const SelectionModel& selection,
VisualCursorDirection direction) OVERRIDE;
- virtual ui::Range GetGlyphBounds(size_t index) OVERRIDE;
- virtual std::vector<Rect> GetSubstringBounds(const ui::Range& range) OVERRIDE;
+ virtual Range GetGlyphBounds(size_t index) OVERRIDE;
+ virtual std::vector<Rect> GetSubstringBounds(const Range& range) OVERRIDE;
virtual size_t TextIndexToLayoutIndex(size_t index) const OVERRIDE;
virtual size_t LayoutIndexToTextIndex(size_t index) const OVERRIDE;
virtual bool IsCursorablePosition(size_t position) OVERRIDE;
@@ -86,7 +86,10 @@ class RenderTextWin : public RenderText {
virtual void DrawVisualText(Canvas* canvas) OVERRIDE;
private:
+ FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Win_BreakRunsByUnicodeBlocks);
FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Win_LogicalClusters);
+ FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Multiline_MinWidth);
+ FRIEND_TEST_ALL_PREFIXES(RenderTextTest, Multiline_NormalWidth);
void ItemizeLogicalText();
void LayoutVisualText();
@@ -121,11 +124,12 @@ class RenderTextWin : public RenderText {
SCRIPT_STATE script_state_;
ScopedVector<internal::TextRun> runs_;
- Size string_size_;
- // A common vertical baseline for all the text runs. This is computed as the
- // largest baseline over all the runs' fonts.
- int common_baseline_;
+ // Single line width of the layout text.
+ int string_width_;
+
+ // Wrapped multiline size of the layout text.
+ Size multiline_string_size_;
scoped_ptr<int[]> visual_to_logical_;
scoped_ptr<int[]> logical_to_visual_;
diff --git a/chromium/ui/gfx/safe_integer_conversions.h b/chromium/ui/gfx/safe_integer_conversions.h
index edd8a4cafee..523b1f3441f 100644
--- a/chromium/ui/gfx/safe_integer_conversions.h
+++ b/chromium/ui/gfx/safe_integer_conversions.h
@@ -8,7 +8,7 @@
#include <cmath>
#include <limits>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/base/gtk/scoped_gobject.h b/chromium/ui/gfx/scoped_gobject.h
index 2e62e8f2c83..860849ec84e 100644
--- a/chromium/ui/base/gtk/scoped_gobject.h
+++ b/chromium/ui/gfx/scoped_gobject.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_GTK_SCOPED_GOBJECT_H_
-#define UI_BASE_GTK_SCOPED_GOBJECT_H_
+#ifndef UI_GFX_SCOPED_GOBJECT_H_
+#define UI_GFX_SCOPED_GOBJECT_H_
#include <glib-object.h>
@@ -31,4 +31,4 @@ struct ScopedGObject {
} // namespace ui
-#endif // UI_BASE_GTK_SCOPED_GOBJECT_H_
+#endif // UI_GFX_SCOPED_GOBJECT_H_
diff --git a/chromium/ui/gfx/scoped_ns_graphics_context_save_gstate_mac.h b/chromium/ui/gfx/scoped_ns_graphics_context_save_gstate_mac.h
index f4b11ad228e..9b0b77829b6 100644
--- a/chromium/ui/gfx/scoped_ns_graphics_context_save_gstate_mac.h
+++ b/chromium/ui/gfx/scoped_ns_graphics_context_save_gstate_mac.h
@@ -6,7 +6,7 @@
#define UI_GFX_SCOPED_NS_GRAPHICS_CONTEXT_SAVE_GSTATE_MAC_H_
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#if defined(__OBJC__)
@class NSGraphicsContext;
diff --git a/chromium/ui/gfx/screen.h b/chromium/ui/gfx/screen.h
index 9410d028889..a181cc8d256 100644
--- a/chromium/ui/gfx/screen.h
+++ b/chromium/ui/gfx/screen.h
@@ -5,9 +5,11 @@
#ifndef UI_GFX_SCREEN_H_
#define UI_GFX_SCREEN_H_
+#include <vector>
+
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
#include "ui/gfx/display.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/point.h"
#include "ui/gfx/screen_type_delegate.h"
@@ -18,6 +20,11 @@ class Rect;
// A utility class for getting various info about screen size, displays,
// cursor position, etc.
+//
+// Note that this class does not represent an individual display connected to a
+// computer -- see the Display class for that. A single Screen object exists on
+// most operating systems regardless of the number of connected displays. On
+// Windows 8, two Screens exist: one for Metro UI and another for the desktop.
class UI_EXPORT Screen {
public:
// Retrieves the Screen that the specified NativeView belongs to. A value of
@@ -50,17 +57,23 @@ class UI_EXPORT Screen {
virtual gfx::Point GetCursorScreenPoint() = 0;
// Returns the window under the cursor.
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() = 0;
+ virtual gfx::NativeWindow GetWindowUnderCursor() = 0;
+
+ // Returns the window at the given screen coordinate |point|.
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point) = 0;
// Returns the number of displays.
// Mirrored displays are excluded; this method is intended to return the
// number of distinct, usable displays.
- virtual int GetNumDisplays() = 0;
+ virtual int GetNumDisplays() const = 0;
+
+ // Returns the list of displays that are currently available.
+ virtual std::vector<gfx::Display> GetAllDisplays() const = 0;
// Returns the display nearest the specified window.
virtual gfx::Display GetDisplayNearestWindow(NativeView view) const = 0;
- // Returns the the display nearest the specified point.
+ // Returns the display nearest the specified point.
virtual gfx::Display GetDisplayNearestPoint(
const gfx::Point& point) const = 0;
diff --git a/chromium/ui/gfx/screen_android.cc b/chromium/ui/gfx/screen_android.cc
index 6c4d63325d6..e90bb76725d 100644
--- a/chromium/ui/gfx/screen_android.cc
+++ b/chromium/ui/gfx/screen_android.cc
@@ -19,7 +19,13 @@ class ScreenAndroid : public Screen {
virtual gfx::Point GetCursorScreenPoint() OVERRIDE { return gfx::Point(); }
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() OVERRIDE {
+ virtual gfx::NativeWindow GetWindowUnderCursor() OVERRIDE {
+ NOTIMPLEMENTED();
+ return NULL;
+ }
+
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point)
+ OVERRIDE {
NOTIMPLEMENTED();
return NULL;
}
@@ -50,7 +56,11 @@ class ScreenAndroid : public Screen {
return GetPrimaryDisplay();
}
- virtual int GetNumDisplays() OVERRIDE { return 1; }
+ virtual int GetNumDisplays() const OVERRIDE { return 1; }
+
+ virtual std::vector<gfx::Display> GetAllDisplays() const OVERRIDE {
+ return std::vector<gfx::Display>(1, GetPrimaryDisplay());
+ }
virtual gfx::Display GetDisplayMatching(
const gfx::Rect& match_rect) const OVERRIDE {
diff --git a/chromium/ui/gfx/screen_gtk.cc b/chromium/ui/gfx/screen_gtk.cc
index 8ef803dca1f..ac2464bbbd7 100644
--- a/chromium/ui/gfx/screen_gtk.cc
+++ b/chromium/ui/gfx/screen_gtk.cc
@@ -47,14 +47,20 @@ bool GetScreenWorkArea(gfx::Rect* out_rect) {
return true;
}
-gfx::Rect NativePrimaryMonitorBounds() {
- GdkScreen* screen = gdk_screen_get_default();
- GdkRectangle rect;
- gdk_screen_get_monitor_geometry(screen, 0, &rect);
- return gfx::Rect(rect);
+gfx::Display GetDisplayForMonitorNum(GdkScreen* screen, gint monitor_num) {
+ GdkRectangle bounds;
+ gdk_screen_get_monitor_geometry(screen, monitor_num, &bounds);
+ // Use |monitor_num| as display id.
+ gfx::Display display(monitor_num, gfx::Rect(bounds));
+ if (gdk_screen_get_primary_monitor(screen) == monitor_num) {
+ gfx::Rect rect;
+ if (GetScreenWorkArea(&rect))
+ display.set_work_area(gfx::IntersectRects(rect, display.bounds()));
+ }
+ return display;
}
-gfx::Rect GetMonitorAreaNearestWindow(gfx::NativeView view) {
+gfx::Display GetMonitorAreaNearestWindow(gfx::NativeView view) {
GdkScreen* screen = gdk_screen_get_default();
gint monitor_num = 0;
if (view && GTK_IS_WINDOW(view)) {
@@ -66,9 +72,7 @@ gfx::Rect GetMonitorAreaNearestWindow(gfx::NativeView view) {
screen,
gtk_widget_get_window(top_level));
}
- GdkRectangle bounds;
- gdk_screen_get_monitor_geometry(screen, monitor_num, &bounds);
- return gfx::Rect(bounds);
+ return GetDisplayForMonitorNum(screen, monitor_num);
}
class ScreenGtk : public gfx::Screen {
@@ -90,7 +94,7 @@ class ScreenGtk : public gfx::Screen {
}
// Returns the window under the cursor.
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() OVERRIDE {
+ virtual gfx::NativeWindow GetWindowUnderCursor() OVERRIDE {
GdkWindow* window = gdk_window_at_pointer(NULL, NULL);
if (!window)
return NULL;
@@ -104,20 +108,34 @@ class ScreenGtk : public gfx::Screen {
return GTK_IS_WINDOW(widget) ? GTK_WINDOW(widget) : NULL;
}
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point)
+ OVERRIDE {
+ NOTIMPLEMENTED();
+ return NULL;
+ }
+
// Returns the number of displays.
// Mirrored displays are excluded; this method is intended to return the
// number of distinct, usable displays.
- virtual int GetNumDisplays() OVERRIDE {
+ virtual int GetNumDisplays() const OVERRIDE {
// This query is kinda bogus for Linux -- do we want number of X screens?
// The number of monitors Xinerama has? We'll just use whatever GDK uses.
GdkScreen* screen = gdk_screen_get_default();
return gdk_screen_get_n_monitors(screen);
}
+ virtual std::vector<gfx::Display> GetAllDisplays() const OVERRIDE {
+ GdkScreen* screen = gdk_screen_get_default();
+ gint num_of_displays = gdk_screen_get_n_monitors(screen);
+ std::vector<gfx::Display> all_displays;
+ for (gint i = 0; i < num_of_displays; ++i)
+ all_displays.push_back(GetDisplayForMonitorNum(screen, i));
+ return all_displays;
+ }
+
// Returns the display nearest the specified window.
virtual gfx::Display GetDisplayNearestWindow(
gfx::NativeView view) const OVERRIDE {
- gfx::Rect bounds = GetMonitorAreaNearestWindow(view);
// Do not use the _NET_WORKAREA here, this is supposed to be an area on a
// specific monitor, and _NET_WORKAREA is a hint from the WM that
// generally spans across all monitors. This would make the work area
@@ -127,8 +145,8 @@ class ScreenGtk : public gfx::Screen {
// means to compute this rect would be to watch all windows with
// _NET_WM_STRUT(_PARTIAL) hints, and subtract their space from the
// physical area of the display to construct a work area.
- // TODO(oshima): Implement ID and Observer.
- return gfx::Display(0, bounds);
+ // TODO(oshima): Implement Observer.
+ return GetMonitorAreaNearestWindow(view);
}
// Returns the the display nearest the specified point.
@@ -137,32 +155,36 @@ class ScreenGtk : public gfx::Screen {
GdkScreen* screen = gdk_screen_get_default();
gint monitor = gdk_screen_get_monitor_at_point(
screen, point.x(), point.y());
- GdkRectangle bounds;
- gdk_screen_get_monitor_geometry(screen, monitor, &bounds);
- // TODO(oshima): Implement ID and Observer.
- return gfx::Display(0, gfx::Rect(bounds));
+ // TODO(oshima): Implement Observer.
+ return GetDisplayForMonitorNum(screen, monitor);
}
// Returns the display that most closely intersects the provided bounds.
virtual gfx::Display GetDisplayMatching(
const gfx::Rect& match_rect) const OVERRIDE {
- // TODO(thestig) Implement multi-monitor support.
- return GetPrimaryDisplay();
+ std::vector<gfx::Display> displays = GetAllDisplays();
+ gfx::Display maxIntersectDisplay;
+ gfx::Rect maxIntersection;
+ for (std::vector<gfx::Display>::iterator it = displays.begin();
+ it != displays.end(); ++it) {
+ gfx::Rect displayIntersection = it->bounds();
+ displayIntersection.Intersect(match_rect);
+ if (displayIntersection.size().GetArea() >
+ maxIntersection.size().GetArea()) {
+ maxIntersectDisplay = *it;
+ maxIntersection = displayIntersection;
+ }
+ }
+ return maxIntersectDisplay.is_valid() ?
+ maxIntersectDisplay : GetPrimaryDisplay();
}
// Returns the primary display.
virtual gfx::Display GetPrimaryDisplay() const OVERRIDE {
- gfx::Rect bounds = NativePrimaryMonitorBounds();
- // TODO(oshima): Implement ID and Observer.
- gfx::Display display(0, bounds);
- gfx::Rect rect;
- if (GetScreenWorkArea(&rect)) {
- display.set_work_area(gfx::IntersectRects(rect, bounds));
- } else {
- // Return the best we've got.
- display.set_work_area(bounds);
- }
- return display;
+ GdkScreen* screen = gdk_screen_get_default();
+ gint primary_monitor_index = gdk_screen_get_primary_monitor(screen);
+ // TODO(oshima): Implement Observer.
+ return GetDisplayForMonitorNum(screen, primary_monitor_index);
}
virtual void AddObserver(gfx::DisplayObserver* observer) OVERRIDE {
diff --git a/chromium/ui/gfx/screen_ios.mm b/chromium/ui/gfx/screen_ios.mm
index dfb0d1b62bb..a2770298ca8 100644
--- a/chromium/ui/gfx/screen_ios.mm
+++ b/chromium/ui/gfx/screen_ios.mm
@@ -21,12 +21,18 @@ class ScreenIos : public gfx::Screen {
return gfx::Point(0, 0);
}
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() OVERRIDE {
+ virtual gfx::NativeWindow GetWindowUnderCursor() OVERRIDE {
NOTIMPLEMENTED();
return gfx::NativeWindow();
}
- virtual int GetNumDisplays() OVERRIDE {
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point)
+ OVERRIDE {
+ NOTIMPLEMENTED();
+ return gfx::NativeWindow();
+ }
+
+ virtual int GetNumDisplays() const OVERRIDE {
#if TARGET_IPHONE_SIMULATOR
// UIScreen does not reliably return correct results on the simulator.
return 1;
@@ -35,6 +41,11 @@ class ScreenIos : public gfx::Screen {
#endif
}
+ virtual std::vector<gfx::Display> GetAllDisplays() const OVERRIDE {
+ NOTIMPLEMENTED();
+ return std::vector<gfx::Display>(1, GetPrimaryDisplay());
+ }
+
// Returns the display nearest the specified window.
virtual gfx::Display GetDisplayNearestWindow(
gfx::NativeView view) const OVERRIDE {
diff --git a/chromium/ui/gfx/screen_mac.mm b/chromium/ui/gfx/screen_mac.mm
index d9e1f0a71c9..28707ca7ea3 100644
--- a/chromium/ui/gfx/screen_mac.mm
+++ b/chromium/ui/gfx/screen_mac.mm
@@ -84,12 +84,18 @@ class ScreenMac : public gfx::Screen {
return gfx::Point(mouseLocation.x, mouseLocation.y);
}
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() OVERRIDE {
+ virtual gfx::NativeWindow GetWindowUnderCursor() OVERRIDE {
NOTIMPLEMENTED();
return gfx::NativeWindow();
}
- virtual int GetNumDisplays() OVERRIDE {
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point)
+ OVERRIDE {
+ NOTIMPLEMENTED();
+ return gfx::NativeWindow();
+ }
+
+ virtual int GetNumDisplays() const OVERRIDE {
// Don't just return the number of online displays. It includes displays
// that mirror other displays, which are not desired in the count. It's
// tempting to use the count returned by CGGetActiveDisplayList, but active
@@ -123,6 +129,11 @@ class ScreenMac : public gfx::Screen {
return display_count;
}
+ virtual std::vector<gfx::Display> GetAllDisplays() const OVERRIDE {
+ NOTIMPLEMENTED();
+ return std::vector<gfx::Display>(1, GetPrimaryDisplay());
+ }
+
virtual gfx::Display GetDisplayNearestWindow(
gfx::NativeView view) const OVERRIDE {
NSWindow* window = [view window];
diff --git a/chromium/ui/gfx/screen_win.cc b/chromium/ui/gfx/screen_win.cc
index 06c14bd1732..7903cc5fdd5 100644
--- a/chromium/ui/gfx/screen_win.cc
+++ b/chromium/ui/gfx/screen_win.cc
@@ -6,28 +6,47 @@
#include <windows.h>
+#include "base/hash.h"
#include "base/logging.h"
-#include "ui/base/win/dpi.h"
+#include "base/strings/utf_string_conversions.h"
+#include "base/win/win_util.h"
#include "ui/gfx/display.h"
+#include "ui/gfx/win/dpi.h"
namespace {
-MONITORINFO GetMonitorInfoForMonitor(HMONITOR monitor) {
- MONITORINFO monitor_info = { 0 };
+MONITORINFOEX GetMonitorInfoForMonitor(HMONITOR monitor) {
+ MONITORINFOEX monitor_info;
+ ZeroMemory(&monitor_info, sizeof(MONITORINFOEX));
monitor_info.cbSize = sizeof(monitor_info);
- GetMonitorInfo(monitor, &monitor_info);
+ base::win::GetMonitorInfoWrapper(monitor, &monitor_info);
return monitor_info;
}
-gfx::Display GetDisplay(MONITORINFO& monitor_info) {
- // TODO(oshima): Implement ID and Observer.
+gfx::Display GetDisplay(MONITORINFOEX& monitor_info) {
+ // TODO(oshima): Implement Observer.
+ int64 id = static_cast<int64>(base::Hash(WideToUTF8(monitor_info.szDevice)));
gfx::Rect bounds = gfx::Rect(monitor_info.rcMonitor);
- gfx::Display display(0, bounds);
+ gfx::Display display(id, bounds);
display.set_work_area(gfx::Rect(monitor_info.rcWork));
- display.SetScaleAndBounds(ui::win::GetDeviceScaleFactor(), bounds);
+ display.SetScaleAndBounds(gfx::win::GetDeviceScaleFactor(), bounds);
return display;
}
+BOOL CALLBACK EnumMonitorCallback(HMONITOR monitor,
+ HDC hdc,
+ LPRECT rect,
+ LPARAM data) {
+ std::vector<gfx::Display>* all_displays =
+ reinterpret_cast<std::vector<gfx::Display>*>(data);
+ DCHECK(all_displays);
+
+ MONITORINFOEX monitor_info = GetMonitorInfoForMonitor(monitor);
+ gfx::Display display = GetDisplay(monitor_info);
+ all_displays->push_back(display);
+ return TRUE;
+}
+
} // namespace
namespace gfx {
@@ -39,7 +58,7 @@ ScreenWin::~ScreenWin() {
}
bool ScreenWin::IsDIPEnabled() {
- return ui::IsInHighDPIMode();
+ return IsInHighDPIMode();
}
gfx::Point ScreenWin::GetCursorScreenPoint() {
@@ -48,16 +67,27 @@ gfx::Point ScreenWin::GetCursorScreenPoint() {
return gfx::Point(pt);
}
-gfx::NativeWindow ScreenWin::GetWindowAtCursorScreenPoint() {
- POINT location;
- HWND window_hwnd = GetCursorPos(&location) ? WindowFromPoint(location) : NULL;
- return GetNativeWindowFromHWND(window_hwnd);
+gfx::NativeWindow ScreenWin::GetWindowUnderCursor() {
+ POINT cursor_loc;
+ HWND hwnd = GetCursorPos(&cursor_loc) ? WindowFromPoint(cursor_loc) : NULL;
+ return GetNativeWindowFromHWND(hwnd);
+}
+
+gfx::NativeWindow ScreenWin::GetWindowAtScreenPoint(const gfx::Point& point) {
+ return GetNativeWindowFromHWND(WindowFromPoint(point.ToPOINT()));
}
-int ScreenWin::GetNumDisplays() {
+int ScreenWin::GetNumDisplays() const {
return GetSystemMetrics(SM_CMONITORS);
}
+std::vector<gfx::Display> ScreenWin::GetAllDisplays() const {
+ std::vector<gfx::Display> all_displays;
+ EnumDisplayMonitors(NULL, NULL, EnumMonitorCallback,
+ reinterpret_cast<LPARAM>(&all_displays));
+ return all_displays;
+}
+
gfx::Display ScreenWin::GetDisplayNearestWindow(gfx::NativeView window) const {
HWND window_hwnd = GetHWNDFromNativeView(window);
if (!window_hwnd) {
@@ -67,37 +97,39 @@ gfx::Display ScreenWin::GetDisplayNearestWindow(gfx::NativeView window) const {
return GetPrimaryDisplay();
}
- MONITORINFO monitor_info;
+ MONITORINFOEX monitor_info;
monitor_info.cbSize = sizeof(monitor_info);
- GetMonitorInfo(MonitorFromWindow(window_hwnd, MONITOR_DEFAULTTONEAREST),
- &monitor_info);
+ base::win::GetMonitorInfoWrapper(
+ MonitorFromWindow(window_hwnd, MONITOR_DEFAULTTONEAREST), &monitor_info);
return GetDisplay(monitor_info);
}
gfx::Display ScreenWin::GetDisplayNearestPoint(const gfx::Point& point) const {
POINT initial_loc = { point.x(), point.y() };
HMONITOR monitor = MonitorFromPoint(initial_loc, MONITOR_DEFAULTTONEAREST);
- MONITORINFO mi = {0};
+ MONITORINFOEX mi;
+ ZeroMemory(&mi, sizeof(MONITORINFOEX));
mi.cbSize = sizeof(mi);
- if (monitor && GetMonitorInfo(monitor, &mi))
+ if (monitor && base::win::GetMonitorInfoWrapper(monitor, &mi)) {
return GetDisplay(mi);
+ }
return gfx::Display();
}
gfx::Display ScreenWin::GetDisplayMatching(const gfx::Rect& match_rect) const {
RECT other_bounds_rect = match_rect.ToRECT();
- MONITORINFO monitor_info = GetMonitorInfoForMonitor(MonitorFromRect(
+ MONITORINFOEX monitor_info = GetMonitorInfoForMonitor(MonitorFromRect(
&other_bounds_rect, MONITOR_DEFAULTTONEAREST));
return GetDisplay(monitor_info);
}
gfx::Display ScreenWin::GetPrimaryDisplay() const {
- MONITORINFO mi = GetMonitorInfoForMonitor(
+ MONITORINFOEX mi = GetMonitorInfoForMonitor(
MonitorFromWindow(NULL, MONITOR_DEFAULTTOPRIMARY));
gfx::Display display = GetDisplay(mi);
// TODO(kevers|girard): Test if these checks can be reintroduced for high-DIP
// once more of the app is DIP-aware.
- if (!ui::IsInHighDPIMode()) {
+ if (!IsInHighDPIMode()) {
DCHECK_EQ(GetSystemMetrics(SM_CXSCREEN), display.size().width());
DCHECK_EQ(GetSystemMetrics(SM_CYSCREEN), display.size().height());
}
diff --git a/chromium/ui/gfx/screen_win.h b/chromium/ui/gfx/screen_win.h
index f6b7d40ae8d..a9fb7f518ff 100644
--- a/chromium/ui/gfx/screen_win.h
+++ b/chromium/ui/gfx/screen_win.h
@@ -6,7 +6,7 @@
#define UI_GFX_SCREEN_WIN_H_
#include "base/compiler_specific.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/screen.h"
namespace gfx {
@@ -20,8 +20,11 @@ class UI_EXPORT ScreenWin : public gfx::Screen {
// Overridden from gfx::Screen:
virtual bool IsDIPEnabled() OVERRIDE;
virtual gfx::Point GetCursorScreenPoint() OVERRIDE;
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() OVERRIDE;
- virtual int GetNumDisplays() OVERRIDE;
+ virtual gfx::NativeWindow GetWindowUnderCursor() OVERRIDE;
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point)
+ OVERRIDE;
+ virtual int GetNumDisplays() const OVERRIDE;
+ virtual std::vector<gfx::Display> GetAllDisplays() const OVERRIDE;
virtual gfx::Display GetDisplayNearestWindow(
gfx::NativeView window) const OVERRIDE;
virtual gfx::Display GetDisplayNearestPoint(
diff --git a/chromium/ui/gfx/scrollbar_size.h b/chromium/ui/gfx/scrollbar_size.h
index 43f1ca5ee5e..d11774d17a7 100644
--- a/chromium/ui/gfx/scrollbar_size.h
+++ b/chromium/ui/gfx/scrollbar_size.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_SCROLLBAR_SIZE_H_
#define UI_GFX_SCROLLBAR_SIZE_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/selection_model.cc b/chromium/ui/gfx/selection_model.cc
index c3a31dae107..5352d8653cd 100644
--- a/chromium/ui/gfx/selection_model.cc
+++ b/chromium/ui/gfx/selection_model.cc
@@ -10,14 +10,17 @@
namespace gfx {
SelectionModel::SelectionModel()
- : selection_(0), caret_affinity_(CURSOR_BACKWARD) {}
+ : selection_(0),
+ caret_affinity_(CURSOR_BACKWARD) {}
SelectionModel::SelectionModel(size_t position, LogicalCursorDirection affinity)
- : selection_(position), caret_affinity_(affinity) {}
+ : selection_(position),
+ caret_affinity_(affinity) {}
-SelectionModel::SelectionModel(ui::Range selection,
+SelectionModel::SelectionModel(const Range& selection,
LogicalCursorDirection affinity)
- : selection_(selection), caret_affinity_(affinity) {}
+ : selection_(selection),
+ caret_affinity_(affinity) {}
bool SelectionModel::operator==(const SelectionModel& sel) const {
return selection_ == sel.selection() &&
diff --git a/chromium/ui/gfx/selection_model.h b/chromium/ui/gfx/selection_model.h
index b99b383714b..0b811d1c5ce 100644
--- a/chromium/ui/gfx/selection_model.h
+++ b/chromium/ui/gfx/selection_model.h
@@ -7,8 +7,8 @@
#include <string>
-#include "ui/base/range/range.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
+#include "ui/gfx/range/range.h"
namespace gfx {
@@ -67,9 +67,9 @@ class UI_EXPORT SelectionModel {
SelectionModel(size_t position, LogicalCursorDirection affinity);
// Create a SelectionModel representing a selection (which may be empty).
// The caret position is the end of the range.
- SelectionModel(ui::Range selection, LogicalCursorDirection affinity);
+ SelectionModel(const Range& selection, LogicalCursorDirection affinity);
- const ui::Range& selection() const { return selection_; }
+ const Range& selection() const { return selection_; }
size_t caret_pos() const { return selection_.end(); }
LogicalCursorDirection caret_affinity() const { return caret_affinity_; }
@@ -87,7 +87,7 @@ class UI_EXPORT SelectionModel {
void set_selection_start(size_t pos) { selection_.set_start(pos); }
// Logical selection. The logical caret position is the end of the selection.
- ui::Range selection_;
+ Range selection_;
// The logical direction from the caret position (selection_.end()) to the
// character it is attached to for display purposes. This matters only when
diff --git a/chromium/ui/gfx/shadow_value.h b/chromium/ui/gfx/shadow_value.h
index d07ac94043b..46d84b4be3f 100644
--- a/chromium/ui/gfx/shadow_value.h
+++ b/chromium/ui/gfx/shadow_value.h
@@ -9,7 +9,7 @@
#include <vector>
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point.h"
namespace gfx {
diff --git a/chromium/ui/gfx/size.h b/chromium/ui/gfx/size.h
index f6152a3aa12..c2340ebce63 100644
--- a/chromium/ui/gfx/size.h
+++ b/chromium/ui/gfx/size.h
@@ -8,7 +8,7 @@
#include <string>
#include "base/compiler_specific.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/size_base.h"
#include "ui/gfx/size_f.h"
diff --git a/chromium/ui/gfx/size_base.h b/chromium/ui/gfx/size_base.h
index 6f23fa3cedb..72d47d2c37b 100644
--- a/chromium/ui/gfx/size_base.h
+++ b/chromium/ui/gfx/size_base.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_SIZE_BASE_H_
#define UI_GFX_SIZE_BASE_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/size_f.h b/chromium/ui/gfx/size_f.h
index a38d3f6caff..ee90189f7d9 100644
--- a/chromium/ui/gfx/size_f.h
+++ b/chromium/ui/gfx/size_f.h
@@ -8,7 +8,7 @@
#include <string>
#include "base/compiler_specific.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/size_base.h"
namespace gfx {
diff --git a/chromium/ui/gfx/skbitmap_operations.h b/chromium/ui/gfx/skbitmap_operations.h
index eb41d0f7090..3a0d3c97504 100644
--- a/chromium/ui/gfx/skbitmap_operations.h
+++ b/chromium/ui/gfx/skbitmap_operations.h
@@ -6,8 +6,8 @@
#define UI_GFX_SKBITMAP_OPERATIONS_H_
#include "base/gtest_prod_util.h"
-#include "ui/base/ui_export.h"
#include "ui/gfx/color_utils.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/shadow_value.h"
namespace gfx {
diff --git a/chromium/ui/gfx/skia_util.h b/chromium/ui/gfx/skia_util.h
index 4a2cfcf2035..592ff5f2f66 100644
--- a/chromium/ui/gfx/skia_util.h
+++ b/chromium/ui/gfx/skia_util.h
@@ -12,7 +12,7 @@
#include "third_party/skia/include/core/SkColor.h"
#include "third_party/skia/include/core/SkRect.h"
#include "third_party/skia/include/core/SkShader.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
class SkBitmap;
class SkDrawLooper;
diff --git a/chromium/ui/gfx/skia_utils_gtk.h b/chromium/ui/gfx/skia_utils_gtk.h
index 6d56e0fab8a..abe397722ac 100644
--- a/chromium/ui/gfx/skia_utils_gtk.h
+++ b/chromium/ui/gfx/skia_utils_gtk.h
@@ -6,7 +6,7 @@
#define UI_GFX_SKIA_UTILS_GTK_H_
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
typedef struct _GdkColor GdkColor;
diff --git a/chromium/ui/gfx/switches.cc b/chromium/ui/gfx/switches.cc
index 55452c3c7c7..2f2eb9a3b82 100644
--- a/chromium/ui/gfx/switches.cc
+++ b/chromium/ui/gfx/switches.cc
@@ -4,7 +4,6 @@
#include "ui/gfx/switches.h"
-namespace gfx {
namespace switches {
// Let text glyphs have X-positions that aren't snapped to the pixel grid in
@@ -17,5 +16,10 @@ const char kEnableBrowserTextSubpixelPositioning[] =
const char kEnableWebkitTextSubpixelPositioning[] =
"enable-webkit-text-subpixel-positioning";
+// Overrides the device scale factor for the browser UI and the contents.
+const char kForceDeviceScaleFactor[] = "force-device-scale-factor";
+
+// Enables/Disables High DPI support (windows)
+const char kHighDPISupport[] = "high-dpi-support";
+
} // namespace switches
-} // namespace gfx
diff --git a/chromium/ui/gfx/switches.h b/chromium/ui/gfx/switches.h
index 3bae4521f7d..e3cd9e7db85 100644
--- a/chromium/ui/gfx/switches.h
+++ b/chromium/ui/gfx/switches.h
@@ -5,15 +5,15 @@
#ifndef UI_GFX_SWITCHES_H_
#define UI_GFX_SWITCHES_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
-namespace gfx {
namespace switches {
UI_EXPORT extern const char kEnableBrowserTextSubpixelPositioning[];
UI_EXPORT extern const char kEnableWebkitTextSubpixelPositioning[];
+UI_EXPORT extern const char kForceDeviceScaleFactor[];
+UI_EXPORT extern const char kHighDPISupport[];
} // namespace switches
-} // namespace gfx
#endif // UI_GFX_SWITCHES_H_
diff --git a/chromium/ui/gfx/sys_color_change_listener.cc b/chromium/ui/gfx/sys_color_change_listener.cc
index 7a9fc84478f..d5646b3a81c 100644
--- a/chromium/ui/gfx/sys_color_change_listener.cc
+++ b/chromium/ui/gfx/sys_color_change_listener.cc
@@ -13,7 +13,7 @@
#include "base/memory/singleton.h"
#include "base/observer_list.h"
#if defined(OS_WIN)
-#include "ui/base/win/singleton_hwnd.h"
+#include "ui/gfx/win/singleton_hwnd.h"
#endif
namespace gfx {
@@ -48,7 +48,7 @@ bool IsInvertedColorScheme() {
}
#if defined(OS_WIN)
-class SysColorChangeObserver : public ui::SingletonHwnd::Observer {
+class SysColorChangeObserver : public gfx::SingletonHwnd::Observer {
public:
static SysColorChangeObserver* GetInstance();
@@ -75,11 +75,11 @@ SysColorChangeObserver* SysColorChangeObserver::GetInstance() {
}
SysColorChangeObserver::SysColorChangeObserver() {
- ui::SingletonHwnd::GetInstance()->AddObserver(this);
+ gfx::SingletonHwnd::GetInstance()->AddObserver(this);
}
SysColorChangeObserver::~SysColorChangeObserver() {
- ui::SingletonHwnd::GetInstance()->RemoveObserver(this);
+ gfx::SingletonHwnd::GetInstance()->RemoveObserver(this);
}
void SysColorChangeObserver::AddListener(SysColorChangeListener* listener) {
diff --git a/chromium/ui/gfx/sys_color_change_listener.h b/chromium/ui/gfx/sys_color_change_listener.h
index 2d196630b5e..db3f9df74cc 100644
--- a/chromium/ui/gfx/sys_color_change_listener.h
+++ b/chromium/ui/gfx/sys_color_change_listener.h
@@ -7,7 +7,7 @@
#include "base/basictypes.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/base/text/text_elider.cc b/chromium/ui/gfx/text_elider.cc
index 05909816cf3..bc4eb3bb858 100644
--- a/chromium/ui/base/text/text_elider.cc
+++ b/chromium/ui/gfx/text_elider.cc
@@ -7,7 +7,7 @@
// Note that several of the functions declared in text_elider.h are implemented
// in this file using helper classes in an unnamed namespace.
-#include "ui/base/text/text_elider.h"
+#include "ui/gfx/text_elider.h"
#include <string>
#include <vector>
@@ -26,10 +26,11 @@
#include "net/base/registry_controlled_domains/registry_controlled_domain.h"
#include "third_party/icu/source/common/unicode/rbbi.h"
#include "third_party/icu/source/common/unicode/uloc.h"
-#include "ui/gfx/font.h"
+#include "ui/gfx/font_list.h"
+#include "ui/gfx/text_utils.h"
#include "url/gurl.h"
-namespace ui {
+namespace gfx {
// U+2026 in utf8
const char kEllipsis[] = "\xE2\x80\xA6";
@@ -115,7 +116,7 @@ string16 BuildPathFromComponents(const string16& path_prefix,
// Add |filename|, ellipsis if necessary.
if (num_components != (path_elements.size() - 1))
- path += UTF8ToUTF16(kEllipsis) + kForwardSlash;
+ path += string16(kEllipsisUTF16) + kForwardSlash;
path += filename;
return path;
@@ -128,7 +129,7 @@ string16 ElideComponentizedPath(const string16& url_path_prefix,
const std::vector<string16>& url_path_elements,
const string16& url_filename,
const string16& url_query,
- const gfx::Font& font,
+ const gfx::FontList& font_list,
int available_pixel_width) {
const size_t url_path_number_of_elements = url_path_elements.size();
@@ -136,9 +137,9 @@ string16 ElideComponentizedPath(const string16& url_path_prefix,
for (size_t i = url_path_number_of_elements - 1; i > 0; --i) {
string16 elided_path = BuildPathFromComponents(url_path_prefix,
url_path_elements, url_filename, i);
- if (available_pixel_width >= font.GetStringWidth(elided_path))
- return ElideText(elided_path + url_query,
- font, available_pixel_width, ELIDE_AT_END);
+ if (available_pixel_width >= gfx::GetStringWidth(elided_path, font_list))
+ return ElideText(elided_path + url_query, font_list,
+ available_pixel_width, ELIDE_AT_END);
}
return string16();
@@ -147,9 +148,9 @@ string16 ElideComponentizedPath(const string16& url_path_prefix,
} // namespace
string16 ElideEmail(const string16& email,
- const gfx::Font& font,
+ const gfx::FontList& font_list,
int available_pixel_width) {
- if (font.GetStringWidth(email) <= available_pixel_width)
+ if (gfx::GetStringWidth(email, font_list) <= available_pixel_width)
return email;
// Split the email into its local-part (username) and domain-part. The email
@@ -166,16 +167,17 @@ string16 ElideEmail(const string16& email,
// Subtract the @ symbol from the available width as it is mandatory.
const string16 kAtSignUTF16 = ASCIIToUTF16("@");
- available_pixel_width -= font.GetStringWidth(kAtSignUTF16);
+ available_pixel_width -= gfx::GetStringWidth(kAtSignUTF16, font_list);
// Check whether eliding the domain is necessary: if eliding the username
// is sufficient, the domain will not be elided.
- const int full_username_width = font.GetStringWidth(username);
+ const int full_username_width = gfx::GetStringWidth(username, font_list);
const int available_domain_width =
available_pixel_width -
std::min(full_username_width,
- font.GetStringWidth(username.substr(0, 1) + kEllipsisUTF16));
- if (font.GetStringWidth(domain) > available_domain_width) {
+ gfx::GetStringWidth(username.substr(0, 1) + kEllipsisUTF16,
+ font_list));
+ if (gfx::GetStringWidth(domain, font_list) > available_domain_width) {
// Elide the domain so that it only takes half of the available width.
// Should the username not need all the width available in its half, the
// domain will occupy the leftover width.
@@ -186,7 +188,8 @@ string16 ElideEmail(const string16& email,
std::min(available_domain_width,
std::max(available_pixel_width - full_username_width,
available_pixel_width / 2));
- domain = ElideText(domain, font, desired_domain_width, ELIDE_IN_MIDDLE);
+ domain = ElideText(domain, font_list, desired_domain_width,
+ ELIDE_IN_MIDDLE);
// Failing to elide the domain such that at least one character remains
// (other than the ellipsis itself) remains: return a single ellipsis.
if (domain.length() <= 1U)
@@ -196,20 +199,25 @@ string16 ElideEmail(const string16& email,
// Fit the username in the remaining width (at this point the elided username
// is guaranteed to fit with at least one character remaining given all the
// precautions taken earlier).
- username = ElideText(username,
- font,
- available_pixel_width - font.GetStringWidth(domain),
+ available_pixel_width -= gfx::GetStringWidth(domain, font_list);
+ username = ElideText(username, font_list, available_pixel_width,
ELIDE_AT_END);
return username + kAtSignUTF16 + domain;
}
+string16 ElideEmail(const string16& email,
+ const gfx::Font& font,
+ int available_pixel_width) {
+ return ElideEmail(email, gfx::FontList(font), available_pixel_width);
+}
+
// TODO(pkasting): http://crbug.com/77883 This whole function gets
// kerning/ligatures/etc. issues potentially wrong by assuming that the width of
// a rendered string is always the sum of the widths of its substrings. Also I
// suspect it could be made simpler.
string16 ElideUrl(const GURL& url,
- const gfx::Font& font,
+ const gfx::FontList& font_list,
int available_pixel_width,
const std::string& languages) {
// Get a formatted string and corresponding parsing of the url.
@@ -222,11 +230,12 @@ string16 ElideUrl(const GURL& url,
// If non-standard, return plain eliding.
if (!url.IsStandard())
- return ElideText(url_string, font, available_pixel_width, ELIDE_AT_END);
+ return ElideText(url_string, font_list, available_pixel_width,
+ ELIDE_AT_END);
// Now start eliding url_string to fit within available pixel width.
// Fist pass - check to see whether entire url_string fits.
- const int pixel_width_url_string = font.GetStringWidth(url_string);
+ const int pixel_width_url_string = gfx::GetStringWidth(url_string, font_list);
if (available_pixel_width >= pixel_width_url_string)
return url_string;
@@ -239,8 +248,9 @@ string16 ElideUrl(const GURL& url,
// Return general elided text if url minus the query fits.
const string16 url_minus_query =
url_string.substr(0, path_start_index + path_len);
- if (available_pixel_width >= font.GetStringWidth(url_minus_query))
- return ElideText(url_string, font, available_pixel_width, ELIDE_AT_END);
+ if (available_pixel_width >= gfx::GetStringWidth(url_minus_query, font_list))
+ return ElideText(url_string, font_list, available_pixel_width,
+ ELIDE_AT_END);
// Get Host.
string16 url_host = UTF8ToUTF16(url.host());
@@ -288,15 +298,17 @@ string16 ElideUrl(const GURL& url,
}
// Second Pass - remove scheme - the rest fits.
- const int pixel_width_url_host = font.GetStringWidth(url_host);
- const int pixel_width_url_path = font.GetStringWidth(url_path_query_etc);
+ const int pixel_width_url_host = gfx::GetStringWidth(url_host, font_list);
+ const int pixel_width_url_path = gfx::GetStringWidth(url_path_query_etc,
+ font_list);
if (available_pixel_width >=
pixel_width_url_host + pixel_width_url_path)
return url_host + url_path_query_etc;
// Third Pass: Subdomain, domain and entire path fits.
- const int pixel_width_url_domain = font.GetStringWidth(url_domain);
- const int pixel_width_url_subdomain = font.GetStringWidth(url_subdomain);
+ const int pixel_width_url_domain = gfx::GetStringWidth(url_domain, font_list);
+ const int pixel_width_url_subdomain = gfx::GetStringWidth(url_subdomain,
+ font_list);
if (available_pixel_width >=
pixel_width_url_subdomain + pixel_width_url_domain +
pixel_width_url_path)
@@ -304,15 +316,15 @@ string16 ElideUrl(const GURL& url,
// Query element.
string16 url_query;
- const int kPixelWidthDotsTrailer =
- font.GetStringWidth(UTF8ToUTF16(kEllipsis));
+ const int kPixelWidthDotsTrailer = gfx::GetStringWidth(
+ string16(kEllipsisUTF16), font_list);
if (parsed.query.is_nonempty()) {
url_query = UTF8ToUTF16("?") + url_string.substr(parsed.query.begin);
- if (available_pixel_width >= (pixel_width_url_subdomain +
- pixel_width_url_domain + pixel_width_url_path -
- font.GetStringWidth(url_query))) {
+ if (available_pixel_width >=
+ (pixel_width_url_subdomain + pixel_width_url_domain +
+ pixel_width_url_path - gfx::GetStringWidth(url_query, font_list))) {
return ElideText(url_subdomain + url_domain + url_path_query_etc,
- font, available_pixel_width, ELIDE_AT_END);
+ font_list, available_pixel_width, ELIDE_AT_END);
}
}
@@ -339,18 +351,19 @@ string16 ElideUrl(const GURL& url,
url_path_number_of_elements > kMaxNumberOfUrlPathElementsAllowed) {
// No path to elide, or too long of a path (could overflow in loop below)
// Just elide this as a text string.
- return ElideText(url_subdomain + url_domain + url_path_query_etc, font,
+ return ElideText(url_subdomain + url_domain + url_path_query_etc, font_list,
available_pixel_width, ELIDE_AT_END);
}
// Start eliding the path and replacing elements by ".../".
- const string16 kEllipsisAndSlash = UTF8ToUTF16(kEllipsis) + kForwardSlash;
- const int pixel_width_ellipsis_slash = font.GetStringWidth(kEllipsisAndSlash);
+ const string16 kEllipsisAndSlash = string16(kEllipsisUTF16) + kForwardSlash;
+ const int pixel_width_ellipsis_slash = gfx::GetStringWidth(kEllipsisAndSlash,
+ font_list);
// Check with both subdomain and domain.
string16 elided_path =
ElideComponentizedPath(url_subdomain + url_domain, url_path_elements,
- url_filename, url_query, font,
+ url_filename, url_query, font_list,
available_pixel_width);
if (!elided_path.empty())
return elided_path;
@@ -368,7 +381,7 @@ string16 ElideUrl(const GURL& url,
url_elided_domain = url_domain;
elided_path = ElideComponentizedPath(url_elided_domain, url_path_elements,
- url_filename, url_query, font,
+ url_filename, url_query, font_list,
available_pixel_width);
if (!elided_path.empty())
@@ -377,24 +390,32 @@ string16 ElideUrl(const GURL& url,
// Return elided domain/.../filename anyway.
string16 final_elided_url_string(url_elided_domain);
- const int url_elided_domain_width = font.GetStringWidth(url_elided_domain);
+ const int url_elided_domain_width = gfx::GetStringWidth(url_elided_domain,
+ font_list);
// A hack to prevent trailing ".../...".
if ((available_pixel_width - url_elided_domain_width) >
pixel_width_ellipsis_slash + kPixelWidthDotsTrailer +
- font.GetStringWidth(ASCIIToUTF16("UV"))) {
+ gfx::GetStringWidth(ASCIIToUTF16("UV"), font_list)) {
final_elided_url_string += BuildPathFromComponents(string16(),
url_path_elements, url_filename, 1);
} else {
final_elided_url_string += url_path;
}
- return ElideText(final_elided_url_string, font, available_pixel_width,
+ return ElideText(final_elided_url_string, font_list, available_pixel_width,
ELIDE_AT_END);
}
+string16 ElideUrl(const GURL& url,
+ const gfx::Font& font,
+ int available_pixel_width,
+ const std::string& languages) {
+ return ElideUrl(url, gfx::FontList(font), available_pixel_width, languages);
+}
+
string16 ElideFilename(const base::FilePath& filename,
- const gfx::Font& font,
+ const gfx::FontList& font_list,
int available_pixel_width) {
#if defined(OS_WIN)
string16 filename_utf16 = filename.value();
@@ -409,18 +430,18 @@ string16 ElideFilename(const base::FilePath& filename,
filename.BaseName().RemoveExtension().value()));
#endif
- const int full_width = font.GetStringWidth(filename_utf16);
+ const int full_width = gfx::GetStringWidth(filename_utf16, font_list);
if (full_width <= available_pixel_width)
return base::i18n::GetDisplayStringInLTRDirectionality(filename_utf16);
if (rootname.empty() || extension.empty()) {
- const string16 elided_name = ElideText(filename_utf16, font,
+ const string16 elided_name = ElideText(filename_utf16, font_list,
available_pixel_width, ELIDE_AT_END);
return base::i18n::GetDisplayStringInLTRDirectionality(elided_name);
}
- const int ext_width = font.GetStringWidth(extension);
- const int root_width = font.GetStringWidth(rootname);
+ const int ext_width = gfx::GetStringWidth(extension, font_list);
+ const int root_width = gfx::GetStringWidth(rootname, font_list);
// We may have trimmed the path.
if (root_width + ext_width <= available_pixel_width) {
@@ -429,7 +450,7 @@ string16 ElideFilename(const base::FilePath& filename,
}
if (ext_width >= available_pixel_width) {
- const string16 elided_name = ElideText(rootname + extension, font,
+ const string16 elided_name = ElideText(rootname + extension, font_list,
available_pixel_width,
ELIDE_IN_MIDDLE);
return base::i18n::GetDisplayStringInLTRDirectionality(elided_name);
@@ -437,19 +458,25 @@ string16 ElideFilename(const base::FilePath& filename,
int available_root_width = available_pixel_width - ext_width;
string16 elided_name =
- ElideText(rootname, font, available_root_width, ELIDE_AT_END);
+ ElideText(rootname, font_list, available_root_width, ELIDE_AT_END);
elided_name += extension;
return base::i18n::GetDisplayStringInLTRDirectionality(elided_name);
}
+string16 ElideFilename(const base::FilePath& filename,
+ const gfx::Font& font,
+ int available_pixel_width) {
+ return ElideFilename(filename, gfx::FontList(font), available_pixel_width);
+}
+
string16 ElideText(const string16& text,
- const gfx::Font& font,
+ const gfx::FontList& font_list,
int available_pixel_width,
ElideBehavior elide_behavior) {
if (text.empty())
return text;
- const int current_text_pixel_width = font.GetStringWidth(text);
+ const int current_text_pixel_width = gfx::GetStringWidth(text, font_list);
const bool elide_in_middle = (elide_behavior == ELIDE_IN_MIDDLE);
const bool insert_ellipsis = (elide_behavior != TRUNCATE_AT_END);
@@ -466,13 +493,14 @@ string16 ElideText(const string16& text,
// ridiculous), but we should check other widths for bogus values as well.
if (current_text_pixel_width <= 0 && !text.empty()) {
const string16 cut = slicer.CutString(text.length() / 2, false);
- return ElideText(cut, font, available_pixel_width, elide_behavior);
+ return ElideText(cut, font_list, available_pixel_width, elide_behavior);
}
if (current_text_pixel_width <= available_pixel_width)
return text;
- if (insert_ellipsis && font.GetStringWidth(ellipsis) > available_pixel_width)
+ if (insert_ellipsis &&
+ gfx::GetStringWidth(ellipsis, font_list) > available_pixel_width)
return string16();
// Use binary search to compute the elided text.
@@ -483,12 +511,12 @@ string16 ElideText(const string16& text,
// We check the length of the whole desired string at once to ensure we
// handle kerning/ligatures/etc. correctly.
const string16 cut = slicer.CutString(guess, insert_ellipsis);
- const int guess_length = font.GetStringWidth(cut);
+ const int guess_length = gfx::GetStringWidth(cut, font_list);
// Check again that we didn't hit a Pango width overflow. If so, cut the
// current string in half and start over.
if (guess_length <= 0) {
return ElideText(slicer.CutString(guess / 2, false),
- font, available_pixel_width, elide_behavior);
+ font_list, available_pixel_width, elide_behavior);
}
if (guess_length > available_pixel_width)
hi = guess - 1;
@@ -499,6 +527,14 @@ string16 ElideText(const string16& text,
return slicer.CutString(guess, insert_ellipsis);
}
+string16 ElideText(const string16& text,
+ const gfx::Font& font,
+ int available_pixel_width,
+ ElideBehavior elide_behavior) {
+ return ElideText(text, gfx::FontList(font), available_pixel_width,
+ elide_behavior);
+}
+
SortedDisplayURL::SortedDisplayURL(const GURL& url,
const std::string& languages) {
net::AppendFormattedHost(url, languages, &sort_host_);
@@ -606,8 +642,6 @@ bool ElideString(const string16& input, int max_len, string16* output) {
return true;
}
-} // namespace ui
-
namespace {
// Internal class used to track progress of a rectangular string elide
@@ -775,13 +809,13 @@ void RectangleString::NewLine(bool output) {
// can be broken into smaller methods sharing this state.
class RectangleText {
public:
- RectangleText(const gfx::Font& font,
+ RectangleText(const gfx::FontList& font_list,
int available_pixel_width,
int available_pixel_height,
- ui::WordWrapBehavior wrap_behavior,
+ WordWrapBehavior wrap_behavior,
std::vector<string16>* lines)
- : font_(font),
- line_height_(font.GetHeight()),
+ : font_list_(font_list),
+ line_height_(font_list.GetHeight()),
available_pixel_width_(available_pixel_width),
available_pixel_height_(available_pixel_height),
wrap_behavior_(wrap_behavior),
@@ -833,8 +867,8 @@ class RectangleText {
// Set the current position to the beginning of the next line.
bool NewLine();
- // The font used for measuring text width.
- const gfx::Font& font_;
+ // The font list used for measuring text width.
+ const gfx::FontList& font_list_;
// The height of each line of text.
const int line_height_;
@@ -846,7 +880,7 @@ class RectangleText {
const int available_pixel_height_;
// The wrap behavior for words that are too long to fit on a single line.
- const ui::WordWrapBehavior wrap_behavior_;
+ const WordWrapBehavior wrap_behavior_;
// The current running width.
int current_width_;
@@ -902,12 +936,12 @@ int RectangleText::Finalize() {
}
if (last_line_ended_in_lf_)
lines_->push_back(string16());
- return (insufficient_width_ ? ui::INSUFFICIENT_SPACE_HORIZONTAL : 0) |
- (insufficient_height_ ? ui::INSUFFICIENT_SPACE_VERTICAL : 0);
+ return (insufficient_width_ ? INSUFFICIENT_SPACE_HORIZONTAL : 0) |
+ (insufficient_height_ ? INSUFFICIENT_SPACE_VERTICAL : 0);
}
void RectangleText::AddLine(const string16& line) {
- const int line_width = font_.GetStringWidth(line);
+ const int line_width = gfx::GetStringWidth(line, font_list_);
if (line_width <= available_pixel_width_) {
AddToCurrentLineWithWidth(line, line_width);
} else {
@@ -948,7 +982,8 @@ int RectangleText::WrapWord(const string16& word) {
bool first_fragment = true;
while (!insufficient_height_ && !text.empty()) {
string16 fragment =
- ui::ElideText(text, font_, available_pixel_width_, ui::TRUNCATE_AT_END);
+ ElideText(text, font_list_, available_pixel_width_,
+ TRUNCATE_AT_END);
// At least one character has to be added at every line, even if the
// available space is too small.
if(fragment.empty())
@@ -972,17 +1007,16 @@ int RectangleText::AddWordOverflow(const string16& word) {
lines_added++;
}
- if (wrap_behavior_ == ui::IGNORE_LONG_WORDS) {
+ if (wrap_behavior_ == IGNORE_LONG_WORDS) {
current_line_ = word;
current_width_ = available_pixel_width_;
- } else if (wrap_behavior_ == ui::WRAP_LONG_WORDS) {
+ } else if (wrap_behavior_ == WRAP_LONG_WORDS) {
lines_added += WrapWord(word);
} else {
- const ui::ElideBehavior elide_behavior =
- (wrap_behavior_ == ui::ELIDE_LONG_WORDS ? ui::ELIDE_AT_END :
- ui::TRUNCATE_AT_END);
+ const ElideBehavior elide_behavior =
+ (wrap_behavior_ == ELIDE_LONG_WORDS ? ELIDE_AT_END : TRUNCATE_AT_END);
const string16 elided_word =
- ui::ElideText(word, font_, available_pixel_width_, elide_behavior);
+ ElideText(word, font_list_, available_pixel_width_, elide_behavior);
AddToCurrentLine(elided_word);
insufficient_width_ = true;
}
@@ -994,7 +1028,7 @@ int RectangleText::AddWord(const string16& word) {
int lines_added = 0;
string16 trimmed;
TrimWhitespace(word, TRIM_TRAILING, &trimmed);
- const int trimmed_width = font_.GetStringWidth(trimmed);
+ const int trimmed_width = gfx::GetStringWidth(trimmed, font_list_);
if (trimmed_width <= available_pixel_width_) {
// Word can be made to fit, no need to fragment it.
if ((current_width_ + trimmed_width > available_pixel_width_) && NewLine())
@@ -1002,14 +1036,14 @@ int RectangleText::AddWord(const string16& word) {
// Append the non-trimmed word, in case more words are added after.
AddToCurrentLine(word);
} else {
- lines_added = AddWordOverflow(wrap_behavior_ == ui::IGNORE_LONG_WORDS ?
+ lines_added = AddWordOverflow(wrap_behavior_ == IGNORE_LONG_WORDS ?
trimmed : word);
}
return lines_added;
}
void RectangleText::AddToCurrentLine(const string16& text) {
- AddToCurrentLineWithWidth(text, font_.GetStringWidth(text));
+ AddToCurrentLineWithWidth(text, gfx::GetStringWidth(text, font_list_));
}
void RectangleText::AddToCurrentLineWithWidth(const string16& text,
@@ -1038,8 +1072,6 @@ bool RectangleText::NewLine() {
} // namespace
-namespace ui {
-
bool ElideRectangleString(const string16& input, size_t max_rows,
size_t max_cols, bool strict, string16* output) {
RectangleString rect(max_rows, max_cols, strict, output);
@@ -1049,12 +1081,12 @@ bool ElideRectangleString(const string16& input, size_t max_rows,
}
int ElideRectangleText(const string16& input,
- const gfx::Font& font,
- int available_pixel_width,
- int available_pixel_height,
- WordWrapBehavior wrap_behavior,
- std::vector<string16>* lines) {
- RectangleText rect(font,
+ const gfx::FontList& font_list,
+ int available_pixel_width,
+ int available_pixel_height,
+ WordWrapBehavior wrap_behavior,
+ std::vector<string16>* lines) {
+ RectangleText rect(font_list,
available_pixel_width,
available_pixel_height,
wrap_behavior,
@@ -1064,6 +1096,17 @@ int ElideRectangleText(const string16& input,
return rect.Finalize();
}
+int ElideRectangleText(const string16& input,
+ const gfx::Font& font,
+ int available_pixel_width,
+ int available_pixel_height,
+ WordWrapBehavior wrap_behavior,
+ std::vector<string16>* lines) {
+ return ElideRectangleText(input, gfx::FontList(font),
+ available_pixel_width, available_pixel_height,
+ wrap_behavior, lines);
+}
+
string16 TruncateString(const string16& string, size_t length) {
if (string.size() <= length)
// String fits, return it.
@@ -1126,4 +1169,4 @@ string16 TruncateString(const string16& string, size_t length) {
return string.substr(0, index) + kElideString;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/text/text_elider.h b/chromium/ui/gfx/text_elider.h
index 1d31f8eea63..008a1cd1b5b 100644
--- a/chromium/ui/base/text/text_elider.h
+++ b/chromium/ui/gfx/text_elider.h
@@ -4,8 +4,8 @@
//
// This file defines utility functions for eliding and formatting UI text.
-#ifndef UI_BASE_TEXT_TEXT_ELIDER_H_
-#define UI_BASE_TEXT_TEXT_ELIDER_H_
+#ifndef UI_GFX_TEXT_ELIDER_H_
+#define UI_GFX_TEXT_ELIDER_H_
#include <string>
#include <vector>
@@ -14,8 +14,7 @@
#include "base/strings/string16.h"
#include "third_party/icu/source/common/unicode/uchar.h"
#include "third_party/icu/source/i18n/unicode/coll.h"
-#include "ui/base/ui_export.h"
-#include "ui/gfx/font.h"
+#include "ui/gfx/gfx_export.h"
class GURL;
@@ -23,13 +22,15 @@ namespace base {
class FilePath;
}
-namespace ui {
+namespace gfx {
+class Font;
+class FontList;
UI_EXPORT extern const char kEllipsis[];
UI_EXPORT extern const char16 kEllipsisUTF16[];
// Elides a well-formed email address (e.g. username@domain.com) to fit into
-// |available_pixel_width| using the specified |font|.
+// |available_pixel_width| using the specified |font_list|.
// This function guarantees that the string returned will contain at least one
// character, other than the ellipses, on either side of the '@'. If it is
// impossible to achieve these requirements: only an ellipsis will be returned.
@@ -39,6 +40,10 @@ UI_EXPORT extern const char16 kEllipsisUTF16[];
// doesn't need half the available width: the elided domain will occupy that
// extra width).
UI_EXPORT string16 ElideEmail(const string16& email,
+ const gfx::FontList& font_list,
+ int available_pixel_width);
+// Obsolete version. Use the above version which takes gfx::FontList.
+UI_EXPORT string16 ElideEmail(const string16& email,
const gfx::Font& font,
int available_pixel_width);
@@ -57,6 +62,11 @@ UI_EXPORT string16 ElideEmail(const string16& email,
// is displayed properly in an RTL context. Please refer to
// http://crbug.com/6487 for more information.
UI_EXPORT string16 ElideUrl(const GURL& url,
+ const gfx::FontList& font_list,
+ int available_pixel_width,
+ const std::string& languages);
+// Obsolete version. Use the above version which takes gfx::FontList.
+UI_EXPORT string16 ElideUrl(const GURL& url,
const gfx::Font& font,
int available_pixel_width,
const std::string& languages);
@@ -73,6 +83,11 @@ enum ElideBehavior {
// Elides |text| to fit in |available_pixel_width| according to the specified
// |elide_behavior|.
UI_EXPORT string16 ElideText(const string16& text,
+ const gfx::FontList& font_list,
+ int available_pixel_width,
+ ElideBehavior elide_behavior);
+// Obsolete version. Use the above version which takes gfx::FontList.
+UI_EXPORT string16 ElideText(const string16& text,
const gfx::Font& font,
int available_pixel_width,
ElideBehavior elide_behavior);
@@ -84,6 +99,10 @@ UI_EXPORT string16 ElideText(const string16& text,
// the elided filename is wrapped with LRE (Left-To-Right Embedding) mark and
// PDF (Pop Directional Formatting) mark.
UI_EXPORT string16 ElideFilename(const base::FilePath& filename,
+ const gfx::FontList& font_list,
+ int available_pixel_width);
+// Obsolete version. Use the above version which takes gfx::FontList.
+UI_EXPORT string16 ElideFilename(const base::FilePath& filename,
const gfx::Font& font,
int available_pixel_width);
@@ -181,12 +200,19 @@ enum ReformattingResultFlags {
// Reformats |text| into output vector |lines| so that the resulting text fits
// into an |available_pixel_width| by |available_pixel_height| rectangle with
-// the specified |font|. Input newlines are respected, but lines that are too
-// long are broken into pieces. For words that are too wide to fit on a single
-// line, the wrapping behavior can be specified with the |wrap_behavior| param.
-// Returns a combination of |ReformattingResultFlags| that indicate whether the
-// given rectangle had insufficient space to accommodate |texŧ|, leading to
-// elision or truncation (and not just reformatting).
+// the specified |font_list|. Input newlines are respected, but lines that are
+// too long are broken into pieces. For words that are too wide to fit on a
+// single line, the wrapping behavior can be specified with the |wrap_behavior|
+// param. Returns a combination of |ReformattingResultFlags| that indicate
+// whether the given rectangle had insufficient space to accommodate |texŧ|,
+// leading to elision or truncation (and not just reformatting).
+UI_EXPORT int ElideRectangleText(const string16& text,
+ const gfx::FontList& font_list,
+ int available_pixel_width,
+ int available_pixel_height,
+ WordWrapBehavior wrap_behavior,
+ std::vector<string16>* lines);
+// Obsolete version. Use the above version which takes gfx::FontList.
UI_EXPORT int ElideRectangleText(const string16& text,
const gfx::Font& font,
int available_pixel_width,
@@ -201,6 +227,6 @@ UI_EXPORT int ElideRectangleText(const string16& text,
// less.
UI_EXPORT string16 TruncateString(const string16& string, size_t length);
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_TEXT_TEXT_ELIDER_H_
+#endif // UI_GFX_TEXT_ELIDER_H_
diff --git a/chromium/ui/base/text/text_elider_unittest.cc b/chromium/ui/gfx/text_elider_unittest.cc
index 3c06cb543cf..2a90e5d73cb 100644
--- a/chromium/ui/base/text/text_elider_unittest.cc
+++ b/chromium/ui/gfx/text_elider_unittest.cc
@@ -4,7 +4,7 @@
//
// Unit tests for eliding and formatting utility functions.
-#include "ui/base/text/text_elider.h"
+#include "ui/gfx/text_elider.h"
#include "base/files/file_path.h"
#include "base/i18n/rtl.h"
@@ -15,7 +15,7 @@
#include "ui/gfx/font.h"
#include "url/gurl.h"
-namespace ui {
+namespace gfx {
namespace {
@@ -53,6 +53,20 @@ void RunUrlTest(Testcase* testcases, size_t num_testcases) {
}
}
+gfx::Font GetTestingFont() {
+ gfx::Font font;
+#if defined(OS_MACOSX)
+ // Use a specific font for certain tests on Mac.
+ // 1) Different Mac machines might be configured with different default font.
+ // The number of extra pixels needed to make ElideEmail/TestFilenameEliding
+ // tests work might vary per the default font.
+ // 2) This specific font helps expose the line width exceeding problem as in
+ // ElideRectangleTextCheckLineWidth.
+ font = gfx::Font("LucidaGrande", 12);
+#endif
+ return font;
+}
+
} // namespace
// TODO(ios): Complex eliding is off by one for some of those tests on iOS.
@@ -107,13 +121,22 @@ TEST(TextEliderTest, MAYBE_ElideEmail) {
{"mmmmm@llllllllll", "m" + kEllipsisStr + "@l" + kEllipsisStr},
};
- const gfx::Font font;
+ const gfx::Font font = GetTestingFont();
for (size_t i = 0; i < arraysize(testcases); ++i) {
const string16 expected_output = UTF8ToUTF16(testcases[i].output);
+ int available_width = font.GetStringWidth(expected_output);
+#if defined(OS_MACOSX)
+ // Give two extra pixels to offset the ceiling width returned by
+ // GetStringWidth on Mac. This workaround will no longer be needed once
+ // the floating point width is adopted (http://crbug.com/288987).
+ // Note that we need one more pixel than TestFilenameEliding because
+ // multiple strings are elided and we need to offset more.
+ available_width += 2;
+#endif
EXPECT_EQ(expected_output,
ElideEmail(UTF8ToUTF16(testcases[i].input),
font,
- font.GetStringWidth(expected_output)));
+ available_width));
}
}
@@ -311,14 +334,19 @@ TEST(TextEliderTest, MAYBE_TestFilenameEliding) {
"file.name.re" + kEllipsisStr + "emelylongext"}
};
- static const gfx::Font font;
+ static const gfx::Font font = GetTestingFont();
for (size_t i = 0; i < arraysize(testcases); ++i) {
base::FilePath filepath(testcases[i].input);
string16 expected = UTF8ToUTF16(testcases[i].output);
expected = base::i18n::GetDisplayStringInLTRDirectionality(expected);
- EXPECT_EQ(expected, ElideFilename(filepath,
- font,
- font.GetStringWidth(UTF8ToUTF16(testcases[i].output))));
+ int available_width = font.GetStringWidth(UTF8ToUTF16(testcases[i].output));
+#if defined(OS_MACOSX)
+ // Give one extra pixel to offset the ceiling width returned by
+ // GetStringWidth on Mac. This workaround will no longer be needed once
+ // the floating point width is adopted (http://crbug.com/288987).
+ available_width += 1;
+#endif
+ EXPECT_EQ(expected, ElideFilename(filepath, font, available_width));
}
}
@@ -707,6 +735,37 @@ TEST(TextEliderTest, ElideRectangleTextLongWords) {
}
}
+// TODO(ios): Complex eliding is off by one for some of those tests on iOS.
+// See crbug.com/154019
+#if defined(OS_IOS)
+#define MAYBE_ElideRectangleTextCheckLineWidth \
+ DISABLED_ElideRectangleTextCheckLineWidth
+#else
+#define MAYBE_ElideRectangleTextCheckLineWidth ElideRectangleTextCheckLineWidth
+#endif
+
+// This test is to make sure that the width of each wrapped line does not
+// exceed the available width. On some platform like Mac, this test used to
+// fail because the truncated integer width is returned for the string
+// and the accumulation of the truncated values causes the elide function
+// to wrap incorrectly.
+TEST(TextEliderTest, MAYBE_ElideRectangleTextCheckLineWidth) {
+ gfx::Font font = GetTestingFont();
+ const int kAvailableWidth = 235;
+ const int kAvailableHeight = 1000;
+ const char text[] = "that Russian place we used to go to after fencing";
+ std::vector<string16> lines;
+ EXPECT_EQ(0, ElideRectangleText(UTF8ToUTF16(text),
+ font,
+ kAvailableWidth,
+ kAvailableHeight,
+ WRAP_LONG_WORDS,
+ &lines));
+ ASSERT_EQ(2u, lines.size());
+ EXPECT_LE(font.GetStringWidth(lines[0]), kAvailableWidth);
+ EXPECT_LE(font.GetStringWidth(lines[1]), kAvailableWidth);
+}
+
TEST(TextEliderTest, ElideRectangleString) {
struct TestData {
const char* input;
@@ -931,4 +990,4 @@ TEST(TextEliderTest, TruncateString) {
EXPECT_EQ(L"\x2026", UTF16ToWide(TruncateString(ASCIIToUTF16(" "), 2)));
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/gfx/text_utils.h b/chromium/ui/gfx/text_utils.h
index 42bce439731..bd94902fba6 100644
--- a/chromium/ui/gfx/text_utils.h
+++ b/chromium/ui/gfx/text_utils.h
@@ -6,10 +6,12 @@
#define UI_GFX_TEXT_UTILS_H_
#include "base/strings/string16.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
+class FontList;
+
// Strip the accelerator char (typically '&') from a menu string. A double
// accelerator char ('&&') will be converted to a single char. The out params
// |accelerated_char_pos| and |accelerated_char_span| will be set to the index
@@ -20,6 +22,11 @@ UI_EXPORT base::string16 RemoveAcceleratorChar(const base::string16& s,
int* accelerated_char_pos,
int* accelerated_char_span);
+// Returns the number of horizontal pixels needed to display the specified
+// |text| with |font_list|.
+UI_EXPORT int GetStringWidth(const base::string16& text,
+ const FontList& font_list);
+
} // namespace gfx
#endif // UI_GFX_TEXT_UTILS_H_
diff --git a/chromium/ui/gfx/text_utils_android.cc b/chromium/ui/gfx/text_utils_android.cc
new file mode 100644
index 00000000000..c564b9b1db0
--- /dev/null
+++ b/chromium/ui/gfx/text_utils_android.cc
@@ -0,0 +1,16 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gfx/text_utils.h"
+
+#include "base/logging.h"
+
+namespace gfx {
+
+int GetStringWidth(const base::string16& text, const FontList& font_list) {
+ NOTIMPLEMENTED();
+ return 0;
+}
+
+} // namespace gfx
diff --git a/chromium/ui/gfx/text_utils_ios.mm b/chromium/ui/gfx/text_utils_ios.mm
new file mode 100644
index 00000000000..1841864ff85
--- /dev/null
+++ b/chromium/ui/gfx/text_utils_ios.mm
@@ -0,0 +1,22 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gfx/text_utils.h"
+
+#import <UIKit/UIKit.h>
+
+#include <cmath>
+
+#include "base/strings/sys_string_conversions.h"
+#include "ui/gfx/font_list.h"
+
+namespace gfx {
+
+int GetStringWidth(const base::string16& text, const FontList& font_list) {
+ NSString* ns_text = base::SysUTF16ToNSString(text);
+ NativeFont native_font = font_list.GetPrimaryFont().GetNativeFont();
+ return std::ceil([ns_text sizeWithFont:native_font].width);
+}
+
+} // namespace gfx
diff --git a/chromium/ui/gfx/text_utils_skia.cc b/chromium/ui/gfx/text_utils_skia.cc
new file mode 100644
index 00000000000..0de1156a14b
--- /dev/null
+++ b/chromium/ui/gfx/text_utils_skia.cc
@@ -0,0 +1,15 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gfx/text_utils.h"
+
+#include "ui/gfx/canvas.h"
+
+namespace gfx {
+
+int GetStringWidth(const base::string16& text, const FontList& font_list) {
+ return Canvas::GetStringWidth(text, font_list);
+}
+
+} // namespace gfx
diff --git a/chromium/ui/gfx/transform.cc b/chromium/ui/gfx/transform.cc
index c7bf91af411..5f8a36760d1 100644
--- a/chromium/ui/gfx/transform.cc
+++ b/chromium/ui/gfx/transform.cc
@@ -9,6 +9,7 @@
#include <cmath>
+#include "base/logging.h"
#include "base/strings/stringprintf.h"
#include "ui/gfx/point.h"
#include "ui/gfx/point3_f.h"
@@ -23,61 +24,72 @@ namespace gfx {
namespace {
// Taken from SkMatrix44.
-const double kEpsilon = 1e-8;
+const SkMScalar kEpsilon = 1e-8;
-double TanDegrees(double degrees) {
- double radians = degrees * M_PI / 180;
+SkMScalar TanDegrees(double degrees) {
+ SkMScalar radians = degrees * M_PI / 180;
return std::tan(radians);
}
} // namespace
-Transform::Transform(
- double col1row1, double col2row1, double col3row1, double col4row1,
- double col1row2, double col2row2, double col3row2, double col4row2,
- double col1row3, double col2row3, double col3row3, double col4row3,
- double col1row4, double col2row4, double col3row4, double col4row4)
- : matrix_(SkMatrix44::kUninitialized_Constructor)
-{
- matrix_.setDouble(0, 0, col1row1);
- matrix_.setDouble(1, 0, col1row2);
- matrix_.setDouble(2, 0, col1row3);
- matrix_.setDouble(3, 0, col1row4);
-
- matrix_.setDouble(0, 1, col2row1);
- matrix_.setDouble(1, 1, col2row2);
- matrix_.setDouble(2, 1, col2row3);
- matrix_.setDouble(3, 1, col2row4);
-
- matrix_.setDouble(0, 2, col3row1);
- matrix_.setDouble(1, 2, col3row2);
- matrix_.setDouble(2, 2, col3row3);
- matrix_.setDouble(3, 2, col3row4);
-
- matrix_.setDouble(0, 3, col4row1);
- matrix_.setDouble(1, 3, col4row2);
- matrix_.setDouble(2, 3, col4row3);
- matrix_.setDouble(3, 3, col4row4);
-}
-
-Transform::Transform(
- double col1row1, double col2row1,
- double col1row2, double col2row2,
- double x_translation, double y_translation)
- : matrix_(SkMatrix44::kIdentity_Constructor)
-{
- matrix_.setDouble(0, 0, col1row1);
- matrix_.setDouble(1, 0, col1row2);
- matrix_.setDouble(0, 1, col2row1);
- matrix_.setDouble(1, 1, col2row2);
- matrix_.setDouble(0, 3, x_translation);
- matrix_.setDouble(1, 3, y_translation);
+Transform::Transform(SkMScalar col1row1,
+ SkMScalar col2row1,
+ SkMScalar col3row1,
+ SkMScalar col4row1,
+ SkMScalar col1row2,
+ SkMScalar col2row2,
+ SkMScalar col3row2,
+ SkMScalar col4row2,
+ SkMScalar col1row3,
+ SkMScalar col2row3,
+ SkMScalar col3row3,
+ SkMScalar col4row3,
+ SkMScalar col1row4,
+ SkMScalar col2row4,
+ SkMScalar col3row4,
+ SkMScalar col4row4)
+ : matrix_(SkMatrix44::kUninitialized_Constructor) {
+ matrix_.set(0, 0, col1row1);
+ matrix_.set(1, 0, col1row2);
+ matrix_.set(2, 0, col1row3);
+ matrix_.set(3, 0, col1row4);
+
+ matrix_.set(0, 1, col2row1);
+ matrix_.set(1, 1, col2row2);
+ matrix_.set(2, 1, col2row3);
+ matrix_.set(3, 1, col2row4);
+
+ matrix_.set(0, 2, col3row1);
+ matrix_.set(1, 2, col3row2);
+ matrix_.set(2, 2, col3row3);
+ matrix_.set(3, 2, col3row4);
+
+ matrix_.set(0, 3, col4row1);
+ matrix_.set(1, 3, col4row2);
+ matrix_.set(2, 3, col4row3);
+ matrix_.set(3, 3, col4row4);
+}
+
+Transform::Transform(SkMScalar col1row1,
+ SkMScalar col2row1,
+ SkMScalar col1row2,
+ SkMScalar col2row2,
+ SkMScalar x_translation,
+ SkMScalar y_translation)
+ : matrix_(SkMatrix44::kIdentity_Constructor) {
+ matrix_.set(0, 0, col1row1);
+ matrix_.set(1, 0, col1row2);
+ matrix_.set(0, 1, col2row1);
+ matrix_.set(1, 1, col2row2);
+ matrix_.set(0, 3, x_translation);
+ matrix_.set(1, 3, y_translation);
}
void Transform::RotateAboutXAxis(double degrees) {
double radians = degrees * M_PI / 180;
- double cosTheta = std::cos(radians);
- double sinTheta = std::sin(radians);
+ SkMScalar cosTheta = SkDoubleToMScalar(std::cos(radians));
+ SkMScalar sinTheta = SkDoubleToMScalar(std::sin(radians));
if (matrix_.isIdentity()) {
matrix_.set3x3(1, 0, 0,
0, cosTheta, sinTheta,
@@ -93,8 +105,8 @@ void Transform::RotateAboutXAxis(double degrees) {
void Transform::RotateAboutYAxis(double degrees) {
double radians = degrees * M_PI / 180;
- double cosTheta = std::cos(radians);
- double sinTheta = std::sin(radians);
+ SkMScalar cosTheta = SkDoubleToMScalar(std::cos(radians));
+ SkMScalar sinTheta = SkDoubleToMScalar(std::sin(radians));
if (matrix_.isIdentity()) {
// Note carefully the placement of the -sinTheta for rotation about
// y-axis is different than rotation about x-axis or z-axis.
@@ -112,8 +124,8 @@ void Transform::RotateAboutYAxis(double degrees) {
void Transform::RotateAboutZAxis(double degrees) {
double radians = degrees * M_PI / 180;
- double cosTheta = std::cos(radians);
- double sinTheta = std::sin(radians);
+ SkMScalar cosTheta = SkDoubleToMScalar(std::cos(radians));
+ SkMScalar sinTheta = SkDoubleToMScalar(std::sin(radians));
if (matrix_.isIdentity()) {
matrix_.set3x3(cosTheta, sinTheta, 0,
-sinTheta, cosTheta, 0,
@@ -129,68 +141,62 @@ void Transform::RotateAboutZAxis(double degrees) {
void Transform::RotateAbout(const Vector3dF& axis, double degrees) {
if (matrix_.isIdentity()) {
- matrix_.setRotateDegreesAbout(SkDoubleToMScalar(axis.x()),
- SkDoubleToMScalar(axis.y()),
- SkDoubleToMScalar(axis.z()),
- SkDoubleToMScalar(degrees));
+ matrix_.setRotateDegreesAbout(SkFloatToMScalar(axis.x()),
+ SkFloatToMScalar(axis.y()),
+ SkFloatToMScalar(axis.z()),
+ degrees);
} else {
SkMatrix44 rot(SkMatrix44::kUninitialized_Constructor);
- rot.setRotateDegreesAbout(SkDoubleToMScalar(axis.x()),
- SkDoubleToMScalar(axis.y()),
- SkDoubleToMScalar(axis.z()),
- SkDoubleToMScalar(degrees));
+ rot.setRotateDegreesAbout(SkFloatToMScalar(axis.x()),
+ SkFloatToMScalar(axis.y()),
+ SkFloatToMScalar(axis.z()),
+ degrees);
matrix_.preConcat(rot);
}
}
-void Transform::Scale(double x, double y) {
- matrix_.preScale(SkDoubleToMScalar(x), SkDoubleToMScalar(y), 1);
-}
+void Transform::Scale(SkMScalar x, SkMScalar y) { matrix_.preScale(x, y, 1); }
-void Transform::Scale3d(double x, double y, double z) {
- matrix_.preScale(SkDoubleToMScalar(x),
- SkDoubleToMScalar(y),
- SkDoubleToMScalar(z));
+void Transform::Scale3d(SkMScalar x, SkMScalar y, SkMScalar z) {
+ matrix_.preScale(x, y, z);
}
-void Transform::Translate(double x, double y) {
- matrix_.preTranslate(SkDoubleToMScalar(x), SkDoubleToMScalar(y), 0);
+void Transform::Translate(SkMScalar x, SkMScalar y) {
+ matrix_.preTranslate(x, y, 0);
}
-void Transform::Translate3d(double x, double y, double z) {
- matrix_.preTranslate(SkDoubleToMScalar(x),
- SkDoubleToMScalar(y),
- SkDoubleToMScalar(z));
+void Transform::Translate3d(SkMScalar x, SkMScalar y, SkMScalar z) {
+ matrix_.preTranslate(x, y, z);
}
-void Transform::SkewX(double angle_x) {
+void Transform::SkewX(SkMScalar angle_x) {
if (matrix_.isIdentity())
- matrix_.setDouble(0, 1, TanDegrees(angle_x));
+ matrix_.set(0, 1, TanDegrees(angle_x));
else {
SkMatrix44 skew(SkMatrix44::kIdentity_Constructor);
- skew.setDouble(0, 1, TanDegrees(angle_x));
+ skew.set(0, 1, TanDegrees(angle_x));
matrix_.preConcat(skew);
}
}
-void Transform::SkewY(double angle_y) {
+void Transform::SkewY(SkMScalar angle_y) {
if (matrix_.isIdentity())
- matrix_.setDouble(1, 0, TanDegrees(angle_y));
+ matrix_.set(1, 0, TanDegrees(angle_y));
else {
SkMatrix44 skew(SkMatrix44::kIdentity_Constructor);
- skew.setDouble(1, 0, TanDegrees(angle_y));
+ skew.set(1, 0, TanDegrees(angle_y));
matrix_.preConcat(skew);
}
}
-void Transform::ApplyPerspectiveDepth(double depth) {
+void Transform::ApplyPerspectiveDepth(SkMScalar depth) {
if (depth == 0)
return;
if (matrix_.isIdentity())
- matrix_.setDouble(3, 2, -1.0 / depth);
+ matrix_.set(3, 2, -1.0 / depth);
else {
SkMatrix44 m(SkMatrix44::kIdentity_Constructor);
- m.setDouble(3, 2, -1.0 / depth);
+ m.set(3, 2, -1.0 / depth);
matrix_.preConcat(m);
}
}
@@ -208,9 +214,9 @@ bool Transform::IsIdentityOrIntegerTranslation() const {
return false;
bool no_fractional_translation =
- static_cast<int>(matrix_.getDouble(0, 3)) == matrix_.getDouble(0, 3) &&
- static_cast<int>(matrix_.getDouble(1, 3)) == matrix_.getDouble(1, 3) &&
- static_cast<int>(matrix_.getDouble(2, 3)) == matrix_.getDouble(2, 3);
+ static_cast<int>(matrix_.get(0, 3)) == matrix_.get(0, 3) &&
+ static_cast<int>(matrix_.get(1, 3)) == matrix_.get(1, 3) &&
+ static_cast<int>(matrix_.get(2, 3)) == matrix_.get(2, 3);
return no_fractional_translation;
}
@@ -243,34 +249,22 @@ bool Transform::IsBackFaceVisible() const {
// Compute the cofactor of the 3rd row, 3rd column.
double cofactor_part_1 =
- matrix_.getDouble(0, 0) *
- matrix_.getDouble(1, 1) *
- matrix_.getDouble(3, 3);
+ matrix_.get(0, 0) * matrix_.get(1, 1) * matrix_.get(3, 3);
double cofactor_part_2 =
- matrix_.getDouble(0, 1) *
- matrix_.getDouble(1, 3) *
- matrix_.getDouble(3, 0);
+ matrix_.get(0, 1) * matrix_.get(1, 3) * matrix_.get(3, 0);
double cofactor_part_3 =
- matrix_.getDouble(0, 3) *
- matrix_.getDouble(1, 0) *
- matrix_.getDouble(3, 1);
+ matrix_.get(0, 3) * matrix_.get(1, 0) * matrix_.get(3, 1);
double cofactor_part_4 =
- matrix_.getDouble(0, 0) *
- matrix_.getDouble(1, 3) *
- matrix_.getDouble(3, 1);
+ matrix_.get(0, 0) * matrix_.get(1, 3) * matrix_.get(3, 1);
double cofactor_part_5 =
- matrix_.getDouble(0, 1) *
- matrix_.getDouble(1, 0) *
- matrix_.getDouble(3, 3);
+ matrix_.get(0, 1) * matrix_.get(1, 0) * matrix_.get(3, 3);
double cofactor_part_6 =
- matrix_.getDouble(0, 3) *
- matrix_.getDouble(1, 1) *
- matrix_.getDouble(3, 0);
+ matrix_.get(0, 3) * matrix_.get(1, 1) * matrix_.get(3, 0);
double cofactor33 =
cofactor_part_1 +
@@ -316,30 +310,30 @@ bool Transform::Preserves2dAxisAlignment() const {
// values: The current implementation conservatively assumes that axis
// alignment is not preserved.
- bool has_x_or_y_perspective = matrix_.getDouble(3, 0) != 0 ||
- matrix_.getDouble(3, 1) != 0;
+ bool has_x_or_y_perspective =
+ matrix_.get(3, 0) != 0 || matrix_.get(3, 1) != 0;
int num_non_zero_in_row_0 = 0;
int num_non_zero_in_row_1 = 0;
int num_non_zero_in_col_0 = 0;
int num_non_zero_in_col_1 = 0;
- if (std::abs(matrix_.getDouble(0, 0)) > kEpsilon) {
+ if (std::abs(matrix_.get(0, 0)) > kEpsilon) {
num_non_zero_in_row_0++;
num_non_zero_in_col_0++;
}
- if (std::abs(matrix_.getDouble(0, 1)) > kEpsilon) {
+ if (std::abs(matrix_.get(0, 1)) > kEpsilon) {
num_non_zero_in_row_0++;
num_non_zero_in_col_1++;
}
- if (std::abs(matrix_.getDouble(1, 0)) > kEpsilon) {
+ if (std::abs(matrix_.get(1, 0)) > kEpsilon) {
num_non_zero_in_row_1++;
num_non_zero_in_col_0++;
}
- if (std::abs(matrix_.getDouble(1, 1)) > kEpsilon) {
+ if (std::abs(matrix_.get(1, 1)) > kEpsilon) {
num_non_zero_in_row_1++;
num_non_zero_in_col_1++;
}
@@ -357,24 +351,33 @@ void Transform::Transpose() {
}
void Transform::FlattenTo2d() {
- matrix_.setDouble(2, 0, 0.0);
- matrix_.setDouble(2, 1, 0.0);
- matrix_.setDouble(0, 2, 0.0);
- matrix_.setDouble(1, 2, 0.0);
- matrix_.setDouble(2, 2, 1.0);
- matrix_.setDouble(3, 2, 0.0);
- matrix_.setDouble(2, 3, 0.0);
+ matrix_.set(2, 0, 0.0);
+ matrix_.set(2, 1, 0.0);
+ matrix_.set(0, 2, 0.0);
+ matrix_.set(1, 2, 0.0);
+ matrix_.set(2, 2, 1.0);
+ matrix_.set(3, 2, 0.0);
+ matrix_.set(2, 3, 0.0);
+}
+
+Vector2dF Transform::To2dTranslation() const {
+ return gfx::Vector2dF(SkMScalarToFloat(matrix_.get(0, 3)),
+ SkMScalarToFloat(matrix_.get(1, 3)));
}
-void Transform::TransformPoint(Point& point) const {
+void Transform::TransformPoint(Point* point) const {
+ DCHECK(point);
TransformPointInternal(matrix_, point);
}
-void Transform::TransformPoint(Point3F& point) const {
+void Transform::TransformPoint(Point3F* point) const {
+ DCHECK(point);
TransformPointInternal(matrix_, point);
}
-bool Transform::TransformPointReverse(Point& point) const {
+bool Transform::TransformPointReverse(Point* point) const {
+ DCHECK(point);
+
// TODO(sad): Try to avoid trying to invert the matrix.
SkMatrix44 inverse(SkMatrix44::kUninitialized_Constructor);
if (!matrix_.invert(&inverse))
@@ -384,7 +387,9 @@ bool Transform::TransformPointReverse(Point& point) const {
return true;
}
-bool Transform::TransformPointReverse(Point3F& point) const {
+bool Transform::TransformPointReverse(Point3F* point) const {
+ DCHECK(point);
+
// TODO(sad): Try to avoid trying to invert the matrix.
SkMatrix44 inverse(SkMatrix44::kUninitialized_Constructor);
if (!matrix_.invert(&inverse))
@@ -419,7 +424,7 @@ bool Transform::TransformRectReverse(RectF* rect) const {
return true;
}
-bool Transform::Blend(const Transform& from, double progress) {
+bool Transform::Blend(const Transform& from, SkMScalar progress) {
DecomposedTransform to_decomp;
DecomposedTransform from_decomp;
if (!DecomposeTransform(&to_decomp, *this) ||
@@ -434,41 +439,33 @@ bool Transform::Blend(const Transform& from, double progress) {
}
void Transform::TransformPointInternal(const SkMatrix44& xform,
- Point3F& point) const {
+ Point3F* point) const {
if (xform.isIdentity())
return;
- SkMScalar p[4] = {
- SkDoubleToMScalar(point.x()),
- SkDoubleToMScalar(point.y()),
- SkDoubleToMScalar(point.z()),
- SkDoubleToMScalar(1)
- };
+ SkMScalar p[4] = {SkFloatToMScalar(point->x()), SkFloatToMScalar(point->y()),
+ SkFloatToMScalar(point->z()), 1};
xform.mapMScalars(p);
if (p[3] != 1 && abs(p[3]) > 0) {
- point.SetPoint(p[0] / p[3], p[1] / p[3], p[2]/ p[3]);
+ point->SetPoint(p[0] / p[3], p[1] / p[3], p[2]/ p[3]);
} else {
- point.SetPoint(p[0], p[1], p[2]);
+ point->SetPoint(p[0], p[1], p[2]);
}
}
void Transform::TransformPointInternal(const SkMatrix44& xform,
- Point& point) const {
+ Point* point) const {
if (xform.isIdentity())
return;
- SkMScalar p[4] = {
- SkDoubleToMScalar(point.x()),
- SkDoubleToMScalar(point.y()),
- SkDoubleToMScalar(0),
- SkDoubleToMScalar(1)
- };
+ SkMScalar p[4] = {SkFloatToMScalar(point->x()), SkFloatToMScalar(point->y()),
+ 0, 1};
xform.mapMScalars(p);
- point.SetPoint(ToRoundedInt(p[0]), ToRoundedInt(p[1]));
+ point->SetPoint(ToRoundedInt(p[0]), ToRoundedInt(p[1]));
}
std::string Transform::ToString() const {
@@ -477,22 +474,22 @@ std::string Transform::ToString() const {
" %+0.4f %+0.4f %+0.4f %+0.4f \n"
" %+0.4f %+0.4f %+0.4f %+0.4f \n"
" %+0.4f %+0.4f %+0.4f %+0.4f ]\n",
- matrix_.getDouble(0, 0),
- matrix_.getDouble(0, 1),
- matrix_.getDouble(0, 2),
- matrix_.getDouble(0, 3),
- matrix_.getDouble(1, 0),
- matrix_.getDouble(1, 1),
- matrix_.getDouble(1, 2),
- matrix_.getDouble(1, 3),
- matrix_.getDouble(2, 0),
- matrix_.getDouble(2, 1),
- matrix_.getDouble(2, 2),
- matrix_.getDouble(2, 3),
- matrix_.getDouble(3, 0),
- matrix_.getDouble(3, 1),
- matrix_.getDouble(3, 2),
- matrix_.getDouble(3, 3));
+ matrix_.get(0, 0),
+ matrix_.get(0, 1),
+ matrix_.get(0, 2),
+ matrix_.get(0, 3),
+ matrix_.get(1, 0),
+ matrix_.get(1, 1),
+ matrix_.get(1, 2),
+ matrix_.get(1, 3),
+ matrix_.get(2, 0),
+ matrix_.get(2, 1),
+ matrix_.get(2, 2),
+ matrix_.get(2, 3),
+ matrix_.get(3, 0),
+ matrix_.get(3, 1),
+ matrix_.get(3, 2),
+ matrix_.get(3, 3));
}
} // namespace gfx
diff --git a/chromium/ui/gfx/transform.h b/chromium/ui/gfx/transform.h
index 66e76ea0514..8e51d7941be 100644
--- a/chromium/ui/gfx/transform.h
+++ b/chromium/ui/gfx/transform.h
@@ -9,7 +9,8 @@
#include "base/compiler_specific.h"
#include "third_party/skia/include/utils/SkMatrix44.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
+#include "ui/gfx/vector2d_f.h"
namespace gfx {
@@ -39,16 +40,31 @@ class UI_EXPORT Transform {
: matrix_(lhs.matrix_, rhs.matrix_) {}
// Constructs a transform from explicit 16 matrix elements. Elements
// should be given in row-major order.
- Transform(double col1row1, double col2row1, double col3row1, double col4row1,
- double col1row2, double col2row2, double col3row2, double col4row2,
- double col1row3, double col2row3, double col3row3, double col4row3,
- double col1row4, double col2row4, double col3row4, double col4row4);
+ Transform(SkMScalar col1row1,
+ SkMScalar col2row1,
+ SkMScalar col3row1,
+ SkMScalar col4row1,
+ SkMScalar col1row2,
+ SkMScalar col2row2,
+ SkMScalar col3row2,
+ SkMScalar col4row2,
+ SkMScalar col1row3,
+ SkMScalar col2row3,
+ SkMScalar col3row3,
+ SkMScalar col4row3,
+ SkMScalar col1row4,
+ SkMScalar col2row4,
+ SkMScalar col3row4,
+ SkMScalar col4row4);
// Constructs a transform from explicit 2d elements. All other matrix
// elements remain the same as the corresponding elements of an identity
// matrix.
- Transform(double col1row1, double col2row1,
- double col1row2, double col2row2,
- double x_translation, double y_translation);
+ Transform(SkMScalar col1row1,
+ SkMScalar col2row1,
+ SkMScalar col1row2,
+ SkMScalar col2row2,
+ SkMScalar x_translation,
+ SkMScalar y_translation);
~Transform() {}
bool operator==(const Transform& rhs) const { return matrix_ == rhs.matrix_; }
@@ -70,22 +86,22 @@ class UI_EXPORT Transform {
// Applies the current transformation on a scaling and assigns the result
// to |this|.
- void Scale(double x, double y);
- void Scale3d(double x, double y, double z);
+ void Scale(SkMScalar x, SkMScalar y);
+ void Scale3d(SkMScalar x, SkMScalar y, SkMScalar z);
// Applies the current transformation on a translation and assigns the result
// to |this|.
- void Translate(double x, double y);
- void Translate3d(double x, double y, double z);
+ void Translate(SkMScalar x, SkMScalar y);
+ void Translate3d(SkMScalar x, SkMScalar y, SkMScalar z);
// Applies the current transformation on a skew and assigns the result
// to |this|.
- void SkewX(double angle_x);
- void SkewY(double angle_y);
+ void SkewX(SkMScalar angle_x);
+ void SkewY(SkMScalar angle_y);
// Applies the current transformation on a perspective transform and assigns
// the result to |this|.
- void ApplyPerspectiveDepth(double depth);
+ void ApplyPerspectiveDepth(SkMScalar depth);
// Applies a transformation on the current transformation
// (i.e. 'this = this * transform;').
@@ -107,9 +123,8 @@ class UI_EXPORT Transform {
bool IsPositiveScaleOrTranslation() const {
if (!IsScaleOrTranslation())
return false;
- return matrix_.getDouble(0, 0) > 0.0 &&
- matrix_.getDouble(1, 1) > 0.0 &&
- matrix_.getDouble(2, 2) > 0.0;
+ return matrix_.get(0, 0) > 0.0 && matrix_.get(1, 1) > 0.0 &&
+ matrix_.get(2, 2) > 0.0;
}
// Returns true if the matrix is either identity or pure, non-fractional
@@ -161,21 +176,24 @@ class UI_EXPORT Transform {
//
void FlattenTo2d();
+ // Returns the x and y translation components of the matrix.
+ Vector2dF To2dTranslation() const;
+
// Applies the transformation on the point. Returns true if the point is
// transformed successfully.
- void TransformPoint(Point3F& point) const;
+ void TransformPoint(Point3F* point) const;
// Applies the transformation on the point. Returns true if the point is
// transformed successfully. Rounds the result to the nearest point.
- void TransformPoint(Point& point) const;
+ void TransformPoint(Point* point) const;
// Applies the reverse transformation on the point. Returns true if the
// transformation can be inverted.
- bool TransformPointReverse(Point3F& point) const;
+ bool TransformPointReverse(Point3F* point) const;
// Applies the reverse transformation on the point. Returns true if the
// transformation can be inverted. Rounds the result to the nearest point.
- bool TransformPointReverse(Point& point) const;
+ bool TransformPointReverse(Point* point) const;
// Applies transformation on the rectangle. Returns true if the transformed
// rectangle was axis aligned. If it returns false, rect will be the
@@ -197,7 +215,7 @@ class UI_EXPORT Transform {
// you're going to be calling this rapidly (e.g., in an animation) you should
// decompose once using gfx::DecomposeTransforms and reuse your
// DecomposedTransform.
- bool Blend(const Transform& from, double progress);
+ bool Blend(const Transform& from, SkMScalar progress);
// Returns |this| * |other|.
Transform operator*(const Transform& other) const {
@@ -218,10 +236,10 @@ class UI_EXPORT Transform {
private:
void TransformPointInternal(const SkMatrix44& xform,
- Point& point) const;
+ Point* point) const;
void TransformPointInternal(const SkMatrix44& xform,
- Point3F& point) const;
+ Point3F* point) const;
SkMatrix44 matrix_;
diff --git a/chromium/ui/gfx/transform_unittest.cc b/chromium/ui/gfx/transform_unittest.cc
index f56ca6dc887..4394af67896 100644
--- a/chromium/ui/gfx/transform_unittest.cc
+++ b/chromium/ui/gfx/transform_unittest.cc
@@ -207,7 +207,7 @@ TEST(XFormTest, ConcatTranslate) {
xform = translation * xform;
Point3F p1(value.x1, value.y1, 0);
Point3F p2(value.x2, value.y2, 0);
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.tx == value.tx &&
value.ty == value.ty) {
EXPECT_TRUE(PointsAreNearlyEqual(p1, p2));
@@ -236,7 +236,7 @@ TEST(XFormTest, ConcatScale) {
xform = scale * xform;
Point3F p1(value.before, value.before, 0);
Point3F p2(value.after, value.after, 0);
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.scale == value.scale) {
EXPECT_TRUE(PointsAreNearlyEqual(p1, p2));
}
@@ -267,7 +267,7 @@ TEST(XFormTest, ConcatRotate) {
xform = rotation * xform;
Point3F p1(value.x1, value.y1, 0);
Point3F p2(value.x2, value.y2, 0);
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.degrees == value.degrees) {
EXPECT_TRUE(PointsAreNearlyEqual(p1, p2));
}
@@ -312,11 +312,11 @@ TEST(XFormTest, SetTranslate) {
break;
}
p0 = p1;
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.tx == value.tx &&
value.ty == value.ty) {
EXPECT_TRUE(PointsAreNearlyEqual(p1, p2));
- xform.TransformPointReverse(p1);
+ xform.TransformPointReverse(&p1);
EXPECT_TRUE(PointsAreNearlyEqual(p1, p0));
}
}
@@ -359,11 +359,11 @@ TEST(XFormTest, SetScale) {
break;
}
p0 = p1;
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.s == value.s) {
EXPECT_TRUE(PointsAreNearlyEqual(p1, p2));
if (value.s != 0.0f) {
- xform.TransformPointReverse(p1);
+ xform.TransformPointReverse(&p1);
EXPECT_TRUE(PointsAreNearlyEqual(p1, p0));
}
}
@@ -399,9 +399,9 @@ TEST(XFormTest, SetRotate) {
xform.Rotate(value.degree);
// just want to make sure that we don't crash in the case of NaN.
if (value.degree == value.degree) {
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
EXPECT_TRUE(PointsAreNearlyEqual(p1, p2));
- xform.TransformPointReverse(p1);
+ xform.TransformPointReverse(&p1);
EXPECT_TRUE(PointsAreNearlyEqual(p1, p0));
}
}
@@ -434,7 +434,7 @@ TEST(XFormTest, ConcatTranslate2D) {
xform = translation * xform;
Point p1(value.x1, value.y1);
Point p2(value.x2, value.y2);
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.tx == value.tx &&
value.ty == value.ty) {
EXPECT_EQ(p1.x(), p2.x());
@@ -464,7 +464,7 @@ TEST(XFormTest, ConcatScale2D) {
xform = scale * xform;
Point p1(value.before, value.before);
Point p2(value.after, value.after);
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.scale == value.scale) {
EXPECT_EQ(p1.x(), p2.x());
EXPECT_EQ(p1.y(), p2.y());
@@ -496,7 +496,7 @@ TEST(XFormTest, ConcatRotate2D) {
xform = rotation * xform;
Point p1(value.x1, value.y1);
Point p2(value.x2, value.y2);
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.degrees == value.degrees) {
EXPECT_EQ(p1.x(), p2.x());
EXPECT_EQ(p1.y(), p2.y());
@@ -545,12 +545,12 @@ TEST(XFormTest, SetTranslate2D) {
break;
}
p0 = p1;
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.tx == value.tx &&
value.ty == value.ty) {
EXPECT_EQ(p1.x(), p2.x());
EXPECT_EQ(p1.y(), p2.y());
- xform.TransformPointReverse(p1);
+ xform.TransformPointReverse(&p1);
EXPECT_EQ(p1.x(), p0.x());
EXPECT_EQ(p1.y(), p0.y());
}
@@ -600,12 +600,12 @@ TEST(XFormTest, SetScale2D) {
break;
}
p0 = p1;
- xform.TransformPoint(p1);
+ xform.TransformPoint(&p1);
if (value.s == value.s) {
EXPECT_EQ(p1.x(), p2.x());
EXPECT_EQ(p1.y(), p2.y());
if (value.s != 0.0f) {
- xform.TransformPointReverse(p1);
+ xform.TransformPointReverse(&p1);
EXPECT_EQ(p1.x(), p0.x());
EXPECT_EQ(p1.y(), p0.y());
}
@@ -643,10 +643,10 @@ TEST(XFormTest, SetRotate2D) {
xform.Rotate(value.degree + j * epsilon);
// just want to make sure that we don't crash in the case of NaN.
if (value.degree == value.degree) {
- xform.TransformPoint(pt);
+ xform.TransformPoint(&pt);
EXPECT_EQ(value.xprime, pt.x());
EXPECT_EQ(value.yprime, pt.y());
- xform.TransformPointReverse(pt);
+ xform.TransformPointReverse(&pt);
EXPECT_EQ(pt.x(), value.x);
EXPECT_EQ(pt.y(), value.y);
}
@@ -2293,10 +2293,10 @@ static bool EmpiricallyPreserves2dAxisAlignment(const Transform& transform) {
PointF(p4.x(), p4.y()));
EXPECT_TRUE(test_quad.IsRectilinear());
- transform.TransformPoint(p1);
- transform.TransformPoint(p2);
- transform.TransformPoint(p3);
- transform.TransformPoint(p4);
+ transform.TransformPoint(&p1);
+ transform.TransformPoint(&p2);
+ transform.TransformPoint(&p3);
+ transform.TransformPoint(&p4);
QuadF transformedQuad(PointF(p1.x(), p1.y()),
PointF(p2.x(), p2.y()),
@@ -2494,6 +2494,16 @@ TEST(XFormTest, Preserves2dAxisAlignment) {
EXPECT_TRUE(transform.Preserves2dAxisAlignment());
}
+TEST(XFormTest, To2dTranslation) {
+ Vector2dF translation(3.f, 7.f);
+ Transform transform;
+ transform.Translate(translation.x(), translation.y() + 1);
+ EXPECT_NE(translation.ToString(), transform.To2dTranslation().ToString());
+ transform.MakeIdentity();
+ transform.Translate(translation.x(), translation.y());
+ EXPECT_EQ(translation.ToString(), transform.To2dTranslation().ToString());
+}
+
} // namespace
} // namespace gfx
diff --git a/chromium/ui/gfx/transform_util.cc b/chromium/ui/gfx/transform_util.cc
index 90c8b56e554..9bb3bbcbcfb 100644
--- a/chromium/ui/gfx/transform_util.cc
+++ b/chromium/ui/gfx/transform_util.cc
@@ -4,6 +4,7 @@
#include "ui/gfx/transform_util.h"
+#include <algorithm>
#include <cmath>
#include "ui/gfx/point.h"
@@ -12,51 +13,51 @@ namespace gfx {
namespace {
-double Length3(double v[3]) {
+SkMScalar Length3(SkMScalar v[3]) {
return std::sqrt(v[0] * v[0] + v[1] * v[1] + v[2] * v[2]);
}
-void Scale3(double v[3], double scale) {
+void Scale3(SkMScalar v[3], SkMScalar scale) {
for (int i = 0; i < 3; ++i)
v[i] *= scale;
}
template <int n>
-double Dot(const double* a, const double* b) {
- double toReturn = 0;
+SkMScalar Dot(const SkMScalar* a, const SkMScalar* b) {
+ SkMScalar toReturn = 0;
for (int i = 0; i < n; ++i)
toReturn += a[i] * b[i];
return toReturn;
}
template <int n>
-void Combine(double* out,
- const double* a,
- const double* b,
- double scale_a,
- double scale_b) {
+void Combine(SkMScalar* out,
+ const SkMScalar* a,
+ const SkMScalar* b,
+ SkMScalar scale_a,
+ SkMScalar scale_b) {
for (int i = 0; i < n; ++i)
out[i] = a[i] * scale_a + b[i] * scale_b;
}
-void Cross3(double out[3], double a[3], double b[3]) {
- double x = a[1] * b[2] - a[2] * b[1];
- double y = a[2] * b[0] - a[0] * b[2];
- double z = a[0] * b[1] - a[1] * b[0];
+void Cross3(SkMScalar out[3], SkMScalar a[3], SkMScalar b[3]) {
+ SkMScalar x = a[1] * b[2] - a[2] * b[1];
+ SkMScalar y = a[2] * b[0] - a[0] * b[2];
+ SkMScalar z = a[0] * b[1] - a[1] * b[0];
out[0] = x;
out[1] = y;
out[2] = z;
}
// Taken from http://www.w3.org/TR/css3-transforms/.
-bool Slerp(double out[4],
- const double q1[4],
- const double q2[4],
- double progress) {
- double product = Dot<4>(q1, q2);
+bool Slerp(SkMScalar out[4],
+ const SkMScalar q1[4],
+ const SkMScalar q2[4],
+ SkMScalar progress) {
+ SkMScalar product = Dot<4>(q1, q2);
// Clamp product to -1.0 <= product <= 1.0.
- product = std::min(std::max(product, -1.0), 1.0);
+ product = std::min(std::max(product, -SK_MScalar1), SK_MScalar1);
// Interpolate angles along the shortest path. For example, to interpolate
// between a 175 degree angle and a 185 degree angle, interpolate along the
@@ -65,25 +66,25 @@ bool Slerp(double out[4],
// the current W3C spec. Fixing the spec to match this approach is discussed
// at:
// http://lists.w3.org/Archives/Public/www-style/2013May/0131.html
- double scale1 = 1.0;
+ SkMScalar scale1 = SK_MScalar1;
if (product < 0) {
product = -product;
- scale1 = -1.0;
+ scale1 = -SK_MScalar1;
}
- const double epsilon = 1e-5;
- if (std::abs(product - 1.0) < epsilon) {
+ const SkMScalar epsilon = 1e-5;
+ if (std::abs(product - SK_MScalar1) < epsilon) {
for (int i = 0; i < 4; ++i)
out[i] = q1[i];
return true;
}
- double denom = std::sqrt(1 - product * product);
- double theta = std::acos(product);
- double w = std::sin(progress * theta) * (1 / denom);
+ SkMScalar denom = std::sqrt(1 - product * product);
+ SkMScalar theta = std::acos(product);
+ SkMScalar w = std::sin(progress * theta) * (1 / denom);
scale1 *= std::cos(progress * theta) - product * w;
- double scale2 = w;
+ SkMScalar scale2 = w;
Combine<4>(out, q1, q2, scale1, scale2);
return true;
@@ -91,14 +92,14 @@ bool Slerp(double out[4],
// Returns false if the matrix cannot be normalized.
bool Normalize(SkMatrix44& m) {
- if (m.getDouble(3, 3) == 0.0)
+ if (m.get(3, 3) == 0.0)
// Cannot normalize.
return false;
- double scale = 1.0 / m.getDouble(3, 3);
+ SkMScalar scale = 1.0 / m.get(3, 3);
for (int i = 0; i < 4; i++)
for (int j = 0; j < 4; j++)
- m.setDouble(i, j, m.getDouble(i, j) * scale);
+ m.set(i, j, m.get(i, j) * scale);
return true;
}
@@ -125,9 +126,9 @@ DecomposedTransform::DecomposedTransform() {
bool BlendDecomposedTransforms(DecomposedTransform* out,
const DecomposedTransform& to,
const DecomposedTransform& from,
- double progress) {
- double scalea = progress;
- double scaleb = 1.0 - progress;
+ SkMScalar progress) {
+ SkMScalar scalea = progress;
+ SkMScalar scaleb = SK_MScalar1 - progress;
Combine<3>(out->translate, to.translate, from.translate, scalea, scaleb);
Combine<3>(out->scale, to.scale, from.scale, scalea, scaleb);
Combine<3>(out->skew, to.skew, from.skew, scalea, scaleb);
@@ -152,18 +153,17 @@ bool DecomposeTransform(DecomposedTransform* decomp,
SkMatrix44 perspectiveMatrix = matrix;
for (int i = 0; i < 3; ++i)
- perspectiveMatrix.setDouble(3, i, 0.0);
+ perspectiveMatrix.set(3, i, 0.0);
- perspectiveMatrix.setDouble(3, 3, 1.0);
+ perspectiveMatrix.set(3, 3, 1.0);
// If the perspective matrix is not invertible, we are also unable to
// decompose, so we'll bail early. Constant taken from SkMatrix44::invert.
if (std::abs(perspectiveMatrix.determinant()) < 1e-8)
return false;
- if (matrix.getDouble(3, 0) != 0.0 ||
- matrix.getDouble(3, 1) != 0.0 ||
- matrix.getDouble(3, 2) != 0.0) {
+ if (matrix.get(3, 0) != 0.0 || matrix.get(3, 1) != 0.0 ||
+ matrix.get(3, 2) != 0.0) {
// rhs is the right hand side of the equation.
SkMScalar rhs[4] = {
matrix.get(3, 0),
@@ -195,12 +195,12 @@ bool DecomposeTransform(DecomposedTransform* decomp,
}
for (int i = 0; i < 3; i++)
- decomp->translate[i] = matrix.getDouble(i, 3);
+ decomp->translate[i] = matrix.get(i, 3);
- double row[3][3];
+ SkMScalar row[3][3];
for (int i = 0; i < 3; i++)
for (int j = 0; j < 3; ++j)
- row[i][j] = matrix.getDouble(j, i);
+ row[i][j] = matrix.get(j, i);
// Compute X scale factor and normalize first row.
decomp->scale[0] = Length3(row[0]);
@@ -235,7 +235,7 @@ bool DecomposeTransform(DecomposedTransform* decomp,
// At this point, the matrix (in rows) is orthonormal.
// Check for a coordinate system flip. If the determinant
// is -1, then negate the matrix and the scaling factors.
- double pdum3[3];
+ SkMScalar pdum3[3];
Cross3(pdum3, row[1], row[2]);
if (Dot<3>(row[0], pdum3) < 0) {
for (int i = 0; i < 3; i++) {
@@ -268,16 +268,15 @@ bool DecomposeTransform(DecomposedTransform* decomp,
Transform ComposeTransform(const DecomposedTransform& decomp) {
SkMatrix44 matrix(SkMatrix44::kIdentity_Constructor);
for (int i = 0; i < 4; i++)
- matrix.setDouble(3, i, decomp.perspective[i]);
+ matrix.set(3, i, decomp.perspective[i]);
- matrix.preTranslate(SkDoubleToMScalar(decomp.translate[0]),
- SkDoubleToMScalar(decomp.translate[1]),
- SkDoubleToMScalar(decomp.translate[2]));
+ matrix.preTranslate(
+ decomp.translate[0], decomp.translate[1], decomp.translate[2]);
- double x = decomp.quaternion[0];
- double y = decomp.quaternion[1];
- double z = decomp.quaternion[2];
- double w = decomp.quaternion[3];
+ SkMScalar x = decomp.quaternion[0];
+ SkMScalar y = decomp.quaternion[1];
+ SkMScalar z = decomp.quaternion[2];
+ SkMScalar w = decomp.quaternion[3];
SkMatrix44 rotation_matrix(SkMatrix44::kUninitialized_Constructor);
rotation_matrix.set3x3(1.0 - 2.0 * (y * y + z * z),
@@ -294,25 +293,23 @@ Transform ComposeTransform(const DecomposedTransform& decomp) {
SkMatrix44 temp(SkMatrix44::kIdentity_Constructor);
if (decomp.skew[2]) {
- temp.setDouble(1, 2, decomp.skew[2]);
+ temp.set(1, 2, decomp.skew[2]);
matrix.preConcat(temp);
}
if (decomp.skew[1]) {
- temp.setDouble(1, 2, 0);
- temp.setDouble(0, 2, decomp.skew[1]);
+ temp.set(1, 2, 0);
+ temp.set(0, 2, decomp.skew[1]);
matrix.preConcat(temp);
}
if (decomp.skew[0]) {
- temp.setDouble(0, 2, 0);
- temp.setDouble(0, 1, decomp.skew[0]);
+ temp.set(0, 2, 0);
+ temp.set(0, 1, decomp.skew[0]);
matrix.preConcat(temp);
}
- matrix.preScale(SkDoubleToMScalar(decomp.scale[0]),
- SkDoubleToMScalar(decomp.scale[1]),
- SkDoubleToMScalar(decomp.scale[2]));
+ matrix.preScale(decomp.scale[0], decomp.scale[1], decomp.scale[2]);
Transform to_return;
to_return.matrix() = matrix;
diff --git a/chromium/ui/gfx/transform_util.h b/chromium/ui/gfx/transform_util.h
index b6da7b0782d..be5ba4c03ce 100644
--- a/chromium/ui/gfx/transform_util.h
+++ b/chromium/ui/gfx/transform_util.h
@@ -5,7 +5,7 @@
#ifndef UI_GFX_TRANSFORM_UTIL_H_
#define UI_GFX_TRANSFORM_UTIL_H_
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/transform.h"
namespace gfx {
@@ -22,11 +22,11 @@ struct UI_EXPORT DecomposedTransform {
// if used with Compose below, will produce the identity transform.
DecomposedTransform();
- double translate[3];
- double scale[3];
- double skew[3];
- double perspective[4];
- double quaternion[4];
+ SkMScalar translate[3];
+ SkMScalar scale[3];
+ SkMScalar skew[3];
+ SkMScalar perspective[4];
+ SkMScalar quaternion[4];
// Copy and assign are allowed.
};
@@ -38,7 +38,7 @@ struct UI_EXPORT DecomposedTransform {
UI_EXPORT bool BlendDecomposedTransforms(DecomposedTransform* out,
const DecomposedTransform& to,
const DecomposedTransform& from,
- double progress);
+ SkMScalar progress);
// Decomposes this transform into its translation, scale, skew, perspective,
// and rotation components following the routines detailed in this spec:
diff --git a/chromium/ui/gfx/transform_util_unittest.cc b/chromium/ui/gfx/transform_util_unittest.cc
index 01ddbe538d0..94195c29bb9 100644
--- a/chromium/ui/gfx/transform_util_unittest.cc
+++ b/chromium/ui/gfx/transform_util_unittest.cc
@@ -21,7 +21,7 @@ TEST(TransformUtilTest, GetScaleTransform) {
for (int sign_y = -1; sign_y <= 1; ++sign_y) {
Point test(kAnchor.x() + sign_x * kOffset,
kAnchor.y() + sign_y * kOffset);
- scale.TransformPoint(test);
+ scale.TransformPoint(&test);
EXPECT_EQ(Point(kAnchor.x() + sign_x * kOffset * kScale,
kAnchor.y() + sign_y * kOffset * kScale),
diff --git a/chromium/ui/base/text/utf16_indexing.cc b/chromium/ui/gfx/utf16_indexing.cc
index d217f5d75c4..6af10c18499 100644
--- a/chromium/ui/base/text/utf16_indexing.cc
+++ b/chromium/ui/gfx/utf16_indexing.cc
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/text/utf16_indexing.h"
+#include "ui/gfx/utf16_indexing.h"
#include "base/logging.h"
#include "base/third_party/icu/icu_utf.h"
-namespace ui {
+namespace gfx {
bool IsValidCodePointIndex(const string16& s, size_t index) {
return index == 0 || index == s.length() ||
@@ -52,4 +52,4 @@ size_t UTF16OffsetToIndex(const string16& s, size_t base, ptrdiff_t offset) {
return pos;
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/text/utf16_indexing.h b/chromium/ui/gfx/utf16_indexing.h
index a1af3d9acd8..7f56384299f 100644
--- a/chromium/ui/base/text/utf16_indexing.h
+++ b/chromium/ui/gfx/utf16_indexing.h
@@ -2,13 +2,13 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_TEXT_UTF16_INDEXING_H_
-#define UI_BASE_TEXT_UTF16_INDEXING_H_
+#ifndef UI_GFX_UTF16_INDEXING_H_
+#define UI_GFX_UTF16_INDEXING_H_
#include "base/strings/string16.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
-namespace ui {
+namespace gfx {
// Returns false if s[index-1] is a high surrogate and s[index] is a low
// surrogate, true otherwise.
@@ -44,6 +44,6 @@ UI_EXPORT size_t UTF16OffsetToIndex(const string16& s,
size_t base,
ptrdiff_t offset);
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_TEXT_UTF16_INDEXING_H_
+#endif // UI_GFX_UTF16_INDEXING_H_
diff --git a/chromium/ui/base/text/utf16_indexing_unittest.cc b/chromium/ui/gfx/utf16_indexing_unittest.cc
index 1bf8c30dbce..da2f8f5b56c 100644
--- a/chromium/ui/base/text/utf16_indexing_unittest.cc
+++ b/chromium/ui/gfx/utf16_indexing_unittest.cc
@@ -3,9 +3,9 @@
// found in the LICENSE file.
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/text/utf16_indexing.h"
+#include "ui/gfx/utf16_indexing.h"
-namespace ui {
+namespace gfx {
TEST(UTF16IndexingTest, IndexOffsetConversions) {
// Valid surrogate pair surrounded by unpaired surrogates
@@ -29,4 +29,4 @@ TEST(UTF16IndexingTest, IndexOffsetConversions) {
}
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/gfx/vector2d.h b/chromium/ui/gfx/vector2d.h
index 69f6b400ce3..9494120d26d 100644
--- a/chromium/ui/gfx/vector2d.h
+++ b/chromium/ui/gfx/vector2d.h
@@ -13,7 +13,7 @@
#include <string>
#include "base/basictypes.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/vector2d_f.h"
namespace gfx {
diff --git a/chromium/ui/gfx/vector2d_f.h b/chromium/ui/gfx/vector2d_f.h
index 4faf28ae226..ebd0b5b4fb5 100644
--- a/chromium/ui/gfx/vector2d_f.h
+++ b/chromium/ui/gfx/vector2d_f.h
@@ -12,7 +12,7 @@
#include <string>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
diff --git a/chromium/ui/gfx/vector3d_f.h b/chromium/ui/gfx/vector3d_f.h
index 17ad332f3aa..aaa415b53bd 100644
--- a/chromium/ui/gfx/vector3d_f.h
+++ b/chromium/ui/gfx/vector3d_f.h
@@ -12,7 +12,7 @@
#include <string>
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/vector2d_f.h"
namespace gfx {
diff --git a/chromium/ui/base/win/dpi.cc b/chromium/ui/gfx/win/dpi.cc
index 63804594d8e..98d23bd5ef9 100644
--- a/chromium/ui/base/win/dpi.cc
+++ b/chromium/ui/gfx/win/dpi.cc
@@ -2,15 +2,16 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/win/dpi.h"
+#include "ui/gfx/win/dpi.h"
#include <windows.h>
#include "base/command_line.h"
#include "base/win/scoped_hdc.h"
+#include "base/win/windows_version.h"
#include "ui/base/layout.h"
#include "base/win/registry.h"
-#include "ui/base/ui_base_switches.h"
#include "ui/gfx/display.h"
+#include "ui/gfx/switches.h"
#include "ui/gfx/point_conversions.h"
#include "ui/gfx/rect_conversions.h"
#include "ui/gfx/size_conversions.h"
@@ -23,7 +24,8 @@ int kDefaultDPIY = 96;
// Tests to see if the command line flag "--high-dpi-support" is set.
bool IsHighDPIEnabled() {
// Default is disabled.
- if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kHighDPISupport)) {
+ if (CommandLine::ForCurrentProcess()->HasSwitch(
+ switches::kHighDPISupport)) {
return CommandLine::ForCurrentProcess()->GetSwitchValueASCII(
switches::kHighDPISupport).compare("1") == 0;
}
@@ -36,7 +38,7 @@ bool IsHighDPIEnabled() {
float GetDeviceScaleFactorImpl() {
if (IsHighDPIEnabled()) {
float scale = gfx::Display::HasForceDeviceScaleFactor() ?
- gfx::Display::GetForcedDeviceScaleFactor() : ui::GetDPIScale();
+ gfx::Display::GetForcedDeviceScaleFactor() : gfx::GetDPIScale();
// Quantize to nearest supported scale factor.
scale = ui::GetScaleFactorScale(ui::GetScaleFactorFromScale(scale));
return scale;
@@ -56,9 +58,9 @@ BOOL IsProcessDPIAwareWrapper() {
} // namespace
-namespace ui {
+namespace gfx {
-gfx::Size GetDPI() {
+Size GetDPI() {
static int dpi_x = 0;
static int dpi_y = 0;
static bool should_initialize = true;
@@ -72,7 +74,7 @@ gfx::Size GetDPI() {
dpi_x = GetDeviceCaps(screen_dc, LOGPIXELSX);
dpi_y = GetDeviceCaps(screen_dc, LOGPIXELSY);
}
- return gfx::Size(dpi_x, dpi_y);
+ return Size(dpi_x, dpi_y);
}
float GetDPIScale() {
@@ -106,35 +108,33 @@ float GetDeviceScaleFactor() {
return device_scale_factor;
}
-gfx::Point ScreenToDIPPoint(const gfx::Point& pixel_point) {
- return gfx::ToFlooredPoint(
- gfx::ScalePoint(pixel_point, 1.0f / GetDeviceScaleFactor()));
+Point ScreenToDIPPoint(const Point& pixel_point) {
+ return ToFlooredPoint(ScalePoint(pixel_point, 1.0f / GetDeviceScaleFactor()));
}
-gfx::Point DIPToScreenPoint(const gfx::Point& dip_point) {
- return gfx::ToFlooredPoint(
- gfx::ScalePoint(dip_point, GetDeviceScaleFactor()));
+Point DIPToScreenPoint(const Point& dip_point) {
+ return ToFlooredPoint(ScalePoint(dip_point, GetDeviceScaleFactor()));
}
-gfx::Rect ScreenToDIPRect(const gfx::Rect& pixel_bounds) {
+Rect ScreenToDIPRect(const Rect& pixel_bounds) {
// TODO(kevers): Switch to non-deprecated method for float to int conversions.
- return gfx::ToFlooredRectDeprecated(
- gfx::ScaleRect(pixel_bounds, 1.0f / GetDeviceScaleFactor()));
+ return ToFlooredRectDeprecated(
+ ScaleRect(pixel_bounds, 1.0f / GetDeviceScaleFactor()));
}
-gfx::Rect DIPToScreenRect(const gfx::Rect& dip_bounds) {
+Rect DIPToScreenRect(const Rect& dip_bounds) {
// TODO(kevers): Switch to non-deprecated method for float to int conversions.
- return gfx::ToFlooredRectDeprecated(
- gfx::ScaleRect(dip_bounds, GetDeviceScaleFactor()));
+ return ToFlooredRectDeprecated(
+ ScaleRect(dip_bounds, GetDeviceScaleFactor()));
}
-gfx::Size ScreenToDIPSize(const gfx::Size& size_in_pixels) {
- return gfx::ToFlooredSize(
- gfx::ScaleSize(size_in_pixels, 1.0f / GetDeviceScaleFactor()));
+Size ScreenToDIPSize(const Size& size_in_pixels) {
+ return ToFlooredSize(
+ ScaleSize(size_in_pixels, 1.0f / GetDeviceScaleFactor()));
}
-gfx::Size DIPToScreenSize(const gfx::Size& dip_size) {
- return gfx::ToFlooredSize(gfx::ScaleSize(dip_size, GetDeviceScaleFactor()));
+Size DIPToScreenSize(const Size& dip_size) {
+ return ToFlooredSize(ScaleSize(dip_size, GetDeviceScaleFactor()));
}
int GetSystemMetricsInDIP(int metric) {
@@ -162,6 +162,14 @@ double GetUndocumentedDPIScale() {
return scale;
}
-} // namespace win
-} // namespace ui
+double GetUndocumentedDPITouchScale() {
+ static double scale =
+ (base::win::GetVersion() < base::win::VERSION_WIN8_1) ?
+ GetUndocumentedDPIScale() : 1.0;
+ return scale;
+}
+
+
+} // namespace win
+} // namespace gfx
diff --git a/chromium/ui/base/win/dpi.h b/chromium/ui/gfx/win/dpi.h
index 90edc7ca397..a056f532661 100644
--- a/chromium/ui/base/win/dpi.h
+++ b/chromium/ui/gfx/win/dpi.h
@@ -2,17 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_WIN_DPI_H_
-#define UI_BASE_WIN_DPI_H_
+#ifndef UI_GFX_DPI_WIN_H_
+#define UI_GFX_DPI_WIN_H_
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/size.h"
-#include "ui/base/ui_export.h"
-namespace ui {
+namespace gfx {
-UI_EXPORT gfx::Size GetDPI();
+UI_EXPORT Size GetDPI();
// Gets the scale factor of the display. For example, if the display DPI is
// 96 then the scale factor is 1.0.
@@ -28,31 +28,36 @@ namespace win {
UI_EXPORT float GetDeviceScaleFactor();
-UI_EXPORT gfx::Point ScreenToDIPPoint(const gfx::Point& pixel_point);
+UI_EXPORT Point ScreenToDIPPoint(const Point& pixel_point);
-UI_EXPORT gfx::Point DIPToScreenPoint(const gfx::Point& dip_point);
+UI_EXPORT Point DIPToScreenPoint(const Point& dip_point);
-UI_EXPORT gfx::Rect ScreenToDIPRect(const gfx::Rect& pixel_bounds);
+UI_EXPORT Rect ScreenToDIPRect(const Rect& pixel_bounds);
-UI_EXPORT gfx::Rect DIPToScreenRect(const gfx::Rect& dip_bounds);
+UI_EXPORT Rect DIPToScreenRect(const Rect& dip_bounds);
-UI_EXPORT gfx::Size ScreenToDIPSize(const gfx::Size& size_in_pixels);
+UI_EXPORT Size ScreenToDIPSize(const Size& size_in_pixels);
-UI_EXPORT gfx::Size DIPToScreenSize(const gfx::Size& dip_size);
+UI_EXPORT Size DIPToScreenSize(const Size& dip_size);
// Win32's GetSystemMetrics uses pixel measures. This function calls
// GetSystemMetrics for the given |metric|, then converts the result to DIP.
UI_EXPORT int GetSystemMetricsInDIP(int metric);
-// The OS secretly scales apps that are not DPIAware. This is not visible
-// through standard OS calls like GetWindowPos(), or through GetDPIScale().
+// Sometimes the OS secretly scales apps that are not DPIAware. This is not
+// visible through standard OS calls like GetWindowPos(), or through
+// GetDPIScale().
// Returns the scale factor of the display, where 96 DPI is 1.0.
// (Avoid this function... use GetDPIScale() instead.)
// TODO(girard): Remove this once DPIAware is enabled - http://crbug.com/149881
UI_EXPORT double GetUndocumentedDPIScale();
-} // namespace win
+// Win7 and Win8 send touch events scaled according to the current DPI
+// scaling. Win8.1 corrects this, and sends touch events in DPI units.
+// This function returns the appropriate scaling factor for touch events.
+UI_EXPORT double GetUndocumentedDPITouchScale();
-} // namespace ui
+} // namespace win
+} // namespace gfx
-#endif // UI_BASE_WIN_DPI_H_
+#endif // UI_GFX_DPI_WIN_H_
diff --git a/chromium/ui/base/win/hwnd_util.cc b/chromium/ui/gfx/win/hwnd_util.cc
index 7299c8cd32d..91f0ddd182a 100644
--- a/chromium/ui/base/win/hwnd_util.cc
+++ b/chromium/ui/gfx/win/hwnd_util.cc
@@ -2,16 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/win/hwnd_util.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "base/i18n/rtl.h"
#include "base/strings/string_util.h"
#include "base/win/metro.h"
+#include "base/win/win_util.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/size.h"
-namespace ui {
+namespace gfx {
namespace {
@@ -23,10 +24,10 @@ void AdjustWindowToFit(HWND hwnd, const RECT& bounds, bool fit_to_monitor) {
if (hmon) {
MONITORINFO mi;
mi.cbSize = sizeof(mi);
- GetMonitorInfo(hmon, &mi);
- gfx::Rect window_rect(bounds);
- gfx::Rect monitor_rect(mi.rcWork);
- gfx::Rect new_window_rect = window_rect;
+ base::win::GetMonitorInfoWrapper(hmon, &mi);
+ Rect window_rect(bounds);
+ Rect monitor_rect(mi.rcWork);
+ Rect new_window_rect = window_rect;
new_window_rect.AdjustToFit(monitor_rect);
if (new_window_rect != window_rect) {
// Window doesn't fit on monitor, move and possibly resize.
@@ -114,7 +115,7 @@ bool DoesWindowBelongToActiveWindow(HWND window) {
void CenterAndSizeWindow(HWND parent,
HWND window,
- const gfx::Size& pref) {
+ const Size& pref) {
DCHECK(window && pref.width() > 0 && pref.height() > 0);
// Calculate the ideal bounds.
@@ -131,7 +132,7 @@ void CenterAndSizeWindow(HWND parent,
if (monitor) {
MONITORINFO mi = {0};
mi.cbSize = sizeof(mi);
- GetMonitorInfo(monitor, &mi);
+ base::win::GetMonitorInfoWrapper(monitor, &mi);
center_bounds = mi.rcWork;
} else {
NOTREACHED() << "Unable to get default monitor";
@@ -176,13 +177,13 @@ void CheckWindowCreated(HWND hwnd) {
void ShowSystemMenu(HWND window) {
RECT rect;
GetWindowRect(window, &rect);
- gfx::Point point = gfx::Point(rect.left, rect.top);
+ Point point = Point(rect.left, rect.top);
static const int kSystemMenuOffset = 10;
point.Offset(kSystemMenuOffset, kSystemMenuOffset);
ShowSystemMenuAtPoint(window, point);
}
-void ShowSystemMenuAtPoint(HWND window, const gfx::Point& point) {
+void ShowSystemMenuAtPoint(HWND window, const Point& point) {
// In the Metro process, we never want to show the system menu.
if (base::win::IsMetroProcess())
return;
@@ -210,4 +211,4 @@ HWND GetWindowToParentTo(bool get_real_hwnd) {
return root_window();
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/win/hwnd_util.h b/chromium/ui/gfx/win/hwnd_util.h
index ece1d3c5b65..70e5f8f1c2b 100644
--- a/chromium/ui/base/win/hwnd_util.h
+++ b/chromium/ui/gfx/win/hwnd_util.h
@@ -2,20 +2,17 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_WIN_HWND_UTIL_H_
-#define UI_BASE_WIN_HWND_UTIL_H_
+#ifndef UI_GFX_WIN_HWND_UTIL_H_
+#define UI_GFX_WIN_HWND_UTIL_H_
#include <windows.h>
#include "base/strings/string16.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
namespace gfx {
class Point;
class Size;
-}
-
-namespace ui {
// A version of the GetClassNameW API that returns the class name in an
// string16. An empty result indicates a failure to get the class name.
@@ -52,6 +49,6 @@ UI_EXPORT void ShowSystemMenuAtPoint(HWND window, const gfx::Point& point);
// container so in those cases you should pass true in |get_real_hwnd|.
UI_EXPORT HWND GetWindowToParentTo(bool get_real_hwnd);
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_WIN_HWND_UTIL_H_
+#endif // UI_GFX_WIN_HWND_UTIL_H_
diff --git a/chromium/ui/base/win/scoped_set_map_mode.h b/chromium/ui/gfx/win/scoped_set_map_mode.h
index bf2b78dca5c..910837d109c 100644
--- a/chromium/ui/base/win/scoped_set_map_mode.h
+++ b/chromium/ui/gfx/win/scoped_set_map_mode.h
@@ -2,15 +2,15 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_WIN_SCOPED_SET_MAP_MODE_H_
-#define UI_BASE_WIN_SCOPED_SET_MAP_MODE_H_
+#ifndef UI_GFX_WIN_SCOPED_SET_MAP_MODE_H_
+#define UI_GFX_WIN_SCOPED_SET_MAP_MODE_H_
#include <windows.h>
#include "base/basictypes.h"
#include "base/logging.h"
-namespace ui {
+namespace gfx {
// Helper class for setting and restore the map mode on a DC.
class ScopedSetMapMode {
@@ -35,6 +35,6 @@ class ScopedSetMapMode {
DISALLOW_COPY_AND_ASSIGN(ScopedSetMapMode);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_WIN_SCOPED_SET_MAP_MODE_H_
+#endif // UI_GFX_WIN_SCOPED_SET_MAP_MODE_H_
diff --git a/chromium/ui/base/win/singleton_hwnd.cc b/chromium/ui/gfx/win/singleton_hwnd.cc
index 9d1685f4977..37993e8f4f0 100644
--- a/chromium/ui/base/win/singleton_hwnd.cc
+++ b/chromium/ui/gfx/win/singleton_hwnd.cc
@@ -2,12 +2,12 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/win/singleton_hwnd.h"
+#include "ui/gfx/win/singleton_hwnd.h"
#include "base/memory/singleton.h"
#include "base/message_loop/message_loop.h"
-namespace ui {
+namespace gfx {
// static
SingletonHwnd* SingletonHwnd::GetInstance() {
@@ -23,7 +23,7 @@ void SingletonHwnd::AddObserver(Observer* observer) {
DLOG(ERROR) << "Cannot create windows on non-UI thread!";
return;
}
- WindowImpl::Init(NULL, gfx::Rect());
+ WindowImpl::Init(NULL, Rect());
}
observer_list_.AddObserver(observer);
}
@@ -52,4 +52,4 @@ SingletonHwnd::SingletonHwnd() {
SingletonHwnd::~SingletonHwnd() {
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/win/singleton_hwnd.h b/chromium/ui/gfx/win/singleton_hwnd.h
index a84b6c0b19b..96af6e79205 100644
--- a/chromium/ui/base/win/singleton_hwnd.h
+++ b/chromium/ui/gfx/win/singleton_hwnd.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_WIN_SINGLETON_HWND_H_
-#define UI_BASE_WIN_SINGLETON_HWND_H_
+#ifndef UI_GFX_WIN_SINGLETON_HWND_H_
+#define UI_GFX_WIN_SINGLETON_HWND_H_
#include <windows.h>
#include <vector>
@@ -11,11 +11,11 @@
#include "base/basictypes.h"
#include "base/callback_forward.h"
#include "base/observer_list.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
template<typename T> struct DefaultSingletonTraits;
-namespace ui {
+namespace gfx {
// Singleton message-only HWND that allows interested clients to receive WM_*
// notifications.
@@ -56,6 +56,6 @@ class SingletonHwnd : public WindowImpl {
DISALLOW_COPY_AND_ASSIGN(SingletonHwnd);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_WIN_SINGLETON_HWND_H_
+#endif // UI_GFX_WIN_SINGLETON_HWND_H_
diff --git a/chromium/ui/base/win/window_impl.cc b/chromium/ui/gfx/win/window_impl.cc
index f53b1bf57ef..e2e6af05c61 100644
--- a/chromium/ui/base/win/window_impl.cc
+++ b/chromium/ui/gfx/win/window_impl.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
#include <list>
@@ -11,9 +11,9 @@
#include "base/strings/string_number_conversions.h"
#include "base/synchronization/lock.h"
#include "base/win/wrapped_window_proc.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/gfx/win/hwnd_util.h"
-namespace ui {
+namespace gfx {
static const DWORD kWindowDefaultChildStyle =
WS_CHILD | WS_VISIBLE | WS_CLIPCHILDREN | WS_CLIPSIBLINGS;
@@ -100,7 +100,6 @@ ATOM ClassRegistrar::RetrieveClassAtom(const ClassInfo& class_info) {
string16 name = string16(WindowImpl::kBaseClassName) +
base::IntToString16(registered_count_++);
- HBRUSH background = NULL;
WNDCLASSEX window_class;
base::win::InitializeWindowClass(
name.c_str(),
@@ -109,7 +108,7 @@ ATOM ClassRegistrar::RetrieveClassAtom(const ClassInfo& class_info) {
0,
0,
NULL,
- reinterpret_cast<HBRUSH>(background + 1),
+ NULL,
NULL,
class_info.icon,
class_info.icon,
@@ -150,7 +149,7 @@ WindowImpl::~WindowImpl() {
ClearUserData();
}
-void WindowImpl::Init(HWND parent, const gfx::Rect& bounds) {
+void WindowImpl::Init(HWND parent, const Rect& bounds) {
if (window_style_ == 0)
window_style_ = parent ? kWindowDefaultChildStyle : kWindowDefaultStyle;
@@ -217,7 +216,7 @@ void WindowImpl::Init(HWND parent, const gfx::Rect& bounds) {
CheckWindowCreated(hwnd_);
// The window procedure should have set the data for us.
- CHECK_EQ(this, ui::GetWindowUserData(hwnd));
+ CHECK_EQ(this, GetWindowUserData(hwnd));
}
HICON WindowImpl::GetDefaultWindowIcon() const {
@@ -237,7 +236,7 @@ LRESULT WindowImpl::OnWndProc(UINT message, WPARAM w_param, LPARAM l_param) {
void WindowImpl::ClearUserData() {
if (::IsWindow(hwnd_))
- ui::SetWindowUserData(hwnd_, NULL);
+ gfx::SetWindowUserData(hwnd_, NULL);
}
// static
@@ -249,7 +248,7 @@ LRESULT CALLBACK WindowImpl::WndProc(HWND hwnd,
CREATESTRUCT* cs = reinterpret_cast<CREATESTRUCT*>(l_param);
WindowImpl* window = reinterpret_cast<WindowImpl*>(cs->lpCreateParams);
DCHECK(window);
- ui::SetWindowUserData(hwnd, window);
+ gfx::SetWindowUserData(hwnd, window);
window->hwnd_ = hwnd;
window->got_create_ = true;
if (hwnd)
@@ -257,8 +256,7 @@ LRESULT CALLBACK WindowImpl::WndProc(HWND hwnd,
return TRUE;
}
- WindowImpl* window = reinterpret_cast<WindowImpl*>(
- ui::GetWindowUserData(hwnd));
+ WindowImpl* window = reinterpret_cast<WindowImpl*>(GetWindowUserData(hwnd));
if (!window)
return 0;
@@ -271,4 +269,4 @@ ATOM WindowImpl::GetWindowClassAtom() {
return ClassRegistrar::GetInstance()->RetrieveClassAtom(class_info);
}
-} // namespace ui
+} // namespace gfx
diff --git a/chromium/ui/base/win/window_impl.h b/chromium/ui/gfx/win/window_impl.h
index 1f3b5d3cf88..2b0018e3f46 100644
--- a/chromium/ui/base/win/window_impl.h
+++ b/chromium/ui/gfx/win/window_impl.h
@@ -2,8 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_BASE_WIN_WINDOW_IMPL_H_
-#define UI_BASE_WIN_WINDOW_IMPL_H_
+#ifndef UI_GFX_WIN_WINDOW_IMPL_H_
+#define UI_GFX_WIN_WINDOW_IMPL_H_
#include <atlbase.h>
#include <atlapp.h>
@@ -13,11 +13,11 @@
#include <string>
#include "base/logging.h"
-#include "ui/base/ui_export.h"
+#include "ui/gfx/gfx_export.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/rect.h"
-namespace ui {
+namespace gfx {
// An interface implemented by classes that use message maps.
// ProcessWindowMessage is implemented by the BEGIN_MESSAGE_MAP_EX macro.
@@ -118,6 +118,6 @@ class UI_EXPORT WindowImpl : public MessageMapInterface {
DISALLOW_COPY_AND_ASSIGN(WindowImpl);
};
-} // namespace ui
+} // namespace gfx
-#endif // UI_BASE_WIN_WINDOW_IMPL_H_
+#endif // UI_GFX_WIN_WINDOW_IMPL_H_
diff --git a/chromium/ui/gfx/x/x11_types.cc b/chromium/ui/gfx/x/x11_types.cc
new file mode 100644
index 00000000000..c47c852527b
--- /dev/null
+++ b/chromium/ui/gfx/x/x11_types.cc
@@ -0,0 +1,16 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/gfx/x/x11_types.h"
+
+#include "base/message_loop/message_loop.h"
+
+namespace gfx {
+
+XDisplay* GetXDisplay() {
+ return base::MessagePumpForUI::GetDefaultXDisplay();
+}
+
+} // namespace gfx
+
diff --git a/chromium/ui/gfx/x/x11_types.h b/chromium/ui/gfx/x/x11_types.h
new file mode 100644
index 00000000000..eab42f2352b
--- /dev/null
+++ b/chromium/ui/gfx/x/x11_types.h
@@ -0,0 +1,25 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_GFX_X_X11_UTIL_H_
+#define UI_GFX_X_X11_UTIL_H_
+
+#include "ui/gfx/gfx_export.h"
+
+typedef unsigned long XID;
+typedef struct _XImage XImage;
+typedef struct _XGC *GC;
+typedef struct _XDisplay XDisplay;
+
+namespace gfx {
+
+// TODO(oshima|evan): This assume there is one display and doesn't work
+// undef multiple displays/monitor environment. Remove this and change the
+// chrome codebase to get the display from window.
+GFX_EXPORT XDisplay* GetXDisplay();
+
+} // namespace gfx
+
+#endif // UI_GFX_X_X11_UTIL_H_
+
diff --git a/chromium/ui/gl/android/gl_jni_registrar.cc b/chromium/ui/gl/android/gl_jni_registrar.cc
deleted file mode 100644
index cba90cef77d..00000000000
--- a/chromium/ui/gl/android/gl_jni_registrar.cc
+++ /dev/null
@@ -1,30 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/gl/android/gl_jni_registrar.h"
-
-#include "base/android/jni_android.h"
-#include "base/android/jni_registrar.h"
-#include "ui/gl/android/surface_texture_bridge.h"
-#include "ui/gl/android/surface_texture_listener.h"
-
-namespace ui {
-namespace gl {
-namespace android {
-
-static base::android::RegistrationMethod kGLRegisteredMethods[] = {
- { "SurfaceTextureBridge",
- gfx::SurfaceTextureBridge::RegisterSurfaceTextureBridge },
- { "SurfaceTextureListener",
- gfx::SurfaceTextureListener::RegisterSurfaceTextureListener },
-};
-
-bool RegisterJni(JNIEnv* env) {
- return RegisterNativeMethods(env, kGLRegisteredMethods,
- arraysize(kGLRegisteredMethods));
-}
-
-} // namespace android
-} // namespace gl
-} // namespace ui
diff --git a/chromium/ui/gl/android/gl_jni_registrar.h b/chromium/ui/gl/android/gl_jni_registrar.h
deleted file mode 100644
index 468557c3e79..00000000000
--- a/chromium/ui/gl/android/gl_jni_registrar.h
+++ /dev/null
@@ -1,23 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_GL_ANDROID_UI_JNI_REGISTRAR_H_
-#define UI_GL_ANDROID_UI_JNI_REGISTRAR_H_
-
-#include <jni.h>
-
-#include "ui/gl/gl_export.h"
-
-namespace ui {
-namespace gl {
-namespace android {
-
-// Register all JNI bindings necessary for chrome.
-GL_EXPORT bool RegisterJni(JNIEnv* env);
-
-} // namespace android
-} // namespace gl
-} // namespace ui
-
-#endif // UI_GL_ANDROID_UI_JNI_REGISTRAR_H_
diff --git a/chromium/ui/gl/android/scoped_java_surface.cc b/chromium/ui/gl/android/scoped_java_surface.cc
index fe6a75e9ace..36f635fe01a 100644
--- a/chromium/ui/gl/android/scoped_java_surface.cc
+++ b/chromium/ui/gl/android/scoped_java_surface.cc
@@ -6,7 +6,7 @@
#include "base/logging.h"
#include "jni/Surface_jni.h"
-#include "ui/gl/android/surface_texture_bridge.h"
+#include "ui/gl/android/surface_texture.h"
namespace {
@@ -37,7 +37,7 @@ ScopedJavaSurface::ScopedJavaSurface(
}
ScopedJavaSurface::ScopedJavaSurface(
- const SurfaceTextureBridge* surface_texture)
+ const SurfaceTexture* surface_texture)
: auto_release_(true),
is_protected_(false) {
JNIEnv* env = base::android::AttachCurrentThread();
diff --git a/chromium/ui/gl/android/scoped_java_surface.h b/chromium/ui/gl/android/scoped_java_surface.h
index b50485b876f..54ed2a45190 100644
--- a/chromium/ui/gl/android/scoped_java_surface.h
+++ b/chromium/ui/gl/android/scoped_java_surface.h
@@ -13,7 +13,7 @@
namespace gfx {
-class SurfaceTextureBridge;
+class SurfaceTexture;
// A helper class for holding a scoped reference to a Java Surface instance.
// When going out of scope, Surface.release() is called on the Java object to
@@ -29,7 +29,7 @@ class GL_EXPORT ScopedJavaSurface {
// Creates a Java Surface from a SurfaceTexture and wraps it in a
// ScopedJavaSurface.
- explicit ScopedJavaSurface(const SurfaceTextureBridge* surface_texture);
+ explicit ScopedJavaSurface(const SurfaceTexture* surface_texture);
// Move constructor. Take the surface from another ScopedJavaSurface object,
// the latter no longer owns the surface afterwards.
diff --git a/chromium/ui/gl/android/surface_texture_bridge.cc b/chromium/ui/gl/android/surface_texture.cc
index 9f2a3372e84..d900972c9d1 100644
--- a/chromium/ui/gl/android/surface_texture_bridge.cc
+++ b/chromium/ui/gl/android/surface_texture.cc
@@ -1,8 +1,8 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/gl/android/surface_texture_bridge.h"
+#include "ui/gl/android/surface_texture.h"
#include <android/native_window_jni.h>
@@ -10,7 +10,7 @@
#include "base/android/build_info.h"
#include "base/android/jni_android.h"
#include "base/logging.h"
-#include "jni/SurfaceTextureBridge_jni.h"
+#include "jni/SurfaceTexturePlatformWrapper_jni.h"
#include "ui/gl/android/scoped_java_surface.h"
#include "ui/gl/android/surface_texture_listener.h"
#include "ui/gl/gl_bindings.h"
@@ -26,36 +26,38 @@ bool GlContextMethodsAvailable() {
namespace gfx {
-SurfaceTextureBridge::SurfaceTextureBridge(int texture_id) {
+SurfaceTexture::SurfaceTexture(int texture_id) {
JNIEnv* env = base::android::AttachCurrentThread();
- j_surface_texture_.Reset(Java_SurfaceTextureBridge_create(env, texture_id));
+ j_surface_texture_.Reset(
+ Java_SurfaceTexturePlatformWrapper_create(env, texture_id));
}
-SurfaceTextureBridge::~SurfaceTextureBridge() {
+SurfaceTexture::~SurfaceTexture() {
JNIEnv* env = base::android::AttachCurrentThread();
- Java_SurfaceTextureBridge_destroy(env, j_surface_texture_.obj());
+ Java_SurfaceTexturePlatformWrapper_destroy(env, j_surface_texture_.obj());
}
-void SurfaceTextureBridge::SetFrameAvailableCallback(
+void SurfaceTexture::SetFrameAvailableCallback(
const base::Closure& callback) {
JNIEnv* env = base::android::AttachCurrentThread();
- Java_SurfaceTextureBridge_setFrameAvailableCallback(
+ Java_SurfaceTexturePlatformWrapper_setFrameAvailableCallback(
env,
j_surface_texture_.obj(),
reinterpret_cast<int>(new SurfaceTextureListener(callback)));
}
-void SurfaceTextureBridge::UpdateTexImage() {
+void SurfaceTexture::UpdateTexImage() {
JNIEnv* env = base::android::AttachCurrentThread();
- Java_SurfaceTextureBridge_updateTexImage(env, j_surface_texture_.obj());
+ Java_SurfaceTexturePlatformWrapper_updateTexImage(env,
+ j_surface_texture_.obj());
}
-void SurfaceTextureBridge::GetTransformMatrix(float mtx[16]) {
+void SurfaceTexture::GetTransformMatrix(float mtx[16]) {
JNIEnv* env = base::android::AttachCurrentThread();
base::android::ScopedJavaLocalRef<jfloatArray> jmatrix(
env, env->NewFloatArray(16));
- Java_SurfaceTextureBridge_getTransformMatrix(
+ Java_SurfaceTexturePlatformWrapper_getTransformMatrix(
env, j_surface_texture_.obj(), jmatrix.obj());
jboolean is_copy;
@@ -66,11 +68,11 @@ void SurfaceTextureBridge::GetTransformMatrix(float mtx[16]) {
env->ReleaseFloatArrayElements(jmatrix.obj(), elements, JNI_ABORT);
}
-void SurfaceTextureBridge::SetDefaultBufferSize(int width, int height) {
+void SurfaceTexture::SetDefaultBufferSize(int width, int height) {
JNIEnv* env = base::android::AttachCurrentThread();
if (width > 0 && height > 0) {
- Java_SurfaceTextureBridge_setDefaultBufferSize(
+ Java_SurfaceTexturePlatformWrapper_setDefaultBufferSize(
env, j_surface_texture_.obj(), static_cast<jint>(width),
static_cast<jint>(height));
} else {
@@ -79,26 +81,26 @@ void SurfaceTextureBridge::SetDefaultBufferSize(int width, int height) {
}
}
-void SurfaceTextureBridge::AttachToGLContext() {
+void SurfaceTexture::AttachToGLContext() {
if (GlContextMethodsAvailable()) {
int texture_id;
glGetIntegerv(GL_TEXTURE_BINDING_EXTERNAL_OES, &texture_id);
DCHECK(texture_id);
JNIEnv* env = base::android::AttachCurrentThread();
- Java_SurfaceTextureBridge_attachToGLContext(
+ Java_SurfaceTexturePlatformWrapper_attachToGLContext(
env, j_surface_texture_.obj(), texture_id);
}
}
-void SurfaceTextureBridge::DetachFromGLContext() {
+void SurfaceTexture::DetachFromGLContext() {
if (GlContextMethodsAvailable()) {
JNIEnv* env = base::android::AttachCurrentThread();
- Java_SurfaceTextureBridge_detachFromGLContext(
+ Java_SurfaceTexturePlatformWrapper_detachFromGLContext(
env, j_surface_texture_.obj());
}
}
-ANativeWindow* SurfaceTextureBridge::CreateSurface() {
+ANativeWindow* SurfaceTexture::CreateSurface() {
JNIEnv* env = base::android::AttachCurrentThread();
ScopedJavaSurface surface(this);
ANativeWindow* native_window = ANativeWindow_fromSurface(
@@ -107,7 +109,7 @@ ANativeWindow* SurfaceTextureBridge::CreateSurface() {
}
// static
-bool SurfaceTextureBridge::RegisterSurfaceTextureBridge(JNIEnv* env) {
+bool SurfaceTexture::RegisterSurfaceTexture(JNIEnv* env) {
return RegisterNativesImpl(env);
}
diff --git a/chromium/ui/gl/android/surface_texture_bridge.h b/chromium/ui/gl/android/surface_texture.h
index 474f0c22d39..62e375f796f 100644
--- a/chromium/ui/gl/android/surface_texture_bridge.h
+++ b/chromium/ui/gl/android/surface_texture.h
@@ -1,9 +1,9 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_GL_ANDROID_SURFACE_TEXTURE_BRIDGE_H_
-#define UI_GL_ANDROID_SURFACE_TEXTURE_BRIDGE_H_
+#ifndef UI_GL_ANDROID_SURFACE_TEXTURE_H_
+#define UI_GL_ANDROID_SURFACE_TEXTURE_H_
#include <jni.h>
@@ -18,10 +18,10 @@ namespace gfx {
// This class serves as a bridge for native code to call java functions inside
// android SurfaceTexture class.
-class GL_EXPORT SurfaceTextureBridge
- : public base::RefCountedThreadSafe<SurfaceTextureBridge>{
+class GL_EXPORT SurfaceTexture
+ : public base::RefCountedThreadSafe<SurfaceTexture>{
public:
- explicit SurfaceTextureBridge(int texture_id);
+ explicit SurfaceTexture(int texture_id);
// Set the listener callback, which will be invoked on the same thread that
// is being called from here for registration.
@@ -57,18 +57,18 @@ class GL_EXPORT SurfaceTextureBridge
return j_surface_texture_;
}
- static bool RegisterSurfaceTextureBridge(JNIEnv* env);
+ static bool RegisterSurfaceTexture(JNIEnv* env);
private:
- friend class base::RefCountedThreadSafe<SurfaceTextureBridge>;
- ~SurfaceTextureBridge();
+ friend class base::RefCountedThreadSafe<SurfaceTexture>;
+ ~SurfaceTexture();
// Java SurfaceTexture instance.
base::android::ScopedJavaGlobalRef<jobject> j_surface_texture_;
- DISALLOW_COPY_AND_ASSIGN(SurfaceTextureBridge);
+ DISALLOW_COPY_AND_ASSIGN(SurfaceTexture);
};
} // namespace gfx
-#endif // UI_GL_ANDROID_SURFACE_TEXTURE_BRIDGE_H_
+#endif // UI_GL_ANDROID_SURFACE_TEXTURE_H_
diff --git a/chromium/ui/gl/android/surface_texture_listener.cc b/chromium/ui/gl/android/surface_texture_listener.cc
index 39d8468dd4a..8e2f89c5256 100644
--- a/chromium/ui/gl/android/surface_texture_listener.cc
+++ b/chromium/ui/gl/android/surface_texture_listener.cc
@@ -8,7 +8,7 @@
#include "base/logging.h"
#include "base/message_loop/message_loop_proxy.h"
#include "jni/SurfaceTextureListener_jni.h"
-#include "ui/gl/android/surface_texture_bridge.h"
+#include "ui/gl/android/surface_texture.h"
namespace gfx {
diff --git a/chromium/ui/gl/android/surface_texture_listener.h b/chromium/ui/gl/android/surface_texture_listener.h
index 60103aad97d..823bc300642 100644
--- a/chromium/ui/gl/android/surface_texture_listener.h
+++ b/chromium/ui/gl/android/surface_texture_listener.h
@@ -33,7 +33,7 @@ class GL_EXPORT SurfaceTextureListener {
SurfaceTextureListener(const base::Closure& callback);
~SurfaceTextureListener();
- friend class SurfaceTextureBridge;
+ friend class SurfaceTexture;
base::Closure callback_;
diff --git a/chromium/ui/gl/generate_bindings.py b/chromium/ui/gl/generate_bindings.py
index 3b37a1708c5..a3f64ae24cf 100755
--- a/chromium/ui/gl/generate_bindings.py
+++ b/chromium/ui/gl/generate_bindings.py
@@ -432,6 +432,13 @@ GL_FUNCTIONS = [
{ 'return_type': 'void*',
'names': ['glMapBuffer', 'glMapBufferOES'],
'arguments': 'GLenum target, GLenum access', },
+{ 'return_type': 'void*',
+ 'names': ['glMapBufferRange'],
+ 'arguments':
+ 'GLenum target, GLintptr offset, GLsizeiptr length, GLenum access', },
+{ 'return_type': 'void',
+ 'names': ['glFlushMappedBufferRange'],
+ 'arguments': 'GLenum target, GLintptr offset, GLsizeiptr length', },
{ 'return_type': 'void',
'names': ['glPixelStorei'],
'arguments': 'GLenum pname, GLint param', },
@@ -740,7 +747,7 @@ GL_FUNCTIONS = [
'APPLE_vertex_array_object',
'ARB_vertex_array_object'] },
{ 'return_type': 'void',
- 'names': ['glDiscardFramebufferEXT'],
+ 'names': ['glDiscardFramebufferEXT', 'glInvalidateFramebuffer'],
'arguments': 'GLenum target, GLsizei numAttachments, '
'const GLenum* attachments' },
]
@@ -945,6 +952,10 @@ EGL_FUNCTIONS = [
'EGLDisplay dpy, EGLSurface surface, '
'EGLuint64CHROMIUM* ust, EGLuint64CHROMIUM* msc, '
'EGLuint64CHROMIUM* sbc', },
+{ 'return_type': 'EGLint',
+ 'names': ['eglWaitSyncKHR'],
+ 'arguments': 'EGLDisplay dpy, EGLSyncKHR sync, EGLint flags',
+ 'other_extensions': ['EGL_KHR_wait_sync'] },
]
WGL_FUNCTIONS = [
diff --git a/chromium/ui/gl/gl.gyp b/chromium/ui/gl/gl.gyp
index 139a88f2626..274065bd8d4 100644
--- a/chromium/ui/gl/gl.gyp
+++ b/chromium/ui/gl/gl.gyp
@@ -44,8 +44,8 @@
'android/gl_jni_registrar.h',
'android/scoped_java_surface.cc',
'android/scoped_java_surface.h',
- 'android/surface_texture_bridge.cc',
- 'android/surface_texture_bridge.h',
+ 'android/surface_texture.cc',
+ 'android/surface_texture.h',
'android/surface_texture_listener.cc',
'android/surface_texture_listener.h',
'gl_bindings.h',
@@ -133,7 +133,8 @@
'action_name': 'generate_gl_bindings',
'variables': {
'generator_path': 'generate_bindings.py',
- 'header_paths': '../../third_party/mesa/src/include:../../third_party/khronos',
+ # Prefer khronos EGL/GLES headers by listing that path first.
+ 'header_paths': '../../third_party/khronos:../../third_party/mesa/src/include',
},
'inputs': [
'<(generator_path)',
@@ -328,7 +329,7 @@
'surface_jni_headers',
],
'sources': [
- '../android/java/src/org/chromium/ui/gfx/SurfaceTextureBridge.java',
+ '../android/java/src/org/chromium/ui/gfx/SurfaceTexturePlatformWrapper.java',
'../android/java/src/org/chromium/ui/gfx/SurfaceTextureListener.java',
],
'variables': {
diff --git a/chromium/ui/gl/gl_bindings.h b/chromium/ui/gl/gl_bindings.h
index 987ec203474..debb0748046 100644
--- a/chromium/ui/gl/gl_bindings.h
+++ b/chromium/ui/gl/gl_bindings.h
@@ -124,8 +124,8 @@
#define GL_LATENCY_QUERY_CHROMIUM 0x84F4
/* GL_CHROMIUM_async_pixel_transfers */
-#define GL_ASYNC_PIXEL_TRANSFERS_COMPLETED_CHROMIUM 0x84F5
-#define GL_ASYNC_READ_PIXELS_COMPLETED_CHROMIUM 0x84F6
+#define GL_ASYNC_PIXEL_UNPACK_COMPLETED_CHROMIUM 0x84F5
+#define GL_ASYNC_PIXEL_PACK_COMPLETED_CHROMIUM 0x84F6
// GL_OES_texure_3D
#define GL_SAMPLER_3D_OES 0x8B5F
diff --git a/chromium/ui/gl/gl_context_android.cc b/chromium/ui/gl/gl_context_android.cc
index d8238db54b6..a9e888b203d 100644
--- a/chromium/ui/gl/gl_context_android.cc
+++ b/chromium/ui/gl/gl_context_android.cc
@@ -20,15 +20,14 @@ namespace {
// Used to render into an already current context+surface,
// that we do not have ownership of (draw callback).
+// TODO(boliu): Make this inherit from GLContextEGL.
class GLNonOwnedContext : public GLContextReal {
public:
GLNonOwnedContext(GLShareGroup* share_group);
// Implement GLContext.
virtual bool Initialize(GLSurface* compatible_surface,
- GpuPreference gpu_preference) OVERRIDE {
- return true;
- }
+ GpuPreference gpu_preference) OVERRIDE;
virtual void Destroy() OVERRIDE {}
virtual bool MakeCurrent(GLSurface* surface) OVERRIDE;
virtual void ReleaseCurrent(GLSurface* surface) OVERRIDE {}
@@ -42,10 +41,18 @@ class GLNonOwnedContext : public GLContextReal {
private:
DISALLOW_COPY_AND_ASSIGN(GLNonOwnedContext);
+
+ EGLDisplay display_;
};
GLNonOwnedContext::GLNonOwnedContext(GLShareGroup* share_group)
- : GLContextReal(share_group) {}
+ : GLContextReal(share_group), display_(NULL) {}
+
+bool GLNonOwnedContext::Initialize(GLSurface* compatible_surface,
+ GpuPreference gpu_preference) {
+ display_ = eglGetDisplay(EGL_DEFAULT_DISPLAY);
+ return true;
+}
bool GLNonOwnedContext::MakeCurrent(GLSurface* surface) {
SetCurrent(surface);
@@ -54,7 +61,11 @@ bool GLNonOwnedContext::MakeCurrent(GLSurface* surface) {
}
std::string GLNonOwnedContext::GetExtensions() {
- return GLContext::GetExtensions();
+ const char* extensions = eglQueryString(display_, EGL_EXTENSIONS);
+ if (!extensions)
+ return GLContext::GetExtensions();
+
+ return GLContext::GetExtensions() + " " + extensions;
}
} // anonymous namespace
@@ -101,7 +112,7 @@ bool GLContextEGL::GetTotalGpuMemory(size_t* bytes) {
// Droid Razr M(1GB) 91MB
// Galaxy Nexus(1GB) 85MB
// Xoom(1GB) 85MB
- // Nexus S(low-end) 16MB
+ // Nexus S(low-end) 8MB
static size_t limit_bytes = 0;
if (limit_bytes == 0) {
if (!base::android::SysUtils::IsLowEndDevice()) {
@@ -114,7 +125,10 @@ bool GLContextEGL::GetTotalGpuMemory(size_t* bytes) {
else
limit_bytes = physical_memory_mb / 16;
} else {
- limit_bytes = physical_memory_mb / 32;
+ // Low-end devices have 512MB or less memory by definition
+ // so we hard code the limit rather than relying on the heuristics
+ // above. Low-end devices use 4444 textures so we can use a lower limit.
+ limit_bytes = 8;
}
limit_bytes = limit_bytes * 1024 * 1024;
}
diff --git a/chromium/ui/gl/gl_fence.cc b/chromium/ui/gl/gl_fence.cc
index b9d9513f926..9b85300fabd 100644
--- a/chromium/ui/gl/gl_fence.cc
+++ b/chromium/ui/gl/gl_fence.cc
@@ -80,6 +80,7 @@ class EGLFenceSync : public gfx::GLFence {
EGLFenceSync() {
display_ = eglGetCurrentDisplay();
sync_ = eglCreateSyncKHR(display_, EGL_SYNC_FENCE_KHR, NULL);
+ glFlush();
}
virtual bool HasCompleted() OVERRIDE {
@@ -90,7 +91,7 @@ class EGLFenceSync : public gfx::GLFence {
}
virtual void ClientWait() OVERRIDE {
- EGLint flags = EGL_SYNC_FLUSH_COMMANDS_BIT_KHR;
+ EGLint flags = 0;
EGLTimeKHR time = EGL_FOREVER_KHR;
eglClientWaitSyncKHR(display_, sync_, flags, time);
}
diff --git a/chromium/ui/gl/gl_image.h b/chromium/ui/gl/gl_image.h
index f1d05371f6b..8d59bc46594 100644
--- a/chromium/ui/gl/gl_image.h
+++ b/chromium/ui/gl/gl_image.h
@@ -38,7 +38,9 @@ class GL_EXPORT GLImage : public base::RefCounted<GLImage> {
// Create a GL image for a GPU Memory buffer.
static scoped_refptr<GLImage> CreateGLImageForGpuMemoryBuffer(
- gfx::GpuMemoryBufferHandle buffer, gfx::Size size);
+ gfx::GpuMemoryBufferHandle buffer,
+ gfx::Size size,
+ unsigned internalformat);
protected:
virtual ~GLImage();
diff --git a/chromium/ui/gl/gl_image_android.cc b/chromium/ui/gl/gl_image_android.cc
index fe871e7b5e3..e56dc2d074b 100644
--- a/chromium/ui/gl/gl_image_android.cc
+++ b/chromium/ui/gl/gl_image_android.cc
@@ -26,13 +26,16 @@ scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
}
scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
- gfx::GpuMemoryBufferHandle buffer, gfx::Size size) {
+ gfx::GpuMemoryBufferHandle buffer,
+ gfx::Size size,
+ unsigned internalformat) {
TRACE_EVENT0("gpu", "GLImage::CreateGLImageForGpuMemoryBuffer");
switch (GetGLImplementation()) {
case kGLImplementationEGLGLES2:
switch (buffer.type) {
case SHARED_MEMORY_BUFFER: {
- scoped_refptr<GLImageShm> image(new GLImageShm(size));
+ scoped_refptr<GLImageShm> image(
+ new GLImageShm(size, internalformat));
if (!image->Initialize(buffer))
return NULL;
diff --git a/chromium/ui/gl/gl_image_mac.cc b/chromium/ui/gl/gl_image_mac.cc
index b244a22ad93..04dc61e870b 100644
--- a/chromium/ui/gl/gl_image_mac.cc
+++ b/chromium/ui/gl/gl_image_mac.cc
@@ -27,7 +27,9 @@ scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
}
scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
- gfx::GpuMemoryBufferHandle buffer, gfx::Size size) {
+ gfx::GpuMemoryBufferHandle buffer,
+ gfx::Size size,
+ unsigned internalformat) {
TRACE_EVENT0("gpu", "GLImage::CreateGLImageForGpuMemoryBuffer");
switch (GetGLImplementation()) {
case kGLImplementationOSMesaGL:
@@ -35,7 +37,8 @@ scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
case kGLImplementationAppleGL:
switch (buffer.type) {
case SHARED_MEMORY_BUFFER: {
- scoped_refptr<GLImageShm> image(new GLImageShm(size));
+ scoped_refptr<GLImageShm> image(
+ new GLImageShm(size, internalformat));
if (!image->Initialize(buffer))
return NULL;
diff --git a/chromium/ui/gl/gl_image_ozone.cc b/chromium/ui/gl/gl_image_ozone.cc
index c217f9992c8..a1c13296aae 100644
--- a/chromium/ui/gl/gl_image_ozone.cc
+++ b/chromium/ui/gl/gl_image_ozone.cc
@@ -27,7 +27,9 @@ scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
}
scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
- gfx::GpuMemoryBufferHandle buffer, gfx::Size size) {
+ gfx::GpuMemoryBufferHandle buffer,
+ gfx::Size size,
+ unsigned internalformat) {
TRACE_EVENT0("gpu", "GLImage::CreateGLImageForGpuMemoryBuffer");
switch (GetGLImplementation()) {
case kGLImplementationOSMesaGL:
diff --git a/chromium/ui/gl/gl_image_shm.cc b/chromium/ui/gl/gl_image_shm.cc
index 14ed8364721..78e816496fb 100644
--- a/chromium/ui/gl/gl_image_shm.cc
+++ b/chromium/ui/gl/gl_image_shm.cc
@@ -10,7 +10,11 @@
namespace gfx {
-GLImageShm::GLImageShm(gfx::Size size) : size_(size) {
+GLImageShm::GLImageShm(gfx::Size size, unsigned internalformat)
+ : size_(size),
+ internalformat_(internalformat) {
+ // GL_RGBA8_OES is currently the only supported internalformat.
+ DCHECK_EQ(static_cast<GLenum>(GL_RGBA8_OES), internalformat);
}
GLImageShm::~GLImageShm() {
@@ -40,8 +44,23 @@ bool GLImageShm::BindTexImage() {
TRACE_EVENT0("gpu", "GLImageShm::BindTexImage");
DCHECK(shared_memory_);
- const int kBytesPerPixel = 4;
- size_t size = size_.GetArea() * kBytesPerPixel;
+ GLenum internalformat;
+ GLenum format;
+ GLenum type;
+ int bytes_per_pixel;
+ switch (internalformat_) {
+ case GL_RGBA8_OES:
+ internalformat = GL_RGBA;
+ format = GL_RGBA;
+ type = GL_UNSIGNED_BYTE;
+ bytes_per_pixel = 4;
+ break;
+ default:
+ DVLOG(0) << "Invalid format: " << internalformat_;
+ return false;
+ }
+
+ size_t size = size_.GetArea() * bytes_per_pixel;
DCHECK(!shared_memory_->memory());
if (!shared_memory_->Map(size)) {
DVLOG(0) << "Failed to map shared memory.";
@@ -51,12 +70,12 @@ bool GLImageShm::BindTexImage() {
DCHECK(shared_memory_->memory());
glTexImage2D(GL_TEXTURE_2D,
0, // mip level
- GL_RGBA,
+ internalformat,
size_.width(),
size_.height(),
0, // border
- GL_RGBA,
- GL_UNSIGNED_BYTE,
+ format,
+ type,
shared_memory_->memory());
shared_memory_->Unmap();
diff --git a/chromium/ui/gl/gl_image_shm.h b/chromium/ui/gl/gl_image_shm.h
index 70233f9a3be..ffdfc8b98da 100644
--- a/chromium/ui/gl/gl_image_shm.h
+++ b/chromium/ui/gl/gl_image_shm.h
@@ -12,7 +12,7 @@ namespace gfx {
class GL_EXPORT GLImageShm : public GLImage {
public:
- explicit GLImageShm(gfx::Size size);
+ GLImageShm(gfx::Size size, unsigned internalformat);
bool Initialize(gfx::GpuMemoryBufferHandle buffer);
@@ -28,6 +28,7 @@ class GL_EXPORT GLImageShm : public GLImage {
private:
scoped_ptr<base::SharedMemory> shared_memory_;
gfx::Size size_;
+ unsigned internalformat_;
DISALLOW_COPY_AND_ASSIGN(GLImageShm);
};
diff --git a/chromium/ui/gl/gl_image_win.cc b/chromium/ui/gl/gl_image_win.cc
index 26b4a8f6920..1486520d6a7 100644
--- a/chromium/ui/gl/gl_image_win.cc
+++ b/chromium/ui/gl/gl_image_win.cc
@@ -27,7 +27,9 @@ scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
}
scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
- gfx::GpuMemoryBufferHandle buffer, gfx::Size size) {
+ gfx::GpuMemoryBufferHandle buffer,
+ gfx::Size size,
+ unsigned internalformat) {
TRACE_EVENT0("gpu", "GLImage::CreateGLImageForGpuMemoryBuffer");
switch (GetGLImplementation()) {
case kGLImplementationOSMesaGL:
@@ -35,7 +37,8 @@ scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
case kGLImplementationEGLGLES2:
switch (buffer.type) {
case SHARED_MEMORY_BUFFER: {
- scoped_refptr<GLImageShm> image(new GLImageShm(size));
+ scoped_refptr<GLImageShm> image(
+ new GLImageShm(size, internalformat));
if (!image->Initialize(buffer))
return NULL;
diff --git a/chromium/ui/gl/gl_image_x11.cc b/chromium/ui/gl/gl_image_x11.cc
index a6c09a15137..6f7d8c6e85b 100644
--- a/chromium/ui/gl/gl_image_x11.cc
+++ b/chromium/ui/gl/gl_image_x11.cc
@@ -35,7 +35,9 @@ scoped_refptr<GLImage> GLImage::CreateGLImage(gfx::PluginWindowHandle window) {
}
scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
- gfx::GpuMemoryBufferHandle buffer, gfx::Size size) {
+ gfx::GpuMemoryBufferHandle buffer,
+ gfx::Size size,
+ unsigned internalformat) {
TRACE_EVENT0("gpu", "GLImage::CreateGLImageForGpuMemoryBuffer");
switch (GetGLImplementation()) {
case kGLImplementationOSMesaGL:
@@ -43,7 +45,8 @@ scoped_refptr<GLImage> GLImage::CreateGLImageForGpuMemoryBuffer(
case kGLImplementationEGLGLES2:
switch (buffer.type) {
case SHARED_MEMORY_BUFFER: {
- scoped_refptr<GLImageShm> image(new GLImageShm(size));
+ scoped_refptr<GLImageShm> image(
+ new GLImageShm(size, internalformat));
if (!image->Initialize(buffer))
return NULL;
diff --git a/chromium/ui/gl/gl_implementation_ozone.cc b/chromium/ui/gl/gl_implementation_ozone.cc
index 607078a4797..d4e3dda9bcc 100644
--- a/chromium/ui/gl/gl_implementation_ozone.cc
+++ b/chromium/ui/gl/gl_implementation_ozone.cc
@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/base/ozone/surface_factory_ozone.h"
+#include "ui/gfx/ozone/surface_factory_ozone.h"
#include "ui/gl/gl_bindings.h"
#include "ui/gl/gl_egl_api_implementation.h"
#include "ui/gl/gl_gl_api_implementation.h"
@@ -41,7 +41,7 @@ bool InitializeGLBindings(GLImplementation implementation) {
case kGLImplementationOSMesaGL:
return InitializeGLBindingsOSMesaGL();
case kGLImplementationEGLGLES2:
- if (!ui::SurfaceFactoryOzone::GetInstance()->LoadEGLGLES2Bindings())
+ if (!gfx::SurfaceFactoryOzone::GetInstance()->LoadEGLGLES2Bindings())
return false;
SetGLImplementation(kGLImplementationEGLGLES2);
InitializeGLBindingsGL();
diff --git a/chromium/ui/gl/gl_implementation_win.cc b/chromium/ui/gl/gl_implementation_win.cc
index c98c3c01314..87328a306f8 100644
--- a/chromium/ui/gl/gl_implementation_win.cc
+++ b/chromium/ui/gl/gl_implementation_win.cc
@@ -8,6 +8,7 @@
#include "base/base_paths.h"
#include "base/bind.h"
#include "base/command_line.h"
+#include "base/debug/trace_event.h"
#include "base/files/file_path.h"
#include "base/logging.h"
#include "base/native_library.h"
@@ -58,6 +59,45 @@ bool LoadD3DXLibrary(const base::FilePath& module_path,
return true;
}
+const unsigned char* AngleGetTraceCategoryEnabledFlag(const char* name) {
+ return TRACE_EVENT_API_GET_CATEGORY_GROUP_ENABLED(name);
+}
+
+void AngleAddTraceEvent(char phase,
+ const unsigned char* category_group_enabled,
+ const char* name,
+ unsigned long long id,
+ int num_args,
+ const char** arg_names,
+ const unsigned char* arg_types,
+ const unsigned long long* arg_values,
+ unsigned char flags) {
+ TRACE_EVENT_API_ADD_TRACE_EVENT(phase,
+ category_group_enabled,
+ name,
+ id,
+ num_args,
+ arg_names,
+ arg_types,
+ arg_values,
+ NULL,
+ flags);
+}
+
+typedef const unsigned char* (*GetCategoryEnabledFlagFunc)(const char* name);
+typedef void (*AddTraceEventFunc)(char phase,
+ const unsigned char* categoryGroupEnabled,
+ const char* name,
+ unsigned long long id,
+ int numArgs,
+ const char** argNames,
+ const unsigned char* argTypes,
+ const unsigned long long* argValues,
+ unsigned char flags);
+typedef void (__stdcall *SetTraceFunctionPointersFunc)(
+ GetCategoryEnabledFlagFunc get_category_enabled_flag,
+ AddTraceEventFunc add_trace_event_func);
+
} // namespace
void GetAllowedGLImplementations(std::vector<GLImplementation>* impls) {
@@ -167,6 +207,17 @@ bool InitializeGLBindings(GLImplementation implementation) {
}
#endif
+ if (!using_swift_shader) {
+ SetTraceFunctionPointersFunc set_trace_function_pointers =
+ reinterpret_cast<SetTraceFunctionPointersFunc>(
+ base::GetFunctionPointerFromNativeLibrary(
+ gles_library, "SetTraceFunctionPointers"));
+ if (set_trace_function_pointers) {
+ set_trace_function_pointers(&AngleGetTraceCategoryEnabledFlag,
+ &AngleAddTraceEvent);
+ }
+ }
+
GLGetProcAddressProc get_proc_address =
reinterpret_cast<GLGetProcAddressProc>(
base::GetFunctionPointerFromNativeLibrary(
diff --git a/chromium/ui/gl/gl_surface_egl.cc b/chromium/ui/gl/gl_surface_egl.cc
index 8c29342ab40..d93a94560fd 100644
--- a/chromium/ui/gl/gl_surface_egl.cc
+++ b/chromium/ui/gl/gl_surface_egl.cc
@@ -32,7 +32,7 @@ extern "C" {
#endif
#if defined (USE_OZONE)
-#include "ui/base/ozone/surface_factory_ozone.h"
+#include "ui/gfx/ozone/surface_factory_ozone.h"
#endif
// From ANGLE's egl/eglext.h.
@@ -100,17 +100,24 @@ bool GLSurfaceEGL::InitializeOneOff() {
if (initialized)
return true;
-#if defined (USE_OZONE)
- ui::SurfaceFactoryOzone::GetInstance()->InitializeHardware();
-#endif
-
#if defined(USE_X11)
g_native_display = base::MessagePumpForUI::GetDefaultXDisplay();
#elif defined(OS_WIN)
g_native_display = EGL_DEFAULT_DISPLAY;
- if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kDisableD3D11)) {
+ if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kDisableD3D11) &&
+ CommandLine::ForCurrentProcess()->HasSwitch(switches::kEnableD3D11)) {
g_native_display = EGL_D3D11_ELSE_D3D9_DISPLAY_ANGLE;
}
+#elif defined(USE_OZONE)
+ gfx::SurfaceFactoryOzone* surface_factory =
+ gfx::SurfaceFactoryOzone::GetInstance();
+ if (surface_factory->InitializeHardware() !=
+ gfx::SurfaceFactoryOzone::INITIALIZED) {
+ LOG(ERROR) << "OZONE failed to initialize hardware";
+ return false;
+ }
+ g_native_display = reinterpret_cast<EGLNativeDisplayType>(
+ surface_factory->GetNativeDisplay());
#else
g_native_display = EGL_DEFAULT_DISPLAY;
#endif
@@ -638,10 +645,10 @@ GLSurface::CreateViewGLSurface(gfx::AcceleratedWidget window) {
scoped_refptr<NativeViewGLSurfaceEGL> surface;
VSyncProvider* sync_provider = NULL;
#if defined(USE_OZONE)
- window = ui::SurfaceFactoryOzone::GetInstance()->RealizeAcceleratedWidget(
+ window = gfx::SurfaceFactoryOzone::GetInstance()->RealizeAcceleratedWidget(
window);
sync_provider =
- ui::SurfaceFactoryOzone::GetInstance()->GetVSyncProvider(window);
+ gfx::SurfaceFactoryOzone::GetInstance()->GetVSyncProvider(window);
#endif
surface = new NativeViewGLSurfaceEGL(window);
if(surface->Initialize(sync_provider))
diff --git a/chromium/ui/gl/gl_surface_glx.cc b/chromium/ui/gl/gl_surface_glx.cc
index 8b705dfbe93..10020d30d9d 100644
--- a/chromium/ui/gl/gl_surface_glx.cc
+++ b/chromium/ui/gl/gl_surface_glx.cc
@@ -10,6 +10,7 @@ extern "C" {
#include "base/basictypes.h"
#include "base/debug/trace_event.h"
+#include "base/lazy_instance.h"
#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/weak_ptr.h"
@@ -39,7 +40,7 @@ class ScopedPtrXFree {
}
};
-Display* g_display;
+Display* g_display = NULL;
const char* g_glx_extensions = NULL;
bool g_glx_context_create = false;
bool g_glx_create_context_robustness_supported = false;
@@ -299,6 +300,73 @@ SGIVideoSyncThread* SGIVideoSyncThread::g_video_sync_thread = NULL;
// goes up (rather than on-demand when we start the thread).
Display* SGIVideoSyncProviderThreadShim::display_ = NULL;
+#if defined(TOOLKIT_GTK)
+// A mechanism for forwarding XExpose events from one window to another.
+// Because in the workaround for http://crbug.com/145600 the child window
+// is placed on top of the parent window, only the child window will receive
+// all expose events. These need to be forwared to the parent window to inform
+// it that it should paint.
+class XExposeEventForwarder : public base::MessagePumpObserver {
+ public:
+ XExposeEventForwarder() {}
+ virtual ~XExposeEventForwarder() {
+ DCHECK(child_to_parent_map_.empty());
+ }
+ void AddParentChildPair(gfx::AcceleratedWidget parent_window,
+ gfx::AcceleratedWidget child_window) {
+ if (child_to_parent_map_.empty())
+ base::MessagePumpX11::Current()->AddObserver(this);
+
+ DCHECK(child_to_parent_map_.find(child_window) ==
+ child_to_parent_map_.end());
+ child_to_parent_map_.insert(std::make_pair(
+ child_window, parent_window));
+ }
+ void RemoveParentChildPair(gfx::AcceleratedWidget parent_window,
+ gfx::AcceleratedWidget child_window) {
+ DCHECK(child_to_parent_map_.find(child_window) !=
+ child_to_parent_map_.end());
+ child_to_parent_map_.erase(child_window);
+
+ if (child_to_parent_map_.empty())
+ base::MessagePumpX11::Current()->RemoveObserver(this);
+ }
+
+ private:
+ virtual base::EventStatus WillProcessEvent (
+ const base::NativeEvent& xevent) OVERRIDE {
+ if (xevent->type != Expose)
+ return base::EVENT_CONTINUE;
+
+ WindowMap::const_iterator found = child_to_parent_map_.find(
+ xevent->xexpose.window);
+ if (found == child_to_parent_map_.end())
+ return base::EVENT_CONTINUE;
+
+ gfx::AcceleratedWidget target_window = found->second;
+ XEvent forwarded_event = *xevent;
+ forwarded_event.xexpose.window = target_window;
+ XSendEvent(g_display, target_window, False, ExposureMask,
+ &forwarded_event);
+ return base::EVENT_CONTINUE;
+ }
+ virtual void DidProcessEvent(const base::NativeEvent& xevent) OVERRIDE {
+ }
+
+ typedef std::map<gfx::AcceleratedWidget, gfx::AcceleratedWidget> WindowMap;
+ WindowMap child_to_parent_map_;
+
+ DISALLOW_COPY_AND_ASSIGN(XExposeEventForwarder);
+};
+
+static base::LazyInstance<XExposeEventForwarder> g_xexpose_event_forwarder =
+ LAZY_INSTANCE_INITIALIZER;
+
+// Do not use this workaround when running in test harnesses that do not have
+// a message loop or do not have a TYPE_GPU message loop.
+bool g_create_child_windows = false;
+#endif
+
} // namespace
GLSurfaceGLX::GLSurfaceGLX() {}
@@ -315,7 +383,21 @@ bool GLSurfaceGLX::InitializeOneOff() {
// it's own thread.
XInitThreads();
+#if defined(TOOLKIT_GTK)
+ // Be sure to use the X display handle and not the GTK display handle if this
+ // is the GPU process.
+ g_create_child_windows =
+ base::MessageLoop::current() &&
+ base::MessageLoop::current()->type() == base::MessageLoop::TYPE_GPU;
+
+ if (g_create_child_windows)
+ g_display = base::MessagePumpX11::GetDefaultXDisplay();
+ else
+ g_display = base::MessagePumpForUI::GetDefaultXDisplay();
+#else
g_display = base::MessagePumpForUI::GetDefaultXDisplay();
+#endif
+
if (!g_display) {
LOG(ERROR) << "XOpenDisplay failed.";
return false;
@@ -388,31 +470,127 @@ void* GLSurfaceGLX::GetDisplay() {
GLSurfaceGLX::~GLSurfaceGLX() {}
+#if defined(TOOLKIT_GTK)
+bool NativeViewGLSurfaceGLX::SetBackbufferAllocation(bool allocated) {
+ backbuffer_allocated_ = allocated;
+ AdjustBufferAllocation();
+ return true;
+}
+
+void NativeViewGLSurfaceGLX::SetFrontbufferAllocation(bool allocated) {
+ frontbuffer_allocated_ = allocated;
+ AdjustBufferAllocation();
+}
+
+void NativeViewGLSurfaceGLX::AdjustBufferAllocation() {
+ if (!g_create_child_windows)
+ return;
+
+ if (frontbuffer_allocated_ || backbuffer_allocated_)
+ CreateChildWindow();
+ else
+ DestroyChildWindow();
+}
+
+void NativeViewGLSurfaceGLX::CreateChildWindow() {
+ DCHECK(g_create_child_windows);
+
+ if (child_window_)
+ return;
+
+ XSetWindowAttributes set_window_attributes;
+ set_window_attributes.event_mask = ExposureMask;
+ child_window_ = XCreateWindow(
+ g_display, parent_window_, 0, 0, size_.width(), size_.height(), 0,
+ CopyFromParent, InputOutput, CopyFromParent, CWEventMask,
+ &set_window_attributes);
+ g_xexpose_event_forwarder.Pointer()->AddParentChildPair(
+ parent_window_, child_window_);
+
+ XMapWindow(g_display, child_window_);
+ XFlush(g_display);
+}
+
+void NativeViewGLSurfaceGLX::DestroyChildWindow() {
+ if (!child_window_)
+ return;
+
+ g_xexpose_event_forwarder.Pointer()->RemoveParentChildPair(
+ parent_window_, child_window_);
+ XDestroyWindow(g_display, child_window_);
+ XFlush(g_display);
+ child_window_ = 0;
+}
+#endif
+
NativeViewGLSurfaceGLX::NativeViewGLSurfaceGLX(gfx::AcceleratedWidget window)
- : window_(window),
+ : parent_window_(window),
+#if defined(TOOLKIT_GTK)
+ child_window_(0),
+ dummy_window_(0),
+ backbuffer_allocated_(true),
+ frontbuffer_allocated_(true),
+#endif
config_(NULL) {
}
+gfx::AcceleratedWidget NativeViewGLSurfaceGLX::GetDrawableHandle() const {
+#if defined(TOOLKIT_GTK)
+ if (g_create_child_windows) {
+ if (child_window_)
+ return child_window_;
+ return dummy_window_;
+ }
+#endif
+ return parent_window_;
+}
+
bool NativeViewGLSurfaceGLX::Initialize() {
XWindowAttributes attributes;
- if (!XGetWindowAttributes(g_display, window_, &attributes)) {
- LOG(ERROR) << "XGetWindowAttributes failed for window " << window_ << ".";
+ if (!XGetWindowAttributes(g_display, parent_window_, &attributes)) {
+ LOG(ERROR) << "XGetWindowAttributes failed for window " << parent_window_
+ << ".";
return false;
}
size_ = gfx::Size(attributes.width, attributes.height);
+ gfx::AcceleratedWidget window_for_vsync = parent_window_;
+
+#if defined(TOOLKIT_GTK)
+ if (g_create_child_windows) {
+ dummy_window_ = XCreateWindow(
+ g_display,
+ RootWindow(g_display, XScreenNumberOfScreen(attributes.screen)),
+ 0, 0, 1, 1, 0, CopyFromParent, InputOutput, attributes.visual, 0, NULL);
+ window_for_vsync = dummy_window_;
+ CreateChildWindow();
+ }
+#endif
+
if (g_glx_oml_sync_control_supported)
- vsync_provider_.reset(new OMLSyncControlVSyncProvider(window_));
+ vsync_provider_.reset(new OMLSyncControlVSyncProvider(window_for_vsync));
else if (g_glx_sgi_video_sync_supported)
- vsync_provider_.reset(new SGIVideoSyncVSyncProvider(window_));
+ vsync_provider_.reset(new SGIVideoSyncVSyncProvider(window_for_vsync));
return true;
}
void NativeViewGLSurfaceGLX::Destroy() {
+#if defined(TOOLKIT_GTK)
+ DestroyChildWindow();
+ if (dummy_window_)
+ XDestroyWindow(g_display, dummy_window_);
+ dummy_window_ = 0;
+#endif
}
bool NativeViewGLSurfaceGLX::Resize(const gfx::Size& size) {
+#if defined(TOOLKIT_GTK)
+ if (child_window_) {
+ XResizeWindow(g_display, child_window_, size.width(), size.height());
+ XFlush(g_display);
+ }
+#endif
size_ = size;
return true;
}
@@ -422,7 +600,7 @@ bool NativeViewGLSurfaceGLX::IsOffscreen() {
}
bool NativeViewGLSurfaceGLX::SwapBuffers() {
- glXSwapBuffers(g_display, window_);
+ glXSwapBuffers(g_display, GetDrawableHandle());
return true;
}
@@ -431,7 +609,7 @@ gfx::Size NativeViewGLSurfaceGLX::GetSize() {
}
void* NativeViewGLSurfaceGLX::GetHandle() {
- return reinterpret_cast<void*>(window_);
+ return reinterpret_cast<void*>(GetDrawableHandle());
}
std::string NativeViewGLSurfaceGLX::GetExtensions() {
@@ -460,10 +638,10 @@ void* NativeViewGLSurfaceGLX::GetConfig() {
XWindowAttributes attributes;
if (!XGetWindowAttributes(
g_display,
- window_,
+ parent_window_,
&attributes)) {
LOG(ERROR) << "XGetWindowAttributes failed for window " <<
- window_ << ".";
+ parent_window_ << ".";
return NULL;
}
@@ -507,7 +685,7 @@ void* NativeViewGLSurfaceGLX::GetConfig() {
bool NativeViewGLSurfaceGLX::PostSubBuffer(
int x, int y, int width, int height) {
DCHECK(gfx::g_driver_glx.ext.b_GLX_MESA_copy_sub_buffer);
- glXCopySubBufferMESA(g_display, window_, x, y, width, height);
+ glXCopySubBufferMESA(g_display, GetDrawableHandle(), x, y, width, height);
return true;
}
@@ -516,7 +694,13 @@ VSyncProvider* NativeViewGLSurfaceGLX::GetVSyncProvider() {
}
NativeViewGLSurfaceGLX::NativeViewGLSurfaceGLX()
- : window_(0),
+ : parent_window_(0),
+#if defined(TOOLKIT_GTK)
+ child_window_(0),
+ dummy_window_(0),
+ backbuffer_allocated_(true),
+ frontbuffer_allocated_(true),
+#endif
config_(NULL) {
}
diff --git a/chromium/ui/gl/gl_surface_glx.h b/chromium/ui/gl/gl_surface_glx.h
index 355b65d1c45..8e7bd1c0c78 100644
--- a/chromium/ui/gl/gl_surface_glx.h
+++ b/chromium/ui/gl/gl_surface_glx.h
@@ -69,9 +69,41 @@ class GL_EXPORT NativeViewGLSurfaceGLX : public GLSurfaceGLX {
NativeViewGLSurfaceGLX();
virtual ~NativeViewGLSurfaceGLX();
- gfx::AcceleratedWidget window_;
-
private:
+ // The handle for the drawable to make current or swap.
+ gfx::AcceleratedWidget GetDrawableHandle() const;
+
+ // Window passed in at creation. Always valid.
+ gfx::AcceleratedWidget parent_window_;
+
+#if defined(TOOLKIT_GTK)
+ // Some NVIDIA drivers don't allow deleting GLX windows separately from their
+ // parent X windows. Work around this by creating a child X window to the
+ // window passed in to the constructor, creating the GLX window against the
+ // child window, and then destroying the child window to destroy the GLX
+ // window.
+ // http://crbug.com/145600
+ void CreateChildWindow();
+ void DestroyChildWindow();
+
+ // Destroy the child window when both the front and back buffers are
+ // deallocated.
+ virtual bool SetBackbufferAllocation(bool allocated) OVERRIDE;
+ virtual void SetFrontbufferAllocation(bool allocated) OVERRIDE;
+ void AdjustBufferAllocation();
+
+ // Child window which is used with GLX, and is discarded when it is
+ // backgrounded.
+ gfx::AcceleratedWidget child_window_;
+
+ // Dummy 1x1 window which is supplied to glXMakeCurrent when making
+ // the context current while its output surface is destroyed.
+ gfx::AcceleratedWidget dummy_window_;
+
+ bool backbuffer_allocated_;
+ bool frontbuffer_allocated_;
+#endif
+
void* config_;
gfx::Size size_;
diff --git a/chromium/ui/gl/gl_switches.cc b/chromium/ui/gl/gl_switches.cc
index 2649abac806..6addfe126fc 100644
--- a/chromium/ui/gl/gl_switches.cc
+++ b/chromium/ui/gl/gl_switches.cc
@@ -18,6 +18,9 @@ const char kGLImplementationMockName[] = "mock";
namespace switches {
+// Enables use of D3D11 when available.
+const char kEnableD3D11[] = "enable-d3d11";
+
// Disables use of D3D11.
const char kDisableD3D11[] = "disable-d3d11";
@@ -70,6 +73,7 @@ const char kTestGLLib[] = "test-gl-lib";
// to read it in the GPU process, else don't add it.
const char* kGLSwitchesCopiedFromGpuProcessHost[] = {
kDisableGpuVsync,
+ kEnableD3D11,
kDisableD3D11,
kEnableGPUServiceLogging,
kEnableGPUServiceTracing,
diff --git a/chromium/ui/gl/gl_switches.h b/chromium/ui/gl/gl_switches.h
index f776f5b4538..57590d7bd87 100644
--- a/chromium/ui/gl/gl_switches.h
+++ b/chromium/ui/gl/gl_switches.h
@@ -23,6 +23,7 @@ extern const char kGLImplementationMockName[];
namespace switches {
+GL_EXPORT extern const char kEnableD3D11[];
GL_EXPORT extern const char kDisableD3D11[];
GL_EXPORT extern const char kDisableGpuVsync[];
GL_EXPORT extern const char kEnableGPUServiceLogging[];
diff --git a/chromium/ui/keyboard/keyboard.gyp b/chromium/ui/keyboard/keyboard.gyp
index d4d7ea17298..7ec43f36edb 100644
--- a/chromium/ui/keyboard/keyboard.gyp
+++ b/chromium/ui/keyboard/keyboard.gyp
@@ -92,14 +92,13 @@
'keyboard_test_suite.cc',
],
'conditions': [
- [ 'os_posix == 1 and OS != "mac" and OS != "android" and OS != "ios"', {
- 'conditions': [
- ['linux_use_tcmalloc==1', {
- 'dependencies': [
- '../../base/allocator/allocator.gyp:allocator',
- ],
- }],
+ ['OS=="linux" and linux_use_tcmalloc==1', {
+ 'dependencies': [
+ '<(DEPTH)/base/allocator/allocator.gyp:allocator',
],
+ 'link_settings': {
+ 'ldflags': ['-rdynamic'],
+ },
}],
],
},
diff --git a/chromium/ui/keyboard/keyboard_controller.cc b/chromium/ui/keyboard/keyboard_controller.cc
index 1a3d88db3e1..83e7f321c5c 100644
--- a/chromium/ui/keyboard/keyboard_controller.cc
+++ b/chromium/ui/keyboard/keyboard_controller.cc
@@ -4,9 +4,11 @@
#include "ui/keyboard/keyboard_controller.h"
+#include "base/bind.h"
#include "ui/aura/layout_manager.h"
#include "ui/aura/window.h"
#include "ui/aura/window_delegate.h"
+#include "ui/base/cursor/cursor.h"
#include "ui/base/hit_test.h"
#include "ui/base/ime/input_method.h"
#include "ui/base/ime/text_input_client.h"
@@ -19,6 +21,8 @@
namespace {
+const int kHideKeyboardDelayMs = 100;
+
gfx::Rect KeyboardBoundsFromWindowBounds(const gfx::Rect& window_bounds) {
const float kKeyboardHeightRatio = 0.3f;
return gfx::Rect(
@@ -68,7 +72,8 @@ class KeyboardWindowDelegate : public aura::WindowDelegate {
gfx::Rect keyboard_bounds = KeyboardBoundsFromWindowBounds(bounds_);
mask->addRect(RectToSkRect(keyboard_bounds));
}
- virtual scoped_refptr<ui::Texture> CopyTexture() OVERRIDE { return NULL; }
+ virtual void DidRecreateLayer(ui::Layer* old_layer,
+ ui::Layer* new_layer) OVERRIDE {}
gfx::Rect bounds_;
DISALLOW_COPY_AND_ASSIGN(KeyboardWindowDelegate);
@@ -118,7 +123,9 @@ class KeyboardLayoutManager : public aura::LayoutManager {
KeyboardController::KeyboardController(KeyboardControllerProxy* proxy)
: proxy_(proxy),
container_(NULL),
- input_method_(NULL) {
+ input_method_(NULL),
+ keyboard_visible_(false),
+ weak_factory_(this) {
CHECK(proxy);
input_method_ = proxy_->GetInputMethod();
input_method_->AddObserver(this);
@@ -142,6 +149,16 @@ aura::Window* KeyboardController::GetContainerWindow() {
return container_;
}
+void KeyboardController::HideKeyboard() {
+ keyboard_visible_ = false;
+
+ FOR_EACH_OBSERVER(KeyboardControllerObserver,
+ observer_list_,
+ OnKeyboardBoundsChanging(gfx::Rect()));
+
+ proxy_->HideKeyboardContainer(container_);
+}
+
void KeyboardController::AddObserver(KeyboardControllerObserver* observer) {
observer_list_.AddObserver(observer);
}
@@ -166,9 +183,11 @@ void KeyboardController::OnTextInputStateChanged(
if (!container_)
return;
- bool was_showing = container_->IsVisible();
+ bool was_showing = keyboard_visible_;
bool should_show = was_showing;
- if (!client || client->GetTextInputType() == ui::TEXT_INPUT_TYPE_NONE) {
+ ui::TextInputType type =
+ client ? client->GetTextInputType() : ui::TEXT_INPUT_TYPE_NONE;
+ if (type == ui::TEXT_INPUT_TYPE_NONE) {
should_show = false;
} else {
if (container_->children().empty()) {
@@ -177,25 +196,34 @@ void KeyboardController::OnTextInputStateChanged(
container_->AddChild(keyboard);
container_->layout_manager()->OnWindowResized();
}
+ proxy_->SetUpdateInputType(type);
container_->parent()->StackChildAtTop(container_);
should_show = true;
}
if (was_showing != should_show) {
- gfx::Rect new_bounds(
- should_show ? container_->children()[0]->bounds() : gfx::Rect());
-
- FOR_EACH_OBSERVER(
- KeyboardControllerObserver,
- observer_list_,
- OnKeyboardBoundsChanging(new_bounds));
-
- if (should_show)
+ if (should_show) {
+ keyboard_visible_ = true;
+ weak_factory_.InvalidateWeakPtrs();
+ if (container_->IsVisible())
+ return;
+
+ FOR_EACH_OBSERVER(
+ KeyboardControllerObserver,
+ observer_list_,
+ OnKeyboardBoundsChanging(container_->children()[0]->bounds()));
proxy_->ShowKeyboardContainer(container_);
- else
- proxy_->HideKeyboardContainer(container_);
+ } else {
+ // Set the visibility state here so that any queries for visibility
+ // before the timer fires returns the correct future value.
+ keyboard_visible_ = false;
+ base::MessageLoop::current()->PostDelayedTask(
+ FROM_HERE,
+ base::Bind(&KeyboardController::HideKeyboard,
+ weak_factory_.GetWeakPtr()),
+ base::TimeDelta::FromMilliseconds(kHideKeyboardDelayMs));
+ }
}
-
// TODO(bryeung): whenever the TextInputClient changes we need to notify the
// keyboard (with the TextInputType) so that it can reset it's state (e.g.
// abandon compositions in progress)
@@ -207,4 +235,8 @@ void KeyboardController::OnInputMethodDestroyed(
input_method_ = NULL;
}
+bool KeyboardController::WillHideKeyboard() const {
+ return weak_factory_.HasWeakPtrs();
+}
+
} // namespace keyboard
diff --git a/chromium/ui/keyboard/keyboard_controller.h b/chromium/ui/keyboard/keyboard_controller.h
index 6022339c380..31f48d3da43 100644
--- a/chromium/ui/keyboard/keyboard_controller.h
+++ b/chromium/ui/keyboard/keyboard_controller.h
@@ -42,6 +42,11 @@ class KEYBOARD_EXPORT KeyboardController : public ui::InputMethodObserver,
// It is the responsibility of the caller to Show() the returned window.
aura::Window* GetContainerWindow();
+ // Hides virtual keyboard and notifies observer bounds change.
+ // This function should be called with a delay to avoid layout flicker
+ // when the focus of input field quickly change.
+ void HideKeyboard();
+
// Management of the observer list.
virtual void AddObserver(KeyboardControllerObserver* observer);
virtual void RemoveObserver(KeyboardControllerObserver* observer);
@@ -61,9 +66,14 @@ class KEYBOARD_EXPORT KeyboardController : public ui::InputMethodObserver,
virtual void OnInputMethodDestroyed(
const ui::InputMethod* input_method) OVERRIDE;
+ // Returns true if keyboard is scheduled to hide.
+ bool WillHideKeyboard() const;
+
scoped_ptr<KeyboardControllerProxy> proxy_;
aura::Window* container_;
ui::InputMethod* input_method_;
+ bool keyboard_visible_;
+ base::WeakPtrFactory<KeyboardController> weak_factory_;
ObserverList<KeyboardControllerObserver> observer_list_;
diff --git a/chromium/ui/keyboard/keyboard_controller_proxy.cc b/chromium/ui/keyboard/keyboard_controller_proxy.cc
index 6f73f276139..1cfb99d92b1 100644
--- a/chromium/ui/keyboard/keyboard_controller_proxy.cc
+++ b/chromium/ui/keyboard/keyboard_controller_proxy.cc
@@ -4,16 +4,53 @@
#include "ui/keyboard/keyboard_controller_proxy.h"
+#include "base/values.h"
#include "content/public/browser/site_instance.h"
#include "content/public/browser/web_contents.h"
+#include "content/public/browser/web_contents.h"
#include "content/public/browser/web_contents_delegate.h"
#include "content/public/browser/web_contents_observer.h"
#include "content/public/browser/web_contents_view.h"
+#include "content/public/browser/web_ui.h"
+#include "content/public/common/bindings_policy.h"
#include "ui/aura/window.h"
#include "ui/keyboard/keyboard_constants.h"
namespace {
+// Converts ui::TextInputType to string.
+std::string TextInputTypeToString(ui::TextInputType type) {
+ switch (type) {
+ case ui::TEXT_INPUT_TYPE_NONE:
+ return "none";
+ case ui::TEXT_INPUT_TYPE_PASSWORD:
+ return "password";
+ case ui::TEXT_INPUT_TYPE_EMAIL:
+ return "email";
+ case ui::TEXT_INPUT_TYPE_NUMBER:
+ return "number";
+ case ui::TEXT_INPUT_TYPE_TELEPHONE:
+ return "tel";
+ case ui::TEXT_INPUT_TYPE_URL:
+ return "url";
+ case ui::TEXT_INPUT_TYPE_DATE:
+ return "date";
+ case ui::TEXT_INPUT_TYPE_TEXT:
+ case ui::TEXT_INPUT_TYPE_SEARCH:
+ case ui::TEXT_INPUT_TYPE_DATE_TIME:
+ case ui::TEXT_INPUT_TYPE_DATE_TIME_LOCAL:
+ case ui::TEXT_INPUT_TYPE_MONTH:
+ case ui::TEXT_INPUT_TYPE_TIME:
+ case ui::TEXT_INPUT_TYPE_WEEK:
+ case ui::TEXT_INPUT_TYPE_TEXT_AREA:
+ case ui::TEXT_INPUT_TYPE_CONTENT_EDITABLE:
+ case ui::TEXT_INPUT_TYPE_DATE_TIME_FIELD:
+ return "text";
+ }
+ NOTREACHED();
+ return "";
+}
+
// The WebContentsDelegate for the keyboard.
// The delegate deletes itself when the keyboard is destroyed.
class KeyboardContentsDelegate : public content::WebContentsDelegate,
@@ -91,6 +128,20 @@ void KeyboardControllerProxy::HideKeyboardContainer(aura::Window* container) {
container->Hide();
}
+void KeyboardControllerProxy::SetUpdateInputType(ui::TextInputType type) {
+ content::WebUI* webui = keyboard_contents_ ?
+ keyboard_contents_->GetCommittedWebUI() : NULL;
+
+ if (webui &&
+ (0 != (webui->GetBindings() & content::BINDINGS_POLICY_WEB_UI))) {
+ // Only call OnTextInputBoxFocused function if it is a web ui keyboard,
+ // not an extension based keyboard.
+ base::DictionaryValue input_context;
+ input_context.SetString("type", TextInputTypeToString(type));
+ webui->CallJavascriptFunction("OnTextInputBoxFocused", input_context);
+ }
+}
+
void KeyboardControllerProxy::SetupWebContents(content::WebContents* contents) {
}
diff --git a/chromium/ui/keyboard/keyboard_controller_proxy.h b/chromium/ui/keyboard/keyboard_controller_proxy.h
index e88e52b6005..53585977998 100644
--- a/chromium/ui/keyboard/keyboard_controller_proxy.h
+++ b/chromium/ui/keyboard/keyboard_controller_proxy.h
@@ -7,6 +7,7 @@
#include "base/memory/scoped_ptr.h"
#include "content/public/common/media_stream_request.h"
+#include "ui/base/ime/text_input_type.h"
#include "ui/keyboard/keyboard_export.h"
namespace aura {
@@ -56,6 +57,11 @@ class KEYBOARD_EXPORT KeyboardControllerProxy {
// necesasry animation, or delay the visibility change as it desires.
virtual void HideKeyboardContainer(aura::Window* container);
+ // Updates the type of the focused text input box. The default implementation
+ // calls OnTextInputBoxFocused javascript function through webui to update the
+ // type the of focused input box.
+ virtual void SetUpdateInputType(ui::TextInputType type);
+
protected:
// Gets the BrowserContext to use for creating the WebContents hosting the
// keyboard.
diff --git a/chromium/ui/keyboard/keyboard_controller_unittest.cc b/chromium/ui/keyboard/keyboard_controller_unittest.cc
index 49c695a6177..1d461166ff6 100644
--- a/chromium/ui/keyboard/keyboard_controller_unittest.cc
+++ b/chromium/ui/keyboard/keyboard_controller_unittest.cc
@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "base/bind.h"
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_loop.h"
#include "testing/gtest/include/gtest/gtest.h"
@@ -134,16 +135,16 @@ class TestTextInputClient : public ui::TextInputClient {
return false;
}
virtual bool HasCompositionText() OVERRIDE { return false; }
- virtual bool GetTextRange(ui::Range* range) OVERRIDE { return false; }
- virtual bool GetCompositionTextRange(ui::Range* range) OVERRIDE {
+ virtual bool GetTextRange(gfx::Range* range) OVERRIDE { return false; }
+ virtual bool GetCompositionTextRange(gfx::Range* range) OVERRIDE {
return false;
}
- virtual bool GetSelectionRange(ui::Range* range) OVERRIDE { return false; }
- virtual bool SetSelectionRange(const ui::Range& range) OVERRIDE {
+ virtual bool GetSelectionRange(gfx::Range* range) OVERRIDE { return false; }
+ virtual bool SetSelectionRange(const gfx::Range& range) OVERRIDE {
return false;
}
- virtual bool DeleteRange(const ui::Range& range) OVERRIDE { return false; }
- virtual bool GetTextFromRange(const ui::Range& range,
+ virtual bool DeleteRange(const gfx::Range& range) OVERRIDE { return false; }
+ virtual bool GetTextFromRange(const gfx::Range& range,
base::string16* text) OVERRIDE {
return false;
}
@@ -158,6 +159,27 @@ class TestTextInputClient : public ui::TextInputClient {
DISALLOW_COPY_AND_ASSIGN(TestTextInputClient);
};
+class KeyboardContainerObserver : public aura::WindowObserver {
+ public:
+ explicit KeyboardContainerObserver(aura::Window* window) : window_(window) {
+ window_->AddObserver(this);
+ }
+ virtual ~KeyboardContainerObserver() {
+ window_->RemoveObserver(this);
+ }
+
+ private:
+ virtual void OnWindowVisibilityChanged(aura::Window* window,
+ bool visible) OVERRIDE {
+ if (!visible)
+ base::MessageLoop::current()->Quit();
+ }
+
+ aura::Window* window_;
+
+ DISALLOW_COPY_AND_ASSIGN(KeyboardContainerObserver);
+};
+
} // namespace
class KeyboardControllerTest : public testing::Test {
@@ -170,6 +192,8 @@ class KeyboardControllerTest : public testing::Test {
aura_test_helper_->SetUp();
ui::SetUpInputMethodFactoryForTesting();
focus_controller_.reset(new TestFocusController(root_window()));
+ proxy_ = new TestKeyboardControllerProxy();
+ controller_.reset(new KeyboardController(proxy_));
}
virtual void TearDown() OVERRIDE {
@@ -178,37 +202,43 @@ class KeyboardControllerTest : public testing::Test {
}
aura::RootWindow* root_window() { return aura_test_helper_->root_window(); }
+ KeyboardControllerProxy* proxy() { return proxy_; }
+ KeyboardController* controller() { return controller_.get(); }
- void ShowKeyboard(KeyboardController* controller) {
+ void ShowKeyboard() {
TestTextInputClient test_text_input_client(ui::TEXT_INPUT_TYPE_TEXT);
- controller->OnTextInputStateChanged(&test_text_input_client);
+ controller_->OnTextInputStateChanged(&test_text_input_client);
}
protected:
+ bool WillHideKeyboard() {
+ return controller_->WillHideKeyboard();
+ }
+
base::MessageLoopForUI message_loop_;
scoped_ptr<aura::test::AuraTestHelper> aura_test_helper_;
scoped_ptr<TestFocusController> focus_controller_;
private:
+ KeyboardControllerProxy* proxy_;
+ scoped_ptr<KeyboardController> controller_;
+
DISALLOW_COPY_AND_ASSIGN(KeyboardControllerTest);
};
TEST_F(KeyboardControllerTest, KeyboardSize) {
- KeyboardControllerProxy* proxy = new TestKeyboardControllerProxy();
- KeyboardController controller(proxy);
-
- scoped_ptr<aura::Window> container(controller.GetContainerWindow());
+ scoped_ptr<aura::Window> container(controller()->GetContainerWindow());
gfx::Rect bounds(0, 0, 100, 100);
container->SetBounds(bounds);
- const gfx::Rect& before_bounds = proxy->GetKeyboardWindow()->bounds();
+ const gfx::Rect& before_bounds = proxy()->GetKeyboardWindow()->bounds();
gfx::Rect new_bounds(
before_bounds.x(), before_bounds.y(),
before_bounds.width() / 2, before_bounds.height() / 2);
// The KeyboardController's LayoutManager shouldn't let this happen
- proxy->GetKeyboardWindow()->SetBounds(new_bounds);
- ASSERT_EQ(before_bounds, proxy->GetKeyboardWindow()->bounds());
+ proxy()->GetKeyboardWindow()->SetBounds(new_bounds);
+ ASSERT_EQ(before_bounds, proxy()->GetKeyboardWindow()->bounds());
}
// Tests that tapping/clicking inside the keyboard does not give it focus.
@@ -222,16 +252,14 @@ TEST_F(KeyboardControllerTest, ClickDoesNotFocusKeyboard) {
window->Show();
window->Focus();
- KeyboardControllerProxy* proxy = new TestKeyboardControllerProxy();
- KeyboardController controller(proxy);
-
- scoped_ptr<aura::Window> keyboard_container(controller.GetContainerWindow());
+ scoped_ptr<aura::Window> keyboard_container(
+ controller()->GetContainerWindow());
keyboard_container->SetBounds(root_bounds);
root_window()->AddChild(keyboard_container.get());
keyboard_container->Show();
- ShowKeyboard(&controller);
+ ShowKeyboard();
EXPECT_TRUE(window->IsVisible());
EXPECT_TRUE(keyboard_container->IsVisible());
@@ -244,7 +272,7 @@ TEST_F(KeyboardControllerTest, ClickDoesNotFocusKeyboard) {
keyboard_container->AddPreTargetHandler(&observer);
aura::test::EventGenerator generator(root_window());
- generator.MoveMouseTo(proxy->GetKeyboardWindow()->bounds().CenterPoint());
+ generator.MoveMouseTo(proxy()->GetKeyboardWindow()->bounds().CenterPoint());
generator.ClickLeftButton();
EXPECT_TRUE(window->HasFocus());
EXPECT_FALSE(keyboard_container->HasFocus());
@@ -260,32 +288,43 @@ TEST_F(KeyboardControllerTest, ClickDoesNotFocusKeyboard) {
TEST_F(KeyboardControllerTest, VisibilityChangeWithTextInputTypeChange) {
const gfx::Rect& root_bounds = root_window()->bounds();
- aura::test::EventCountDelegate delegate;
- scoped_ptr<aura::Window> window(new aura::Window(&delegate));
- window->Init(ui::LAYER_NOT_DRAWN);
- window->SetBounds(root_bounds);
- root_window()->AddChild(window.get());
- window->Show();
- window->Focus();
-
- KeyboardControllerProxy* proxy = new TestKeyboardControllerProxy();
- ui::InputMethod* input_method = proxy->GetInputMethod();
- TestTextInputClient input_client(ui::TEXT_INPUT_TYPE_TEXT);
- TestTextInputClient no_input_client(ui::TEXT_INPUT_TYPE_NONE);
- input_method->SetFocusedTextInputClient(&input_client);
- KeyboardController controller(proxy);
-
- scoped_ptr<aura::Window> keyboard_container(controller.GetContainerWindow());
+ ui::InputMethod* input_method = proxy()->GetInputMethod();
+ TestTextInputClient input_client_0(ui::TEXT_INPUT_TYPE_TEXT);
+ TestTextInputClient input_client_1(ui::TEXT_INPUT_TYPE_TEXT);
+ TestTextInputClient input_client_2(ui::TEXT_INPUT_TYPE_TEXT);
+ TestTextInputClient no_input_client_0(ui::TEXT_INPUT_TYPE_NONE);
+ TestTextInputClient no_input_client_1(ui::TEXT_INPUT_TYPE_NONE);
+ input_method->SetFocusedTextInputClient(&input_client_0);
+
+ scoped_ptr<aura::Window> keyboard_container(
+ controller()->GetContainerWindow());
+ scoped_ptr<KeyboardContainerObserver> keyboard_container_observer(
+ new KeyboardContainerObserver(keyboard_container.get()));
keyboard_container->SetBounds(root_bounds);
root_window()->AddChild(keyboard_container.get());
EXPECT_TRUE(keyboard_container->IsVisible());
- input_method->SetFocusedTextInputClient(&no_input_client);
+ input_method->SetFocusedTextInputClient(&no_input_client_0);
+ // Keyboard should not immediately hide itself. It is delayed to avoid layout
+ // flicker when the focus of input field quickly change.
+ EXPECT_TRUE(keyboard_container->IsVisible());
+ EXPECT_TRUE(WillHideKeyboard());
+ // Wait for hide keyboard to finish.
+ base::MessageLoop::current()->Run();
EXPECT_FALSE(keyboard_container->IsVisible());
- input_method->SetFocusedTextInputClient(&input_client);
+ input_method->SetFocusedTextInputClient(&input_client_1);
+ EXPECT_TRUE(keyboard_container->IsVisible());
+
+ // Schedule to hide keyboard.
+ input_method->SetFocusedTextInputClient(&no_input_client_1);
+ EXPECT_TRUE(WillHideKeyboard());
+ // Cancel keyboard hide.
+ input_method->SetFocusedTextInputClient(&input_client_2);
+
+ EXPECT_FALSE(WillHideKeyboard());
EXPECT_TRUE(keyboard_container->IsVisible());
}
diff --git a/chromium/ui/keyboard/keyboard_resources.grd b/chromium/ui/keyboard/keyboard_resources.grd
index 2509d68dc64..8e3da16b8ab 100644
--- a/chromium/ui/keyboard/keyboard_resources.grd
+++ b/chromium/ui/keyboard/keyboard_resources.grd
@@ -23,11 +23,13 @@
<include name="IDR_KEYBOARD_ELEMENTS_ALTKEY_SET" file="resources/elements/kb-altkey-set.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_KEY" file="resources/elements/kb-key.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_KEY_BASE" file="resources/elements/kb-key-base.html" type="BINDATA" />
+ <include name="IDR_KEYBOARD_ELEMENTS_KEY_CODES" file="resources/elements/kb-key-codes.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_KEY_IMPORT" file="resources/elements/kb-key-import.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_KEY_SEQUENCE" file="resources/elements/kb-key-sequence.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_KEYBOARD" file="resources/elements/kb-keyboard.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_KEYSET" file="resources/elements/kb-keyset.html" type="BINDATA" />
<include name="IDR_KEYBOARD_ELEMENTS_ROW" file="resources/elements/kb-row.html" type="BINDATA" />
+ <include name="IDR_KEYBOARD_ELEMENTS_SHIFT_KEY" file="resources/elements/kb-shift-key.html" type="BINDATA" />
<include name="IDR_KEYBOARD_IMAGES_KEYBOARD" file="resources/images/keyboard.svg" type="BINDATA" />
<include name="IDR_KEYBOARD_IMAGES_MICROPHONE" file="resources/images/microphone.svg" type="BINDATA" />
<include name="IDR_KEYBOARD_IMAGES_MICROPHONE_GREEN" file="resources/images/microphone-green.svg" type="BINDATA" />
@@ -35,6 +37,7 @@
<include name="IDR_KEYBOARD_INDEX" file="resources/index.html" allowexternalscript="true" type="BINDATA" />
<include name="IDR_KEYBOARD_LAYOUTS_DVORAK" file="resources/layouts/dvorak.html" type="BINDATA" />
<include name="IDR_KEYBOARD_LAYOUTS_LATIN_ACCENTS" file="resources/layouts/latin-accents.js" type="BINDATA" />
+ <include name="IDR_KEYBOARD_LAYOUTS_NUMERIC" file="resources/layouts/numeric.html" type="BINDATA" />
<include name="IDR_KEYBOARD_LAYOUTS_QWERTY" file="resources/layouts/qwerty.html" type="BINDATA" />
<include name="IDR_KEYBOARD_LAYOUTS_SYMBOL_ALTKEYS" file="resources/layouts/symbol-altkeys.js" type="BINDATA" />
<include name="IDR_KEYBOARD_MAIN_JS" file="resources/main.js" type="BINDATA" />
diff --git a/chromium/ui/keyboard/keyboard_ui_controller.cc b/chromium/ui/keyboard/keyboard_ui_controller.cc
index 1ee8d40a43b..8bc009202d0 100644
--- a/chromium/ui/keyboard/keyboard_ui_controller.cc
+++ b/chromium/ui/keyboard/keyboard_ui_controller.cc
@@ -30,17 +30,22 @@ content::WebUIDataSource* CreateKeyboardUIDataSource() {
source->AddResourcePath("elements/kb-key.html", IDR_KEYBOARD_ELEMENTS_KEY);
source->AddResourcePath("elements/kb-key-base.html",
IDR_KEYBOARD_ELEMENTS_KEY_BASE);
+ source->AddResourcePath("elements/kb-key-codes.html",
+ IDR_KEYBOARD_ELEMENTS_KEY_CODES);
source->AddResourcePath("elements/kb-keyboard.html",
IDR_KEYBOARD_ELEMENTS_KEYBOARD);
source->AddResourcePath("elements/kb-keyset.html",
IDR_KEYBOARD_ELEMENTS_KEYSET);
source->AddResourcePath("elements/kb-row.html", IDR_KEYBOARD_ELEMENTS_ROW);
+ source->AddResourcePath("elements/kb-shift-key.html",
+ IDR_KEYBOARD_ELEMENTS_SHIFT_KEY);
source->AddResourcePath("images/microphone.svg",
IDR_KEYBOARD_IMAGES_MICROPHONE);
source->AddResourcePath("images/microphone-green.svg",
IDR_KEYBOARD_IMAGES_MICROPHONE_GREEN);
source->AddResourcePath("layouts/latin-accents.js",
IDR_KEYBOARD_LAYOUTS_LATIN_ACCENTS);
+ source->AddResourcePath("layouts/numeric.html", IDR_KEYBOARD_LAYOUTS_NUMERIC);
source->AddResourcePath("main.js", IDR_KEYBOARD_MAIN_JS);
source->AddResourcePath("polymer.min.js", IDR_KEYBOARD_POLYMER);
source->AddResourcePath("voice_input.js", IDR_KEYBOARD_VOICE_INPUT_JS);
diff --git a/chromium/ui/keyboard/keyboard_ui_handler.cc b/chromium/ui/keyboard/keyboard_ui_handler.cc
index 0c412675d3e..26909c2d49e 100644
--- a/chromium/ui/keyboard/keyboard_ui_handler.cc
+++ b/chromium/ui/keyboard/keyboard_ui_handler.cc
@@ -12,7 +12,12 @@
#include "content/public/browser/web_contents.h"
#include "content/public/browser/web_contents_view.h"
#include "content/public/browser/web_ui.h"
+#include "ui/aura/client/aura_constants.h"
+#include "ui/aura/root_window.h"
#include "ui/aura/window.h"
+#include "ui/base/ime/input_method.h"
+#include "ui/base/ime/text_input_client.h"
+#include "ui/keyboard/keyboard_controller.h"
#include "ui/keyboard/keyboard_util.h"
namespace keyboard {
@@ -28,6 +33,18 @@ void KeyboardUIHandler::RegisterMessages() {
"insertText",
base::Bind(&KeyboardUIHandler::HandleInsertTextMessage,
base::Unretained(this)));
+ web_ui()->RegisterMessageCallback(
+ "getInputContext",
+ base::Bind(&KeyboardUIHandler::HandleGetInputContextMessage,
+ base::Unretained(this)));
+ web_ui()->RegisterMessageCallback(
+ "sendKeyEvent",
+ base::Bind(&KeyboardUIHandler::HandleSendKeyEventMessage,
+ base::Unretained(this)));
+ web_ui()->RegisterMessageCallback(
+ "hideKeyboard",
+ base::Bind(&KeyboardUIHandler::HandleHideKeyboard,
+ base::Unretained(this)));
}
void KeyboardUIHandler::HandleInsertTextMessage(const base::ListValue* args) {
@@ -48,4 +65,75 @@ void KeyboardUIHandler::HandleInsertTextMessage(const base::ListValue* args) {
LOG(ERROR) << "insertText failed";
}
+void KeyboardUIHandler::HandleGetInputContextMessage(
+ const base::ListValue* args) {
+ int request_id;
+ if (!args->GetInteger(0, &request_id)) {
+ LOG(ERROR) << "getInputContext failed: bad argument";
+ return;
+ }
+ base::DictionaryValue results;
+ results.SetInteger("requestId", request_id);
+
+ aura::RootWindow* root_window =
+ web_ui()->GetWebContents()->GetView()->GetNativeView()->GetRootWindow();
+ if (!root_window) {
+ LOG(ERROR) << "getInputContext failed: no root window";
+ return;
+ }
+ ui::InputMethod* input_method =
+ root_window->GetProperty(aura::client::kRootWindowInputMethodKey);
+ if (!input_method) {
+ LOG(ERROR) << "getInputContext failed: no input method";
+ return;
+ }
+
+ ui::TextInputClient* tic = input_method->GetTextInputClient();
+ results.SetInteger("type",
+ tic ? tic->GetTextInputType() : ui::TEXT_INPUT_TYPE_NONE);
+
+ web_ui()->CallJavascriptFunction("GetInputContextCallback",
+ results);
+}
+
+void KeyboardUIHandler::HandleSendKeyEventMessage(
+ const base::ListValue* args) {
+ const base::DictionaryValue* params = NULL;
+ std::string type;
+ int char_value;
+ int key_code;
+ bool shift_modifier;
+
+ if (!args->GetDictionary(0, &params) ||
+ !params->GetString("type", &type) ||
+ !params->GetInteger("charValue", &char_value) ||
+ !params->GetInteger("keyCode", &key_code) ||
+ !params->GetBoolean("shiftKey", &shift_modifier)) {
+ LOG(ERROR) << "SendKeyEvent failed: bad argument";
+ return;
+ }
+
+ aura::RootWindow* root_window =
+ web_ui()->GetWebContents()->GetView()->GetNativeView()->GetRootWindow();
+ if (!root_window) {
+ LOG(ERROR) << "sendKeyEvent failed: no root window";
+ return;
+ }
+
+ if (!keyboard::SendKeyEvent(type,
+ char_value,
+ key_code,
+ shift_modifier,
+ root_window)) {
+ LOG(ERROR) << "sendKeyEvent failed";
+ }
+}
+
+void KeyboardUIHandler::HandleHideKeyboard(const base::ListValue* args) {
+ // TODO(stevet): Call into the keyboard controller to hide the keyboard
+ // directly.
+ NOTIMPLEMENTED();
+ return;
+}
+
} // namespace keyboard
diff --git a/chromium/ui/keyboard/keyboard_ui_handler.h b/chromium/ui/keyboard/keyboard_ui_handler.h
index 0800453192d..3c14f7473e5 100644
--- a/chromium/ui/keyboard/keyboard_ui_handler.h
+++ b/chromium/ui/keyboard/keyboard_ui_handler.h
@@ -25,6 +25,18 @@ class KeyboardUIHandler : public content::WebUIMessageHandler {
// Callback for the "insertText" message.
void HandleInsertTextMessage(const base::ListValue* args);
+ // Callback for the "getInputContext" message. The first element in
+ // |args| should be an integer representing request ID.
+ void HandleGetInputContextMessage(const base::ListValue* args);
+
+ // Callback for the "sendKeyEvent" message. The first element in |args| is a
+ // dictionary containing an event type, the character being pressed or
+ // released, a virtual key code, and the state of the shift key.
+ void HandleSendKeyEventMessage(const base::ListValue* args);
+
+ // Callback for the "hideKeyboard" message.
+ void HandleHideKeyboard(const base::ListValue* args);
+
DISALLOW_COPY_AND_ASSIGN(KeyboardUIHandler);
};
diff --git a/chromium/ui/keyboard/keyboard_util.cc b/chromium/ui/keyboard/keyboard_util.cc
index 1579068f884..8389e55f03b 100644
--- a/chromium/ui/keyboard/keyboard_util.cc
+++ b/chromium/ui/keyboard/keyboard_util.cc
@@ -17,6 +17,20 @@
#include "ui/base/ime/text_input_client.h"
#include "ui/keyboard/keyboard_switches.h"
+namespace {
+
+const char kKeyDown[] ="keydown";
+const char kKeyUp[] = "keyup";
+
+void SendProcessKeyEvent(ui::EventType type, aura::RootWindow* root_window) {
+ ui::TranslatedKeyEvent event(type == ui::ET_KEY_PRESSED,
+ ui::VKEY_PROCESSKEY,
+ ui::EF_NONE);
+ root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&event);
+}
+
+} // namespace
+
namespace keyboard {
bool IsKeyboardEnabled() {
@@ -28,28 +42,6 @@ bool InsertText(const base::string16& text, aura::RootWindow* root_window) {
if (!root_window)
return false;
- // Handle Backspace and Enter specially: using TextInputClient::InsertText is
- // very unreliable for these characters.
- // TODO(bryeung): remove this code once virtual keyboards are able to send
- // these events directly via the Input Injection API.
- if (text.length() == 1) {
- ui::KeyboardCode code = ui::VKEY_UNKNOWN;
- if (text[0] == L'\n')
- code = ui::VKEY_RETURN;
- else if (text[0] == L'\b')
- code = ui::VKEY_BACK;
-
- if (code != ui::VKEY_UNKNOWN) {
- ui::KeyEvent press_event(ui::ET_KEY_PRESSED, code, 0, 0);
- root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&press_event);
-
- ui::KeyEvent release_event(ui::ET_KEY_RELEASED, code, 0, 0);
- root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&release_event);
-
- return true;
- }
- }
-
ui::InputMethod* input_method = root_window->GetProperty(
aura::client::kRootWindowInputMethodKey);
if (!input_method)
@@ -103,6 +95,47 @@ bool MoveCursor(int swipe_direction,
return true;
}
+bool SendKeyEvent(const std::string type,
+ int key_value,
+ int key_code,
+ bool shift_modifier,
+ aura::RootWindow* root_window) {
+ ui::EventType event_type = ui::ET_UNKNOWN;
+ if (type == kKeyDown)
+ event_type = ui::ET_KEY_PRESSED;
+ else if (type == kKeyUp)
+ event_type = ui::ET_KEY_RELEASED;
+ if (event_type == ui::ET_UNKNOWN)
+ return false;
+
+ int flags = ui::EF_NONE;
+ if (shift_modifier)
+ flags = ui::EF_SHIFT_DOWN;
+
+ ui::KeyboardCode code = static_cast<ui::KeyboardCode>(key_code);
+
+ if (code == ui::VKEY_UNKNOWN) {
+ // Handling of special printable characters (e.g. accented characters) for
+ // which there is no key code.
+ if (event_type == ui::ET_KEY_RELEASED) {
+ ui::InputMethod* input_method = root_window->GetProperty(
+ aura::client::kRootWindowInputMethodKey);
+ if (!input_method)
+ return false;
+
+ ui::TextInputClient* tic = input_method->GetTextInputClient();
+
+ SendProcessKeyEvent(ui::ET_KEY_PRESSED, root_window);
+ tic->InsertChar(static_cast<uint16>(key_value), ui::EF_NONE);
+ SendProcessKeyEvent(ui::ET_KEY_RELEASED, root_window);
+ }
+ } else {
+ ui::KeyEvent event(event_type, code, flags, false);
+ root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&event);
+ }
+ return true;
+}
+
const GritResourceMap* GetKeyboardExtensionResources(size_t* size) {
// This looks a lot like the contents of a resource map; however it is
// necessary to have a custom path for the extension path, so the resource
@@ -118,6 +151,7 @@ const GritResourceMap* GetKeyboardExtensionResources(size_t* size) {
{"keyboard/elements/kb-altkey-set.html", IDR_KEYBOARD_ELEMENTS_ALTKEY_SET},
{"keyboard/elements/kb-key.html", IDR_KEYBOARD_ELEMENTS_KEY},
{"keyboard/elements/kb-key-base.html", IDR_KEYBOARD_ELEMENTS_KEY_BASE},
+ {"keyboard/elements/kb-key-codes.html", IDR_KEYBOARD_ELEMENTS_KEY_CODES},
{"keyboard/elements/kb-key-import.html",
IDR_KEYBOARD_ELEMENTS_KEY_IMPORT},
{"keyboard/elements/kb-key-sequence.html",
@@ -125,6 +159,7 @@ const GritResourceMap* GetKeyboardExtensionResources(size_t* size) {
{"keyboard/elements/kb-keyboard.html", IDR_KEYBOARD_ELEMENTS_KEYBOARD},
{"keyboard/elements/kb-keyset.html", IDR_KEYBOARD_ELEMENTS_KEYSET},
{"keyboard/elements/kb-row.html", IDR_KEYBOARD_ELEMENTS_ROW},
+ {"keyboard/elements/kb-shift-key.html", IDR_KEYBOARD_ELEMENTS_SHIFT_KEY},
{"keyboard/images/keyboard.svg", IDR_KEYBOARD_IMAGES_KEYBOARD},
{"keyboard/images/microphone.svg", IDR_KEYBOARD_IMAGES_MICROPHONE},
{"keyboard/images/microphone-green.svg",
@@ -132,6 +167,7 @@ const GritResourceMap* GetKeyboardExtensionResources(size_t* size) {
{"keyboard/index.html", IDR_KEYBOARD_INDEX},
{"keyboard/layouts/dvorak.html", IDR_KEYBOARD_LAYOUTS_DVORAK},
{"keyboard/layouts/latin-accents.js", IDR_KEYBOARD_LAYOUTS_LATIN_ACCENTS},
+ {"keyboard/layouts/numeric.html", IDR_KEYBOARD_LAYOUTS_NUMERIC},
{"keyboard/layouts/qwerty.html", IDR_KEYBOARD_LAYOUTS_QWERTY},
{"keyboard/layouts/symbol-altkeys.js",
IDR_KEYBOARD_LAYOUTS_SYMBOL_ALTKEYS},
diff --git a/chromium/ui/keyboard/keyboard_util.h b/chromium/ui/keyboard/keyboard_util.h
index 7d4643335c9..bb0edfb7bd7 100644
--- a/chromium/ui/keyboard/keyboard_util.h
+++ b/chromium/ui/keyboard/keyboard_util.h
@@ -29,7 +29,7 @@ enum CursorMoveDirection {
KEYBOARD_EXPORT bool IsKeyboardEnabled();
// Insert |text| into the active TextInputClient associated with |root_window|,
-// if there is one. Returns true if |text| was successfully inserted. Note
+// if there is one. Returns true if |text| was successfully inserted. Note
// that this may convert |text| into ui::KeyEvents for injection in some
// special circumstances (i.e. VKEY_RETURN, VKEY_BACK).
KEYBOARD_EXPORT bool InsertText(const base::string16& text,
@@ -41,7 +41,18 @@ KEYBOARD_EXPORT bool MoveCursor(int swipe_direction,
int modifier_flags,
aura::RootWindow* root_window);
-// Get the list of keyboard resources. |size| is populated with the number of
+// Sends a fabricated key event, where |type| is the event type, |key_value|
+// is the unicode value of the character, |key_code| is the legacy key code
+// value, and |shift_modifier| indicates if the shift key is being virtually
+// pressed. The event is dispatched to the active TextInputClient associated
+// with |root_window|. The type may be "keydown" or "keyup".
+KEYBOARD_EXPORT bool SendKeyEvent(std::string type,
+ int key_value,
+ int key_code,
+ bool shift_modifier,
+ aura::RootWindow* root_window);
+
+// Get the list of keyboard resources. |size| is populated with the number of
// resources in the returned array.
KEYBOARD_EXPORT const GritResourceMap* GetKeyboardExtensionResources(
size_t* size);
diff --git a/chromium/ui/keyboard/resources/OWNERS b/chromium/ui/keyboard/resources/OWNERS
index eca3960110e..7a6ff670440 100644
--- a/chromium/ui/keyboard/resources/OWNERS
+++ b/chromium/ui/keyboard/resources/OWNERS
@@ -1,2 +1,3 @@
bryeung@chromium.org
bshe@chromium.org
+kevers@chromium.org
diff --git a/chromium/ui/keyboard/resources/api_adapter.js b/chromium/ui/keyboard/resources/api_adapter.js
index eb95e35cb8b..049c3666242 100644
--- a/chromium/ui/keyboard/resources/api_adapter.js
+++ b/chromium/ui/keyboard/resources/api_adapter.js
@@ -1,4 +1,4 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
@@ -9,10 +9,23 @@ function logIfError() {
}
function insertText(text) {
- chrome.experimental.input.virtualKeyboard.insertText(text, logIfError);
+ chrome.virtualKeyboardPrivate.insertText(text, logIfError);
}
function MoveCursor(swipe_direction, swipe_flags) {
- chrome.experimental.input.virtualKeyboard.moveCursor(swipe_direction,
- swipe_flags);
+ chrome.virtualKeyboardPrivate.moveCursor(swipe_direction, swipe_flags);
}
+
+function sendKeyEvent(event) {
+ chrome.virtualKeyboardPrivate.sendKeyEvent(event, logIfError);
+}
+
+function hideKeyboard() {
+ chrome.virtualKeyboardPrivate.hideKeyboard(logIfError);
+}
+
+chrome.virtualKeyboardPrivate.onTextInputBoxFocused.addListener(
+ function (inputContext) {
+ // TODO(bshe): Making keyboard aware of inputContext.
+ }
+);
diff --git a/chromium/ui/keyboard/resources/elements/kb-altkey-data.html b/chromium/ui/keyboard/resources/elements/kb-altkey-data.html
index 8f8b9a96420..67f793ad4b1 100644
--- a/chromium/ui/keyboard/resources/elements/kb-altkey-data.html
+++ b/chromium/ui/keyboard/resources/elements/kb-altkey-data.html
@@ -10,8 +10,21 @@
var altKeys = {};
var idMap = {};
- function createId(char) {
- return 'id' + char.charCodeAt(0);
+ /**
+ * Creates a unique identifier based on the key provided.
+ * This identifier is of the form 'idHASH' where HASH is
+ * the concatenation of the keycodes of every character in the string.
+ * @param {string} key Key for which we want an identifier.
+ * @return {string} The unique id for key.
+ */
+ function createId(key) {
+ var hash = key.split('').map(
+ // Returns the key code for the character.
+ function(character) {
+ return character.charCodeAt(0);
+ }
+ ).join('');
+ return 'id' + hash;
}
Polymer('kb-altkey-data', {
@@ -21,7 +34,7 @@
* @param {string} char The base character.
* @param {boolean=} opt_force If true, force the creation of a list
* even if empty. Used when constructing a set of alternates for keys
- * with superscripts.
+ * with hintTexts.
* @return {?Object.{id: string, list: string}}
*/
getAltkeys: function(char, opt_force) {
diff --git a/chromium/ui/keyboard/resources/elements/kb-key-base.html b/chromium/ui/keyboard/resources/elements/kb-key-base.html
index 497da30f6c4..89a174809d3 100644
--- a/chromium/ui/keyboard/resources/elements/kb-key-base.html
+++ b/chromium/ui/keyboard/resources/elements/kb-key-base.html
@@ -6,7 +6,7 @@
<polymer-element name="kb-key-base"
on-pointerdown="down" on-pointerup="up" on-pointerout="out"
- attributes="accents char invert repeat superscript toKeyset toLayout">
+ attributes="accents char invert repeat hintText toKeyset toLayout">
<script>
/**
* The long-press delay in milliseconds before long-press handler is
@@ -109,43 +109,58 @@
}
},
down: function(event) {
- var detail = {
- char: this.char || this.textContent,
- toLayout: this.toLayout,
- repeat: this.repeat
- };
+ var detail = this.populateDetails();
if (this.keysetRules && this.keysetRules.down != undefined) {
detail.toKeyset = this.keysetRules.down[TO_KEYSET - OFFSET];
detail.nextKeyset = this.keysetRules.down[NEXT_KEYSET - OFFSET];
}
this.fire('key-down', detail);
- this.longPressTimer = this.asyncMethod(function() {
- var detail = {
- char: this.char || this.textContent,
- superscript: this.superscript
- };
- if (this.keysetRules && this.keysetRules.long != undefined) {
- detail.toKeyset = this.keysetRules.long[TO_KEYSET - OFFSET];
- detail.nextKeyset = this.keysetRules.long[NEXT_KEYSET - OFFSET];
- }
- this.fire('key-longpress', detail);
- }, null, LONGPRESS_DELAY_MSEC);
+ this.longPressTimer = this.generateLongPressTimer();
},
out: function(event) {
clearTimeout(this.longPressTimer);
},
up: function(event) {
clearTimeout(this.longPressTimer);
- var detail = {
- char: this.char || this.textContent,
- toLayout: this.toLayout
- };
+ var detail = this.populateDetails();
if (this.keysetRules && this.keysetRules.up != undefined) {
detail.toKeyset = this.keysetRules.up[TO_KEYSET - OFFSET];
detail.nextKeyset = this.keysetRules.up[NEXT_KEYSET - OFFSET];
}
this.fire('key-up', detail);
- }
+ },
+
+ /**
+ * Character value associated with the key. Typically, the value is a
+ * single charcater, but may be multi-character in cases like a ".com"
+ * button.
+ * @type {string}
+ */
+ get charValue() {
+ return this.char || this.textContent;
+ },
+
+ populateDetails: function() {
+ return {
+ char: this.charValue,
+ toLayout: this.toLayout,
+ repeat: this.repeat
+ };
+ },
+
+ generateLongPressTimer: function() {
+ return this.asyncMethod(function() {
+ var detail = {
+ char: this.charValue,
+ hintText: this.hintText
+ };
+ if (this.keysetRules && this.keysetRules.long != undefined) {
+ detail.toKeyset = this.keysetRules.long[TO_KEYSET - OFFSET];
+ detail.nextKeyset = this.keysetRules.long[NEXT_KEYSET - OFFSET];
+ }
+ this.fire('key-longpress', detail);
+ }, null, LONGPRESS_DELAY_MSEC);
+ },
});
</script>
</polymer-element>
diff --git a/chromium/ui/keyboard/resources/elements/kb-key-codes.html b/chromium/ui/keyboard/resources/elements/kb-key-codes.html
new file mode 100644
index 00000000000..b8353ecd938
--- /dev/null
+++ b/chromium/ui/keyboard/resources/elements/kb-key-codes.html
@@ -0,0 +1,180 @@
+<!--
+ -- Copyright 2013 The Chromium Authors. All rights reserved.
+ -- Use of this source code is governed by a BSD-style license that can be
+ -- found in the LICENSE file.
+ -->
+
+<polymer-element name="kb-key-codes">
+<script>
+ (function() {
+ // Each virtual key event is assigned a unique ID.
+ var nextRequestID = 0;
+
+ // Keycodes have been deprecated in the KeyEvent specification, but are
+ // nonetheless required to support legacy web content. The Keycodes in the
+ // following table are based on subset of US-EN 101-key keyboard. These
+ // codes are used in the absence of explicit keycodes for kb-key and
+ // kb-keysequence elements. Keyboard layout authors may explicitly set the
+ // keyCode attribute for kb-key or kb-keysequence elements to refer to
+ // indices in this table in order to emulate a physical keyboard with an
+ // alternate layout. Not all keys on a virtual keyboard are required to
+ // have keyCodes.
+ var keyCodes = {
+ '\b': {keyCode: 0x08, shiftModifier: false},
+ '\t': {keyCode: 0x09, shiftModifier: false},
+ '\n': {keyCode: 0x0D, shiftModifier: false},
+ ' ': {keyCode: 0x20, shiftModifier: false},
+ '0': {keyCode: 0x30, shiftModifier: false},
+ ')': {keyCode: 0x30, shiftModifier: true},
+ '1': {keyCode: 0x31, shiftModifier: false},
+ '!': {keyCode: 0x31, shiftModifier: true},
+ '2': {keyCode: 0x32, shiftModifier: false},
+ '@': {keyCode: 0x32, shiftModifier: true},
+ '3': {keyCode: 0x33, shiftModifier: false},
+ '#': {keyCode: 0x33, shiftModifier: true},
+ '4': {keyCode: 0x34, shiftModifier: false},
+ '$': {keyCode: 0x34, shiftModifier: true},
+ '5': {keyCode: 0x35, shiftModifier: false},
+ '%': {keyCode: 0x35, shiftModifier: true},
+ '6': {keyCode: 0x36, shiftModifier: false},
+ '^': {keyCode: 0x36, shiftModifier: true},
+ '7': {keyCode: 0x37, shiftModifier: false},
+ '&': {keyCode: 0x37, shiftModifier: true},
+ '8': {keyCode: 0x38, shiftModifier: false},
+ '*': {keyCode: 0x38, shiftModifier: true},
+ '9': {keyCode: 0x39, shiftModifier: false},
+ '(': {keyCode: 0x39, shiftModifier: true},
+ 'a': {keyCode: 0x41, shiftModifier: false},
+ 'A': {keyCode: 0x41, shiftModifier: true},
+ 'b': {keyCode: 0x42, shiftModifier: false},
+ 'B': {keyCode: 0x42, shiftModifier: true},
+ 'c': {keyCode: 0x43, shiftModifier: false},
+ 'C': {keyCode: 0x43, shiftModifier: true},
+ 'd': {keyCode: 0x44, shiftModifier: false},
+ 'D': {keyCode: 0x44, shiftModifier: true},
+ 'e': {keyCode: 0x45, shiftModifier: false},
+ 'E': {keyCode: 0x45, shiftModifier: true},
+ 'f': {keyCode: 0x46, shiftModifier: false},
+ 'F': {keyCode: 0x46, shiftModifier: true},
+ 'g': {keyCode: 0x47, shiftModifier: false},
+ 'G': {keyCode: 0x47, shiftModifier: true},
+ 'h': {keyCode: 0x48, shiftModifier: false},
+ 'H': {keyCode: 0x48, shiftModifier: true},
+ 'i': {keyCode: 0x49, shiftModifier: false},
+ 'I': {keyCode: 0x49, shiftModifier: true},
+ 'j': {keyCode: 0x4A, shiftModifier: false},
+ 'J': {keyCode: 0x4A, shiftModifier: true},
+ 'k': {keyCode: 0x4B, shiftModifier: false},
+ 'K': {keyCode: 0x4B, shiftModifier: true},
+ 'l': {keyCode: 0x4C, shiftModifier: false},
+ 'L': {keyCode: 0x4C, shiftModifier: true},
+ 'm': {keyCode: 0x4D, shiftModifier: false},
+ 'M': {keyCode: 0x4D, shiftModifier: true},
+ 'n': {keyCode: 0x4E, shiftModifier: false},
+ 'N': {keyCode: 0x4E, shiftModifier: true},
+ 'o': {keyCode: 0x4F, shiftModifier: false},
+ 'O': {keyCode: 0x4F, shiftModifier: true},
+ 'p': {keyCode: 0x50, shiftModifier: false},
+ 'P': {keyCode: 0x50, shiftModifier: true},
+ 'q': {keyCode: 0x51, shiftModifier: false},
+ 'Q': {keyCode: 0x51, shiftModifier: true},
+ 'r': {keyCode: 0x52, shiftModifier: false},
+ 'R': {keyCode: 0x52, shiftModifier: true},
+ 's': {keyCode: 0x53, shiftModifier: false},
+ 'S': {keyCode: 0x53, shiftModifier: true},
+ 't': {keyCode: 0x54, shiftModifier: false},
+ 'T': {keyCode: 0x54, shiftModifier: true},
+ 'u': {keyCode: 0x55, shiftModifier: false},
+ 'U': {keyCode: 0x55, shiftModifier: true},
+ 'v': {keyCode: 0x56, shiftModifier: false},
+ 'V': {keyCode: 0x56, shiftModifier: true},
+ 'w': {keyCode: 0x57, shiftModifier: false},
+ 'W': {keyCode: 0x57, shiftModifier: true},
+ 'x': {keyCode: 0x58, shiftModifier: false},
+ 'X': {keyCode: 0x58, shiftModifier: true},
+ 'y': {keyCode: 0x59, shiftModifier: false},
+ 'Y': {keyCode: 0x59, shiftModifier: true},
+ 'z': {keyCode: 0x5A, shiftModifier: false},
+ 'Z': {keyCode: 0x5A, shiftModifier: true},
+ ';': {keyCode: 0xBA, shiftModifier: false},
+ ':': {keyCode: 0xBA, shiftModifier: true},
+ '=': {keyCode: 0xBB, shiftModifier: false},
+ '+': {keyCode: 0xBB, shiftModifier: true},
+ ',': {keyCode: 0xBC, shiftModifier: false},
+ '<': {keyCode: 0xBC, shiftModifier: true},
+ '-': {keyCode: 0xBD, shiftModifier: false},
+ '_': {keyCode: 0xBD, shiftModifier: true},
+ '.': {keyCode: 0xBE, shiftModifier: false},
+ '>': {keyCode: 0xBE, shiftModifier: true},
+ '/': {keyCode: 0xBF, shiftModifier: false},
+ '?': {keyCode: 0xBF, shiftModifier: true},
+ '`': {keyCode: 0xC0, shiftModifier: false},
+ '~': {keyCode: 0xC0, shiftModifier: true},
+ '[': {keyCode: 0xDB, shiftModifier: false},
+ '{': {keyCode: 0xDB, shiftModifier: true},
+ '\\': {keyCode: 0xDC, shiftModifier: false},
+ '|': {keyCode: 0xDC, shiftModifier: true},
+ ']': {keyCode: 0xDD, shiftModifier: false},
+ '}': {keyCode: 0xDD, shiftModifier: true},
+ '\'': {keyCode: 0xDE, shiftModifier: false},
+ '"': {keyCode: 0xDE, shiftModifier: true},
+ };
+
+ Polymer('kb-key-codes', {
+ /**
+ * Retrieves the keyCode and status of the shift modifier.
+ * @param {string} id ID of an entry in the code table.
+ * @return {keyCode: numeric, shiftModifier: boolean}
+ */
+ GetKeyCodeAndModifiers: function(id) {
+ var entry = keyCodes[id];
+ if (entry) {
+ return {
+ keyCode: entry.keyCode,
+ shiftModifier: entry.shiftModifier
+ };
+ }
+ return {
+ keyCode: 0,
+ shiftModifier: false
+ };
+ },
+
+ /**
+ * Creates a virtual key event for use with the keyboard extension API.
+ * See http://www.w3.org/TR/DOM-Level-3-Events/#events-KeyboardEvent.
+ * @param {Object} detail Attribute of the key being pressed or released.
+ * @param {string} type The type of key event, which may be keydown
+ * or keyup.
+ * @return {?KeyboardEvent} A KeyboardEvent object, or undefined on
+ * failure.
+ */
+ createVirtualKeyEvent: function(detail, type) {
+ var char = detail.char;
+ if (!char || char.length != 1) {
+ console.error('Invalid key. Expected single character.');
+ return;
+ }
+ var keyCode = detail.keyCode;
+ var shiftModifier = detail.shiftModifier;
+ if (keyCode == undefined) {
+ var state = this.GetKeyCodeAndModifiers(char);
+ if (state) {
+ keyCode = state.keyCode;
+ shiftModifier = state.shiftModifier;
+ } else {
+ keyCode = 0;
+ shiftModifier = false;
+ }
+ }
+ return {
+ type: type,
+ charValue: char.charCodeAt(0),
+ keyCode: keyCode,
+ shiftKey: shiftModifier
+ };
+ },
+ });
+ })();
+</script>
+</polymer-element>
diff --git a/chromium/ui/keyboard/resources/elements/kb-key-sequence.html b/chromium/ui/keyboard/resources/elements/kb-key-sequence.html
index dee295bec3b..ad01003b2a1 100644
--- a/chromium/ui/keyboard/resources/elements/kb-key-sequence.html
+++ b/chromium/ui/keyboard/resources/elements/kb-key-sequence.html
@@ -4,7 +4,7 @@
-- found in the LICENSE file.
-->
-<polymer-element name="kb-key-sequence" attributes="keys superscripts">
+<polymer-element name="kb-key-sequence" attributes="keys hintTexts keyCodes">
<template>
<style>
@host {
@@ -13,6 +13,7 @@
}
}
</style>
+ <kb-key-codes id="keyCodeMetadata"></kb-key-codes>
</template>
<script>
Polymer('kb-key-sequence', {
@@ -23,9 +24,14 @@
var result;
if (this.keys) {
var newKeys = this.keys;
- var newSuperScripts = this.superscripts;
- if (newSuperScripts && newKeys.length != newSuperScripts.length) {
- console.error('keys and superscripts do not match');
+ var newHintTexts = this.hintTexts;
+ if (newHintTexts && newKeys.length != newHintTexts.length) {
+ console.error('keys and hintTexts do not match');
+ return;
+ }
+ var keyCodes = this.keyCodes || newKeys;
+ if (keyCodes && newKeys.length != keyCodes.length) {
+ console.error('keys and keyCodes do not match');
return;
}
var replacement = document.createDocumentFragment();
@@ -33,8 +39,14 @@
var key = document.createElement('kb-key');
key.innerText = newKeys[i];
key.accents = newKeys[i];
- if (newSuperScripts)
- key.superscript = newSuperScripts[i];
+ if (newHintTexts)
+ key.hintText = newHintTexts[i];
+ var state = this.$.keyCodeMetadata.GetKeyCodeAndModifiers(
+ keyCodes[i]);
+ if (state) {
+ key.keyCode = state.keyCode;
+ key.shiftModifier = state.shiftModifier;
+ }
replacement.appendChild(key);
}
result = replacement;
diff --git a/chromium/ui/keyboard/resources/elements/kb-key.html b/chromium/ui/keyboard/resources/elements/kb-key.html
index fc366bbee92..d9bf0776750 100644
--- a/chromium/ui/keyboard/resources/elements/kb-key.html
+++ b/chromium/ui/keyboard/resources/elements/kb-key.html
@@ -4,7 +4,8 @@
-- found in the LICENSE file.
-->
-<polymer-element name="kb-key" extends="kb-key-base" attributes="weight">
+<polymer-element name="kb-key" extends="kb-key-base"
+ attributes="keyCode shiftModifier weight">
<template>
<style>
@host {
@@ -16,45 +17,67 @@
<div id="key" pseudo="x-key" inverted?={{invert}}>
<content></content>
</div>
- <div pseudo="x-superscript" inverted?={{invert}}>{{superscript}}</div>
+ <div pseudo="x-hinttext" inverted?={{invert}}>{{hintText}}</div>
</template>
<script>
Polymer('kb-key', {
- weight: 1
+ /**
+ * Key codes have been deprecated in DOM3 key events, but are required
+ * for legacy web content. The key codes depend on the position of the
+ * key on the keyboard and is independent of which modifier keys (shift,
+ * alt, ...) are active.
+ * @type {number|undefined}
+ */
+ keyCode: undefined,
+ /**
+ * Whether the shift key is pressed when producing the key value.
+ * @type {boolean}
+ */
+ shiftModifier: false,
+ /**
+ * Weighting to use for layout in order to properly size the key.
+ * Keys with a high weighting are wider than normal keys.
+ * @type {number}
+ */
+ weight: 1,
+
+ /**
+ * Returns a subset of the key attributes.
+ * @return {Object} Mapping of attributes for the key element.
+ */
+ populateDetails: function() {
+ var details = this.super();
+ details.keyCode = this.keyCode;
+ details.shiftModifier = this.shiftModifier;
+ return details;
+ },
});
</script>
</polymer-element>
<!-- Special keys -->
-<polymer-element name="kb-shift-key" class="shift dark" char="Shift"
+<!--
+ -- TODO(kevers): Rip this out if and when we are done implementing the proper
+ -- layout switcher.
+ -->
+<polymer-element name="kb-layout-selector" class="layout-selector dark" char="Invalid"
extends="kb-key">
<script>
- Polymer('kb-shift-key', {
- down: function(event) {
- this.super();
- var detail = {};
- if (this.keysetRules && this.keysetRules.dbl != undefined) {
- detail.char = this.char || this.textContent;
- detail.toKeyset = this.keysetRules.dbl[TO_KEYSET - OFFSET];
- detail.nextKeyset = this.keysetRules.dbl[NEXT_KEYSET - OFFSET];
- }
- this.fire('enable-dbl', detail);
- this.fire('enable-sel');
- }
+ Polymer('kb-layout-selector', {
+ toLayout: 'qwerty'
});
</script>
</polymer-element>
-<!--
- -- TODO(kevers): Display popup menu for selecting layout on keypress. Display
- -- code for keyboard layout in place of image.
- -->
-<polymer-element name="kb-layout-selector" class="layout-selector dark" char="Invalid"
+<polymer-element name="kb-hide-keyboard-key" class="hide-keyboard dark" char="Invalid"
extends="kb-key">
<script>
- Polymer('kb-layout-selector', {
- toLayout: 'qwerty'
+ Polymer('kb-hide-keyboard-key', {
+ down: function(event) {},
+ up: function(event) {
+ hideKeyboard();
+ }
});
</script>
</polymer-element>
diff --git a/chromium/ui/keyboard/resources/elements/kb-keyboard.html b/chromium/ui/keyboard/resources/elements/kb-keyboard.html
index f4efb314084..ea09e372f78 100644
--- a/chromium/ui/keyboard/resources/elements/kb-keyboard.html
+++ b/chromium/ui/keyboard/resources/elements/kb-keyboard.html
@@ -1,5 +1,5 @@
<!--
- -- Copyright (c) 2013 The Chromium Authors. All rights reserved.
+ -- Copyright 2013 The Chromium Authors. All rights reserved.
-- Use of this source code is governed by a BSD-style license that can be
-- found in the LICENSE file.
-->
@@ -7,7 +7,8 @@
<polymer-element name="kb-keyboard" on-key-over="keyOver" on-key-up="keyUp"
on-key-down="keyDown" on-key-longpress="keyLongpress" on-pointerup="up"
on-pointerdown="down" on-enable-sel="enableSel"
- on-enable-dbl="enableDbl" attributes="keyset layout rows">
+ on-enable-dbl="enableDbl"
+ attributes="keyset layout rows inputType inputTypeToLayoutMap">
<template>
<style>
@host {
@@ -23,6 +24,7 @@
-- keyboard layouts.
-->
<content select="#{{layout}}-{{keyset}}"></content>
+ <kb-key-codes id="keyCodeMetadata"></kb-key-codes>
</template>
<script>
/**
@@ -50,6 +52,20 @@
var DBL_INTERVAL_MSEC = 300;
/**
+ * The index of the name of the keyset when searching for all keysets.
+ * @const
+ * @type {number}
+ */
+ var REGEX_KEYSET_INDEX = 1;
+
+ /**
+ * The integer number of matches when searching for keysets.
+ * @const
+ * @type {number}
+ */
+ var REGEX_MATCH_COUNT = 2;
+
+ /**
* The boolean to decide if keyboard should transit to upper case keyset
* when spacebar is pressed. If a closing punctuation is followed by a
* spacebar, keyboard should automatically transit to upper case.
@@ -112,7 +128,6 @@
/**
* The boolean to decide if it is swipe in process or finished.
- * @const
* @type {boolean}
*/
var swipeInProgress = false;
@@ -179,6 +194,18 @@
dblDetail_: null,
dblTimer_: null,
swipeHandler: null,
+ shift: null,
+ inputType: null,
+
+ /**
+ * The default input type to keyboard layout map. The key must be one of
+ * the input box type values.
+ * @type {object}
+ */
+ inputTypeToLayoutMap: {
+ number: "numeric",
+ text: "qwerty"
+ },
ready: function() {
this.voiceInput_ = new VoiceInput(this);
@@ -186,6 +213,20 @@
},
/**
+ * Called when the type of focused input box changes. If a keyboard layout
+ * is defined for the current input type, that layout will be loaded.
+ * Otherwise, the keyboard layout for 'text' type will be loaded.
+ */
+ inputTypeChanged: function() {
+ // TODO(bshe): Toggle visibility of some keys in a keyboard layout
+ // according to the input type.
+ var layout = this.inputTypeToLayoutMap[this.inputType];
+ if (!layout)
+ layout = this.inputTypeToLayoutMap.text;
+ this.layout = layout;
+ },
+
+ /**
* When double click/tap event is enabled, the second key-down and key-up
* events on the same key should be skipped. Return true when the event
* with |detail| should be skipped.
@@ -262,6 +303,24 @@
this.lastPressedKey = event.target;
this.lastPressedKey.classList.add('active');
repeatKey.cancel();
+
+ var char = detail.char;
+ switch(char) {
+ case 'Shift':
+ // Removes caps-lock if caps-locked.
+ if(this.classList.contains('caps-locked')) {
+ this.classList.remove('caps-locked');
+ }
+ break;
+ default:
+ // Non-control key pressed, notify control keys.
+ // Control keys are shift, control and alt.
+ if(this.shift)
+ this.shift.onNonControlKeyDown();
+ break;
+ }
+
+ // A transition key was pressed, immediately move to new keyset.
var toKeyset = detail.toKeyset;
if (toKeyset) {
this.keyset = toKeyset;
@@ -271,12 +330,13 @@
}
if (detail.repeat) {
- insertText(detail.char);
+ this.keyTyped(detail);
repeatKey.key = this.lastPressedKey;
+ var self = this;
repeatKey.timer = setTimeout(function() {
repeatKey.timer = undefined;
repeatKey.interval = setInterval(function() {
- insertText(detail.char);
+ self.keyTyped(detail);
}, REPEAT_INTERVAL_MSEC);
}, Math.max(0, REPEAT_DELAY_MSEC - REPEAT_INTERVAL_MSEC));
}
@@ -294,6 +354,7 @@
this.dblDetail_.clickCount = 0;
var self = this;
this.dblTimer_ = setTimeout(function() {
+ self.dblDetail_.callback = null;
self.dblDetail_ = null;
}, DBL_INTERVAL_MSEC);
}
@@ -330,10 +391,15 @@
if (this.dblDetail_) {
this.dblDetail_.clickCount++;
if (this.dblDetail_.clickCount == 2) {
+ this.dblDetail_.callback();
this.keyset = this.dblDetail_.toKeyset;
- var keysetId = '#' + this.layout + '-' + this.keyset
- this.querySelector(keysetId).nextKeyset = this.dblTimer_.nextKeyset;
+ var keysetId = '#' + this.layout + '-' + this.keyset;
+ var keyset = this.querySelector(keysetId);
+ keyset.nextKeyset = this.dblTimer_.nextKeyset;
clearTimeout(this.dblTimer_);
+
+ this.classList.add('caps-locked');
+
this.dblDetail_ = null;
}
}
@@ -347,7 +413,6 @@
swipeInProgress = false;
swipeStatus.resetAll();
}
- // Remove the pointermove event hander here.
this.removeEventListener('pointermove', this.swipeHandler, false);
},
@@ -362,31 +427,48 @@
if (swipeInProgress)
return;
this.lastPressedKey.classList.remove('active');
- if (this.lastPressedKey != event.target)
+ if (this.lastPressedKey.char != event.target.char)
return;
if (repeatKey.key == event.target) {
repeatKey.cancel();
return;
}
- var toKeyset = detail.toKeyset;
- // Keyset transition key.
- if (toKeyset) {
- this.keyset = toKeyset;
+ var toKeysetId = detail.toKeyset;
+ // Keyset transition key. This is needed to transition from upper
+ // to lower case when we are not in caps mode.
+ if (toKeysetId) {
+ this.keyset = toKeysetId;
this.querySelector('#' + this.layout + '-' + this.keyset).nextKeyset =
detail.nextKeyset;
}
- var toLayout = detail.toLayout;
+ var toLayoutId = detail.toLayout;
// Layout transition key.
- if (toLayout)
- this.layout = toLayout;
+ if (toLayoutId)
+ this.layout = toLayoutId;
var char = detail.char;
if (enterUpperOnSpace) {
enterUpperOnSpace = false;
- if (char == ' ')
- this.keyset = 'upper';
+ if (char == ' ') {
+ // If shift key defined in layout.
+ if(this.shift) {
+ var shiftDetail = this.shift.onSpaceAfterPunctuation();
+ var toKeyset = shiftDetail.toKeyset;
+ // Check if transition defined.
+ if(toKeyset) {
+ this.keyset = toKeyset;
+ this.querySelector('#' + this.layout + '-' +
+ this.keyset).nextKeyset = shiftDetail.nextKeyset;
+ }
+ } else {
+ console.error('Capitalization on space after punctuation \
+ enabled, but cannot find target keyset.');
+ }
+ }
}
switch(char) {
case 'Invalid':
+ swipeStatus.swipeFlags = 0;
+ return;
case 'Shift':
swipeStatus.swipeFlags = 0;
return;
@@ -401,7 +483,10 @@
default:
break;
}
- insertText(char);
+ if (char.length == 1)
+ this.keyTyped(detail);
+ else
+ insertText(char);
},
/*
@@ -411,12 +496,17 @@
* @param {Object} detail The detail of pressed key.
*/
keyLongpress: function(event, detail) {
+ // If the gesture is long press, remove the pointermove listener.
+ this.removeEventListener('pointermove', this.swipeHandler, false);
var toKeyset = detail.toKeyset;
// Keyset transtion key.
if (toKeyset) {
this.keyset = toKeyset;
this.querySelector('#' + this.layout + '-' + this.keyset).nextKeyset =
detail.nextKeyset;
+
+ // Locks the keyset before removing active to prevent flicker.
+ this.classList.add('caps-locked');
// Makes last pressed key inactive if transit to a new keyset on long
// press.
this.lastPressedKey.classList.remove('active');
@@ -424,7 +514,7 @@
},
/**
- * Handles a change in the keyboard layout. Auto-selects the default
+ * Handles a change in the keyboard layout. Auto-selects the default
* keyset for the new layout.
*/
layoutChanged: function() {
@@ -435,14 +525,46 @@
keyboard.appendChild(flattenKeysets(keysets.content));
this.selectDefaultKeyset();
} else {
- console.error('Unable to find layout ' + this.layout);
- }
+ // Add link for the keysets if missing from the document. Force
+ // a layout change after resolving the import of the link.
+ var query = 'link[id=' + this.layout + ']';
+ if (!document.querySelector(query)) {
+ // Layout has not beeen loaded yet.
+ var link = document.createElement('link');
+ link.id = this.layout;
+ link.setAttribute('rel', 'import');
+ link.setAttribute('href', 'layouts/' + this.layout + '.html');
+ document.head.appendChild(link);
+
+ // Load content for the new link element.
+ var self = this;
+ HTMLImports.importer.load(document, function() {
+ HTMLImports.parser.parseLink(link);
+ self.layoutChanged();
+ });
+ }
+ }
}
+ this.classList.remove('caps-locked');
+ this.shift = this.querySelector('kb-shift-key');
+ if(this.shift)
+ this.shift.reset();
+ },
+
+ /**
+ * Generates fabricated key events to simulate typing on a
+ * physical keyboard.
+ * @param {Object} detail Attributes of the key being typed.
+ */
+ keyTyped: function(detail) {
+ var builder = this.$.keyCodeMetadata;
+ sendKeyEvent(builder.createVirtualKeyEvent(detail, "keydown"));
+ sendKeyEvent(builder.createVirtualKeyEvent(detail, "keyup"));
},
/**
* Selects the default keyset for a layout.
- * @return {boolean} True if successful. This method can fail if the
+ * @return {boolean} True if successful. This method can fail if the
* keysets corresponding to the layout have not been injected.
*/
selectDefaultKeyset: function() {
@@ -452,10 +574,10 @@
var keysetsLoaded = false;
for (var i = 0; i < keysets.length; i++) {
var matches = keysets[i].id.match(regex);
- if (matches && matches.length == 2) {
+ if (matches && matches.length == REGEX_MATCH_COUNT) {
keysetsLoaded = true;
if (keysets[i].isDefault) {
- this.keyset = matches[1];
+ this.keyset = matches[REGEX_KEYSET_INDEX];
return true;
}
}
@@ -467,4 +589,3 @@
});
</script>
</polymer-element>
-
diff --git a/chromium/ui/keyboard/resources/elements/kb-keyset.html b/chromium/ui/keyboard/resources/elements/kb-keyset.html
index 365649d9830..92dd8b7f687 100644
--- a/chromium/ui/keyboard/resources/elements/kb-keyset.html
+++ b/chromium/ui/keyboard/resources/elements/kb-keyset.html
@@ -4,8 +4,9 @@
-- found in the LICENSE file.
-->
-<polymer-element name="kb-keyset" attributes="nextKeyset isDefault"
- on-key-up="keyUp" on-key-longpress="keyLongpress">
+<polymer-element name="kb-keyset" attributes="nextKeyset isDefault
+ capsLocksTo capsLockable" on-key-up="keyUp"
+ on-key-longpress="keyLongpress">
<template>
<style>
@host {
@@ -40,7 +41,7 @@
var altkeyMetadata = this.$.altkeyMetadata;
var altkeys = altkeyMetadata.getAltkeys(detail.char,
- !!detail.superscript);
+ !!detail.hintText);
if (!altkeys)
return;
@@ -55,7 +56,7 @@
activeAltKeySet = altkeyMetadata.createAltkeySet(detail.char,
maxLeftOffset,
maxRightOffset,
- detail.superscript);
+ detail.hintText);
altkeyContainer.appendChild(activeAltKeySet);
}
diff --git a/chromium/ui/keyboard/resources/elements/kb-row.html b/chromium/ui/keyboard/resources/elements/kb-row.html
index 0a00058a060..0398587daa2 100644
--- a/chromium/ui/keyboard/resources/elements/kb-row.html
+++ b/chromium/ui/keyboard/resources/elements/kb-row.html
@@ -12,8 +12,11 @@
-webkit-box-flex: 1;
display: -webkit-box;
text-align: center;
- margin-right: 5px;
- margin-top: 7px;
+ margin-right: 0.25em;
+ margin-top: 0.25em;
+ }
+ *:last-of-type {
+ margin-bottom: 0.25em;
}
}
content::-webkit-distributed(kb-key) {
diff --git a/chromium/ui/keyboard/resources/elements/kb-shift-key.html b/chromium/ui/keyboard/resources/elements/kb-shift-key.html
new file mode 100644
index 00000000000..686a59c5125
--- /dev/null
+++ b/chromium/ui/keyboard/resources/elements/kb-shift-key.html
@@ -0,0 +1,186 @@
+<!--
+ -- Copyright 2013 The Chromium Authors. All rights reserved.
+ -- Use of this source code is governed by a BSD-style license that can be
+ -- found in the LICENSE file.
+ -->
+
+<polymer-element name="kb-shift-key"
+ attributes="lowerCaseKeysetId upperCaseKeysetId"
+ class="shift dark" char="Shift" extends="kb-key">
+ <script>
+ (function () {
+
+ /**
+ * The possible states of the shift key.
+ * Unlocked is the default state. Locked for capslocked, pressed is a
+ * key-down and tapped for a key-down followed by an immediate key-up.
+ * @const
+ * @type {Enum}
+ */
+ var KEY_STATES = {
+ PRESSED: "pressed", // Key-down on shift key.
+ LOCKED: "locked", // Key is capslocked.
+ UNLOCKED: "unlocked", // Default state.
+ TAPPED: "tapped" // Key-down followed by key-up.
+ };
+
+ /**
+ * Uses a closure to define one long press timer among all shift keys
+ * regardless of the layout they are in.
+ * @type {function}
+ */
+ var shiftLongPressTimer = undefined;
+
+ /**
+ * The current state of the shift key.
+ * @type {Enum}
+ */
+ var state = KEY_STATES.UNLOCKED;
+
+ Polymer('kb-shift-key', {
+ /**
+ * Defines how capslock effects keyset transition. We always transition
+ * from the lowerCaseKeysetId to the upperCaseKeysetId if capslock is on.
+ * @type {string}
+ */
+ lowerCaseKeysetId: 'lower',
+ upperCaseKeysetId: 'upper',
+
+ up: function(event) {
+ if (state == KEY_STATES.PRESSED) {
+ state = KEY_STATES.TAPPED;
+ // TODO(rsadam@): Add chording logic here.
+ }
+ this.super();
+ },
+
+ down: function(event) {
+ // First transition state so that populateDetails generates
+ // correct data.
+ switch (state) {
+ case KEY_STATES.UNLOCKED:
+ state = KEY_STATES.PRESSED;
+ break;
+ case KEY_STATES.TAPPED:
+ case KEY_STATES.LOCKED:
+ state = KEY_STATES.UNLOCKED;
+ break;
+ case KEY_STATES.PRESSED:
+ // We pressed another shift key at the same time,
+ // so ignore second press.
+ break;
+ default:
+ console.error("Undefined shift key state: " + state);
+ break;
+ }
+ // Trigger parent behaviour.
+ this.super();
+ this.fire('enable-sel');
+ // Populate double click transition details.
+ var detail = {};
+ detail.char = this.char || this.textContent;
+ detail.toKeyset = this.upperCaseKeysetId;
+ detail.nextKeyset = undefined;
+ detail.callback = this.onDoubleClick;
+ this.fire('enable-dbl', detail);
+ },
+
+ generateLongPressTimer: function() {
+ return this.asyncMethod(function() {
+ var detail = this.populateDetails();
+ if (state == KEY_STATES.LOCKED) {
+ // We don't care about the longpress if we are already
+ // capitalized.
+ return;
+ } else {
+ state = KEY_STATES.LOCKED;
+ detail.toKeyset = this.upperCaseKeysetId;
+ detail.nextKeyset = undefined;
+ }
+ this.fire('key-longpress', detail);
+ }, null, LONGPRESS_DELAY_MSEC);
+ },
+
+ /**
+ * Callback function for when a double click is triggered.
+ */
+ onDoubleClick: function() {
+ state = KEY_STATES.LOCKED;
+ },
+
+ /**
+ * Notifies shift key that a non-control key was pressed down.
+ * A control key is defined as one of shift, control or alt.
+ */
+ onNonControlKeyDown: function() {
+ // TODO(rsadam@): add logic for chording here.
+ switch (state) {
+ case (KEY_STATES.TAPPED):
+ state = KEY_STATES.UNLOCKED;
+ break;
+ case (KEY_STATES.PRESSED):
+ // Enter chording mode. First disable longpress timer.
+ clearTimeout(this.shiftLongPressTimer);
+ break;
+ default:
+ break;
+ }
+ },
+
+ /**
+ * Callback function for when a space is pressed after punctuation.
+ * @return {Object} The keyset transitions the keyboard should make.
+ */
+ onSpaceAfterPunctuation: function() {
+ var detail = {};
+ detail.toKeyset = this.upperCaseKeysetId;
+ detail.nextKeyset = this.lowerCaseKeysetId;
+ state = KEY_STATES.TAPPED;
+ return detail;
+ },
+
+ populateDetails: function() {
+ var detail = this.super();
+ switch(state) {
+ case(KEY_STATES.LOCKED):
+ detail.toKeyset = this.upperCaseKeysetId;
+ break;
+ case(KEY_STATES.UNLOCKED):
+ detail.toKeyset = this.lowerCaseKeysetId;
+ break;
+ case(KEY_STATES.PRESSED):
+ detail.toKeyset = this.upperCaseKeysetId;
+ break;
+ case(KEY_STATES.TAPPED):
+ detail.toKeyset = this.upperCaseKeysetId;
+ detail.nextKeyset = this.lowerCaseKeysetId;
+ break;
+ }
+ return detail;
+ },
+
+ /**
+ * Resets the shift key state.
+ */
+ reset: function() {
+ state = KEY_STATES.UNLOCKED;
+ },
+
+ /**
+ * Overrides longPressTimer for the shift key.
+ */
+ get longPressTimer() {
+ return shiftLongPressTimer;
+ },
+
+ set longPressTimer(timer) {
+ shiftLongPressTimer = timer;
+ },
+
+ get state() {
+ return state;
+ }
+ });
+ })();
+ </script>
+</polymer-element> \ No newline at end of file
diff --git a/chromium/ui/keyboard/resources/index.html b/chromium/ui/keyboard/resources/index.html
index ac2982b4bc0..c18e8e89285 100644
--- a/chromium/ui/keyboard/resources/index.html
+++ b/chromium/ui/keyboard/resources/index.html
@@ -23,20 +23,22 @@
<link rel="import" href="elements/kb-altkey.html">
<link rel="import" href="elements/kb-altkey-data.html">
<link rel="import" href="elements/kb-altkey-set.html">
-
+ <link rel="import" href="elements/kb-key-codes.html">
<link rel="import" href="elements/kb-key-base.html">
<link rel="import" href="elements/kb-key.html">
<link rel="import" href="elements/kb-keyboard.html">
<link rel="import" href="elements/kb-keyset.html">
<link rel="import" href="elements/kb-row.html">
- <!-- TODO(kevers|biao): Switch to dynamic loading strategy once supported
- in Polymer (http://www.crbug.com/260278).-->
- <link id="dvorak" rel="import" href="layouts/dvorak.html">
- <link id="qwerty" rel="import" href="layouts/qwerty.html">
- <!--TODO(stevet): Import 'Open Sans' font. -->
+ <link rel="import" href="elements/kb-shift-key.html">
+ <link rel="import" href="elements/kb-key-sequence.html">
+ <link rel="import" href="elements/kb-key-import.html">
+ <!-- New layouts are dynamically loaded on demand. The link elements are
+ -- inserted here.
+ -->
</head>
<body>
- <kb-keyboard id="keyboard" touch-action="none" layout="qwerty">
+ <!-- TODO(bshe): initial input type should not be hard coded to text. -->
+ <kb-keyboard id="keyboard" touch-action="none" inputType="text">
</kb-keyboard>
</body>
</html>
diff --git a/chromium/ui/keyboard/resources/layouts/dvorak.html b/chromium/ui/keyboard/resources/layouts/dvorak.html
index 2f90470a8d1..1bd2300aefd 100644
--- a/chromium/ui/keyboard/resources/layouts/dvorak.html
+++ b/chromium/ui/keyboard/resources/layouts/dvorak.html
@@ -4,15 +4,13 @@
-- found in the LICENSE file.
-->
-<link rel="import" href="../elements/kb-key-sequence.html">
-<link rel="import" href="../elements/kb-key-import.html">
<link id="spacebar-row" rel="import" href="spacebar-row.html">
<template>
<kb-keyset id="dvorak-upper">
<kb-row>
<kb-key class="tab dark" char="&#x0009;" align="left">tab</kb-key>
- <kb-key-sequence keys="&quot;,.PYFGCRL" superscripts="1234567890"></kb-key-sequence>
+ <kb-key-sequence keys="&quot;,.PYFGCRL" hintTexts="1234567890"></kb-key-sequence>
<kb-key class="backspace dark" char="&#x0008;" repeat align="right">backspace</kb-key>
</kb-row>
<kb-row>
@@ -21,14 +19,14 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-shift-key toKeyset="up:lower" weight="1.8" align="left">shift</kb-shift-key>
+ <kb-shift-key weight="1.8" align="left">shift</kb-shift-key>
<kb-key-sequence keys=";QJKXBMWVZ"></kb-key-sequence>
- <kb-shift-key toKeyset="up:lower" weight="1.8" align="right">shift</kb-shift-key>
+ <kb-shift-key weight="1.8" align="right">shift</kb-shift-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="left">#123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="left">#123</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="right">#123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="right">#123</kb-key>
<kb-layout-selector></kb-layout-selector>
</kb-row>
<kb-altkey-container hidden>
@@ -38,7 +36,7 @@
<kb-keyset id="dvorak-lower" isDefault=true>
<kb-row>
<kb-key class="tab dark" char="&#x0009;" align="left">tab</kb-key>
- <kb-key-sequence keys="&quot;,.pyfgcrl" superscripts="1234567890"></kb-key-sequence>
+ <kb-key-sequence keys="&quot;,.pyfgcrl" hintTexts="1234567890"></kb-key-sequence>
<kb-key class="backspace dark" char="&#x0008;" repeat align="right">backspace</kb-key>
</kb-row>
<kb-row>
@@ -47,14 +45,14 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-shift-key toKeyset="up:upper:lower; long:upper; dbl:upper" weight="1.8" align="left">shift</kb-shift-key>
+ <kb-shift-key weight="1.8" align="left">shift</kb-shift-key>
<kb-key-sequence keys=";qjkxbmwvz"></kb-key-sequence>
- <kb-shift-key toKeyset="up:upper:lower; long:upper; dbl:upper" weight="1.8" align="right">shift</kb-shift-key>
+ <kb-shift-key weight="1.8" align="right">shift</kb-shift-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="left">#123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="left">#123</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="right">#123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="right">#123</kb-key>
<kb-layout-selector></kb-layout-selector>
</kb-row>
<kb-altkey-container hidden>
@@ -73,14 +71,14 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-key class="left-more dark" toKeyset="up:more" char="Invalid" align="left">more</kb-key>
+ <kb-key class="left-more dark" toKeyset="down:more" char="Invalid" align="left">more</kb-key>
<kb-key-sequence keys="!&quot;':;/?"></kb-key-sequence>
- <kb-key class="right-more dark" toKeyset="up:more" char="Invalid" align="right">more</kb-key>
+ <kb-key class="right-more dark" toKeyset="down:more" char="Invalid" align="right">more</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="left">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="left">abc</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="right">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="right">abc</kb-key>
<kb-layout-selector></kb-layout-selector>
</kb-row>
<kb-altkey-container hidden>
@@ -103,16 +101,16 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-key class="left-more dark" toKeyset="up:symbol" char="Invalid" align="left">#123</kb-key>
+ <kb-key class="left-more dark" toKeyset="down:symbol" char="Invalid" align="left">#123</kb-key>
<kb-key>&#x00D7</kb-key><kb-key>&#x00F7</kb-key><kb-key>_</kb-key><kb-key>&#x00A7</kb-key>
<kb-key>&#x00B6</kb-key><kb-key>&#x00A1</kb-key><kb-key>&#x00BF</kb-key><kb-key>&#x2022</kb-key>
<kb-key>&#x0394</kb-key>
- <kb-key class="right-more dark" toKeyset="up:symbol" char="Invalid" align="right">#123</kb-key>
+ <kb-key class="right-more dark" toKeyset="down:symbol" char="Invalid" align="right">#123</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="left">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="left">abc</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="right">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="right">abc</kb-key>
<kb-layout-selector></kb-layout-selector>
</kb-row>
</kb-keyset>
diff --git a/chromium/ui/keyboard/resources/layouts/numeric.html b/chromium/ui/keyboard/resources/layouts/numeric.html
new file mode 100644
index 00000000000..6375f734a5f
--- /dev/null
+++ b/chromium/ui/keyboard/resources/layouts/numeric.html
@@ -0,0 +1,28 @@
+<!--
+ -- Copyright 2013 The Chromium Authors. All rights reserved.
+ -- Use of this source code is governed by a BSD-style license that can be
+ -- found in the LICENSE file.
+ -->
+
+<template>
+ <kb-keyset id="numeric-symbol" isDefault=true>
+ <kb-row>
+ <kb-key>1</kb-key><kb-key>2</kb-key><kb-key>3</kb-key>
+ <kb-key class="dark">-</kb-key>
+ </kb-row>
+ <kb-row>
+ <kb-key>4</kb-key><kb-key>5</kb-key><kb-key>6</kb-key>
+ <kb-key class="dark">,</kb-key>
+ </kb-row>
+ <kb-row>
+ <kb-key>7</kb-key><kb-key>8</kb-key><kb-key>9</kb-key>
+ <kb-key char="&#x0008;" repeat class="dark">backspace</kb-key>
+ </kb-row>
+ <kb-row>
+ <kb-key char=" " class="dark">space</kb-key>
+ <kb-key>0</kb-key>
+ <kb-key class="dark">.</kb-key>
+ <kb-key char="&#x0009;" class="dark">next</kb-key>
+ </kb-row>
+ </kb-keyset>
+</template>
diff --git a/chromium/ui/keyboard/resources/layouts/qwerty.html b/chromium/ui/keyboard/resources/layouts/qwerty.html
index 0f19ebf80f3..361eaf0e726 100644
--- a/chromium/ui/keyboard/resources/layouts/qwerty.html
+++ b/chromium/ui/keyboard/resources/layouts/qwerty.html
@@ -4,15 +4,13 @@
-- found in the LICENSE file.
-->
-<link rel="import" href="../elements/kb-key-sequence.html">
-<link rel="import" href="../elements/kb-key-import.html">
<link id="spacebar-row" rel="import" href="spacebar-row.html">
<template>
<kb-keyset id="qwerty-upper">
<kb-row>
<kb-key class="tab dark" char="&#x0009;" align="left">tab</kb-key>
- <kb-key-sequence keys="QWERTYUIOP" superscripts="1234567890"></kb-key-sequence>
+ <kb-key-sequence keys="QWERTYUIOP" hintTexts="1234567890"></kb-key-sequence>
<kb-key class="backspace dark" char="&#x0008;" repeat align="right">backspace</kb-key>
</kb-row>
<kb-row>
@@ -21,17 +19,17 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-shift-key toKeyset="up:lower" weight="1.8" align="left">shift</kb-shift-key>
+ <kb-shift-key weight="1.8" align="left">shift</kb-shift-key>
<kb-key-sequence keys="ZXCVBNM"></kb-key-sequence>
- <kb-key invert superscript="!" char="!">,</kb-key>
- <kb-key invert superscript="?" char="?">.</kb-key>
- <kb-shift-key toKeyset="up:lower" weight="1.8" align="right">shift</kb-shift-key>
+ <kb-key invert hintText="!" char="!">,</kb-key>
+ <kb-key invert hintText="?" char="?">.</kb-key>
+ <kb-shift-key weight="1.8" align="right">shift</kb-shift-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="left">#123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="left">#123</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="right">#123</kb-key>
- <kb-layout-selector toLayout="dvorak"></kb-layout-selector>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="right">#123</kb-key>
+ <kb-hide-keyboard-key></kb-hide-keyboard-key>
</kb-row>
<kb-altkey-container hidden>
</kb-altkey-container>
@@ -40,7 +38,7 @@
<kb-keyset id="qwerty-lower" isDefault=true>
<kb-row>
<kb-key class="tab dark" char="&#x0009;" align="left">tab</kb-key>
- <kb-key-sequence keys="qwertyuiop" superscripts="1234567890"></kb-key-sequence>
+ <kb-key-sequence keys="qwertyuiop" hintTexts="1234567890"></kb-key-sequence>
<kb-key class="backspace dark" char="&#x0008;" repeat align="right">backspace</kb-key>
</kb-row>
<kb-row>
@@ -49,16 +47,16 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-shift-key toKeyset="up:upper:lower; long:upper; dbl:upper" weight="1.8" align="left">shift</kb-shift-key>
+ <kb-shift-key weight="1.8" align="left">shift</kb-shift-key>
<kb-key-sequence keys="zxcvbnm"></kb-key-sequence>
- <kb-key superscript="!">,</kb-key><kb-key superscript="?">.</kb-key>
- <kb-shift-key toKeyset="up:upper:lower; long:upper; dbl:upper" weight="1.8" align="right">shift</kb-shift-key>
+ <kb-key hintText="!">,</kb-key><kb-key hintText="?">.</kb-key>
+ <kb-shift-key weight="1.8" align="right">shift</kb-shift-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="left">#123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="left">#123</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid" align="right">#123</kb-key>
- <kb-layout-selector toLayout="dvorak"></kb-layout-selector>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid" align="right">#123</kb-key>
+ <kb-hide-keyboard-key></kb-hide-keyboard-key>
</kb-row>
<kb-altkey-container hidden>
</kb-altkey-container>
@@ -82,17 +80,17 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-key class="left-more dark" toKeyset="up:more" char="Invalid" align="left">more</kb-key>
+ <kb-key class="left-more dark" toKeyset="down:more" char="Invalid" align="left">more</kb-key>
<kb-key>:</kb-key><kb-key>;</kb-key><kb-key>-</kb-key><kb-key>'</kb-key>
<kb-key>"</kb-key><kb-key>!</kb-key>
<kb-key>?</kb-key><kb-key>,</kb-key><kb-key>.</kb-key>
- <kb-key class="right-more dark" toKeyset="up:more" char="Invalid" align="right">more</kb-key>
+ <kb-key class="right-more dark" toKeyset="down:more" char="Invalid" align="right">more</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="left">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="left">abc</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="right">abc</kb-key>
- <kb-layout-selector toLayout="dvorak"></kb-layout-selector>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="right">abc</kb-key>
+ <kb-hide-keyboard-key></kb-hide-keyboard-key>
</kb-row>
<kb-altkey-container hidden>
</kb-altkey-container>
@@ -114,17 +112,17 @@
<kb-key class='return dark' char="&#x000A;" align="right">enter</kb-key>
</kb-row>
<kb-row>
- <kb-key class="left-more dark" toKeyset="up:symbol" char="Invalid" align="left">#123</kb-key>
+ <kb-key class="left-more dark" toKeyset="down:symbol" char="Invalid" align="left">#123</kb-key>
<kb-key>&#x00D7;</kb-key><kb-key>&#x00F7;</kb-key><kb-key>_</kb-key><kb-key>&#x00A7;</kb-key>
<kb-key>&#x00B6;</kb-key><kb-key>&#x00A1;</kb-key><kb-key>&#x00BF;</kb-key><kb-key>&#x2022;</kb-key>
<kb-key>&#x0394;</kb-key>
- <kb-key class="right-more dark" toKeyset="up:symbol" char="Invalid" align="right">#123</kb-key>
+ <kb-key class="right-more dark" toKeyset="down:symbol" char="Invalid" align="right">#123</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="left">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="left">abc</kb-key>
<kb-key-import importId="spacebar-row"></kb-key-import>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid" align="right">abc</kb-key>
- <kb-layout-selector toLayout="dvorak"></kb-layout-selector>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid" align="right">abc</kb-key>
+ <kb-hide-keyboard-key></kb-hide-keyboard-key>
</kb-row>
</kb-keyset>
</template>
diff --git a/chromium/ui/keyboard/resources/layouts/symbol-altkeys.js b/chromium/ui/keyboard/resources/layouts/symbol-altkeys.js
index 24dfed8757a..a123dbf2a5d 100644
--- a/chromium/ui/keyboard/resources/layouts/symbol-altkeys.js
+++ b/chromium/ui/keyboard/resources/layouts/symbol-altkeys.js
@@ -3,21 +3,21 @@
// found in the LICENSE file.
var symbolAltKeys = {
- '1': ['\u00B9', // Superscript 1
+ '1': ['\u00B9', // HintText 1
'\u00BD', // Vulgar fraction 1/2
'\u2153', // Vulgar fraction 1/3
'\u00BC', // Vulgar fraction 1/4
'\u215B'], // Vulgar fraction 1/8
- '2': ['\u00B2', // Superscript 2
+ '2': ['\u00B2', // HintText 2
'\u2154'], // Vulgar fraction 2/3
- '3': ['\u00B3', // Superscript 3
+ '3': ['\u00B3', // HintText 3
'\u00BE', // Vulgar fraction 3/4
'\u215C'], // Vulgar fraction 3/8
- '4': ['\u2074'], // Superscript 4
+ '4': ['\u2074'], // HintText 4
'5': ['\u215D'], // Vulgar fraction 5/8
'7': ['\u215E'], // Vulgar fraction 7/8
'0': ['\u00D8', // Empty set
- '\u207F'], // Superscript small n
+ '\u207F'], // HintText small n
'$': ['\u20AC', // Euro sign
'\u00A5', // Yen sign
'\u00A3', // Pound sign
@@ -36,7 +36,8 @@ var symbolAltKeys = {
'!': ['\u00A1'], // Inverted exclamation mark
'?': ['\u00BF'], // Inverted question mark
'(': ['<', '{', '['],
- ')': ['>', '}', ']']
+ ')': ['>', '}', ']'],
+ '.com' : ['.net','.org','.gov']
};
document.addEventListener('WebComponentsReady', function() {
diff --git a/chromium/ui/keyboard/resources/layouts/webui_qwerty.html b/chromium/ui/keyboard/resources/layouts/webui_qwerty.html
index 9abd2e67c86..0c5353f810f 100644
--- a/chromium/ui/keyboard/resources/layouts/webui_qwerty.html
+++ b/chromium/ui/keyboard/resources/layouts/webui_qwerty.html
@@ -19,13 +19,13 @@
<div class="half-key-spacer"></div>
</kb-row>
<kb-row>
- <kb-shift-key class="padded-left-special" toKeyset="up:lower" weight="1.4">shift</kb-shift-key>
+ <kb-shift-key class="padded-left-special" weight="1.4">shift</kb-shift-key>
<kb-key>Z</kb-key><kb-key>X</kb-key><kb-key>C</kb-key><kb-key>V</kb-key>
<kb-key>B</kb-key><kb-key>N</kb-key><kb-key>M</kb-key>
<kb-key class="backspace padded-right-special dark" char="&#x0008;" repeat>delete</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid">?123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid">?123</kb-key>
<kb-key class="microphone dark" char="Microphone"></kb-key>
<kb-key class="dark">,</kb-key>
<kb-key class="space dark" char=" "></kb-key>
@@ -50,13 +50,13 @@
<div class="half-key-spacer"></div>
</kb-row>
<kb-row>
- <kb-shift-key class="padded-left-special" toKeyset="up:upper:lower; long:upper; dbl:upper" weight="1.4">shift</kb-shift-key>
+ <kb-shift-key class="padded-left-special" weight="1.4">shift</kb-shift-key>
<kb-key>z</kb-key><kb-key>x</kb-key><kb-key>c</kb-key><kb-key>v</kb-key>
<kb-key>b</kb-key><kb-key>n</kb-key><kb-key>m</kb-key>
<kb-key class="backspace padded-right-special dark" char="&#x0008;" repeat>delete</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:symbol" char="Invalid">?123</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:symbol" char="Invalid">?123</kb-key>
<kb-key class="microphone dark" char="Microphone"></kb-key>
<kb-key class="dark">,</kb-key>
<kb-key class="space dark" char=" "></kb-key>
@@ -78,13 +78,13 @@
<kb-key>/</kb-key><kb-key>(</kb-key><kb-key>)</kb-key>
</kb-row>
<kb-row>
- <kb-key class="left-more padded-left-special dark" toKeyset="up:more" char="Invalid">more</kb-key>
+ <kb-key class="left-more padded-left-special dark" toKeyset="down:more" char="Invalid">more</kb-key>
<kb-key>"</kb-key><kb-key>'</kb-key><kb-key>-</kb-key>
<kb-key>+</kb-key><kb-key>!</kb-key><kb-key>?</kb-key>
<kb-key class="backspace padded-right-special dark" char="&#x0008;" repeat>delete</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid">abc</kb-key>
<kb-key class="microphone dark" char="Microphone"></kb-key>
<kb-key class="dark">,</kb-key>
<kb-key class="space dark" char=" "></kb-key>
@@ -105,13 +105,13 @@
<kb-key>\</kb-key><kb-key>&#x003C;</kb-key><kb-key>&#x003E;</kb-key>
</kb-row>
<kb-row>
- <kb-key class="left-more padded-left-special dark" toKeyset="up:symbol" char="Invalid">?123</kb-key>
+ <kb-key class="left-more padded-left-special dark" toKeyset="down:symbol" char="Invalid">?123</kb-key>
<kb-key>`</kb-key><kb-key>~</kb-key><kb-key>_</kb-key><kb-key>=</kb-key>
<kb-key>[</kb-key><kb-key>]</kb-key>
<kb-key class="backspace padded-right-special dark" char="&#x0008;" repeat>delete</kb-key>
</kb-row>
<kb-row>
- <kb-key class="symbol dark" toKeyset="up:lower" char="Invalid">abc</kb-key>
+ <kb-key class="symbol dark" toKeyset="down:lower" char="Invalid">abc</kb-key>
<kb-key class="microphone dark" char="Microphone"></kb-key>
<kb-key class="dark">,</kb-key>
<kb-key class="space dark" char=" "></kb-key>
diff --git a/chromium/ui/keyboard/resources/main.css b/chromium/ui/keyboard/resources/main.css
index 149384f8e67..b0948afd95c 100644
--- a/chromium/ui/keyboard/resources/main.css
+++ b/chromium/ui/keyboard/resources/main.css
@@ -22,6 +22,7 @@ kb-keyboard {
}
kb-shift-key,
+kb-hide-keyboard-key,
kb-layout-selector,
kb-key {
background-color: #3b3b3e;
@@ -32,9 +33,9 @@ kb-key {
border-radius: 2px;
color: #ffffff;
display: -webkit-box;
- font-family: 'Open Sans', sans-serif;
+ font-family: 'Open Sans', 'Noto Sans UI', sans-serif;
font-weight: 300;
- margin-left: 7px;
+ margin-left: 0.25em;
position: relative;
}
@@ -45,14 +46,14 @@ kb-key::x-key {
height: 1.2em;
left: 0;
margin: auto;
- padding-left: 10px;
- padding-right: 10px;
+ padding-left: 0.7em;
+ padding-right: 0.7em;
position: absolute;
right: 0;
top: 0;
}
-kb-key::x-superscript {
+kb-key::x-hinttext {
color: #7c7c7c;
font-size: 70%;
position: absolute;
@@ -64,13 +65,19 @@ kb-key::x-key[inverted] {
color: #7c7c7c;
}
-kb-key::x-superscript[inverted] {
+kb-key::x-hinttext[inverted] {
color: #ffffff;
}
-kb-shift-key.dark,
-kb-layout-selector.dark,
-kb-key.dark {
+/**
+* Controls whether the shift key should be highlighted or not.
+* Only highlights if we are in the upper keyset, but not capslocked.
+*/
+kb-keyboard:not(.caps-locked)[keyset=upper] kb-shift-key {
+ color: lightblue;
+}
+
+*.dark {
background-color: #2a2a2c;
border-top: 2px solid #3a3a3c;
}
@@ -87,6 +94,7 @@ kb-altkey::x-key {
text-align: center;
}
+.caps-locked kb-shift-key,
.active {
background-color: #848490 !important;
border-top: 2px solid #A9A9AF !important;
@@ -137,25 +145,29 @@ kb-altkey::x-key {
-webkit-box-flex: 0.6 !important;
}
-.backspace,
-.dotcom,
-.left-more,
-.shift,
-.return,
-.right-more,
-.symbol,
-.tab {
+kb-shift-key.shift,
+kb-key:-webkit-any(.backspace,
+ .dotcom,
+ .left-more,
+ .return,
+ .symbol,
+ .tab) {
font-size: 70%;
+ /* Adjust margin for consistent spacing with the smaller font size. */
+ margin-left: 0.35em;
}
.microphone {
background-image: url('images/microphone.svg');
+ background-position: 4%;
+ background-size: 25%;
}
.audio .microphone {
background-image: url('images/microphone-green.svg');
}
+.hide-keyboard,
.layout-selector {
background-image: url('images/keyboard.svg');
}
diff --git a/chromium/ui/keyboard/resources/manifest.json b/chromium/ui/keyboard/resources/manifest.json
index 93d4a8fab52..5cd326c28a1 100644
--- a/chromium/ui/keyboard/resources/manifest.json
+++ b/chromium/ui/keyboard/resources/manifest.json
@@ -10,7 +10,7 @@
},
"permissions": [
"audioCapture",
- "experimental"
+ "virtualKeyboardPrivate"
],
"content_security_policy": "script-src 'self' 'unsafe-eval'; object-src 'self'"
}
diff --git a/chromium/ui/keyboard/resources/webui/api_adapter.js b/chromium/ui/keyboard/resources/webui/api_adapter.js
index 1d24ba68bc2..17d84b9d7c3 100644
--- a/chromium/ui/keyboard/resources/webui/api_adapter.js
+++ b/chromium/ui/keyboard/resources/webui/api_adapter.js
@@ -5,3 +5,78 @@
function insertText(text) {
chrome.send('insertText', [ text ]);
}
+
+function sendKeyEvent(event) {
+ chrome.send('sendKeyEvent', [ event ]);
+}
+
+function hideKeyboard() {
+ chrome.send('hideKeyboard');
+}
+
+(function(exports) {
+ /**
+ * An array to save callbacks of each request.
+ * @type {Array.<function(Object)>}
+ */
+ var requestIdCallbackMap = [];
+
+ /**
+ * An incremental integer that represents a unique requestId.
+ * @type {number}
+ */
+ var requestId = 0;
+
+ /**
+ * Called when a text input box gets focus.
+ * @param {object} inputContext Describes an input context. It only contains
+ * the type of text input box at present and only "password", "number" and
+ * "text" are supported.
+ */
+ function OnTextInputBoxFocused(inputContext) {
+ keyboard.inputType = inputContext.type;
+ }
+
+ /**
+ * Gets the context of the focused input field. The context is returned as a
+ * paramter in the |callback|.
+ * @param {function(Object)} callback The callback function after the webui
+ * function finished.
+ * @return {number} The ID of the new request.
+ */
+ function GetInputContext(callback) {
+ var id = requestId;
+ requestIdCallbackMap[id] = callback;
+ chrome.send('getInputContext', [ id ]);
+ requestId++;
+ return id;
+ }
+
+ /**
+ * Cancel the callback specified by requestId.
+ * @param {number} requestId The requestId of the callback that about to
+ * cancel.
+ */
+ function CancelRequest(requestId) {
+ requestIdCallbackMap[requestId] = undefined;
+ }
+
+ /**
+ * Webui function callback. Any call to chrome.send('getInputContext', [id])
+ * should trigger this function being called with the parameter
+ * inputContext.requestId == id.
+ * @param {Object} inputContext The context of focused input field. Note we
+ * only have type(input box type) and requestId fields now.
+ */
+ function GetInputContextCallback(inputContext) {
+ var requestId = inputContext.requestId;
+ if (!requestIdCallbackMap[requestId])
+ return;
+ requestIdCallbackMap[requestId](inputContext);
+ }
+
+ exports.OnTextInputBoxFocused = OnTextInputBoxFocused;
+ exports.getInputContext = GetInputContext;
+ exports.cancelRequest = CancelRequest;
+ exports.GetInputContextCallback = GetInputContextCallback;
+})(this);
diff --git a/chromium/ui/keyboard/resources/webui/main.css b/chromium/ui/keyboard/resources/webui/main.css
index 5217143c811..092abd26362 100644
--- a/chromium/ui/keyboard/resources/webui/main.css
+++ b/chromium/ui/keyboard/resources/webui/main.css
@@ -31,7 +31,7 @@ kb-key {
display: -webkit-box;
font-family: 'Open Sans', sans-serif;
font-weight: 600;
- margin-left: 3px;
+ margin-left: 0.2em;
position: relative;
}
@@ -41,14 +41,14 @@ kb-key::x-key {
height: 1.2em;
left: 0;
margin: auto;
- padding-left: 10px;
- padding-right: 10px;
+ padding-left: 0.5em;
+ padding-right: 0.5em;
position: absolute;
right: 0;
top: 0;
}
-kb-key::x-superscript {
+kb-key::x-hinttext {
color: #7c7c7c;
font-size: 70%;
position: absolute;
@@ -60,7 +60,7 @@ kb-key::x-key[inverted] {
color: #7c7c7c;
}
-kb-key::x-superscript[inverted] {
+kb-key::x-hinttext[inverted] {
color: #ffffff;
}
diff --git a/chromium/ui/keyboard/resources/webui_index.html b/chromium/ui/keyboard/resources/webui_index.html
index 48b1637571f..47ae8ed169b 100644
--- a/chromium/ui/keyboard/resources/webui_index.html
+++ b/chromium/ui/keyboard/resources/webui_index.html
@@ -25,11 +25,14 @@
<link rel="import" href="elements/kb-altkey-container.html">
<link rel="import" href="elements/kb-altkey-data.html">
<link rel="import" href="elements/kb-altkey-set.html">
+ <link rel="import" href="elements/kb-key-codes.html">
<link rel="import" href="elements/kb-key-base.html">
<link rel="import" href="elements/kb-key.html">
<link rel="import" href="elements/kb-keyboard.html">
<link rel="import" href="elements/kb-keyset.html">
<link rel="import" href="elements/kb-row.html">
+ <link rel="import" href="elements/kb-shift-key.html">
+ <link id="numeric" rel="import" href="layouts/numeric.html">
<link id="qwerty" rel="import" href="layouts/qwerty.html">
<!--TODO(stevet): Import 'Open Sans' font. -->
<script src="main.js"></script>
diff --git a/chromium/ui/linux_ui/linux_ui_export.h b/chromium/ui/linux_ui/linux_ui_export.h
deleted file mode 100644
index 68f2ab544ab..00000000000
--- a/chromium/ui/linux_ui/linux_ui_export.h
+++ /dev/null
@@ -1,36 +0,0 @@
-// Copyright 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_LINUX_UI_LINUX_UI_EXPORT_H_
-#define UI_LINUX_UI_LINUX_UI_EXPORT_H_
-
-// Defines LINUX_UI_EXPORT so that functionality implemented by the
-// native_theme library can be exported to consumers.
-
-#if defined(COMPONENT_BUILD)
-#if defined(WIN32)
-
-#if defined(LINUX_UI_IMPLEMENTATION)
-#define LINUX_UI_EXPORT __declspec(dllexport)
-#else
-#define LINUX_UI_EXPORT __declspec(dllimport)
-#endif // defined(LINUX_UI_IMPLEMENTATION)
-
-#else // !defined(WIN32)
-
-#if defined(LINUX_UI_IMPLEMENTATION)
-#define LINUX_UI_EXPORT __attribute__((visibility("default")))
-#else
-#define LINUX_UI_EXPORT
-#endif
-
-#endif // defined(WIN32)
-
-#else // !defined(COMPONENT_BUILD)
-
-#define LINUX_UI_EXPORT
-
-#endif // defined(COMPONENT_BUILD)
-
-#endif // UI_LINUX_UI_LINUX_UI_EXPORT_H_
diff --git a/chromium/ui/message_center/cocoa/notification_controller.h b/chromium/ui/message_center/cocoa/notification_controller.h
index 41af2b23280..47f1e87b67d 100644
--- a/chromium/ui/message_center/cocoa/notification_controller.h
+++ b/chromium/ui/message_center/cocoa/notification_controller.h
@@ -41,13 +41,16 @@ MESSAGE_CENTER_EXPORT
base::scoped_nsobject<NSImageView> icon_;
// The title of the message.
- base::scoped_nsobject<NSTextField> title_;
+ base::scoped_nsobject<NSTextView> title_;
// Body text of the message. Hidden for list notifications.
- base::scoped_nsobject<NSTextField> message_;
+ base::scoped_nsobject<NSTextView> message_;
- // Container for optional list item views.
- base::scoped_nsobject<NSView> listItemView_;
+ // Context-giving text of the message. Alternate font used to distinguish it.
+ base::scoped_nsobject<NSTextView> contextMessage_;
+
+ // Container for optional list view that contains multiple items.
+ base::scoped_nsobject<NSView> listView_;
// Container for optional progress bar view.
base::scoped_nsobject<NSProgressIndicator> progressBarView_;
diff --git a/chromium/ui/message_center/cocoa/notification_controller.mm b/chromium/ui/message_center/cocoa/notification_controller.mm
index 965ba423f24..3237a72ca94 100644
--- a/chromium/ui/message_center/cocoa/notification_controller.mm
+++ b/chromium/ui/message_center/cocoa/notification_controller.mm
@@ -14,7 +14,7 @@
#import "ui/base/cocoa/hover_image_button.h"
#include "ui/base/l10n/l10n_util_mac.h"
#include "ui/base/resource/resource_bundle.h"
-#include "ui/base/text/text_elider.h"
+#include "ui/gfx/text_elider.h"
#include "ui/message_center/message_center.h"
#include "ui/message_center/message_center_style.h"
#include "ui/message_center/notification.h"
@@ -150,6 +150,14 @@
[controller_ notificationClicked];
}
+- (NSView*)hitTest:(NSPoint)point {
+ // Route the mouse click events on NSTextView to the container view.
+ NSView* hitView = [super hitTest:point];
+ if (hitView)
+ return [hitView isKindOfClass:[NSTextView class]] ? self : hitView;
+ return nil;
+}
+
- (BOOL)accessibilityIsIgnored {
return NO;
}
@@ -181,12 +189,6 @@
////////////////////////////////////////////////////////////////////////////////
@interface MCNotificationController (Private)
-// Returns a string with item's title in title color and item's message in
-// message color.
-+ (NSAttributedString*)
- attributedStringForItem:(const message_center::NotificationItem&)item
- font:(NSFont*)font;
-
// Configures a NSBox to be borderless, titleless, and otherwise appearance-
// free.
- (void)configureCustomBox:(NSBox*)box;
@@ -203,20 +205,24 @@
// Initializes message_ in the given frame.
- (void)configureBodyInFrame:(NSRect)rootFrame;
-// Creates a NSTextField that the caller owns configured as a label in a
+// Initializes contextMessage_ in the given frame.
+- (void)configureContextMessageInFrame:(NSRect)rootFrame;
+
+// Creates a NSTextView that the caller owns configured as a label in a
// notification.
-- (NSTextField*)newLabelWithFrame:(NSRect)frame;
+- (NSTextView*)newLabelWithFrame:(NSRect)frame;
// Gets the rectangle in which notification content should be placed. This
// rectangle is to the right of the icon and left of the control buttons.
// This depends on the icon_ and closeButton_ being initialized.
- (NSRect)currentContentRect;
-// Returns the wrapped text that could fit within the given text field with not
-// more than the given number of lines. The Ellipsis could be added at the end
-// of the last line if it is too long.
+// Returns the wrapped text that could fit within the content rect with not
+// more than the given number of lines. The wrapped text would be painted using
+// the given font. The Ellipsis could be added at the end of the last line if
+// it is too long.
- (string16)wrapText:(const string16&)text
- forField:(NSTextField*)field
+ forFont:(NSFont*)font
maxNumberOfLines:(size_t)lines;
@end
@@ -260,6 +266,10 @@
[self configureBodyInFrame:rootFrame];
[rootView addSubview:message_];
+ // Create the context message body.
+ [self configureContextMessageInFrame:rootFrame];
+ [rootView addSubview:contextMessage_];
+
// Populate the data.
[self updateNotification:notification_];
}
@@ -285,48 +295,78 @@
CGFloat messageTopGap =
roundf([[message_ font] ascender] - [[message_ font] capHeight]);
+ CGFloat messageBottomGap = roundf(fabs([[message_ font] descender]));
CGFloat messagePadding =
message_center::kTextTopPadding - titleBottomGap - messageTopGap;
+ CGFloat contextMessageTopGap = roundf(
+ [[contextMessage_ font] ascender] - [[contextMessage_ font] capHeight]);
+ CGFloat contextMessagePadding =
+ message_center::kTextTopPadding - messageBottomGap - contextMessageTopGap;
+
// Set the title and recalculate the frame.
- [title_ setStringValue:base::SysUTF16ToNSString(
+ [title_ setString:base::SysUTF16ToNSString(
[self wrapText:notification_->title()
- forField:title_
+ forFont:[title_ font]
maxNumberOfLines:message_center::kTitleLineLimit])];
[title_ sizeToFit];
NSRect titleFrame = [title_ frame];
titleFrame.origin.y = NSMaxY(rootFrame) - titlePadding - NSHeight(titleFrame);
// Set the message and recalculate the frame.
- [message_ setStringValue:base::SysUTF16ToNSString(
+ [message_ setString:base::SysUTF16ToNSString(
[self wrapText:notification_->message()
- forField:title_
+ forFont:[message_ font]
maxNumberOfLines:message_center::kMessageExpandedLineLimit])];
- [message_ setHidden:NO];
[message_ sizeToFit];
NSRect messageFrame = [message_ frame];
- messageFrame.origin.y =
- NSMinY(titleFrame) - messagePadding - NSHeight(messageFrame);
- messageFrame.size.height = NSHeight([message_ frame]);
- // Create the list item views (up to a maximum).
- [listItemView_ removeFromSuperview];
+ // If there are list items, then the message_ view should not be displayed.
const std::vector<message_center::NotificationItem>& items =
notification->items();
- NSRect listFrame = NSZeroRect;
if (items.size() > 0) {
- // If there are list items, then the message_ view should not be displayed.
[message_ setHidden:YES];
messageFrame.origin.y = titleFrame.origin.y;
messageFrame.size.height = 0;
+ } else {
+ [message_ setHidden:NO];
+ messageFrame.origin.y =
+ NSMinY(titleFrame) - messagePadding - NSHeight(messageFrame);
+ messageFrame.size.height = NSHeight([message_ frame]);
+ }
+ // Set the context message and recalculate the frame.
+ [contextMessage_ setString:base::SysUTF16ToNSString(
+ [self wrapText:notification_->context_message()
+ forFont:[contextMessage_ font]
+ maxNumberOfLines:message_center::kContextMessageLineLimit])];
+ [contextMessage_ sizeToFit];
+ NSRect contextMessageFrame = [contextMessage_ frame];
+
+ if (notification_->context_message().empty()) {
+ [contextMessage_ setHidden:YES];
+ contextMessageFrame.origin.y = messageFrame.origin.y;
+ contextMessageFrame.size.height = 0;
+ } else {
+ [contextMessage_ setHidden:NO];
+ contextMessageFrame.origin.y =
+ NSMinY(messageFrame) -
+ contextMessagePadding -
+ NSHeight(contextMessageFrame);
+ contextMessageFrame.size.height = NSHeight([contextMessage_ frame]);
+ }
+
+ // Create the list item views (up to a maximum).
+ [listView_ removeFromSuperview];
+ NSRect listFrame = NSZeroRect;
+ if (items.size() > 0) {
listFrame = [self currentContentRect];
listFrame.origin.y = 0;
listFrame.size.height = 0;
- listItemView_.reset([[NSView alloc] initWithFrame:listFrame]);
- [listItemView_ accessibilitySetOverrideValue:NSAccessibilityListRole
+ listView_.reset([[NSView alloc] initWithFrame:listFrame]);
+ [listView_ accessibilitySetOverrideValue:NSAccessibilityListRole
forAttribute:NSAccessibilityRoleAttribute];
- [listItemView_
+ [listView_
accessibilitySetOverrideValue:NSAccessibilityContentListSubrole
forAttribute:NSAccessibilitySubroleAttribute];
CGFloat y = 0;
@@ -337,23 +377,50 @@
const int kNumNotifications =
std::min(items.size(), message_center::kNotificationMaximumItems);
for (int i = kNumNotifications - 1; i >= 0; --i) {
- NSTextField* field = [self newLabelWithFrame:
+ NSTextView* itemView = [self newLabelWithFrame:
NSMakeRect(0, y, NSWidth(listFrame), lineHeight)];
- [[field cell] setUsesSingleLineMode:YES];
- [field setAttributedStringValue:
- [MCNotificationController attributedStringForItem:items[i]
- font:font]];
- [listItemView_ addSubview:field];
+ [itemView setFont:font];
+
+ // Disable the word-wrap in order to show the text in single line.
+ [[itemView textContainer] setContainerSize:NSMakeSize(FLT_MAX, FLT_MAX)];
+ [[itemView textContainer] setWidthTracksTextView:NO];
+
+ // Construct the text from the title and message.
+ string16 text =
+ items[i].title + base::UTF8ToUTF16(" ") + items[i].message;
+ string16 ellidedText =
+ [self wrapText:text forFont:font maxNumberOfLines:1];
+ [itemView setString:base::SysUTF16ToNSString(ellidedText)];
+
+ // Use dim color for the title part.
+ NSColor* titleColor =
+ gfx::SkColorToCalibratedNSColor(message_center::kRegularTextColor);
+ NSRange titleRange = NSMakeRange(
+ 0,
+ std::min(ellidedText.size(), items[i].title.size()));
+ [itemView setTextColor:titleColor range:titleRange];
+
+ // Use dim color for the message part if it has not been truncated.
+ if (ellidedText.size() > items[i].title.size() + 1) {
+ NSColor* messageColor =
+ gfx::SkColorToCalibratedNSColor(message_center::kDimTextColor);
+ NSRange messageRange = NSMakeRange(
+ items[i].title.size() + 1,
+ ellidedText.size() - items[i].title.size() - 1);
+ [itemView setTextColor:messageColor range:messageRange];
+ }
+
+ [listView_ addSubview:itemView];
y += lineHeight;
}
// TODO(thakis): The spacing is not completely right.
CGFloat listTopPadding =
- message_center::kTextTopPadding - messageTopGap;
+ message_center::kTextTopPadding - contextMessageTopGap;
listFrame.size.height = y;
listFrame.origin.y =
- NSMinY(titleFrame) - listTopPadding - NSHeight(listFrame);
- [listItemView_ setFrame:listFrame];
- [[self view] addSubview:listItemView_];
+ NSMinY(contextMessageFrame) - listTopPadding - NSHeight(listFrame);
+ [listView_ setFrame:listFrame];
+ [[self view] addSubview:listView_];
}
// Create the progress bar view if needed.
@@ -361,7 +428,7 @@
NSRect progressBarFrame = NSZeroRect;
if (notification->type() == message_center::NOTIFICATION_TYPE_PROGRESS) {
progressBarFrame = [self currentContentRect];
- progressBarFrame.origin.y = NSMinY(messageFrame) -
+ progressBarFrame.origin.y = NSMinY(contextMessageFrame) -
message_center::kProgressBarTopPadding -
message_center::kProgressBarThickness;
progressBarFrame.size.height = message_center::kProgressBarThickness;
@@ -376,8 +443,8 @@
// If the bottom-most element so far is out of the rootView's bounds, resize
// the view.
- CGFloat minY = NSMinY(messageFrame);
- if (listItemView_ && NSMinY(listFrame) < minY)
+ CGFloat minY = NSMinY(contextMessageFrame);
+ if (listView_ && NSMinY(listFrame) < minY)
minY = NSMinY(listFrame);
if (progressBarView_ && NSMinY(progressBarFrame) < minY)
minY = NSMinY(progressBarFrame);
@@ -386,6 +453,7 @@
rootFrame.size.height += delta;
titleFrame.origin.y += delta;
messageFrame.origin.y += delta;
+ contextMessageFrame.origin.y += delta;
listFrame.origin.y += delta;
progressBarFrame.origin.y += delta;
}
@@ -456,6 +524,7 @@
rootFrame.size.height += NSHeight(frame);
titleFrame.origin.y += NSHeight(frame);
messageFrame.origin.y += NSHeight(frame);
+ contextMessageFrame.origin.y += NSHeight(frame);
listFrame.origin.y += NSHeight(frame);
progressBarFrame.origin.y += NSHeight(frame);
@@ -467,6 +536,7 @@
rootFrame.size.height += bottomAdjust;
titleFrame.origin.y += bottomAdjust;
messageFrame.origin.y += bottomAdjust;
+ contextMessageFrame.origin.y += bottomAdjust;
listFrame.origin.y += bottomAdjust;
progressBarFrame.origin.y += bottomAdjust;
}
@@ -474,7 +544,8 @@
[[self view] setFrame:rootFrame];
[title_ setFrame:titleFrame];
[message_ setFrame:messageFrame];
- [listItemView_ setFrame:listFrame];
+ [contextMessage_ setFrame:contextMessageFrame];
+ [listView_ setFrame:listFrame];
[progressBarView_ setFrame:progressBarFrame];
return rootFrame;
@@ -504,42 +575,6 @@
// Private /////////////////////////////////////////////////////////////////////
-+ (NSAttributedString*)
- attributedStringForItem:(const message_center::NotificationItem&)item
- font:(NSFont*)font {
- NSString* text = base::SysUTF16ToNSString(
- item.title + base::UTF8ToUTF16(" ") + item.message);
- NSMutableAttributedString* formattedText =
- [[[NSMutableAttributedString alloc] initWithString:text] autorelease];
-
- base::scoped_nsobject<NSMutableParagraphStyle> paragraphStyle(
- [[NSParagraphStyle defaultParagraphStyle] mutableCopy]);
- [paragraphStyle setLineBreakMode:NSLineBreakByTruncatingTail];
- NSDictionary* sharedAttribs = @{
- NSFontAttributeName : font,
- NSParagraphStyleAttributeName : paragraphStyle,
- };
- const NSRange range = NSMakeRange(0, [formattedText length] - 1);
- [formattedText addAttributes:sharedAttribs range:range];
-
- NSDictionary* titleAttribs = @{
- NSForegroundColorAttributeName :
- gfx::SkColorToCalibratedNSColor(message_center::kRegularTextColor),
- };
- const NSRange titleRange = NSMakeRange(0, item.title.size());
- [formattedText addAttributes:titleAttribs range:titleRange];
-
- NSDictionary* messageAttribs = @{
- NSForegroundColorAttributeName :
- gfx::SkColorToCalibratedNSColor(message_center::kDimTextColor),
- };
- const NSRange messageRange =
- NSMakeRange(item.title.size() + 1, item.message.size());
- [formattedText addAttributes:messageAttribs range:messageRange];
-
- return formattedText;
-}
-
- (void)configureCustomBox:(NSBox*)box {
[box setBoxType:NSBoxCustom];
[box setBorderType:NSNoBorder];
@@ -611,17 +646,29 @@
message_.reset([self newLabelWithFrame:frame]);
[message_ setAutoresizingMask:NSViewMinYMargin];
[message_ setTextColor:gfx::SkColorToCalibratedNSColor(
- message_center::kDimTextColor)];
+ message_center::kRegularTextColor)];
[message_ setFont:
[NSFont messageFontOfSize:message_center::kMessageFontSize]];
}
-- (NSTextField*)newLabelWithFrame:(NSRect)frame {
- NSTextField* label = [[NSTextField alloc] initWithFrame:frame];
+- (void)configureContextMessageInFrame:(NSRect)rootFrame {
+ NSRect frame = [self currentContentRect];
+ frame.size.height = 0;
+ contextMessage_.reset([self newLabelWithFrame:frame]);
+ [contextMessage_ setAutoresizingMask:NSViewMinYMargin];
+ [contextMessage_ setTextColor:gfx::SkColorToCalibratedNSColor(
+ message_center::kDimTextColor)];
+ [contextMessage_ setFont:
+ [NSFont messageFontOfSize:message_center::kMessageFontSize]];
+}
+
+- (NSTextView*)newLabelWithFrame:(NSRect)frame {
+ NSTextView* label = [[NSTextView alloc] initWithFrame:frame];
[label setDrawsBackground:NO];
- [label setBezeled:NO];
[label setEditable:NO];
[label setSelectable:NO];
+ [label setTextContainerInset:NSMakeSize(0.0f, 0.0f)];
+ [[label textContainer] setLineFragmentPadding:0.0f];
return label;
}
@@ -638,27 +685,33 @@
}
- (string16)wrapText:(const string16&)text
- forField:(NSTextField*)field
+ forFont:(NSFont*)nsfont
maxNumberOfLines:(size_t)lines {
- gfx::Font font([field font]);
+ if (text.empty())
+ return text;
+ gfx::Font font(nsfont);
int width = NSWidth([self currentContentRect]);
int height = (lines + 1) * font.GetHeight();
std::vector<string16> wrapped;
- ui::ElideRectangleText(text, font, width, height,
- ui::WRAP_LONG_WORDS, &wrapped);
+ gfx::ElideRectangleText(text, font, width, height,
+ gfx::WRAP_LONG_WORDS, &wrapped);
+
+ // This could be possible when the input text contains only spaces.
+ if (wrapped.empty())
+ return string16();
if (wrapped.size() > lines) {
// Add an ellipsis to the last line. If this ellipsis makes the last line
- // too wide, that line will be further elided by the ui::ElideText below.
- string16 last = wrapped[lines - 1] + UTF8ToUTF16(ui::kEllipsis);
+ // too wide, that line will be further elided by the gfx::ElideText below.
+ string16 last = wrapped[lines - 1] + UTF8ToUTF16(gfx::kEllipsis);
if (font.GetStringWidth(last) > width)
- last = ui::ElideText(last, font, width, ui::ELIDE_AT_END);
+ last = gfx::ElideText(last, font, width, gfx::ELIDE_AT_END);
wrapped.resize(lines - 1);
wrapped.push_back(last);
}
- return JoinString(wrapped, '\n');
+ return lines == 1 ? wrapped[0] : JoinString(wrapped, '\n');
}
@end
diff --git a/chromium/ui/message_center/cocoa/notification_controller_unittest.mm b/chromium/ui/message_center/cocoa/notification_controller_unittest.mm
index ea7968e96e7..8ba6026782d 100644
--- a/chromium/ui/message_center/cocoa/notification_controller_unittest.mm
+++ b/chromium/ui/message_center/cocoa/notification_controller_unittest.mm
@@ -76,16 +76,20 @@ class MockMessageCenter : public message_center::FakeMessageCenter {
return icon_.get();
}
-- (NSTextField*)titleView {
+- (NSTextView*)titleView {
return title_.get();
}
-- (NSTextField*)messageView {
+- (NSTextView*)messageView {
return message_.get();
}
-- (NSView*)listItemView {
- return listItemView_.get();
+- (NSTextView*)contextMessageView {
+ return contextMessage_.get();
+}
+
+- (NSView*)listView {
+ return listView_.get();
}
@end
@@ -105,7 +109,7 @@ TEST_F(NotificationControllerTest, BasicLayout) {
ASCIIToUTF16("Jonathan and 5 others"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
notification->set_icon(gfx::Image([TestIcon() retain]));
@@ -116,9 +120,9 @@ TEST_F(NotificationControllerTest, BasicLayout) {
[controller view];
EXPECT_EQ(TestIcon(), [[controller iconView] image]);
- EXPECT_EQ(base::SysNSStringToUTF16([[controller titleView] stringValue]),
+ EXPECT_EQ(base::SysNSStringToUTF16([[controller titleView] string]),
notification->title());
- EXPECT_EQ(base::SysNSStringToUTF16([[controller messageView] stringValue]),
+ EXPECT_EQ(base::SysNSStringToUTF16([[controller messageView] string]),
notification->message());
EXPECT_EQ(controller.get(), [[controller closeButton] target]);
}
@@ -135,7 +139,7 @@ TEST_F(NotificationControllerTest, OverflowText) {
"entire thing?"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
base::scoped_nsobject<MCNotificationController> controller(
@@ -156,7 +160,7 @@ TEST_F(NotificationControllerTest, Close) {
string16(),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
MockMessageCenter message_center;
@@ -183,7 +187,7 @@ TEST_F(NotificationControllerTest, Update) {
"default bounds."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
base::scoped_nsobject<MCNotificationController> controller(
@@ -219,7 +223,7 @@ TEST_F(NotificationControllerTest, Buttons) {
string16(),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
optional,
NULL));
MockMessageCenter message_center;
@@ -244,7 +248,7 @@ TEST_F(NotificationControllerTest, Image) {
string16(),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
NSImage* image = [NSImage imageNamed:NSImageNameFolder];
@@ -272,6 +276,11 @@ TEST_F(NotificationControllerTest, List) {
UTF8ToUTF16("Second title"),
UTF8ToUTF16("second slightly longer message"));
optional.items.push_back(item2);
+ message_center::NotificationItem item3(
+ UTF8ToUTF16(""), // Test for empty string.
+ UTF8ToUTF16(" ")); // Test for string containing only spaces.
+ optional.items.push_back(item3);
+ optional.context_message = UTF8ToUTF16("Context Message");
scoped_ptr<message_center::Notification> notification(
new message_center::Notification(
@@ -281,7 +290,7 @@ TEST_F(NotificationControllerTest, List) {
UTF8ToUTF16("Notification Message - should be hidden"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
optional,
NULL));
@@ -293,8 +302,9 @@ TEST_F(NotificationControllerTest, List) {
EXPECT_FALSE([[controller titleView] isHidden]);
EXPECT_TRUE([[controller messageView] isHidden]);
+ EXPECT_FALSE([[controller contextMessageView] isHidden]);
- EXPECT_EQ(2u, [[[controller listItemView] subviews] count]);
- EXPECT_LT(NSMaxY([[controller listItemView] frame]),
+ EXPECT_EQ(3u, [[[controller listView] subviews] count]);
+ EXPECT_LT(NSMaxY([[controller listView] frame]),
NSMinY([[controller titleView] frame]));
}
diff --git a/chromium/ui/message_center/cocoa/popup_collection_unittest.mm b/chromium/ui/message_center/cocoa/popup_collection_unittest.mm
index 105c824e875..3ec7c3318f2 100644
--- a/chromium/ui/message_center/cocoa/popup_collection_unittest.mm
+++ b/chromium/ui/message_center/cocoa/popup_collection_unittest.mm
@@ -51,7 +51,7 @@ class PopupCollectionTest : public ui::CocoaTest {
" be displayed"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -63,7 +63,7 @@ class PopupCollectionTest : public ui::CocoaTest {
ASCIIToUTF16("This is the second notification."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -76,10 +76,11 @@ class PopupCollectionTest : public ui::CocoaTest {
"that has a much longer body "
"than the other notifications. It "
"may not fit on the screen if we "
- "set the screen size too small."),
+ "set the screen size too small or "
+ "if the notification is way too big"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -134,7 +135,7 @@ TEST_F(PopupCollectionTest, AttemptFourOneOffscreen) {
ASCIIToUTF16("This is the fourth notification."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -183,7 +184,7 @@ TEST_F(PopupCollectionTest, LayoutSpacing) {
ASCIIToUTF16("This is the fourth notification."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
optional,
NULL));
center_->AddNotification(notification.Pass());
@@ -221,7 +222,7 @@ TEST_F(PopupCollectionTest, TinyScreen) {
" be displayed"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -243,7 +244,7 @@ TEST_F(PopupCollectionTest, TinyScreen) {
"long notification."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->UpdateNotification("1", notification.Pass());
@@ -287,7 +288,7 @@ TEST_F(PopupCollectionTest, UpdateIconAndBody) {
"longer body"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -316,7 +317,7 @@ TEST_F(PopupCollectionTest, CloseCollectionBeforeNewPopupAnimationEnds) {
" be displayed"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -349,7 +350,7 @@ TEST_F(PopupCollectionTest, CloseCollectionBeforeUpdatePopupAnimationEnds) {
ASCIIToUTF16("New message."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->UpdateNotification("1", notification.Pass());
diff --git a/chromium/ui/message_center/cocoa/popup_controller_unittest.mm b/chromium/ui/message_center/cocoa/popup_controller_unittest.mm
index 41f627937e7..c39d1631288 100644
--- a/chromium/ui/message_center/cocoa/popup_controller_unittest.mm
+++ b/chromium/ui/message_center/cocoa/popup_controller_unittest.mm
@@ -23,7 +23,7 @@ TEST_F(PopupControllerTest, Creation) {
ASCIIToUTF16("Jonathan and 5 others"),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
diff --git a/chromium/ui/message_center/cocoa/tray_controller.mm b/chromium/ui/message_center/cocoa/tray_controller.mm
index f911ec98353..672525f29dc 100644
--- a/chromium/ui/message_center/cocoa/tray_controller.mm
+++ b/chromium/ui/message_center/cocoa/tray_controller.mm
@@ -105,7 +105,7 @@
// The settings bubble data structures assume that the settings dialog is
// visible only for short periods of time: There's a fixed list of permissions
// for example.
- [viewController_ hideSettings:self];
+ [viewController_ cleanupSettings];
tray_->HideMessageCenterBubble();
}
diff --git a/chromium/ui/message_center/cocoa/tray_view_controller.h b/chromium/ui/message_center/cocoa/tray_view_controller.h
index cb9379b877c..d5f9f1f8876 100644
--- a/chromium/ui/message_center/cocoa/tray_view_controller.h
+++ b/chromium/ui/message_center/cocoa/tray_view_controller.h
@@ -134,7 +134,11 @@ MESSAGE_CENTER_EXPORT
- (void)updateSettings;
// Hides the settings dialog if it's open.
-- (void)hideSettings:(id)sender;
+- (void)showMessages:(id)sender;
+
+// Cleans up settings data structures. Called when messages are shown and when
+// closing the center directly from the settings.
+- (void)cleanupSettings;
// Scroll to the topmost notification in the tray.
- (void)scrollToTop;
diff --git a/chromium/ui/message_center/cocoa/tray_view_controller.mm b/chromium/ui/message_center/cocoa/tray_view_controller.mm
index 67b0cdf712d..17c24f73657 100644
--- a/chromium/ui/message_center/cocoa/tray_view_controller.mm
+++ b/chromium/ui/message_center/cocoa/tray_view_controller.mm
@@ -126,6 +126,9 @@ const CGFloat kTrayBottomMargin = 75;
animation_.reset();
}
if (clearAllInProgress_) {
+ // To stop chain of clearOneNotification calls to start new animations.
+ [NSObject cancelPreviousPerformRequestsWithTarget:self];
+
for (NSViewAnimation* animation in clearAllAnimations_.get()) {
[animation stopAnimation];
[animation setDelegate:nil];
@@ -277,7 +280,7 @@ const CGFloat kTrayBottomMargin = 75;
- (void)showSettings:(id)sender {
if (settingsController_)
- return [self hideSettings:sender];
+ return [self showMessages:sender];
message_center::NotifierSettingsProvider* provider =
messageCenter_->GetNotifierSettingsProvider();
@@ -297,6 +300,7 @@ const CGFloat kTrayBottomMargin = 75;
[scrollView_ setHidden:YES];
[[[self view] window] recalculateKeyViewLoop];
+ messageCenter_->SetVisibility(message_center::VISIBILITY_SETTINGS);
[self updateTrayViewAndWindow];
}
@@ -312,7 +316,14 @@ const CGFloat kTrayBottomMargin = 75;
[self updateTrayViewAndWindow];
}
-- (void)hideSettings:(id)sender {
+- (void)showMessages:(id)sender {
+ messageCenter_->SetVisibility(message_center::VISIBILITY_MESSAGE_CENTER);
+ [self cleanupSettings];
+ [[[self view] window] recalculateKeyViewLoop];
+ [self updateTrayViewAndWindow];
+}
+
+- (void)cleanupSettings {
[scrollView_ setHidden:NO];
[[settingsController_ view] removeFromSuperview];
@@ -324,8 +335,6 @@ const CGFloat kTrayBottomMargin = 75;
[backButton_ setHidden:YES];
[clearAllButton_ setEnabled:YES];
- [[[self view] window] recalculateKeyViewLoop];
- [self updateTrayViewAndWindow];
}
- (void)scrollToTop {
@@ -424,7 +433,7 @@ const CGFloat kTrayBottomMargin = 75;
rb.GetNativeImageNamed(IDR_NOTIFICATION_ARROW_HOVER).ToNSImage()];
[backButton_ setPressedImage:
rb.GetNativeImageNamed(IDR_NOTIFICATION_ARROW_PRESSED).ToNSImage()];
- [backButton_ setAction:@selector(hideSettings:)];
+ [backButton_ setAction:@selector(showMessages:)];
configureButton(backButton_);
[backButton_ setHidden:YES];
[backButton_ setKeyEquivalent:@"\e"];
diff --git a/chromium/ui/message_center/cocoa/tray_view_controller_unittest.mm b/chromium/ui/message_center/cocoa/tray_view_controller_unittest.mm
index 6c82777be9d..03207d965d2 100644
--- a/chromium/ui/message_center/cocoa/tray_view_controller_unittest.mm
+++ b/chromium/ui/message_center/cocoa/tray_view_controller_unittest.mm
@@ -71,7 +71,7 @@ TEST_F(TrayViewControllerTest, AddRemoveOne) {
ASCIIToUTF16("This is a simple test."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification_data.Pass());
@@ -105,7 +105,7 @@ TEST_F(TrayViewControllerTest, AddThreeClearAll) {
ASCIIToUTF16("This is a simple test."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -116,7 +116,7 @@ TEST_F(TrayViewControllerTest, AddThreeClearAll) {
ASCIIToUTF16("This is a simple test."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -127,7 +127,7 @@ TEST_F(TrayViewControllerTest, AddThreeClearAll) {
ASCIIToUTF16("This is a simple test."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -160,7 +160,7 @@ TEST_F(TrayViewControllerTest, NoClearAllWhenNoNotifications) {
ASCIIToUTF16("This is a simple test."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -179,7 +179,7 @@ TEST_F(TrayViewControllerTest, NoClearAllWhenNoNotifications) {
ASCIIToUTF16("This is a simple test."),
gfx::Image(),
string16(),
- std::string(),
+ message_center::NotifierId(),
message_center::RichNotificationData(),
NULL));
center_->AddNotification(notification.Pass());
@@ -225,13 +225,15 @@ TEST_F(TrayViewControllerTest, Settings) {
EXPECT_EQ(0, provider.closed_called_count());
[tray_ showSettings:nil];
+ EXPECT_FALSE(center_->IsMessageCenterVisible());
// There are 0 notifications, but 2 notifiers. The settings pane should be
// higher than the empty tray bubble.
EXPECT_LT(trayHeight, NSHeight([[tray_ view] frame]));
- [tray_ hideSettings:nil];
+ [tray_ showMessages:nil];
EXPECT_EQ(1, provider.closed_called_count());
+ EXPECT_TRUE(center_->IsMessageCenterVisible());
// The tray should be back at its previous height now.
EXPECT_EQ(trayHeight, NSHeight([[tray_ view] frame]));
diff --git a/chromium/ui/message_center/dummy_message_center.cc b/chromium/ui/message_center/dummy_message_center.cc
index 27ecc912eb4..54b30825113 100644
--- a/chromium/ui/message_center/dummy_message_center.cc
+++ b/chromium/ui/message_center/dummy_message_center.cc
@@ -39,7 +39,4 @@ MessageCenter::MessageCenter() {
MessageCenter::~MessageCenter() {
}
-MessageCenter::Delegate::~Delegate() {
-}
-
} // namespace message_center
diff --git a/chromium/ui/message_center/fake_message_center.cc b/chromium/ui/message_center/fake_message_center.cc
index 4deff26b138..eaa4c42cc88 100644
--- a/chromium/ui/message_center/fake_message_center.cc
+++ b/chromium/ui/message_center/fake_message_center.cc
@@ -19,7 +19,11 @@ void FakeMessageCenter::AddObserver(MessageCenterObserver* observer) {
void FakeMessageCenter::RemoveObserver(MessageCenterObserver* observer) {
}
-void FakeMessageCenter::SetDelegate(Delegate* delegate) {
+void FakeMessageCenter::AddNotificationBlocker(NotificationBlocker* blocker) {
+}
+
+void FakeMessageCenter::RemoveNotificationBlocker(
+ NotificationBlocker* blocker) {
}
size_t FakeMessageCenter::NotificationCount() const {
@@ -83,13 +87,8 @@ void FakeMessageCenter::SetNotificationButtonIcon(
const gfx::Image& image) {
}
-void FakeMessageCenter::DisableNotificationsByExtension(const std::string& id) {
-}
-
-void FakeMessageCenter::DisableNotificationsByUrl(const std::string& id) {
-}
-
-void FakeMessageCenter::ShowNotificationSettings(const std::string& id) {
+void FakeMessageCenter::DisableNotificationsByNotifier(
+ const NotifierId& notifier_id) {
}
void FakeMessageCenter::ExpandNotification(const std::string& id) {
@@ -124,7 +123,7 @@ void FakeMessageCenter::EnterQuietModeWithExpire(
const base::TimeDelta& expires_in) {
}
-void FakeMessageCenter::SetMessageCenterVisible(bool visible) {
+void FakeMessageCenter::SetVisibility(Visibility visible) {
}
bool FakeMessageCenter::IsMessageCenterVisible() {
diff --git a/chromium/ui/message_center/fake_message_center.h b/chromium/ui/message_center/fake_message_center.h
index ebb9be210d4..e7fbddcbd9e 100644
--- a/chromium/ui/message_center/fake_message_center.h
+++ b/chromium/ui/message_center/fake_message_center.h
@@ -6,6 +6,7 @@
#define UI_MESSAGE_CENTER_FAKE_MESSAGE_CENTER_H_
#include "ui/message_center/message_center.h"
+#include "ui/message_center/message_center_types.h"
namespace message_center {
@@ -18,9 +19,10 @@ class FakeMessageCenter : public MessageCenter {
virtual ~FakeMessageCenter();
// Overridden from FakeMessageCenter.
- virtual void SetDelegate(Delegate* delegate) OVERRIDE;
virtual void AddObserver(MessageCenterObserver* observer) OVERRIDE;
virtual void RemoveObserver(MessageCenterObserver* observer) OVERRIDE;
+ virtual void AddNotificationBlocker(NotificationBlocker* blocker) OVERRIDE;
+ virtual void RemoveNotificationBlocker(NotificationBlocker* blocker) OVERRIDE;
virtual size_t NotificationCount() const OVERRIDE;
virtual size_t UnreadNotificationCount() const OVERRIDE;
virtual bool HasPopupNotifications() const OVERRIDE;
@@ -45,9 +47,8 @@ class FakeMessageCenter : public MessageCenter {
virtual void SetNotificationButtonIcon(const std::string& notification_id,
int button_index,
const gfx::Image& image) OVERRIDE;
- virtual void DisableNotificationsByExtension(const std::string& id) OVERRIDE;
- virtual void DisableNotificationsByUrl(const std::string& id) OVERRIDE;
- virtual void ShowNotificationSettings(const std::string& id) OVERRIDE;
+ virtual void DisableNotificationsByNotifier(
+ const NotifierId& notifier_id) OVERRIDE;
virtual void ExpandNotification(const std::string& id) OVERRIDE;
virtual void ClickOnNotification(const std::string& id) OVERRIDE;
virtual void ClickOnNotificationButton(const std::string& id,
@@ -61,7 +62,7 @@ class FakeMessageCenter : public MessageCenter {
virtual void SetQuietMode(bool in_quiet_mode) OVERRIDE;
virtual void EnterQuietModeWithExpire(
const base::TimeDelta& expires_in) OVERRIDE;
- virtual void SetMessageCenterVisible(bool visible) OVERRIDE;
+ virtual void SetVisibility(Visibility visible) OVERRIDE;
virtual bool IsMessageCenterVisible() OVERRIDE;
virtual void RestartPopupTimers() OVERRIDE;
virtual void PausePopupTimers() OVERRIDE;
diff --git a/chromium/ui/message_center/fake_notifier_settings_provider.cc b/chromium/ui/message_center/fake_notifier_settings_provider.cc
index d8054cab2e5..f593ed9820f 100644
--- a/chromium/ui/message_center/fake_notifier_settings_provider.cc
+++ b/chromium/ui/message_center/fake_notifier_settings_provider.cc
@@ -15,7 +15,9 @@ FakeNotifierSettingsProvider::NotifierGroupItem::NotifierGroupItem() {
FakeNotifierSettingsProvider::NotifierGroupItem::~NotifierGroupItem() {
}
-FakeNotifierSettingsProvider::FakeNotifierSettingsProvider() {
+FakeNotifierSettingsProvider::FakeNotifierSettingsProvider()
+ : closed_called_count_(0),
+ active_item_index_(0) {
}
FakeNotifierSettingsProvider::FakeNotifierSettingsProvider(
diff --git a/chromium/ui/message_center/fake_notifier_settings_provider.h b/chromium/ui/message_center/fake_notifier_settings_provider.h
index 85348f75924..b71a7e9fb28 100644
--- a/chromium/ui/message_center/fake_notifier_settings_provider.h
+++ b/chromium/ui/message_center/fake_notifier_settings_provider.h
@@ -14,7 +14,8 @@ namespace message_center {
class FakeNotifierSettingsProvider : public NotifierSettingsProvider {
public:
FakeNotifierSettingsProvider();
- FakeNotifierSettingsProvider(const std::vector<Notifier*>& notifiers);
+ explicit FakeNotifierSettingsProvider(
+ const std::vector<Notifier*>& notifiers);
virtual ~FakeNotifierSettingsProvider();
virtual size_t GetNotifierGroupCount() const OVERRIDE;
diff --git a/chromium/ui/message_center/message_center.cc b/chromium/ui/message_center/message_center.cc
index dc0de1c3103..82f2e8443aa 100644
--- a/chromium/ui/message_center/message_center.cc
+++ b/chromium/ui/message_center/message_center.cc
@@ -11,11 +11,6 @@ namespace message_center {
//------------------------------------------------------------------------------
-MessageCenter::Delegate::~Delegate() {
-}
-
-//------------------------------------------------------------------------------
-
namespace {
static MessageCenter* g_message_center;
}
diff --git a/chromium/ui/message_center/message_center.gyp b/chromium/ui/message_center/message_center.gyp
index dc1f1ab6fea..46f4d5b111d 100644
--- a/chromium/ui/message_center/message_center.gyp
+++ b/chromium/ui/message_center/message_center.gyp
@@ -54,10 +54,13 @@
'message_center_tray.cc',
'message_center_tray.h',
'message_center_tray_delegate.h',
+ 'message_center_types.h',
'message_center_util.cc',
'message_center_util.h',
'notification.cc',
'notification.h',
+ 'notification_blocker.cc',
+ 'notification_blocker.h',
'notification_list.cc',
'notification_list.h',
'notification_types.cc',
diff --git a/chromium/ui/message_center/message_center.h b/chromium/ui/message_center/message_center.h
index c0556647148..ebe90d23232 100644
--- a/chromium/ui/message_center/message_center.h
+++ b/chromium/ui/message_center/message_center.h
@@ -11,6 +11,7 @@
#include "base/observer_list.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/message_center/message_center_export.h"
+#include "ui/message_center/message_center_types.h"
#include "ui/message_center/notification_list.h"
#include "ui/message_center/notification_types.h"
@@ -24,12 +25,11 @@ class DictionaryValue;
// [Add|Remove|Update]Notification to create and update notifications in the
// list. It also sends those changes to its observers when a notification
// is shown, closed, or clicked on.
-// It can also implement Delegate to ask platform-dependent features like
-// disabling extensions or opening settings.
namespace message_center {
class MessageCenterObserver;
+class NotificationBlocker;
class NotificationList;
class NotifierSettingsDelegate;
class NotifierSettingsProvider;
@@ -39,33 +39,13 @@ class MESSAGE_CENTER_EXPORT MessageCenter {
// Creates the global message center object.
static void Initialize();
- // Returns the global message center object. Initialize must be called first.
+ // Returns the global message center object. Returns NULL if Initialize is not
+ // called.
static MessageCenter* Get();
// Destroys the global message_center object.
static void Shutdown();
- class MESSAGE_CENTER_EXPORT Delegate {
- public:
- virtual ~Delegate();
-
- // Request to disable the extension associated with |notification_id|.
- virtual void DisableExtension(const std::string& notification_id) = 0;
-
- // Request to disable notifications from the source of |notification_id|.
- virtual void DisableNotificationsFromSource(
- const std::string& notification_id) = 0;
-
- // Request to show the notification settings (|notification_id| is used
- // to identify the requesting browser context).
- virtual void ShowSettings(const std::string& notification_id) = 0;
- };
-
- // Called to set the delegate. Generally called only once, except in tests.
- // Changing the delegate does not affect notifications in its
- // NotificationList.
- virtual void SetDelegate(Delegate* delegate) = 0;
-
// Management of the observer list.
virtual void AddObserver(MessageCenterObserver* observer) = 0;
virtual void RemoveObserver(MessageCenterObserver* observer) = 0;
@@ -83,6 +63,10 @@ class MESSAGE_CENTER_EXPORT MessageCenter {
// Gets all notifications being shown as popups.
virtual NotificationList::PopupNotifications GetPopupNotifications() = 0;
+ // Management of NotificaitonBlockers.
+ virtual void AddNotificationBlocker(NotificationBlocker* blocker) = 0;
+ virtual void RemoveNotificationBlocker(NotificationBlocker* blocker) = 0;
+
// Basic operations of notification: add/remove/update.
// Adds a new notification.
@@ -115,17 +99,8 @@ class MESSAGE_CENTER_EXPORT MessageCenter {
// and settings.
// Searches through the notifications and disables any that match the
// extension id given.
- virtual void DisableNotificationsByExtension(const std::string& id) = 0;
-
- // Disables all notifications that match the given url by querying the
- // delegate and also by matching display_source.
- // TODO(dewittj): Is display_source matching necessary?
- virtual void DisableNotificationsByUrl(const std::string& url) = 0;
-
- // TODO(mukai): settings can be in another class?
- // Shows the settings for a web notification (profile is identified by the
- // given notification id).
- virtual void ShowNotificationSettings(const std::string& id) = 0;
+ virtual void DisableNotificationsByNotifier(
+ const NotifierId& notifier_id) = 0;
// Reformat a notification to show its entire text content.
virtual void ExpandNotification(const std::string& id) = 0;
@@ -168,7 +143,7 @@ class MESSAGE_CENTER_EXPORT MessageCenter {
// Informs the notification list whether the message center is visible.
// This affects whether or not a message has been "read".
- virtual void SetMessageCenterVisible(bool visible) = 0;
+ virtual void SetVisibility(Visibility visible) = 0;
// Allows querying the visibility of the center.
virtual bool IsMessageCenterVisible() = 0;
diff --git a/chromium/ui/message_center/message_center_impl.cc b/chromium/ui/message_center/message_center_impl.cc
index c1d0179dc00..2d8c9f22518 100644
--- a/chromium/ui/message_center/message_center_impl.cc
+++ b/chromium/ui/message_center/message_center_impl.cc
@@ -4,9 +4,13 @@
#include "ui/message_center/message_center_impl.h"
+#include <algorithm>
+
#include "base/observer_list.h"
#include "ui/message_center/message_center_style.h"
+#include "ui/message_center/message_center_types.h"
#include "ui/message_center/notification.h"
+#include "ui/message_center/notification_blocker.h"
#include "ui/message_center/notification_list.h"
#include "ui/message_center/notification_types.h"
@@ -27,6 +31,35 @@ namespace message_center {
namespace internal {
////////////////////////////////////////////////////////////////////////////////
+// NotificationQueueItem
+
+struct NotificationQueueItem {
+ public:
+ Notification* notification;
+ bool is_update;
+ std::string pre_update_id;
+};
+
+void DeleteQueueNotification(NotificationQueueItem item) {
+ if (item.notification)
+ delete item.notification;
+}
+
+
+////////////////////////////////////////////////////////////////////////////////
+// NotificationFinder
+
+struct NotificationFinder {
+ explicit NotificationFinder(const std::string& id) : id(id) {}
+ bool operator()(const NotificationQueueItem& item) {
+ DCHECK(item.notification);
+ return item.notification->id() == id;
+ }
+
+ std::string id;
+};
+
+////////////////////////////////////////////////////////////////////////////////
// PopupTimer
PopupTimer::PopupTimer(const std::string& id,
@@ -194,13 +227,16 @@ void PopupTimersController::OnNotificationRemoved(const std::string& id,
MessageCenterImpl::MessageCenterImpl()
: MessageCenter(),
popup_timers_controller_(new internal::PopupTimersController(this)),
- delegate_(NULL),
settings_provider_(NULL) {
notification_list_.reset(new NotificationList());
}
MessageCenterImpl::~MessageCenterImpl() {
notification_list_.reset();
+ for_each(notification_queue_.begin(),
+ notification_queue_.end(),
+ internal::DeleteQueueNotification);
+ notification_queue_.clear();
}
void MessageCenterImpl::AddObserver(MessageCenterObserver* observer) {
@@ -211,13 +247,41 @@ void MessageCenterImpl::RemoveObserver(MessageCenterObserver* observer) {
observer_list_.RemoveObserver(observer);
}
-void MessageCenterImpl::SetDelegate(Delegate* delegate) {
- delegate_ = delegate;
+void MessageCenterImpl::AddNotificationBlocker(NotificationBlocker* blocker) {
+ if (std::find(blockers_.begin(), blockers_.end(), blocker) !=
+ blockers_.end()) {
+ return;
+ }
+ blocker->AddObserver(this);
+ blockers_.push_back(blocker);
+}
+
+void MessageCenterImpl::RemoveNotificationBlocker(
+ NotificationBlocker* blocker) {
+ std::vector<NotificationBlocker*>::iterator iter =
+ std::find(blockers_.begin(), blockers_.end(), blocker);
+ if (iter == blockers_.end())
+ return;
+ blocker->RemoveObserver(this);
+ blockers_.erase(iter);
}
-void MessageCenterImpl::SetMessageCenterVisible(bool visible) {
+void MessageCenterImpl::OnBlockingStateChanged() {
+ std::list<std::string> blocked_ids;
+ NotificationList::PopupNotifications popups =
+ notification_list_->GetPopupNotifications(blockers_, &blocked_ids);
+
+ for (std::list<std::string>::const_iterator iter = blocked_ids.begin();
+ iter != blocked_ids.end(); ++iter) {
+ MarkSinglePopupAsShown((*iter), true);
+ }
+}
+
+void MessageCenterImpl::SetVisibility(Visibility visibility) {
std::set<std::string> updated_ids;
- notification_list_->SetMessageCenterVisible(visible, &updated_ids);
+ notification_list_->SetMessageCenterVisible(
+ (visibility == VISIBILITY_MESSAGE_CENTER), &updated_ids);
+
for (std::set<std::string>::const_iterator iter = updated_ids.begin();
iter != updated_ids.end();
++iter) {
@@ -225,10 +289,26 @@ void MessageCenterImpl::SetMessageCenterVisible(bool visible) {
MessageCenterObserver, observer_list_, OnNotificationUpdated(*iter));
}
- if (!visible) {
- FOR_EACH_OBSERVER(
- MessageCenterObserver, observer_list_, OnNotificationCenterClosed());
+ if (visibility == VISIBILITY_TRANSIENT) {
+ for (std::list<internal::NotificationQueueItem>::const_iterator iter =
+ notification_queue_.begin();
+ iter != notification_queue_.end();
+ ++iter) {
+ // Warning: After this line, the queue will no longer own the
+ // notifications contained.
+ if ((*iter).is_update)
+ UpdateNotification((*iter).pre_update_id,
+ scoped_ptr<Notification>((*iter).notification));
+ else
+ AddNotification(scoped_ptr<Notification>((*iter).notification));
+ }
+ // This does not delete the internal notification pointers since they are
+ // now owned by the notification list.
+ notification_queue_.clear();
}
+ FOR_EACH_OBSERVER(MessageCenterObserver,
+ observer_list_,
+ OnCenterVisibilityChanged(visibility));
}
bool MessageCenterImpl::IsMessageCenterVisible() {
@@ -244,7 +324,7 @@ size_t MessageCenterImpl::UnreadNotificationCount() const {
}
bool MessageCenterImpl::HasPopupNotifications() const {
- return notification_list_->HasPopupNotifications();
+ return notification_list_->HasPopupNotifications(blockers_);
}
bool MessageCenterImpl::HasNotification(const std::string& id) {
@@ -267,7 +347,7 @@ const NotificationList::Notifications& MessageCenterImpl::GetNotifications() {
NotificationList::PopupNotifications
MessageCenterImpl::GetPopupNotifications() {
- return notification_list_->GetPopupNotifications();
+ return notification_list_->GetPopupNotifications(blockers_, NULL);
}
//------------------------------------------------------------------------------
@@ -275,6 +355,27 @@ NotificationList::PopupNotifications
void MessageCenterImpl::AddNotification(scoped_ptr<Notification> notification) {
DCHECK(notification.get());
+ for (size_t i = 0; i < blockers_.size(); ++i)
+ blockers_[i]->CheckState();
+
+ if (notification_list_->is_message_center_visible()) {
+ std::list<internal::NotificationQueueItem>::iterator iter = std::find_if(
+ notification_queue_.begin(),
+ notification_queue_.end(),
+ internal::NotificationFinder(notification->id()));
+ if (iter != notification_queue_.end()) {
+ internal::DeleteQueueNotification(*iter);
+ notification_queue_.erase(iter);
+ }
+ internal::NotificationQueueItem item = {
+ notification.release(),
+ false,
+ std::string()
+ };
+ notification_queue_.push_back(item);
+ return;
+ }
+
// Sometimes the notification can be added with the same id and the
// |notification_list| will replace the notification instead of adding new.
// This is essentially an update rather than addition.
@@ -294,6 +395,38 @@ void MessageCenterImpl::AddNotification(scoped_ptr<Notification> notification) {
void MessageCenterImpl::UpdateNotification(
const std::string& old_id,
scoped_ptr<Notification> new_notification) {
+ for (size_t i = 0; i < blockers_.size(); ++i)
+ blockers_[i]->CheckState();
+
+ // We will allow notifications that are progress types (and stay progress
+ // types) to be updated even if the message center is open.
+ bool update_keeps_progress_type =
+ new_notification->type() == NOTIFICATION_TYPE_PROGRESS;
+ if (!notification_list_->HasNotificationOfType(old_id,
+ NOTIFICATION_TYPE_PROGRESS)) {
+ update_keeps_progress_type = false;
+ }
+
+ // Updates are allowed only for progress notifications.
+ if (notification_list_->is_message_center_visible() &&
+ !update_keeps_progress_type) {
+ std::list<internal::NotificationQueueItem>::iterator iter = std::find_if(
+ notification_queue_.begin(),
+ notification_queue_.end(),
+ internal::NotificationFinder(old_id));
+ if (iter != notification_queue_.end()) {
+ internal::DeleteQueueNotification(*iter);
+ notification_queue_.erase(iter);
+ }
+ internal::NotificationQueueItem item = {
+ new_notification.release(),
+ true,
+ old_id
+ };
+ notification_queue_.push_back(item);
+ return;
+ }
+
std::string new_id = new_notification->id();
notification_list_->UpdateNotificationMessage(old_id,
new_notification.Pass());
@@ -310,6 +443,15 @@ void MessageCenterImpl::UpdateNotification(
void MessageCenterImpl::RemoveNotification(const std::string& id,
bool by_user) {
+ std::list<internal::NotificationQueueItem>::iterator iter = std::find_if(
+ notification_queue_.begin(),
+ notification_queue_.end(),
+ internal::NotificationFinder(id));
+ if (iter != notification_queue_.end()) {
+ DeleteQueueNotification(*iter);
+ notification_queue_.erase(iter);
+ }
+
if (!HasNotification(id))
return;
@@ -335,6 +477,9 @@ void MessageCenterImpl::RemoveAllNotifications(bool by_user) {
for (NotificationList::Notifications::const_iterator iter =
notifications.begin(); iter != notifications.end(); ++iter) {
ids.insert((*iter)->id());
+ NotificationDelegate* delegate = (*iter)->delegate();
+ if (delegate)
+ delegate->Close(by_user);
}
notification_list_->RemoveAllNotifications();
@@ -348,7 +493,17 @@ void MessageCenterImpl::RemoveAllNotifications(bool by_user) {
void MessageCenterImpl::SetNotificationIcon(const std::string& notification_id,
const gfx::Image& image) {
- if (notification_list_->SetNotificationIcon(notification_id, image)) {
+ std::list<internal::NotificationQueueItem>::iterator iter = std::find_if(
+ notification_queue_.begin(),
+ notification_queue_.end(),
+ internal::NotificationFinder(notification_id));
+ bool found = iter != notification_queue_.end();
+ if (found)
+ iter->notification->set_icon(image);
+ else
+ found = notification_list_->SetNotificationIcon(notification_id, image);
+
+ if (found) {
FOR_EACH_OBSERVER(MessageCenterObserver, observer_list_,
OnNotificationUpdated(notification_id));
}
@@ -374,27 +529,16 @@ void MessageCenterImpl::SetNotificationButtonIcon(
}
}
-void MessageCenterImpl::DisableNotificationsByExtension(
- const std::string& id) {
- if (delegate_)
- delegate_->DisableExtension(id);
-
- NotificationList::Notifications notifications =
- notification_list_->GetNotificationsByExtension(id);
- for (NotificationList::Notifications::const_iterator iter =
- notifications.begin(); iter != notifications.end();) {
- std::string id = (*iter)->id();
- iter++;
- RemoveNotification(id, false);
+void MessageCenterImpl::DisableNotificationsByNotifier(
+ const NotifierId& notifier_id) {
+ if (settings_provider_) {
+ // TODO(mukai): SetNotifierEnabled can just accept notifier_id?
+ Notifier notifier(notifier_id, base::string16(), true);
+ settings_provider_->SetNotifierEnabled(notifier, false);
}
-}
-
-void MessageCenterImpl::DisableNotificationsByUrl(const std::string& id) {
- if (delegate_)
- delegate_->DisableNotificationsFromSource(id);
NotificationList::Notifications notifications =
- notification_list_->GetNotificationsBySource(id);
+ notification_list_->GetNotificationsByNotifierId(notifier_id);
for (NotificationList::Notifications::const_iterator iter =
notifications.begin(); iter != notifications.end();) {
std::string id = (*iter)->id();
@@ -403,11 +547,6 @@ void MessageCenterImpl::DisableNotificationsByUrl(const std::string& id) {
}
}
-void MessageCenterImpl::ShowNotificationSettings(const std::string& id) {
- if (delegate_)
- delegate_->ShowSettings(id);
-}
-
void MessageCenterImpl::ExpandNotification(const std::string& id) {
if (!HasNotification(id))
return;
@@ -477,12 +616,33 @@ NotifierSettingsProvider* MessageCenterImpl::GetNotifierSettingsProvider() {
}
void MessageCenterImpl::SetQuietMode(bool in_quiet_mode) {
- notification_list_->SetQuietMode(in_quiet_mode);
+ if (in_quiet_mode != notification_list_->quiet_mode()) {
+ notification_list_->SetQuietMode(in_quiet_mode);
+ FOR_EACH_OBSERVER(MessageCenterObserver,
+ observer_list_,
+ OnQuietModeChanged(in_quiet_mode));
+ }
+ quiet_mode_timer_.reset();
}
void MessageCenterImpl::EnterQuietModeWithExpire(
const base::TimeDelta& expires_in) {
- notification_list_->EnterQuietModeWithExpire(expires_in);
+ if (quiet_mode_timer_.get()) {
+ // Note that the capital Reset() is the method to restart the timer, not
+ // scoped_ptr::reset().
+ quiet_mode_timer_->Reset();
+ } else {
+ notification_list_->SetQuietMode(true);
+ FOR_EACH_OBSERVER(
+ MessageCenterObserver, observer_list_, OnQuietModeChanged(true));
+
+ quiet_mode_timer_.reset(new base::OneShotTimer<MessageCenterImpl>);
+ quiet_mode_timer_->Start(
+ FROM_HERE,
+ expires_in,
+ base::Bind(
+ &MessageCenterImpl::SetQuietMode, base::Unretained(this), false));
+ }
}
void MessageCenterImpl::RestartPopupTimers() {
diff --git a/chromium/ui/message_center/message_center_impl.h b/chromium/ui/message_center/message_center_impl.h
index 412e0b3b15e..b57f5322858 100644
--- a/chromium/ui/message_center/message_center_impl.h
+++ b/chromium/ui/message_center/message_center_impl.h
@@ -6,6 +6,7 @@
#define UI_MESSAGE_CENTER_MESSAGE_CENTER_IMPL_H_
#include <string>
+#include <vector>
#include "base/memory/weak_ptr.h"
#include "base/stl_util.h"
@@ -13,12 +14,15 @@
#include "base/timer/timer.h"
#include "ui/message_center/message_center.h"
#include "ui/message_center/message_center_observer.h"
+#include "ui/message_center/message_center_types.h"
+#include "ui/message_center/notification_blocker.h"
namespace message_center {
class NotificationDelegate;
class MessageCenterImpl;
namespace internal {
+struct NotificationQueueItem;
class PopupTimersController;
// A class that manages timeout behavior for notification popups. One instance
@@ -129,16 +133,18 @@ class MESSAGE_CENTER_EXPORT PopupTimersController
} // namespace internal
// The default implementation of MessageCenter.
-class MessageCenterImpl : public MessageCenter {
+class MessageCenterImpl : public MessageCenter,
+ public NotificationBlocker::Observer {
public:
MessageCenterImpl();
virtual ~MessageCenterImpl();
// MessageCenter overrides:
- virtual void SetDelegate(Delegate* delegate) OVERRIDE;
virtual void AddObserver(MessageCenterObserver* observer) OVERRIDE;
virtual void RemoveObserver(MessageCenterObserver* observer) OVERRIDE;
- virtual void SetMessageCenterVisible(bool visible) OVERRIDE;
+ virtual void AddNotificationBlocker(NotificationBlocker* blocker) OVERRIDE;
+ virtual void RemoveNotificationBlocker(NotificationBlocker* blocker) OVERRIDE;
+ virtual void SetVisibility(Visibility visible) OVERRIDE;
virtual bool IsMessageCenterVisible() OVERRIDE;
virtual size_t NotificationCount() const OVERRIDE;
virtual size_t UnreadNotificationCount() const OVERRIDE;
@@ -161,9 +167,8 @@ class MessageCenterImpl : public MessageCenter {
virtual void SetNotificationButtonIcon(const std::string& notification_id,
int button_index,
const gfx::Image& image) OVERRIDE;
- virtual void DisableNotificationsByExtension(const std::string& id) OVERRIDE;
- virtual void DisableNotificationsByUrl(const std::string& id) OVERRIDE;
- virtual void ShowNotificationSettings(const std::string& id) OVERRIDE;
+ virtual void DisableNotificationsByNotifier(
+ const NotifierId& notifier_id) OVERRIDE;
virtual void ExpandNotification(const std::string& id) OVERRIDE;
virtual void ClickOnNotification(const std::string& id) OVERRIDE;
virtual void ClickOnNotificationButton(const std::string& id,
@@ -180,6 +185,9 @@ class MessageCenterImpl : public MessageCenter {
virtual void RestartPopupTimers() OVERRIDE;
virtual void PausePopupTimers() OVERRIDE;
+ // NotificationBlocker::Observer overrides:
+ virtual void OnBlockingStateChanged() OVERRIDE;
+
protected:
virtual void DisableTimersForTest() OVERRIDE;
@@ -187,8 +195,13 @@ class MessageCenterImpl : public MessageCenter {
scoped_ptr<NotificationList> notification_list_;
ObserverList<MessageCenterObserver> observer_list_;
scoped_ptr<internal::PopupTimersController> popup_timers_controller_;
- Delegate* delegate_;
+ scoped_ptr<base::OneShotTimer<MessageCenterImpl> > quiet_mode_timer_;
NotifierSettingsProvider* settings_provider_;
+ std::vector<NotificationBlocker*> blockers_;
+
+ // queue for the notifications to delay the addition/updates when the message
+ // center is visible.
+ std::list<internal::NotificationQueueItem> notification_queue_;
DISALLOW_COPY_AND_ASSIGN(MessageCenterImpl);
};
diff --git a/chromium/ui/message_center/message_center_impl_unittest.cc b/chromium/ui/message_center/message_center_impl_unittest.cc
index a7c08a8aeb5..fb6969064a8 100644
--- a/chromium/ui/message_center/message_center_impl_unittest.cc
+++ b/chromium/ui/message_center/message_center_impl_unittest.cc
@@ -9,7 +9,12 @@
#include "base/run_loop.h"
#include "base/strings/utf_string_conversions.h"
#include "testing/gtest/include/gtest/gtest.h"
+#include "ui/base/layout.h"
+#include "ui/gfx/canvas.h"
+#include "ui/gfx/size.h"
#include "ui/message_center/message_center.h"
+#include "ui/message_center/message_center_types.h"
+#include "ui/message_center/notification_blocker.h"
#include "ui/message_center/notification_types.h"
namespace message_center {
@@ -39,6 +44,20 @@ class MessageCenterImplTest : public testing::Test,
base::RunLoop* run_loop() const { return run_loop_.get(); }
base::Closure closure() const { return closure_; }
+ Notification* CreateNotification(const std::string& id) {
+ RichNotificationData optional_fields;
+ optional_fields.buttons.push_back(ButtonInfo(UTF8ToUTF16("foo")));
+ optional_fields.buttons.push_back(ButtonInfo(UTF8ToUTF16("foo")));
+ return new Notification(NOTIFICATION_TYPE_SIMPLE,
+ id,
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16(id),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ NotifierId(NotifierId::APPLICATION, "app1"),
+ optional_fields,
+ NULL);
+ }
private:
MessageCenter* message_center_;
scoped_ptr<base::MessageLoop> loop_;
@@ -48,6 +67,65 @@ class MessageCenterImplTest : public testing::Test,
DISALLOW_COPY_AND_ASSIGN(MessageCenterImplTest);
};
+class ToggledNotificationBlocker : public NotificationBlocker {
+ public:
+ explicit ToggledNotificationBlocker(MessageCenter* message_center)
+ : NotificationBlocker(message_center),
+ notifications_enabled_(true) {}
+ virtual ~ToggledNotificationBlocker() {}
+
+ void SetNotificationsEnabled(bool enabled) {
+ if (notifications_enabled_ != enabled) {
+ notifications_enabled_ = enabled;
+ FOR_EACH_OBSERVER(
+ NotificationBlocker::Observer, observers(), OnBlockingStateChanged());
+ }
+ }
+
+ // NotificationBlocker overrides:
+ virtual bool ShouldShowNotificationAsPopup(
+ const message_center::NotifierId& notifier_id) const OVERRIDE {
+ return notifications_enabled_;
+ }
+
+ private:
+ bool notifications_enabled_;
+
+ DISALLOW_COPY_AND_ASSIGN(ToggledNotificationBlocker);
+};
+
+class PopupNotificationBlocker : public ToggledNotificationBlocker {
+ public:
+ PopupNotificationBlocker(MessageCenter* message_center,
+ const NotifierId& allowed_notifier)
+ : ToggledNotificationBlocker(message_center),
+ allowed_notifier_(allowed_notifier) {}
+ virtual ~PopupNotificationBlocker() {}
+
+ // NotificationBlocker overrides:
+ virtual bool ShouldShowNotificationAsPopup(
+ const NotifierId& notifier_id) const OVERRIDE {
+ return (notifier_id == allowed_notifier_) ||
+ ToggledNotificationBlocker::ShouldShowNotificationAsPopup(notifier_id);
+ }
+
+ private:
+ NotifierId allowed_notifier_;
+
+ DISALLOW_COPY_AND_ASSIGN(PopupNotificationBlocker);
+};
+
+bool PopupNotificationsContain(
+ const NotificationList::PopupNotifications& popups,
+ const std::string& id) {
+ for (NotificationList::PopupNotifications::const_iterator iter =
+ popups.begin(); iter != popups.end(); ++iter) {
+ if ((*iter)->id() == id)
+ return true;
+ }
+ return false;
+}
+
} // namespace
namespace internal {
@@ -205,6 +283,271 @@ TEST_F(MessageCenterImplTest, PopupTimersControllerResetTimer) {
EXPECT_TRUE(popup_timers_controller->timer_finished());
}
-} // namespace internal
+TEST_F(MessageCenterImplTest, NotificationBlocker) {
+ NotifierId notifier_id(NotifierId::APPLICATION, "app1");
+ // Multiple blockers to verify the case that one blocker blocks but another
+ // doesn't.
+ ToggledNotificationBlocker blocker1(message_center());
+ ToggledNotificationBlocker blocker2(message_center());
+
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id1",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id,
+ RichNotificationData(),
+ NULL)));
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id2",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id,
+ RichNotificationData(),
+ NULL)));
+ EXPECT_EQ(2u, message_center()->GetPopupNotifications().size());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ // Block all notifications. All popups are gone and message center should be
+ // hidden.
+ blocker1.SetNotificationsEnabled(false);
+ EXPECT_TRUE(message_center()->GetPopupNotifications().empty());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ // Updates |blocker2| state, which doesn't affect the global state.
+ blocker2.SetNotificationsEnabled(false);
+ EXPECT_TRUE(message_center()->GetPopupNotifications().empty());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ blocker2.SetNotificationsEnabled(true);
+ EXPECT_TRUE(message_center()->GetPopupNotifications().empty());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ // If |blocker2| blocks, then unblocking blocker1 doesn't change the global
+ // state.
+ blocker2.SetNotificationsEnabled(false);
+ blocker1.SetNotificationsEnabled(true);
+ EXPECT_TRUE(message_center()->GetPopupNotifications().empty());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ // Unblock both blockers, which recovers the global state, but the popups
+ // aren't shown.
+ blocker2.SetNotificationsEnabled(true);
+ EXPECT_TRUE(message_center()->GetPopupNotifications().empty());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+}
+
+TEST_F(MessageCenterImplTest, NotificationsDuringBlocked) {
+ NotifierId notifier_id(NotifierId::APPLICATION, "app1");
+ ToggledNotificationBlocker blocker(message_center());
+
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id1",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id,
+ RichNotificationData(),
+ NULL)));
+ EXPECT_EQ(1u, message_center()->GetPopupNotifications().size());
+ EXPECT_EQ(1u, message_center()->GetNotifications().size());
+
+ // Create a notification during blocked. Still no popups.
+ blocker.SetNotificationsEnabled(false);
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id2",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id,
+ RichNotificationData(),
+ NULL)));
+ EXPECT_TRUE(message_center()->GetPopupNotifications().empty());
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ // Unblock notifications, the id1 should appear as a popup.
+ blocker.SetNotificationsEnabled(true);
+ NotificationList::PopupNotifications popups =
+ message_center()->GetPopupNotifications();
+ EXPECT_EQ(1u, popups.size());
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id2"));
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+}
+
+// Similar to other blocker cases but this test case allows |notifier_id2| even
+// in blocked.
+TEST_F(MessageCenterImplTest, NotificationBlockerAllowsPopups) {
+ NotifierId notifier_id1(NotifierId::APPLICATION, "app1");
+ NotifierId notifier_id2(NotifierId::APPLICATION, "app2");
+ PopupNotificationBlocker blocker(message_center(), notifier_id2);
+
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id1",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id1,
+ RichNotificationData(),
+ NULL)));
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id2",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id2,
+ RichNotificationData(),
+ NULL)));
+
+ // "id1" is closed but "id2" is still visible as a popup.
+ blocker.SetNotificationsEnabled(false);
+ NotificationList::PopupNotifications popups =
+ message_center()->GetPopupNotifications();
+ EXPECT_EQ(1u, popups.size());
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id2"));
+ EXPECT_EQ(2u, message_center()->GetNotifications().size());
+
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id3",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id1,
+ RichNotificationData(),
+ NULL)));
+ message_center()->AddNotification(scoped_ptr<Notification>(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ "id4",
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id2,
+ RichNotificationData(),
+ NULL)));
+ popups = message_center()->GetPopupNotifications();
+ EXPECT_EQ(2u, popups.size());
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id2"));
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id4"));
+ EXPECT_EQ(4u, message_center()->GetNotifications().size());
+
+ blocker.SetNotificationsEnabled(true);
+ popups = message_center()->GetPopupNotifications();
+ EXPECT_EQ(3u, popups.size());
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id2"));
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id3"));
+ EXPECT_TRUE(PopupNotificationsContain(popups, "id4"));
+ EXPECT_EQ(4u, message_center()->GetNotifications().size());
+}
+
+TEST_F(MessageCenterImplTest, QueueUpdatesWithCenterVisible) {
+ std::string id("id1");
+ std::string id2("id2");
+ NotifierId notifier_id1(NotifierId::APPLICATION, "app1");
+
+ scoped_ptr<Notification> notification(new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ id,
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id1,
+ RichNotificationData(),
+ NULL));
+
+ message_center()->AddNotification(notification.Pass());
+ notification.reset(new Notification(
+ NOTIFICATION_TYPE_MULTIPLE,
+ id2,
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id1,
+ RichNotificationData(),
+ NULL));
+ message_center()->UpdateNotification(id, notification.Pass());
+ EXPECT_TRUE(message_center()->HasNotification(id2));
+ EXPECT_FALSE(message_center()->HasNotification(id));
+ message_center()->SetVisibility(VISIBILITY_MESSAGE_CENTER);
+ notification.reset(new Notification(
+ NOTIFICATION_TYPE_MULTIPLE,
+ id,
+ UTF8ToUTF16("title"),
+ UTF8ToUTF16("message"),
+ gfx::Image() /* icon */,
+ base::string16() /* display_source */,
+ notifier_id1,
+ RichNotificationData(),
+ NULL));
+ message_center()->UpdateNotification(id2, notification.Pass());
+ EXPECT_TRUE(message_center()->HasNotification(id2));
+ EXPECT_FALSE(message_center()->HasNotification(id));
+ message_center()->SetVisibility(VISIBILITY_TRANSIENT);
+ EXPECT_FALSE(message_center()->HasNotification(id2));
+ EXPECT_TRUE(message_center()->HasNotification(id));
+}
+
+TEST_F(MessageCenterImplTest, QueuedDirectUpdates) {
+ std::string id("id1");
+ std::string id2("id2");
+ NotifierId notifier_id1(NotifierId::APPLICATION, "app1");
+
+ gfx::Size original_size(0, 0);
+ // Open the message center to prevent adding notifications
+ message_center()->SetVisibility(VISIBILITY_MESSAGE_CENTER);
+
+ // Create new notification to be added to the queue; images all have the same
+ // original size.
+ scoped_ptr<Notification> notification(CreateNotification(id));
+
+ // Double-check that sizes all match.
+ EXPECT_EQ(original_size, notification->icon().Size());
+ message_center()->AddNotification(notification.Pass());
+
+ // The notification should be in the queue.
+ EXPECT_FALSE(message_center()->HasNotification(id));
+
+ // Now try setting the icon to a different size.
+ gfx::Size new_size(16, 16);
+ EXPECT_NE(original_size, new_size);
+
+ gfx::Canvas canvas(new_size, ui::SCALE_FACTOR_100P, true);
+ canvas.DrawColor(SK_ColorBLUE);
+ gfx::Image testImage(gfx::Image(gfx::ImageSkia(canvas.ExtractImageRep())));
+ message_center()->SetNotificationIcon(id, testImage);
+ message_center()->SetNotificationButtonIcon(id, 0, testImage);
+ message_center()->SetNotificationButtonIcon(id, 1, testImage);
+
+ // The notification should be in the queue.
+ EXPECT_FALSE(message_center()->HasNotification(id));
+
+ // Close the message center; then the update should have propagated.
+ message_center()->SetVisibility(VISIBILITY_TRANSIENT);
+ // The notification should no longer be in the queue.
+ EXPECT_TRUE(message_center()->HasNotification(id));
+
+ Notification* mc_notification =
+ *(message_center()->GetNotifications().begin());
+
+ EXPECT_EQ(new_size, mc_notification->icon().Size());
+}
+
+} // namespace internal
} // namespace message_center
diff --git a/chromium/ui/message_center/message_center_observer.h b/chromium/ui/message_center/message_center_observer.h
index 8a52792731f..b300db57127 100644
--- a/chromium/ui/message_center/message_center_observer.h
+++ b/chromium/ui/message_center/message_center_observer.h
@@ -8,6 +8,7 @@
#include <string>
#include "ui/message_center/message_center_export.h"
+#include "ui/message_center/message_center_types.h"
namespace message_center {
@@ -42,9 +43,12 @@ class MESSAGE_CENTER_EXPORT MessageCenterObserver {
// displayed.
virtual void OnNotificationDisplayed(const std::string& notification_id) {}
- // Called when the notification list is no longer being displayed as a
- // notification center.
- virtual void OnNotificationCenterClosed() {}
+ // Called when the notification center is shown or hidden.
+ virtual void OnCenterVisibilityChanged(Visibility visibility) {}
+
+ // Called whenever the quiet mode changes as a result of user action or when
+ // quiet mode expires.
+ virtual void OnQuietModeChanged(bool in_quiet_mode) {}
};
} // namespace message_center
diff --git a/chromium/ui/message_center/message_center_style.cc b/chromium/ui/message_center/message_center_style.cc
index 0289a96c7f2..a9036bad48a 100644
--- a/chromium/ui/message_center/message_center_style.cc
+++ b/chromium/ui/message_center/message_center_style.cc
@@ -4,6 +4,8 @@
#include "ui/message_center/message_center_style.h"
+#include <algorithm>
+
namespace message_center {
// Exported values /////////////////////////////////////////////////////////////
@@ -42,8 +44,8 @@ const int kMessageLineHeight = 18;
// Colors.
const SkColor kNotificationBackgroundColor = SkColorSetRGB(255, 255, 255);
const SkColor kLegacyIconBackgroundColor = SkColorSetRGB(0xf5, 0xf5, 0xf5);
-const SkColor kRegularTextColor = SkColorSetRGB(34, 34, 34);
-const SkColor kDimTextColor = SkColorSetRGB(102, 102, 102);
+const SkColor kRegularTextColor = SkColorSetRGB(0x33, 0x33, 0x33);
+const SkColor kDimTextColor = SkColorSetRGB(0x7f, 0x7f, 0x7f);
const SkColor kFocusBorderColor = SkColorSetRGB(64, 128, 250);
// Limits.
diff --git a/chromium/ui/message_center/message_center_style.h b/chromium/ui/message_center/message_center_style.h
index 12353633751..29f9f75175c 100644
--- a/chromium/ui/message_center/message_center_style.h
+++ b/chromium/ui/message_center/message_center_style.h
@@ -43,10 +43,10 @@ extern const int kIconBottomPadding; // Minimum non-zero V space between icon
// and frame.
// Text sizes.
-extern const int kTitleFontSize; // For title only.
-extern const int kTitleLineHeight; // In DIPs.
-extern const int kMessageFontSize; // For everything but title.
-extern const int kMessageLineHeight; // In DIPs.
+extern const int kTitleFontSize; // For title only.
+extern const int kTitleLineHeight; // In DIPs.
+extern const int kMessageFontSize; // For everything but title.
+extern const int kMessageLineHeight; // In DIPs.
// Colors.
extern const SkColor kNotificationBackgroundColor; // Background of the card.
@@ -54,7 +54,7 @@ extern const SkColor kLegacyIconBackgroundColor; // Used behind icons smaller.
// than the icon view.
extern const SkColor kRegularTextColor; // Title, message, ...
extern const SkColor kDimTextColor;
-extern const SkColor kFocusBorderColor; // The focus border.
+extern const SkColor kFocusBorderColor; // The focus border.
// Limits.
@@ -91,6 +91,7 @@ const SkColor kProgressBarSliceColor = SkColorSetRGB(120, 120, 120);
const int kTitleLineLimit = 3;
const int kMessageCollapsedLineLimit = 3;
const int kMessageExpandedLineLimit = 7;
+const int kContextMessageLineLimit = 1;
// Around notifications ////////////////////////////////////////////////////////
diff --git a/chromium/ui/message_center/message_center_tray.cc b/chromium/ui/message_center/message_center_tray.cc
index 7a1fee8d261..f5bf22e3cae 100644
--- a/chromium/ui/message_center/message_center_tray.cc
+++ b/chromium/ui/message_center/message_center_tray.cc
@@ -10,16 +10,9 @@
#include "ui/base/l10n/l10n_util.h"
#include "ui/message_center/message_center.h"
#include "ui/message_center/message_center_tray_delegate.h"
+#include "ui/message_center/message_center_types.h"
namespace message_center {
-namespace {
-
-// Menu commands
-const int kToggleQuietMode = 0;
-const int kEnableQuietModeHour = 1;
-const int kEnableQuietModeDay = 2;
-
-}
MessageCenterTray::MessageCenterTray(
MessageCenterTrayDelegate* delegate,
@@ -39,10 +32,11 @@ bool MessageCenterTray::ShowMessageCenterBubble() {
if (message_center_visible_)
return true;
- HidePopupBubble();
+ HidePopupBubbleInternal();
message_center_visible_ = delegate_->ShowMessageCenter();
- message_center_->SetMessageCenterVisible(message_center_visible_);
+ message_center_->SetVisibility(message_center::VISIBILITY_MESSAGE_CENTER);
+ NotifyMessageCenterTrayChanged();
return message_center_visible_;
}
@@ -58,11 +52,16 @@ void MessageCenterTray::MarkMessageCenterHidden() {
if (!message_center_visible_)
return;
message_center_visible_ = false;
- message_center_->SetMessageCenterVisible(false);
+
// Some notifications (like system ones) should appear as popups again
// after the message center is closed.
- if (message_center_->HasPopupNotifications())
+ if (message_center_->HasPopupNotifications()) {
ShowPopupBubble();
+ return;
+ }
+
+ message_center_->SetVisibility(message_center::VISIBILITY_TRANSIENT);
+
NotifyMessageCenterTrayChanged();
}
@@ -86,37 +85,35 @@ void MessageCenterTray::ShowPopupBubble() {
return;
popups_visible_ = delegate_->ShowPopups();
+
NotifyMessageCenterTrayChanged();
}
bool MessageCenterTray::HidePopupBubble() {
if (!popups_visible_)
return false;
-
- delegate_->HidePopups();
- popups_visible_ = false;
+ HidePopupBubbleInternal();
NotifyMessageCenterTrayChanged();
return true;
}
+void MessageCenterTray::HidePopupBubbleInternal() {
+ if (!popups_visible_)
+ return;
+
+ delegate_->HidePopups();
+ popups_visible_ = false;
+}
+
void MessageCenterTray::ShowNotifierSettingsBubble() {
if (popups_visible_)
- HidePopupBubble();
+ HidePopupBubbleInternal();
message_center_visible_ = delegate_->ShowNotifierSettings();
-}
+ message_center_->SetVisibility(message_center::VISIBILITY_SETTINGS);
-ui::MenuModel* MessageCenterTray::CreateQuietModeMenu() {
- ui::SimpleMenuModel* menu = new ui::SimpleMenuModel(this);
-
- menu->AddCheckItem(kToggleQuietMode,
- l10n_util::GetStringUTF16(IDS_MESSAGE_CENTER_QUIET_MODE));
- menu->AddItem(kEnableQuietModeHour,
- l10n_util::GetStringUTF16(IDS_MESSAGE_CENTER_QUIET_MODE_1HOUR));
- menu->AddItem(kEnableQuietModeDay,
- l10n_util::GetStringUTF16(IDS_MESSAGE_CENTER_QUIET_MODE_1DAY));
- return menu;
+ NotifyMessageCenterTrayChanged();
}
void MessageCenterTray::OnNotificationAdded(
@@ -153,47 +150,19 @@ void MessageCenterTray::OnNotificationDisplayed(
NotifyMessageCenterTrayChanged();
}
-void MessageCenterTray::OnMessageCenterChanged() {
- if (message_center_visible_) {
- if (message_center_->NotificationCount() == 0)
- HideMessageCenterBubble();
- }
-
- if (popups_visible_ && !message_center_->HasPopupNotifications())
- HidePopupBubble();
- else if (message_center_->HasPopupNotifications())
- ShowPopupBubble();
-
+void MessageCenterTray::OnQuietModeChanged(bool in_quiet_mode) {
NotifyMessageCenterTrayChanged();
}
-bool MessageCenterTray::IsCommandIdChecked(int command_id) const {
- if (command_id != kToggleQuietMode)
- return false;
- return message_center()->IsQuietMode();
-}
-
-bool MessageCenterTray::IsCommandIdEnabled(int command_id) const {
- return true;
-}
+void MessageCenterTray::OnMessageCenterChanged() {
+ if (message_center_visible_ && message_center_->NotificationCount() == 0)
+ HideMessageCenterBubble();
-bool MessageCenterTray::GetAcceleratorForCommandId(
- int command_id,
- ui::Accelerator* accelerator) {
- return false;
-}
+ if (popups_visible_ && !message_center_->HasPopupNotifications())
+ HidePopupBubbleInternal();
+ else if (!popups_visible_ && message_center_->HasPopupNotifications())
+ ShowPopupBubble();
-void MessageCenterTray::ExecuteCommand(int command_id, int event_flags) {
- if (command_id == kToggleQuietMode) {
- bool in_quiet_mode = message_center()->IsQuietMode();
- message_center()->SetQuietMode(!in_quiet_mode);
- NotifyMessageCenterTrayChanged();
- return;
- }
- base::TimeDelta expires_in = command_id == kEnableQuietModeDay ?
- base::TimeDelta::FromDays(1):
- base::TimeDelta::FromHours(1);
- message_center()->EnterQuietModeWithExpire(expires_in);
NotifyMessageCenterTrayChanged();
}
diff --git a/chromium/ui/message_center/message_center_tray.h b/chromium/ui/message_center/message_center_tray.h
index 03b86e9391e..444bb2f4ecb 100644
--- a/chromium/ui/message_center/message_center_tray.h
+++ b/chromium/ui/message_center/message_center_tray.h
@@ -6,7 +6,6 @@
#define UI_MESSAGE_CENTER_MESSAGE_CENTER_TRAY_H_
#include "base/observer_list.h"
-#include "ui/base/models/simple_menu_model.h"
#include "ui/message_center/message_center_export.h"
#include "ui/message_center/message_center_observer.h"
#include "ui/message_center/message_center_tray_delegate.h"
@@ -25,9 +24,7 @@ MessageCenterTrayDelegate* CreateMessageCenterTray();
// Class that observes a MessageCenter. Manages the popup and message center
// bubbles. Tells the MessageCenterTrayHost when the tray is changed, as well
// as when bubbles are shown and hidden.
-class MESSAGE_CENTER_EXPORT MessageCenterTray
- : public MessageCenterObserver,
- public ui::SimpleMenuModel::Delegate {
+class MESSAGE_CENTER_EXPORT MessageCenterTray : public MessageCenterObserver {
public:
MessageCenterTray(MessageCenterTrayDelegate* delegate,
message_center::MessageCenter* message_center);
@@ -57,10 +54,6 @@ class MESSAGE_CENTER_EXPORT MessageCenterTray
// Toggles the visibility of the settings view in the message center bubble.
void ShowNotifierSettingsBubble();
- // Creates the menu model for quiet mode and returns it. The caller must
- // take the ownership of the return value.
- ui::MenuModel* CreateQuietModeMenu();
-
bool message_center_visible() { return message_center_visible_; }
bool popups_visible() { return popups_visible_; }
MessageCenterTrayDelegate* delegate() { return delegate_; }
@@ -82,18 +75,12 @@ class MESSAGE_CENTER_EXPORT MessageCenterTray
int button_index) OVERRIDE;
virtual void OnNotificationDisplayed(
const std::string& notification_id) OVERRIDE;
-
- // Overridden from SimpleMenuModel::Delegate.
- virtual bool IsCommandIdChecked(int command_id) const OVERRIDE;
- virtual bool IsCommandIdEnabled(int command_id) const OVERRIDE;
- virtual bool GetAcceleratorForCommandId(
- int command_id,
- ui::Accelerator* accelerator) OVERRIDE;
- virtual void ExecuteCommand(int command_id, int event_flags) OVERRIDE;
+ virtual void OnQuietModeChanged(bool in_quiet_mode) OVERRIDE;
private:
void OnMessageCenterChanged();
void NotifyMessageCenterTrayChanged();
+ void HidePopupBubbleInternal();
// |message_center_| is a weak pointer that must live longer than
// MessageCenterTray.
diff --git a/chromium/ui/message_center/message_center_tray_unittest.cc b/chromium/ui/message_center/message_center_tray_unittest.cc
index 108cee7aa29..6a68b2b989f 100644
--- a/chromium/ui/message_center/message_center_tray_unittest.cc
+++ b/chromium/ui/message_center/message_center_tray_unittest.cc
@@ -71,7 +71,7 @@ class MessageCenterTrayTest : public testing::Test {
ASCIIToUTF16("Notification message body."),
gfx::Image(),
ASCIIToUTF16("www.test.org"),
- "" /* extension id */,
+ NotifierId(),
message_center::RichNotificationData(),
NULL /* delegate */));
message_center_->AddNotification(notification.Pass());
@@ -147,6 +147,7 @@ TEST_F(MessageCenterTrayTest, MessageCenterClosesPopups) {
ASSERT_FALSE(message_center_tray_->popups_visible());
ASSERT_TRUE(message_center_tray_->message_center_visible());
+ // The notification is queued if it's added when message center is visible.
AddNotification("MessageCenterClosesPopups2");
message_center_tray_->ShowPopupBubble();
@@ -156,6 +157,12 @@ TEST_F(MessageCenterTrayTest, MessageCenterClosesPopups) {
message_center_tray_->HideMessageCenterBubble();
+ // The queued notification appears as a popup.
+ ASSERT_TRUE(message_center_tray_->popups_visible());
+ ASSERT_FALSE(message_center_tray_->message_center_visible());
+
+ message_center_tray_->ShowMessageCenterBubble();
+ message_center_tray_->HideMessageCenterBubble();
ASSERT_FALSE(message_center_tray_->popups_visible());
ASSERT_FALSE(message_center_tray_->message_center_visible());
}
@@ -171,7 +178,7 @@ TEST_F(MessageCenterTrayTest, MessageCenterReopenPopupsForSystemPriority) {
ASCIIToUTF16("Notification message body."),
gfx::Image(),
ASCIIToUTF16("www.test.org"),
- "" /* extension id */,
+ NotifierId(),
message_center::RichNotificationData(),
NULL /* delegate */));
notification->SetSystemPriority();
diff --git a/chromium/ui/message_center/message_center_types.h b/chromium/ui/message_center/message_center_types.h
new file mode 100644
index 00000000000..4cfe68e6fad
--- /dev/null
+++ b/chromium/ui/message_center/message_center_types.h
@@ -0,0 +1,21 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_MESSAGE_CENTER_MESSAGE_CENTER_TYPES_H_
+#define UI_MESSAGE_CENTER_MESSAGE_CENTER_TYPES_H_
+
+namespace message_center {
+
+enum Visibility {
+ // When nothing or just toast popups are being displayed.
+ VISIBILITY_TRANSIENT = 0,
+ // When the message center view is being displayed.
+ VISIBILITY_MESSAGE_CENTER,
+ // When the settings view is being displayed.
+ VISIBILITY_SETTINGS
+};
+
+} // namespace message_center
+
+#endif // UI_MESSAGE_CENTER_MESSAGE_CENTER_TYPES_H_
diff --git a/chromium/ui/message_center/notification.cc b/chromium/ui/message_center/notification.cc
index 5d3014e8156..e17667c91c7 100644
--- a/chromium/ui/message_center/notification.cc
+++ b/chromium/ui/message_center/notification.cc
@@ -5,6 +5,7 @@
#include "ui/message_center/notification.h"
#include "base/logging.h"
+#include "ui/message_center/notification_delegate.h"
#include "ui/message_center/notification_types.h"
namespace {
@@ -27,17 +28,21 @@ RichNotificationData::RichNotificationData()
: priority(DEFAULT_PRIORITY),
never_timeout(false),
timestamp(base::Time::Now()),
- progress(0) {}
+ progress(0),
+ should_make_spoken_feedback_for_popup_updates(true) {}
RichNotificationData::RichNotificationData(const RichNotificationData& other)
: priority(other.priority),
never_timeout(other.never_timeout),
timestamp(other.timestamp),
expanded_message(other.expanded_message),
+ context_message(other.context_message),
image(other.image),
items(other.items),
progress(other.progress),
- buttons(other.buttons) {}
+ buttons(other.buttons),
+ should_make_spoken_feedback_for_popup_updates(
+ other.should_make_spoken_feedback_for_popup_updates) {}
RichNotificationData::~RichNotificationData() {}
@@ -47,7 +52,7 @@ Notification::Notification(NotificationType type,
const string16& message,
const gfx::Image& icon,
const string16& display_source,
- const std::string& extension_id,
+ const NotifierId& notifier_id,
const RichNotificationData& optional_fields,
NotificationDelegate* delegate)
: type_(type),
@@ -56,7 +61,7 @@ Notification::Notification(NotificationType type,
message_(message),
icon_(icon),
display_source_(display_source),
- extension_id_(extension_id),
+ notifier_id_(notifier_id),
serial_number_(g_next_serial_number_++),
optional_fields_(optional_fields),
shown_as_popup_(false),
@@ -71,7 +76,7 @@ Notification::Notification(const Notification& other)
message_(other.message_),
icon_(other.icon_),
display_source_(other.display_source_),
- extension_id_(other.extension_id_),
+ notifier_id_(other.notifier_id_),
serial_number_(other.serial_number_),
optional_fields_(other.optional_fields_),
shown_as_popup_(other.shown_as_popup_),
@@ -86,7 +91,7 @@ Notification& Notification::operator=(const Notification& other) {
message_ = other.message_;
icon_ = other.icon_;
display_source_ = other.display_source_;
- extension_id_ = other.extension_id_;
+ notifier_id_ = other.notifier_id_;
serial_number_ = other.serial_number_;
optional_fields_ = other.optional_fields_;
shown_as_popup_ = other.shown_as_popup_;
@@ -119,4 +124,27 @@ void Notification::SetSystemPriority() {
optional_fields_.never_timeout = true;
}
+// static
+scoped_ptr<Notification> Notification::CreateSystemNotification(
+ const std::string& notification_id,
+ const base::string16& title,
+ const base::string16& message,
+ const gfx::Image& icon,
+ int system_component_id,
+ const base::Closure& click_callback) {
+ scoped_ptr<Notification> notification(
+ new Notification(
+ NOTIFICATION_TYPE_SIMPLE,
+ notification_id,
+ title,
+ message,
+ icon,
+ base::string16() /* display_source */,
+ NotifierId(system_component_id),
+ RichNotificationData(),
+ new HandleNotificationClickedDelegate(click_callback)));
+ notification->SetSystemPriority();
+ return notification.Pass();
+}
+
} // namespace message_center
diff --git a/chromium/ui/message_center/notification.h b/chromium/ui/message_center/notification.h
index bda6900fb0c..f61d6d60d60 100644
--- a/chromium/ui/message_center/notification.h
+++ b/chromium/ui/message_center/notification.h
@@ -15,6 +15,7 @@
#include "ui/message_center/message_center_export.h"
#include "ui/message_center/notification_delegate.h"
#include "ui/message_center/notification_types.h"
+#include "ui/message_center/notifier_settings.h"
namespace message_center {
@@ -42,10 +43,12 @@ class MESSAGE_CENTER_EXPORT RichNotificationData {
bool never_timeout;
base::Time timestamp;
string16 expanded_message;
+ string16 context_message;
gfx::Image image;
std::vector<NotificationItem> items;
int progress;
std::vector<ButtonInfo> buttons;
+ bool should_make_spoken_feedback_for_popup_updates;
};
class MESSAGE_CENTER_EXPORT Notification {
@@ -56,7 +59,7 @@ class MESSAGE_CENTER_EXPORT Notification {
const string16& message,
const gfx::Image& icon,
const string16& display_source,
- const std::string& extension_id,
+ const NotifierId& notifier_id,
const RichNotificationData& optional_fields,
NotificationDelegate* delegate);
@@ -81,10 +84,8 @@ class MESSAGE_CENTER_EXPORT Notification {
// A display string for the source of the notification.
const string16& display_source() const { return display_source_; }
- const std::string& extension_id() const { return extension_id_; }
- void set_extension_id(const std::string& extension_id) {
- extension_id_ = extension_id;
- }
+
+ const NotifierId& notifier_id() const { return notifier_id_; }
// Begin unpacked values from optional_fields.
int priority() const { return optional_fields_.priority; }
@@ -102,6 +103,13 @@ class MESSAGE_CENTER_EXPORT Notification {
optional_fields_.expanded_message = expanded_message;
}
+ const string16& context_message() const {
+ return optional_fields_.context_message;
+ }
+ void set_context_message(const string16& context_message) {
+ optional_fields_.context_message = context_message;
+ }
+
const std::vector<NotificationItem>& items() const {
return optional_fields_.items;
}
@@ -167,6 +175,16 @@ class MESSAGE_CENTER_EXPORT Notification {
void ButtonClick(int index) const { delegate()->ButtonClick(index); }
void Close(bool by_user) const { delegate()->Close(by_user); }
+ // Helper method to create a simple System notification. |click_callback|
+ // will be invoked when the notification is clicked.
+ static scoped_ptr<Notification> CreateSystemNotification(
+ const std::string& notification_id,
+ const base::string16& title,
+ const base::string16& message,
+ const gfx::Image& icon,
+ int system_component_id,
+ const base::Closure& click_callback);
+
protected:
// The type of notification we'd like displayed.
NotificationType type_;
@@ -183,7 +201,7 @@ class MESSAGE_CENTER_EXPORT Notification {
string16 display_source_;
private:
- std::string extension_id_;
+ NotifierId notifier_id_;
unsigned serial_number_;
RichNotificationData optional_fields_;
bool shown_as_popup_; // True if this has been shown as a popup.
diff --git a/chromium/ui/message_center/notification_blocker.cc b/chromium/ui/message_center/notification_blocker.cc
new file mode 100644
index 00000000000..6d6c5d3ce16
--- /dev/null
+++ b/chromium/ui/message_center/notification_blocker.cc
@@ -0,0 +1,31 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/message_center/notification_blocker.h"
+
+#include "ui/message_center/message_center.h"
+
+namespace message_center {
+
+NotificationBlocker::NotificationBlocker(MessageCenter* message_center)
+ : message_center_(message_center) {
+ if (message_center_)
+ message_center_->AddNotificationBlocker(this);
+}
+
+NotificationBlocker::~NotificationBlocker() {
+ if (message_center_)
+ message_center_->RemoveNotificationBlocker(this);
+}
+
+void NotificationBlocker::AddObserver(NotificationBlocker::Observer* observer) {
+ observers_.AddObserver(observer);
+}
+
+void NotificationBlocker::RemoveObserver(
+ NotificationBlocker::Observer* observer) {
+ observers_.RemoveObserver(observer);
+}
+
+} // namespace message_center
diff --git a/chromium/ui/message_center/notification_blocker.h b/chromium/ui/message_center/notification_blocker.h
new file mode 100644
index 00000000000..437f0eb1238
--- /dev/null
+++ b/chromium/ui/message_center/notification_blocker.h
@@ -0,0 +1,51 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_MESSAGE_CENTER_NOTIFICATION_BLOCKER_H_
+#define UI_MESSAGE_CENTER_NOTIFICATION_BLOCKER_H_
+
+#include "base/observer_list.h"
+#include "ui/message_center/message_center_export.h"
+#include "ui/message_center/notifier_settings.h"
+
+namespace message_center {
+class MessageCenter;
+
+// NotificationBlocker manages the availability of notifications based on the
+// current system status. Each NotificationBlocker implementation covers a
+// single state such as screen lock or fullscreen.
+class MESSAGE_CENTER_EXPORT NotificationBlocker {
+ public:
+ class Observer {
+ public:
+ virtual void OnBlockingStateChanged() = 0;
+ };
+
+ explicit NotificationBlocker(MessageCenter* message_center);
+ virtual ~NotificationBlocker();
+
+ void AddObserver(Observer* observer);
+ void RemoveObserver(Observer* observer);
+
+ // Checks the current state and updates the availability.
+ virtual void CheckState() {}
+
+ // Returns true when notifications from |notifier_id| should be shown as
+ // popups on screen. If it's false, those notifications should be queued.
+ // When a blocker starts returning false for a notification which is already
+ // shown as a popup, the notification should be closed as a popup immediately.
+ virtual bool ShouldShowNotificationAsPopup(
+ const NotifierId& notifier_id) const = 0;
+
+ protected:
+ ObserverList<Observer>& observers() { return observers_; }
+
+ private:
+ ObserverList<Observer> observers_;
+ MessageCenter* message_center_; // weak
+};
+
+} // namespace message_center
+
+#endif // UI_MESSAGE_CENTER_NOTIFICATION_BLOCKER_H_
diff --git a/chromium/ui/message_center/notification_list.cc b/chromium/ui/message_center/notification_list.cc
index d0527922b8c..bed592c7cb2 100644
--- a/chromium/ui/message_center/notification_list.cc
+++ b/chromium/ui/message_center/notification_list.cc
@@ -11,10 +11,25 @@
#include "base/values.h"
#include "ui/message_center/message_center_style.h"
#include "ui/message_center/notification.h"
+#include "ui/message_center/notification_blocker.h"
#include "ui/message_center/notification_types.h"
namespace message_center {
+namespace {
+
+bool ShouldShowNotificationAsPopup(
+ const NotifierId& notifier_id,
+ const std::vector<NotificationBlocker*>& blockers) {
+ for (size_t i = 0; i < blockers.size(); ++i) {
+ if (!blockers[i]->ShouldShowNotificationAsPopup(notifier_id))
+ return false;
+ }
+ return true;
+}
+
+} // namespace
+
bool ComparePriorityTimestampSerial::operator()(Notification* n1,
Notification* n2) {
if (n1->priority() > n2->priority()) // Higher pri go first.
@@ -114,33 +129,12 @@ void NotificationList::RemoveAllNotifications() {
unread_count_ = 0;
}
-NotificationList::Notifications NotificationList::GetNotificationsBySource(
- const std::string& id) {
- Notifications notifications;
- Notifications::iterator source_iter = GetNotification(id);
- if (source_iter == notifications_.end())
- return notifications;
-
- string16 display_source = (*source_iter)->display_source();
- for (Notifications::iterator iter = notifications_.begin();
- iter != notifications_.end(); ++iter) {
- if ((*iter)->display_source() == display_source)
- notifications.insert(*iter);
- }
- return notifications;
-}
-
-NotificationList::Notifications NotificationList::GetNotificationsByExtension(
- const std::string& id) {
+NotificationList::Notifications NotificationList::GetNotificationsByNotifierId(
+ const NotifierId& notifier_id) {
Notifications notifications;
- Notifications::iterator source_iter = GetNotification(id);
- if (source_iter == notifications_.end())
- return notifications;
-
- std::string extension_id = (*source_iter)->extension_id();
for (Notifications::iterator iter = notifications_.begin();
iter != notifications_.end(); ++iter) {
- if ((*iter)->extension_id() == extension_id)
+ if ((*iter)->notifier_id() == notifier_id)
notifications.insert(*iter);
}
return notifications;
@@ -178,18 +172,32 @@ bool NotificationList::HasNotification(const std::string& id) {
return GetNotification(id) != notifications_.end();
}
-bool NotificationList::HasPopupNotifications() {
+bool NotificationList::HasNotificationOfType(const std::string& id,
+ const NotificationType type) {
+ Notifications::iterator iter = GetNotification(id);
+ if (iter == notifications_.end())
+ return false;
+
+ return (*iter)->type() == type;
+}
+
+bool NotificationList::HasPopupNotifications(
+ const std::vector<NotificationBlocker*>& blockers) {
for (Notifications::iterator iter = notifications_.begin();
iter != notifications_.end(); ++iter) {
if ((*iter)->priority() < DEFAULT_PRIORITY)
break;
+ if (!ShouldShowNotificationAsPopup((*iter)->notifier_id(), blockers))
+ continue;
if (!(*iter)->shown_as_popup())
return true;
}
return false;
}
-NotificationList::PopupNotifications NotificationList::GetPopupNotifications() {
+NotificationList::PopupNotifications NotificationList::GetPopupNotifications(
+ const std::vector<NotificationBlocker*>& blockers,
+ std::list<std::string>* blocked_ids) {
PopupNotifications result;
size_t default_priority_popup_count = 0;
@@ -203,6 +211,12 @@ NotificationList::PopupNotifications NotificationList::GetPopupNotifications() {
if ((*iter)->priority() < DEFAULT_PRIORITY)
continue;
+ if (!ShouldShowNotificationAsPopup((*iter)->notifier_id(), blockers)) {
+ if (blocked_ids)
+ blocked_ids->push_back((*iter)->id());
+ continue;
+ }
+
// Checking limits. No limits for HIGH/MAX priority. DEFAULT priority
// will return at most kMaxVisiblePopupNotifications entries. If the
// popup entries are more, older entries are used. see crbug.com/165768
@@ -216,26 +230,6 @@ NotificationList::PopupNotifications NotificationList::GetPopupNotifications() {
return result;
}
-Notification* NotificationList::GetPopup(const std::string& id) {
- PopupNotifications popups = GetPopupNotifications();
- for (PopupNotifications::iterator iter = popups.begin(); iter != popups.end();
- ++iter) {
- if ((*iter)->id() == id)
- return *iter;
- }
-
- return NULL;
-}
-
-void NotificationList::MarkPopupsAsShown(int priority) {
- PopupNotifications popups = GetPopupNotifications();
- for (PopupNotifications::iterator iter = popups.begin();
- iter != popups.end(); ++iter) {
- if ((*iter)->priority() == priority)
- (*iter)->set_shown_as_popup(true);
- }
-}
-
void NotificationList::MarkSinglePopupAsShown(
const std::string& id, bool mark_notification_as_read) {
Notifications::iterator iter = GetNotification(id);
@@ -285,21 +279,13 @@ NotificationDelegate* NotificationList::GetNotificationDelegate(
}
void NotificationList::SetQuietMode(bool quiet_mode) {
- SetQuietModeInternal(quiet_mode);
- quiet_mode_timer_.reset();
-}
-
-void NotificationList::EnterQuietModeWithExpire(
- const base::TimeDelta& expires_in) {
- if (quiet_mode_timer_.get()) {
- // Note that the capital Reset() is the method to restart the timer, not
- // scoped_ptr::reset().
- quiet_mode_timer_->Reset();
- } else {
- SetQuietModeInternal(true);
- quiet_mode_timer_.reset(new base::OneShotTimer<NotificationList>);
- quiet_mode_timer_->Start(FROM_HERE, expires_in, base::Bind(
- &NotificationList::SetQuietMode, base::Unretained(this), false));
+ quiet_mode_ = quiet_mode;
+ if (quiet_mode_) {
+ for (Notifications::iterator iter = notifications_.begin();
+ iter != notifications_.end();
+ ++iter) {
+ (*iter)->set_shown_as_popup(true);
+ }
}
}
@@ -311,19 +297,8 @@ size_t NotificationList::NotificationCount() const {
return notifications_.size();
}
-void NotificationList::SetQuietModeInternal(bool quiet_mode) {
- quiet_mode_ = quiet_mode;
- if (quiet_mode_) {
- for (Notifications::iterator iter = notifications_.begin();
- iter != notifications_.end();
- ++iter) {
- (*iter)->set_shown_as_popup(true);
- }
- }
-}
-
-NotificationList::Notifications::iterator
- NotificationList::GetNotification(const std::string& id) {
+NotificationList::Notifications::iterator NotificationList::GetNotification(
+ const std::string& id) {
for (Notifications::iterator iter = notifications_.begin();
iter != notifications_.end(); ++iter) {
if ((*iter)->id() == id)
diff --git a/chromium/ui/message_center/notification_list.h b/chromium/ui/message_center/notification_list.h
index ce24498d7e9..69eb9fcf589 100644
--- a/chromium/ui/message_center/notification_list.h
+++ b/chromium/ui/message_center/notification_list.h
@@ -5,6 +5,7 @@
#ifndef UI_MESSAGE_CENTER_NOTIFICATION_LIST_H_
#define UI_MESSAGE_CENTER_NOTIFICATION_LIST_H_
+#include <list>
#include <set>
#include <string>
@@ -23,6 +24,7 @@ class DictionaryValue;
namespace message_center {
+class NotificationBlocker;
class NotificationDelegate;
namespace test {
@@ -67,8 +69,7 @@ class MESSAGE_CENTER_EXPORT NotificationList {
void RemoveAllNotifications();
- Notifications GetNotificationsBySource(const std::string& id);
- Notifications GetNotificationsByExtension(const std::string& id);
+ Notifications GetNotificationsByNotifierId(const NotifierId& notifier_id);
// Returns true if the notification exists and was updated.
bool SetNotificationIcon(const std::string& notification_id,
@@ -83,21 +84,27 @@ class MESSAGE_CENTER_EXPORT NotificationList {
int button_index,
const gfx::Image& image);
+ // Returns true if |id| matches a notification in the list.
bool HasNotification(const std::string& id);
+ // Returns true if |id| matches a notification in the list and that
+ // notification's type matches the given type.
+ bool HasNotificationOfType(const std::string& id,
+ const NotificationType type);
+
// Returns false if the first notification has been shown as a popup (which
// means that all notifications have been shown).
- bool HasPopupNotifications();
+ bool HasPopupNotifications(const std::vector<NotificationBlocker*>& blockers);
// Returns the recent notifications of the priority higher then LOW,
// that have not been shown as a popup. kMaxVisiblePopupNotifications are
// used to limit the number of notifications for the DEFAULT priority.
- // The returned list is sorted by timestamp, newer first.
- PopupNotifications GetPopupNotifications();
- Notification* GetPopup(const std::string& id);
-
- // Marks the popups for the |priority| as shown.
- void MarkPopupsAsShown(int priority);
+ // It also stores the list of notification ids which is blocked by |blockers|
+ // to |blocked_ids|. |blocked_ids| can be NULL if the caller doesn't care
+ // which notifications are blocked.
+ PopupNotifications GetPopupNotifications(
+ const std::vector<NotificationBlocker*>& blockers,
+ std::list<std::string>* blocked_ids);
// Marks a specific popup item as shown. Set |mark_notification_as_read| to
// true in case marking the notification as read too.
@@ -114,8 +121,7 @@ class MESSAGE_CENTER_EXPORT NotificationList {
bool quiet_mode() const { return quiet_mode_; }
- // Sets the current quiet mode status to |quiet_mode|. The new status is not
- // expired.
+ // Sets the current quiet mode status to |quiet_mode|.
void SetQuietMode(bool quiet_mode);
// Sets the current quiet mode to true. The quiet mode will expire in the
@@ -139,14 +145,10 @@ class MESSAGE_CENTER_EXPORT NotificationList {
void PushNotification(scoped_ptr<Notification> notification);
- // Sets the current quiet mode status to |quiet_mode|.
- void SetQuietModeInternal(bool quiet_mode);
-
Notifications notifications_;
bool message_center_visible_;
size_t unread_count_;
bool quiet_mode_;
- scoped_ptr<base::OneShotTimer<NotificationList> > quiet_mode_timer_;
DISALLOW_COPY_AND_ASSIGN(NotificationList);
};
diff --git a/chromium/ui/message_center/notification_list_unittest.cc b/chromium/ui/message_center/notification_list_unittest.cc
index cdd6ad42832..4e6f5d1ee49 100644
--- a/chromium/ui/message_center/notification_list_unittest.cc
+++ b/chromium/ui/message_center/notification_list_unittest.cc
@@ -11,7 +11,9 @@
#include "base/values.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/message_center/message_center_style.h"
+#include "ui/message_center/notification_blocker.h"
#include "ui/message_center/notification_types.h"
+#include "ui/message_center/notifier_settings.h"
namespace message_center {
namespace test {
@@ -40,7 +42,7 @@ class NotificationListTest : public testing::Test {
UTF8ToUTF16(base::StringPrintf(kMessageFormat, counter_)),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION, kExtensionId),
optional_fields,
NULL));
notification_list_->AddNotification(notification.Pass());
@@ -59,8 +61,13 @@ class NotificationListTest : public testing::Test {
return AddNotification(optional);
}
+ NotificationList::PopupNotifications GetPopups() {
+ return notification_list()->GetPopupNotifications(
+ std::vector<NotificationBlocker*>(), NULL);
+ }
+
size_t GetPopupCounts() {
- return notification_list()->GetPopupNotifications().size();
+ return GetPopups().size();
}
Notification* GetNotification(const std::string& id) {
@@ -112,14 +119,16 @@ TEST_F(NotificationListTest, Basic) {
EXPECT_EQ(2u, notification_list()->NotificationCount());
EXPECT_EQ(2u, notification_list()->unread_count());
- EXPECT_TRUE(notification_list()->HasPopupNotifications());
+ EXPECT_TRUE(notification_list()->HasPopupNotifications(
+ std::vector<NotificationBlocker*>()));
EXPECT_TRUE(notification_list()->HasNotification(id0));
EXPECT_TRUE(notification_list()->HasNotification(id1));
EXPECT_FALSE(notification_list()->HasNotification(id1 + "foo"));
EXPECT_EQ(2u, GetPopupCounts());
- notification_list()->MarkPopupsAsShown(0);
+ notification_list()->MarkSinglePopupAsShown(id0, true);
+ notification_list()->MarkSinglePopupAsShown(id1, true);
EXPECT_EQ(2u, notification_list()->NotificationCount());
EXPECT_EQ(0u, GetPopupCounts());
@@ -172,7 +181,7 @@ TEST_F(NotificationListTest, UpdateNotification) {
UTF8ToUTF16("newbody"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION, kExtensionId),
message_center::RichNotificationData(),
NULL));
notification_list()->UpdateNotificationMessage(id0, notification.Pass());
@@ -184,7 +193,11 @@ TEST_F(NotificationListTest, UpdateNotification) {
EXPECT_EQ(UTF8ToUTF16("newbody"), (*notifications.begin())->message());
}
-TEST_F(NotificationListTest, GetNotificationsBySourceOrExtensions) {
+TEST_F(NotificationListTest, GetNotificationsByNotifierId) {
+ NotifierId id0(NotifierId::APPLICATION, "ext0");
+ NotifierId id1(NotifierId::APPLICATION, "ext1");
+ NotifierId id2(GURL("http://example.com"));
+ NotifierId id3(0);
scoped_ptr<Notification> notification(
new Notification(message_center::NOTIFICATION_TYPE_SIMPLE,
"id0",
@@ -192,7 +205,7 @@ TEST_F(NotificationListTest, GetNotificationsBySourceOrExtensions) {
UTF8ToUTF16("message0"),
gfx::Image(),
UTF8ToUTF16("source0"),
- "ext0",
+ id0,
message_center::RichNotificationData(),
NULL));
notification_list()->AddNotification(notification.Pass());
@@ -202,7 +215,7 @@ TEST_F(NotificationListTest, GetNotificationsBySourceOrExtensions) {
UTF8ToUTF16("message1"),
gfx::Image(),
UTF8ToUTF16("source0"),
- "ext0",
+ id0,
message_center::RichNotificationData(),
NULL));
notification_list()->AddNotification(notification.Pass());
@@ -212,7 +225,7 @@ TEST_F(NotificationListTest, GetNotificationsBySourceOrExtensions) {
UTF8ToUTF16("message1"),
gfx::Image(),
UTF8ToUTF16("source1"),
- "ext0",
+ id0,
message_center::RichNotificationData(),
NULL));
notification_list()->AddNotification(notification.Pass());
@@ -222,24 +235,63 @@ TEST_F(NotificationListTest, GetNotificationsBySourceOrExtensions) {
UTF8ToUTF16("message1"),
gfx::Image(),
UTF8ToUTF16("source2"),
- "ext1",
+ id1,
+ message_center::RichNotificationData(),
+ NULL));
+ notification_list()->AddNotification(notification.Pass());
+ notification.reset(new Notification(message_center::NOTIFICATION_TYPE_SIMPLE,
+ "id4",
+ UTF8ToUTF16("title1"),
+ UTF8ToUTF16("message1"),
+ gfx::Image(),
+ UTF8ToUTF16("source2"),
+ id2,
+ message_center::RichNotificationData(),
+ NULL));
+ notification_list()->AddNotification(notification.Pass());
+ notification.reset(new Notification(message_center::NOTIFICATION_TYPE_SIMPLE,
+ "id5",
+ UTF8ToUTF16("title1"),
+ UTF8ToUTF16("message1"),
+ gfx::Image(),
+ UTF8ToUTF16("source2"),
+ id3,
message_center::RichNotificationData(),
NULL));
notification_list()->AddNotification(notification.Pass());
- NotificationList::Notifications by_source =
- notification_list()->GetNotificationsBySource("id0");
- EXPECT_TRUE(IsInNotifications(by_source, "id0"));
- EXPECT_TRUE(IsInNotifications(by_source, "id1"));
- EXPECT_FALSE(IsInNotifications(by_source, "id2"));
- EXPECT_FALSE(IsInNotifications(by_source, "id3"));
-
- NotificationList::Notifications by_extension =
- notification_list()->GetNotificationsByExtension("id0");
- EXPECT_TRUE(IsInNotifications(by_extension, "id0"));
- EXPECT_TRUE(IsInNotifications(by_extension, "id1"));
- EXPECT_TRUE(IsInNotifications(by_extension, "id2"));
- EXPECT_FALSE(IsInNotifications(by_extension, "id3"));
+ NotificationList::Notifications by_notifier_id =
+ notification_list()->GetNotificationsByNotifierId(id0);
+ EXPECT_TRUE(IsInNotifications(by_notifier_id, "id0"));
+ EXPECT_TRUE(IsInNotifications(by_notifier_id, "id1"));
+ EXPECT_TRUE(IsInNotifications(by_notifier_id, "id2"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id3"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id4"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id5"));
+
+ by_notifier_id = notification_list()->GetNotificationsByNotifierId(id1);
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id0"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id1"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id2"));
+ EXPECT_TRUE(IsInNotifications(by_notifier_id, "id3"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id4"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id5"));
+
+ by_notifier_id = notification_list()->GetNotificationsByNotifierId(id2);
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id0"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id1"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id2"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id3"));
+ EXPECT_TRUE(IsInNotifications(by_notifier_id, "id4"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id5"));
+
+ by_notifier_id = notification_list()->GetNotificationsByNotifierId(id3);
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id0"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id1"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id2"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id3"));
+ EXPECT_FALSE(IsInNotifications(by_notifier_id, "id4"));
+ EXPECT_TRUE(IsInNotifications(by_notifier_id, "id5"));
}
TEST_F(NotificationListTest, OldPopupShouldNotBeHidden) {
@@ -247,8 +299,7 @@ TEST_F(NotificationListTest, OldPopupShouldNotBeHidden) {
for (size_t i = 0; i <= kMaxVisiblePopupNotifications; i++)
ids.push_back(AddNotification());
- NotificationList::PopupNotifications popups =
- notification_list()->GetPopupNotifications();
+ NotificationList::PopupNotifications popups = GetPopups();
// The popup should contain the oldest kMaxVisiblePopupNotifications. Newer
// one should come earlier in the popup list. It means, the last element
// of |popups| should be the firstly added one, and so on.
@@ -259,9 +310,12 @@ TEST_F(NotificationListTest, OldPopupShouldNotBeHidden) {
EXPECT_EQ(ids[i], (*iter)->id()) << i;
}
- notification_list()->MarkPopupsAsShown(message_center::DEFAULT_PRIORITY);
+ for (NotificationList::PopupNotifications::const_iterator iter =
+ popups.begin(); iter != popups.end(); ++iter) {
+ notification_list()->MarkSinglePopupAsShown((*iter)->id(), false);
+ }
popups.clear();
- popups = notification_list()->GetPopupNotifications();
+ popups = GetPopups();
EXPECT_EQ(1u, popups.size());
EXPECT_EQ(ids[ids.size() - 1], (*popups.begin())->id());
}
@@ -355,7 +409,7 @@ TEST_F(NotificationListTest, PriorityPromotion) {
UTF8ToUTF16("newbody"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION, kExtensionId),
optional,
NULL));
notification_list()->UpdateNotificationMessage(id0, notification.Pass());
@@ -386,7 +440,7 @@ TEST_F(NotificationListTest, PriorityPromotionWithPopups) {
UTF8ToUTF16("newbody"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION, kExtensionId),
priority,
NULL));
notification_list()->UpdateNotificationMessage(id0, notification.Pass());
@@ -401,7 +455,8 @@ TEST_F(NotificationListTest, PriorityPromotionWithPopups) {
UTF8ToUTF16("newbody2"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION,
+ kExtensionId),
priority,
NULL));
notification_list()->UpdateNotificationMessage(id0, notification.Pass());
@@ -415,7 +470,8 @@ TEST_F(NotificationListTest, PriorityPromotionWithPopups) {
UTF8ToUTF16("newbody"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION,
+ kExtensionId),
priority,
NULL));
notification_list()->UpdateNotificationMessage(id1, notification.Pass());
@@ -431,7 +487,8 @@ TEST_F(NotificationListTest, PriorityPromotionWithPopups) {
UTF8ToUTF16("newbody2"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION,
+ kExtensionId),
priority,
NULL));
notification_list()->UpdateNotificationMessage(id1, notification.Pass());
@@ -447,7 +504,8 @@ TEST_F(NotificationListTest, PriorityPromotionWithPopups) {
UTF8ToUTF16("newbody3"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION,
+ kExtensionId),
priority,
NULL));
notification_list()->UpdateNotificationMessage(id1, notification.Pass());
@@ -473,8 +531,7 @@ TEST_F(NotificationListTest, NotificationOrderAndPriority) {
{
// Popups: latest comes first.
- NotificationList::PopupNotifications popups =
- notification_list()->GetPopupNotifications();
+ NotificationList::PopupNotifications popups = GetPopups();
EXPECT_EQ(3u, popups.size());
NotificationList::PopupNotifications::const_iterator iter = popups.begin();
EXPECT_EQ(default_id, (*iter)->id());
@@ -514,8 +571,7 @@ TEST_F(NotificationListTest, MarkSinglePopupAsShown) {
EXPECT_EQ(3u, notification_list()->NotificationCount());
EXPECT_EQ(1u, notification_list()->unread_count());
EXPECT_EQ(1u, GetPopupCounts());
- NotificationList::PopupNotifications popups =
- notification_list()->GetPopupNotifications();
+ NotificationList::PopupNotifications popups = GetPopups();
EXPECT_EQ(id1, (*popups.begin())->id());
// The notifications in the NotificationCenter are unaffected by popups shown.
@@ -527,39 +583,6 @@ TEST_F(NotificationListTest, MarkSinglePopupAsShown) {
EXPECT_EQ(id2, (*iter)->id());
iter++;
EXPECT_EQ(id1, (*iter)->id());
-
- // Trickier scenario.
- notification_list()->MarkPopupsAsShown(message_center::DEFAULT_PRIORITY);
- std::string id4 = AddNotification();
- std::string id5 = AddNotification();
- std::string id6 = AddNotification();
- notification_list()->MarkSinglePopupAsShown(id5, true);
-
- {
- popups.clear();
- popups = notification_list()->GetPopupNotifications();
- EXPECT_EQ(2u, popups.size());
- NotificationList::PopupNotifications::const_iterator iter = popups.begin();
- EXPECT_EQ(id6, (*iter)->id());
- iter++;
- EXPECT_EQ(id4, (*iter)->id());
- }
-
- notifications.clear();
- notifications = notification_list()->GetNotifications();
- EXPECT_EQ(6u, notifications.size());
- iter = notifications.begin();
- EXPECT_EQ(id6, (*iter)->id());
- iter++;
- EXPECT_EQ(id5, (*iter)->id());
- iter++;
- EXPECT_EQ(id4, (*iter)->id());
- iter++;
- EXPECT_EQ(id3, (*iter)->id());
- iter++;
- EXPECT_EQ(id2, (*iter)->id());
- iter++;
- EXPECT_EQ(id1, (*iter)->id());
}
TEST_F(NotificationListTest, UpdateAfterMarkedAsShown) {
@@ -588,7 +611,7 @@ TEST_F(NotificationListTest, UpdateAfterMarkedAsShown) {
UTF8ToUTF16("newbody"),
gfx::Image(),
UTF8ToUTF16(kDisplaySource),
- kExtensionId,
+ NotifierId(NotifierId::APPLICATION, kExtensionId),
message_center::RichNotificationData(),
NULL));
notification_list()->UpdateNotificationMessage(id1, notification.Pass());
@@ -634,12 +657,38 @@ TEST_F(NotificationListTest, UnreadCountNoNegative) {
UTF8ToUTF16("updated"),
gfx::Image(),
base::string16(),
- std::string(),
+ NotifierId(),
RichNotificationData(),
NULL));
notification_list()->AddNotification(updated_notification.Pass());
EXPECT_EQ(1u, notification_list()->unread_count());
}
+TEST_F(NotificationListTest, TestHasNotificationOfType) {
+ std::string id = AddNotification();
+
+ EXPECT_TRUE(notification_list()->HasNotificationOfType(
+ id, message_center::NOTIFICATION_TYPE_SIMPLE));
+ EXPECT_FALSE(notification_list()->HasNotificationOfType(
+ id, message_center::NOTIFICATION_TYPE_PROGRESS));
+
+ scoped_ptr<Notification> updated_notification(new Notification(
+ message_center::NOTIFICATION_TYPE_PROGRESS,
+ id,
+ UTF8ToUTF16("updated"),
+ UTF8ToUTF16("updated"),
+ gfx::Image(),
+ base::string16(),
+ NotifierId(),
+ RichNotificationData(),
+ NULL));
+ notification_list()->AddNotification(updated_notification.Pass());
+
+ EXPECT_FALSE(notification_list()->HasNotificationOfType(
+ id, message_center::NOTIFICATION_TYPE_SIMPLE));
+ EXPECT_TRUE(notification_list()->HasNotificationOfType(
+ id, message_center::NOTIFICATION_TYPE_PROGRESS));
+}
+
} // namespace test
} // namespace message_center
diff --git a/chromium/ui/message_center/notifier_settings.cc b/chromium/ui/message_center/notifier_settings.cc
index 4355b9459fe..861e65b651f 100644
--- a/chromium/ui/message_center/notifier_settings.cc
+++ b/chromium/ui/message_center/notifier_settings.cc
@@ -11,15 +11,26 @@ NotifierId::NotifierId(NotifierType type,
const std::string& id)
: type(type),
id(id),
- system_component_type(NONE) {
+ system_component_type(-1) {
DCHECK(type == APPLICATION || type == SYNCED_NOTIFICATION_SERVICE);
+ DCHECK(!id.empty());
}
NotifierId::NotifierId(const GURL& url)
- : type(WEB_PAGE), url(url), system_component_type(NONE) {}
+ : type(WEB_PAGE),
+ url(url),
+ system_component_type(-1) {}
-NotifierId::NotifierId(SystemComponentNotifierType system_component_type)
- : type(SYSTEM_COMPONENT), system_component_type(system_component_type) {}
+NotifierId::NotifierId(int type)
+ : type(SYSTEM_COMPONENT),
+ system_component_type(type) {
+ DCHECK_LE(0, system_component_type);
+}
+
+NotifierId::NotifierId()
+ : type(SYSTEM_COMPONENT),
+ system_component_type(-1) {
+}
bool NotifierId::operator==(const NotifierId& other) const {
if (type != other.type)
@@ -58,23 +69,4 @@ NotifierGroup::NotifierGroup(const gfx::Image& icon,
NotifierGroup::~NotifierGroup() {}
-std::string ToString(NotifierId::SystemComponentNotifierType type) {
- switch (type) {
- case NotifierId::SCREENSHOT:
- return "screenshot";
- default:
- NOTREACHED();
- return "";
- }
-}
-
-NotifierId::SystemComponentNotifierType
-ParseSystemComponentName(const std::string& name) {
- if (name == "screenshot") {
- return NotifierId::SCREENSHOT;
- } else {
- NOTREACHED();
- return NotifierId::NONE;
- }
-}
} // namespace message_center
diff --git a/chromium/ui/message_center/notifier_settings.h b/chromium/ui/message_center/notifier_settings.h
index b8771a399cc..6188599e20a 100644
--- a/chromium/ui/message_center/notifier_settings.h
+++ b/chromium/ui/message_center/notifier_settings.h
@@ -33,19 +33,17 @@ struct MESSAGE_CENTER_EXPORT NotifierId {
SYNCED_NOTIFICATION_SERVICE,
};
- enum SystemComponentNotifierType {
- NONE,
- SCREENSHOT,
- };
-
// Constructor for APPLICATION and SYNCED_NOTIFICATION_SERVICE type.
NotifierId(NotifierType type, const std::string& id);
// Constructor for WEB_PAGE type.
explicit NotifierId(const GURL& url);
- // Constructor for SYSTEM_COMPONENT type.
- explicit NotifierId(SystemComponentNotifierType type);
+ // Constructor for system component types. The type should be positive.
+ explicit NotifierId(int type);
+
+ // The default constructor which doesn't specify the notifier. Used for tests.
+ NotifierId();
bool operator==(const NotifierId& other) const;
@@ -58,8 +56,9 @@ struct MESSAGE_CENTER_EXPORT NotifierId {
// The URL pattern of the notifer.
GURL url;
- // The type of system component notifier.
- SystemComponentNotifierType system_component_type;
+ // The type of system component notifier, usually used in ash. -1 if it's not
+ // the system component. See also: ash/system/system_notifier.h
+ int system_component_type;
};
// The struct to hold the information of notifiers. The information will be
@@ -108,11 +107,6 @@ struct MESSAGE_CENTER_EXPORT NotifierGroup {
DISALLOW_COPY_AND_ASSIGN(NotifierGroup);
};
-MESSAGE_CENTER_EXPORT std::string ToString(
- NotifierId::SystemComponentNotifierType type);
-MESSAGE_CENTER_EXPORT NotifierId::SystemComponentNotifierType
- ParseSystemComponentName(const std::string& name);
-
// An observer class implemented by the view of the NotifierSettings to get
// notified when the controller has changed data.
class MESSAGE_CENTER_EXPORT NotifierSettingsObserver {
diff --git a/chromium/ui/message_center/views/bounded_label.cc b/chromium/ui/message_center/views/bounded_label.cc
index 6752795390e..9c6f4df5840 100644
--- a/chromium/ui/message_center/views/bounded_label.cc
+++ b/chromium/ui/message_center/views/bounded_label.cc
@@ -8,8 +8,8 @@
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
-#include "ui/base/text/text_elider.h"
#include "ui/gfx/canvas.h"
+#include "ui/gfx/text_elider.h"
#include "ui/views/controls/label.h"
namespace {
@@ -143,18 +143,18 @@ std::vector<string16> InnerBoundedLabel::GetWrappedText(int width, int lines) {
// Wrap, using INT_MAX for -1 widths that indicate no wrapping.
std::vector<string16> wrapped;
- ui::ElideRectangleText(text(), font(),
- (width < 0) ? std::numeric_limits<int>::max() : width,
- height, ui::WRAP_LONG_WORDS, &wrapped);
+ gfx::ElideRectangleText(text(), font_list(),
+ (width < 0) ? std::numeric_limits<int>::max() : width,
+ height, gfx::WRAP_LONG_WORDS, &wrapped);
// Elide if necessary.
if (lines > 0 && wrapped.size() > static_cast<unsigned int>(lines)) {
// Add an ellipsis to the last line. If this ellipsis makes the last line
- // too wide, that line will be further elided by the ui::ElideText below,
+ // too wide, that line will be further elided by the gfx::ElideText below,
// so for example "ABC" could become "ABC..." and then "AB...".
- string16 last = wrapped[lines - 1] + UTF8ToUTF16(ui::kEllipsis);
+ string16 last = wrapped[lines - 1] + UTF8ToUTF16(gfx::kEllipsis);
if (width > 0 && font().GetStringWidth(last) > width)
- last = ui::ElideText(last, font(), width, ui::ELIDE_AT_END);
+ last = gfx::ElideText(last, font(), width, gfx::ELIDE_AT_END);
wrapped.resize(lines - 1);
wrapped.push_back(last);
}
@@ -259,10 +259,10 @@ void InnerBoundedLabel::SetCachedSize(std::pair<int, int> width_and_lines,
// BoundedLabel ///////////////////////////////////////////////////////////
-BoundedLabel::BoundedLabel(const string16& text, gfx::Font font)
+BoundedLabel::BoundedLabel(const string16& text, const gfx::FontList& font_list)
: line_limit_(-1) {
label_.reset(new InnerBoundedLabel(*this));
- label_->SetFont(font);
+ label_->SetFontList(font_list);
label_->SetText(text);
}
diff --git a/chromium/ui/message_center/views/bounded_label.h b/chromium/ui/message_center/views/bounded_label.h
index 6d97c8850cc..d6b2f49a519 100644
--- a/chromium/ui/message_center/views/bounded_label.h
+++ b/chromium/ui/message_center/views/bounded_label.h
@@ -14,7 +14,7 @@
#include "ui/views/view.h"
namespace gfx {
-class Font;
+class FontList;
}
namespace message_center {
@@ -33,7 +33,7 @@ class BoundedLabelTest;
// bounded_label.cc file for details.
class MESSAGE_CENTER_EXPORT BoundedLabel : public views::View {
public:
- BoundedLabel(const string16& text, gfx::Font font);
+ BoundedLabel(const string16& text, const gfx::FontList& font_list);
BoundedLabel(const string16& text);
virtual ~BoundedLabel();
diff --git a/chromium/ui/message_center/views/bounded_label_unittest.cc b/chromium/ui/message_center/views/bounded_label_unittest.cc
index a73d84bba9e..bdfb0aceeb6 100644
--- a/chromium/ui/message_center/views/bounded_label_unittest.cc
+++ b/chromium/ui/message_center/views/bounded_label_unittest.cc
@@ -10,7 +10,8 @@
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/gfx/font.h"
+#include "ui/gfx/font_list.h"
+#include "ui/gfx/text_utils.h"
#include "ui/views/controls/label.h"
namespace message_center {
@@ -22,9 +23,10 @@ namespace test {
class BoundedLabelTest : public testing::Test {
public:
BoundedLabelTest() {
- digit_pixels_ = font_.GetStringWidth(UTF8ToUTF16("0"));
- space_pixels_ = font_.GetStringWidth(UTF8ToUTF16(" "));
- ellipsis_pixels_ = font_.GetStringWidth(UTF8ToUTF16("\xE2\x80\xA6"));
+ digit_pixels_ = gfx::GetStringWidth(UTF8ToUTF16("0"), font_list_);
+ space_pixels_ = gfx::GetStringWidth(UTF8ToUTF16(" "), font_list_);
+ ellipsis_pixels_ = gfx::GetStringWidth(UTF8ToUTF16("\xE2\x80\xA6"),
+ font_list_);
}
virtual ~BoundedLabelTest() {}
@@ -62,7 +64,7 @@ class BoundedLabelTest : public testing::Test {
// Exercise BounderLabel::GetLinesForWidthAndLimit() using the test label.
int GetLinesForWidth(int width) {
- label_->SetBounds(0, 0, width, font_.GetHeight() * lines_);
+ label_->SetBounds(0, 0, width, font_list_.GetHeight() * lines_);
return label_->GetLinesForWidthAndLimit(width, lines_);
}
@@ -71,13 +73,14 @@ class BoundedLabelTest : public testing::Test {
// test the newly created label using the exercise methods above.
BoundedLabelTest& Label(string16 text, int lines) {
lines_ = lines;
- label_.reset(new BoundedLabel(text, font_));
+ label_.reset(new BoundedLabel(text, font_list_));
label_->SetLineLimit(lines_);
return *this;
}
private:
- gfx::Font font_; // The default font, which will be used for tests.
+ // The default font list, which will be used for tests.
+ gfx::FontList font_list_;
int digit_pixels_;
int space_pixels_;
int ellipsis_pixels_;
diff --git a/chromium/ui/message_center/views/message_center_view.cc b/chromium/ui/message_center/views/message_center_view.cc
index 95c2cc37669..2acece7402a 100644
--- a/chromium/ui/message_center/views/message_center_view.cc
+++ b/chromium/ui/message_center/views/message_center_view.cc
@@ -11,15 +11,16 @@
#include "base/message_loop/message_loop.h"
#include "base/stl_util.h"
#include "grit/ui_strings.h"
-#include "ui/base/animation/multi_animation.h"
-#include "ui/base/animation/slide_animation.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/gfx/animation/multi_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/size.h"
#include "ui/message_center/message_center.h"
#include "ui/message_center/message_center_style.h"
+#include "ui/message_center/message_center_types.h"
#include "ui/message_center/views/message_center_button_bar.h"
#include "ui/message_center/views/message_view.h"
#include "ui/message_center/views/notification_view.h"
@@ -415,7 +416,7 @@ void MessageListView::OnBoundsAnimatorProgressed(
DCHECK_EQ(animator_.get(), animator);
for (std::set<views::View*>::iterator iter = deleted_when_done_.begin();
iter != deleted_when_done_.end(); ++iter) {
- const ui::SlideAnimation* animation = animator->GetAnimationForView(*iter);
+ const gfx::SlideAnimation* animation = animator->GetAnimationForView(*iter);
if (animation)
(*iter)->layer()->SetOpacity(animation->CurrentValueBetween(1.0, 0.0));
}
@@ -683,28 +684,28 @@ void MessageCenterView::SetSettingsVisible(bool visible) {
source_height_ = source_view_->GetHeightForWidth(width());
target_height_ = target_view_->GetHeightForWidth(width());
- ui::MultiAnimation::Parts parts;
+ gfx::MultiAnimation::Parts parts;
// First part: slide resize animation.
- parts.push_back(ui::MultiAnimation::Part(
+ parts.push_back(gfx::MultiAnimation::Part(
(source_height_ == target_height_) ? 0 : kDefaultAnimationDurationMs,
- ui::Tween::EASE_OUT));
+ gfx::Tween::EASE_OUT));
// Second part: fade-out the source_view.
if (source_view_->layer()) {
- parts.push_back(ui::MultiAnimation::Part(
- kDefaultAnimationDurationMs, ui::Tween::LINEAR));
+ parts.push_back(gfx::MultiAnimation::Part(
+ kDefaultAnimationDurationMs, gfx::Tween::LINEAR));
} else {
- parts.push_back(ui::MultiAnimation::Part());
+ parts.push_back(gfx::MultiAnimation::Part());
}
// Third part: fade-in the target_view.
if (target_view_->layer()) {
- parts.push_back(ui::MultiAnimation::Part(
- kDefaultAnimationDurationMs, ui::Tween::LINEAR));
+ parts.push_back(gfx::MultiAnimation::Part(
+ kDefaultAnimationDurationMs, gfx::Tween::LINEAR));
target_view_->layer()->SetOpacity(0);
target_view_->SetVisible(true);
} else {
- parts.push_back(ui::MultiAnimation::Part());
+ parts.push_back(gfx::MultiAnimation::Part());
}
- settings_transition_animation_.reset(new ui::MultiAnimation(
+ settings_transition_animation_.reset(new gfx::MultiAnimation(
parts, base::TimeDelta::FromMicroseconds(1000000 / kDefaultFrameRateHz)));
settings_transition_animation_->set_delegate(this);
settings_transition_animation_->set_continuous(false);
@@ -931,9 +932,14 @@ void MessageCenterView::OnNotificationUpdated(const std::string& id) {
}
}
-void MessageCenterView::AnimationEnded(const ui::Animation* animation) {
+void MessageCenterView::AnimationEnded(const gfx::Animation* animation) {
DCHECK_EQ(animation, settings_transition_animation_.get());
+ Visibility visibility = target_view_ == settings_view_
+ ? VISIBILITY_SETTINGS
+ : VISIBILITY_MESSAGE_CENTER;
+ message_center_->SetVisibility(visibility);
+
source_view_->SetVisible(false);
target_view_->SetVisible(true);
if (source_view_->layer())
@@ -945,7 +951,7 @@ void MessageCenterView::AnimationEnded(const ui::Animation* animation) {
Layout();
}
-void MessageCenterView::AnimationProgressed(const ui::Animation* animation) {
+void MessageCenterView::AnimationProgressed(const gfx::Animation* animation) {
DCHECK_EQ(animation, settings_transition_animation_.get());
PreferredSizeChanged();
if (settings_transition_animation_->current_part_index() == 1 &&
@@ -961,7 +967,7 @@ void MessageCenterView::AnimationProgressed(const ui::Animation* animation) {
}
}
-void MessageCenterView::AnimationCanceled(const ui::Animation* animation) {
+void MessageCenterView::AnimationCanceled(const gfx::Animation* animation) {
DCHECK_EQ(animation, settings_transition_animation_.get());
AnimationEnded(animation);
}
diff --git a/chromium/ui/message_center/views/message_center_view.h b/chromium/ui/message_center/views/message_center_view.h
index d53910c2734..7e3c8296730 100644
--- a/chromium/ui/message_center/views/message_center_view.h
+++ b/chromium/ui/message_center/views/message_center_view.h
@@ -7,15 +7,15 @@
#include "ui/views/view.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
#include "ui/message_center/message_center_export.h"
#include "ui/message_center/message_center_observer.h"
#include "ui/message_center/notification_list.h"
#include "ui/views/controls/button/button.h"
-namespace ui {
+namespace gfx {
class MultiAnimation;
-} // namespace ui
+} // namespace gfx
namespace views {
class Button;
@@ -37,7 +37,7 @@ class NotifierSettingsView;
class MESSAGE_CENTER_EXPORT MessageCenterView : public views::View,
public MessageCenterObserver,
- public ui::AnimationDelegate {
+ public gfx::AnimationDelegate {
public:
MessageCenterView(MessageCenter* message_center,
MessageCenterTray* tray,
@@ -73,10 +73,10 @@ class MESSAGE_CENTER_EXPORT MessageCenterView : public views::View,
bool by_user) OVERRIDE;
virtual void OnNotificationUpdated(const std::string& id) OVERRIDE;
- // Overridden from ui::AnimationDelegate:
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationCanceled(const ui::Animation* animation) OVERRIDE;
+ // Overridden from gfx::AnimationDelegate:
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationCanceled(const gfx::Animation* animation) OVERRIDE;
private:
friend class MessageCenterViewTest;
@@ -102,7 +102,7 @@ class MESSAGE_CENTER_EXPORT MessageCenterView : public views::View,
// Animation managing transition between message center and settings (and vice
// versa).
- scoped_ptr<ui::MultiAnimation> settings_transition_animation_;
+ scoped_ptr<gfx::MultiAnimation> settings_transition_animation_;
// Helper data to keep track of the transition between settings and
// message center views.
diff --git a/chromium/ui/message_center/views/message_center_view_unittest.cc b/chromium/ui/message_center/views/message_center_view_unittest.cc
index f6e05f4e30f..b9e34a1ebd1 100644
--- a/chromium/ui/message_center/views/message_center_view_unittest.cc
+++ b/chromium/ui/message_center/views/message_center_view_unittest.cc
@@ -133,7 +133,7 @@ void MessageCenterViewTest::SetUp() {
UTF8ToUTF16("message"),
gfx::Image(),
UTF8ToUTF16("display source"),
- std::string("extension id"),
+ NotifierId(NotifierId::APPLICATION, "extension_id"),
message_center::RichNotificationData(),
NULL);
diff --git a/chromium/ui/message_center/views/message_popup_collection.cc b/chromium/ui/message_center/views/message_popup_collection.cc
index 130a8650f6a..5355ad6962b 100644
--- a/chromium/ui/message_center/views/message_popup_collection.cc
+++ b/chromium/ui/message_center/views/message_popup_collection.cc
@@ -14,8 +14,8 @@
#include "base/time/time.h"
#include "base/timer/timer.h"
#include "ui/base/accessibility/accessibility_types.h"
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/animation_delegate.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/gfx/screen.h"
#include "ui/message_center/message_center.h"
#include "ui/message_center/message_center_style.h"
@@ -150,9 +150,14 @@ void MessagePopupCollection::UpdateWidgets() {
toasts_.push_back(toast);
gfx::Size preferred_size = toast->GetPreferredSize();
- gfx::Point origin(
- GetToastOriginX(gfx::Rect(preferred_size)) + preferred_size.width(),
- top_down ? base + view_height : base);
+ gfx::Point origin(GetToastOriginX(gfx::Rect(preferred_size)), base);
+ // The toast slides in from the edge of the screen horizontally.
+ if (alignment_ & POPUP_ALIGNMENT_LEFT)
+ origin.set_x(origin.x() - preferred_size.width());
+ else
+ origin.set_x(origin.x() + preferred_size.width());
+ if (top_down)
+ origin.set_y(origin.y() + view_height);
toast->RevealWithAnimation(origin);
// Shift the base line to be a few pixels above the last added toast or (few
@@ -358,9 +363,7 @@ void MessagePopupCollection::OnNotificationRemoved(
return;
target_top_edge_ = (*iter)->bounds().y();
- (*iter)->CloseWithAnimation(true);
- if (by_user) {
- RepositionWidgetsWithTarget();
+ if (by_user && !user_is_closing_toasts_by_clicking_) {
// [Re] start a timeout after which the toasts re-position to their
// normal locations after tracking the mouse pointer for easy deletion.
// This provides a period of time when toasts are easy to remove because
@@ -368,11 +371,18 @@ void MessagePopupCollection::OnNotificationRemoved(
// pointer. If the user continue to remove the toasts, the delay is reset.
// Once user stopped removing the toasts, the toasts re-populate/rearrange
// after the specified delay.
- if (!user_is_closing_toasts_by_clicking_) {
- user_is_closing_toasts_by_clicking_ = true;
- IncrementDeferCounter();
- }
+ user_is_closing_toasts_by_clicking_ = true;
+ IncrementDeferCounter();
}
+
+ // CloseWithAnimation ultimately causes a call to RemoveToast, which calls
+ // OnMouseExited. This means that |user_is_closing_toasts_by_clicking_| must
+ // have been set before this call, otherwise it will remain true even after
+ // the toast is closed, since the defer timer won't be started.
+ (*iter)->CloseWithAnimation(true);
+
+ if (by_user)
+ RepositionWidgetsWithTarget();
}
void MessagePopupCollection::OnDeferTimerExpired() {
diff --git a/chromium/ui/message_center/views/message_popup_collection_unittest.cc b/chromium/ui/message_center/views/message_popup_collection_unittest.cc
index 52299edd6d9..cca2774729e 100644
--- a/chromium/ui/message_center/views/message_popup_collection_unittest.cc
+++ b/chromium/ui/message_center/views/message_popup_collection_unittest.cc
@@ -10,8 +10,8 @@
#include "base/strings/string_number_conversions.h"
#include "base/strings/utf_string_conversions.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/display.h"
#include "ui/gfx/rect.h"
#include "ui/message_center/fake_message_center.h"
@@ -90,7 +90,7 @@ class MessagePopupCollectionTest : public views::ViewsTestBase {
UTF8ToUTF16("test message"),
gfx::Image(),
string16() /* display_source */,
- "" /* extension_id */,
+ NotifierId(),
message_center::RichNotificationData(),
NULL /* delegate */));
MessageCenter::Get()->AddNotification(notification.Pass());
@@ -377,6 +377,29 @@ TEST_F(MessagePopupCollectionTest, DetectMouseHover) {
// TODO(dimich): Test repositioning - both normal one and when user is closing
// the toasts.
+TEST_F(MessagePopupCollectionTest, DetectMouseHoverWithUserClose) {
+ std::string id0 = AddNotification();
+ std::string id1 = AddNotification();
+ WaitForTransitionsDone();
+
+ views::WidgetDelegateView* toast0 = GetToast(id0);
+ EXPECT_TRUE(toast0 != NULL);
+ views::WidgetDelegateView* toast1 = GetToast(id1);
+ ASSERT_TRUE(toast1 != NULL);
+
+ ui::MouseEvent event(ui::ET_MOUSE_MOVED, gfx::Point(), gfx::Point(), 0);
+ toast1->OnMouseEntered(event);
+ static_cast<MessageCenterObserver*>(collection())->OnNotificationRemoved(
+ id1, true);
+
+ EXPECT_FALSE(MouseInCollection());
+ std::string id2 = AddNotification();
+
+ WaitForTransitionsDone();
+ views::WidgetDelegateView* toast2 = GetToast(id2);
+ EXPECT_TRUE(toast2 != NULL);
+}
+
} // namespace test
} // namespace message_center
diff --git a/chromium/ui/message_center/views/message_view.cc b/chromium/ui/message_center/views/message_view.cc
index 7eb9838e24b..e3199ccdb4b 100644
--- a/chromium/ui/message_center/views/message_view.cc
+++ b/chromium/ui/message_center/views/message_view.cc
@@ -35,8 +35,7 @@ const int kShadowBlur = 4;
// Menu constants
const int kTogglePermissionCommand = 0;
-const int kToggleExtensionCommand = 1;
-const int kShowSettingsCommand = 2;
+const int kShowSettingsCommand = 1;
// ControlButtons are ImageButtons whose image can be padded within the button.
// This allows the creation of buttons like the notification close and expand
@@ -170,7 +169,7 @@ class MenuModel : public ui::SimpleMenuModel,
message_center::MessageCenterTray* tray,
const std::string& notification_id,
const string16& display_source,
- const std::string& extension_id);
+ const message_center::NotifierId& notifier_id);
virtual ~MenuModel();
// Overridden from ui::SimpleMenuModel::Delegate:
@@ -186,6 +185,7 @@ class MenuModel : public ui::SimpleMenuModel,
message_center::MessageCenter* message_center_; // Weak reference.
message_center::MessageCenterTray* tray_; // Weak reference.
std::string notification_id_;
+ message_center::NotifierId notifier_id_;
DISALLOW_COPY_AND_ASSIGN(MenuModel);
};
@@ -194,19 +194,16 @@ MenuModel::MenuModel(message_center::MessageCenter* message_center,
message_center::MessageCenterTray* tray,
const std::string& notification_id,
const string16& display_source,
- const std::string& extension_id)
+ const message_center::NotifierId& notifier_id)
: ui::SimpleMenuModel(this),
message_center_(message_center),
tray_(tray),
- notification_id_(notification_id) {
+ notification_id_(notification_id),
+ notifier_id_(notifier_id) {
// Add 'disable notifications' menu item.
- if (!extension_id.empty() && !display_source.empty()) {
- AddItem(kToggleExtensionCommand,
- l10n_util::GetStringFUTF16(IDS_MESSAGE_CENTER_EXTENSIONS_DISABLE,
- display_source));
- } else if (!display_source.empty()) {
+ if (!display_source.empty()) {
AddItem(kTogglePermissionCommand,
- l10n_util::GetStringFUTF16(IDS_MESSAGE_CENTER_SITE_DISABLE,
+ l10n_util::GetStringFUTF16(IDS_MESSAGE_CENTER_NOTIFIER_DISABLE,
display_source));
}
// Add settings menu item.
@@ -236,18 +233,13 @@ bool MenuModel::GetAcceleratorForCommandId(int command_id,
void MenuModel::ExecuteCommand(int command_id, int event_flags) {
switch (command_id) {
- case kToggleExtensionCommand:
- message_center_->DisableNotificationsByExtension(notification_id_);
- break;
case kTogglePermissionCommand:
- message_center_->DisableNotificationsByUrl(notification_id_);
+ message_center_->DisableNotificationsByNotifier(notifier_id_);
break;
case kShowSettingsCommand:
// |tray_| may be NULL in tests.
if (tray_)
tray_->ShowNotifierSettingsBubble();
- else
- message_center_->ShowNotificationSettings(notification_id_);
break;
default:
NOTREACHED();
@@ -276,7 +268,7 @@ class MessageViewContextMenuController : public views::ContextMenuController {
MessageCenterTray* tray_; // Weak reference.
std::string notification_id_;
string16 display_source_;
- std::string extension_id_;
+ NotifierId notifier_id_;
};
MessageViewContextMenuController::MessageViewContextMenuController(
@@ -287,7 +279,7 @@ MessageViewContextMenuController::MessageViewContextMenuController(
tray_(tray),
notification_id_(notification.id()),
display_source_(notification.display_source()),
- extension_id_(notification.extension_id()) {
+ notifier_id_(notification.notifier_id()) {
}
MessageViewContextMenuController::~MessageViewContextMenuController() {
@@ -298,7 +290,7 @@ void MessageViewContextMenuController::ShowContextMenuForView(
const gfx::Point& point,
ui::MenuSourceType source_type) {
MenuModel menu_model(message_center_, tray_, notification_id_,
- display_source_, extension_id_);
+ display_source_, notifier_id_);
if (menu_model.GetItemCount() == 0)
return;
diff --git a/chromium/ui/message_center/views/notification_view.cc b/chromium/ui/message_center/views/notification_view.cc
index abfc1efe689..b6e8bcc8d4b 100644
--- a/chromium/ui/message_center/views/notification_view.cc
+++ b/chromium/ui/message_center/views/notification_view.cc
@@ -10,10 +10,10 @@
#include "grit/ui_resources.h"
#include "ui/base/layout.h"
#include "ui/base/resource/resource_bundle.h"
-#include "ui/base/text/text_elider.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/size.h"
#include "ui/gfx/skia_util.h"
+#include "ui/gfx/text_elider.h"
#include "ui/message_center/message_center.h"
#include "ui/message_center/message_center_style.h"
#include "ui/message_center/message_center_switches.h"
@@ -30,6 +30,10 @@
#include "ui/views/layout/fill_layout.h"
#include "ui/views/widget/widget.h"
+#if defined(USE_AURA)
+#include "ui/base/cursor/cursor.h"
+#endif
+
namespace {
// Dimensions.
@@ -53,12 +57,16 @@ const size_t kTitleCharacterLimit =
const size_t kMessageCharacterLimit =
message_center::kNotificationWidth *
message_center::kMessageExpandedLineLimit / 3;
+const size_t kContextMessageCharacterLimit =
+ message_center::kNotificationWidth *
+ message_center::kContextMessageLineLimit / 3;
// Notification colors. The text background colors below are used only to keep
// view::Label from modifying the text color and will not actually be drawn.
// See view::Label's RecalculateColors() for details.
const SkColor kRegularTextBackgroundColor = SK_ColorWHITE;
const SkColor kDimTextBackgroundColor = SK_ColorWHITE;
+const SkColor kContextTextBackgroundColor = SK_ColorWHITE;
// static
views::Background* MakeBackground(
@@ -462,13 +470,17 @@ NotificationView::NotificationView(const Notification& notification,
top_view_->set_border(MakeEmptyBorder(
kTextTopPadding - 8, 0, kTextBottomPadding - 5, 0));
+ const gfx::FontList default_label_font_list = views::Label().font_list();
+
// Create the title view if appropriate.
title_view_ = NULL;
if (!notification.title().empty()) {
- gfx::Font font = views::Label().font().DeriveFont(2);
- int padding = kTitleLineHeight - font.GetHeight();
+ const gfx::FontList& font_list =
+ default_label_font_list.DeriveFontListWithSizeDelta(2);
+ int padding = kTitleLineHeight - font_list.GetHeight();
title_view_ = new BoundedLabel(
- ui::TruncateString(notification.title(), kTitleCharacterLimit), font);
+ gfx::TruncateString(notification.title(), kTitleCharacterLimit),
+ font_list);
title_view_->SetLineHeight(kTitleLineHeight);
title_view_->SetLineLimit(message_center::kTitleLineLimit);
title_view_->SetColors(message_center::kRegularTextColor,
@@ -481,18 +493,36 @@ NotificationView::NotificationView(const Notification& notification,
// Create the message view if appropriate.
message_view_ = NULL;
if (!notification.message().empty()) {
- int padding = kMessageLineHeight - views::Label().font().GetHeight();
+ int padding = kMessageLineHeight - default_label_font_list.GetHeight();
message_view_ = new BoundedLabel(
- ui::TruncateString(notification.message(), kMessageCharacterLimit));
+ gfx::TruncateString(notification.message(), kMessageCharacterLimit));
message_view_->SetLineHeight(kMessageLineHeight);
message_view_->SetVisible(!is_expanded() || !notification.items().size());
- message_view_->SetColors(message_center::kDimTextColor,
+ message_view_->SetColors(message_center::kRegularTextColor,
kDimTextBackgroundColor);
message_view_->set_border(MakeTextBorder(padding, 4, 0));
top_view_->AddChildView(message_view_);
accessible_lines.push_back(notification.message());
}
+ // Create the context message view if appropriate.
+ context_message_view_ = NULL;
+ if (!notification.context_message().empty()) {
+ int padding = kMessageLineHeight - default_label_font_list.GetHeight();
+ context_message_view_ =
+ new BoundedLabel(gfx::TruncateString(notification.context_message(),
+ kContextMessageCharacterLimit),
+ default_label_font_list);
+ context_message_view_->SetLineLimit(
+ message_center::kContextMessageLineLimit);
+ context_message_view_->SetLineHeight(kMessageLineHeight);
+ context_message_view_->SetColors(message_center::kDimTextColor,
+ kContextTextBackgroundColor);
+ context_message_view_->set_border(MakeTextBorder(padding, 4, 0));
+ top_view_->AddChildView(context_message_view_);
+ accessible_lines.push_back(notification.context_message());
+ }
+
// Create the progress bar view.
progress_bar_view_ = NULL;
if (notification.type() == NOTIFICATION_TYPE_PROGRESS) {
@@ -504,7 +534,7 @@ NotificationView::NotificationView(const Notification& notification,
}
// Create the list item views (up to a maximum).
- int padding = kMessageLineHeight - views::Label().font().GetHeight();
+ int padding = kMessageLineHeight - default_label_font_list.GetHeight();
std::vector<NotificationItem> items = notification.items();
for (size_t i = 0; i < items.size() && i < kNotificationMaximumItems; ++i) {
ItemView* item_view = new ItemView(items[i]);
diff --git a/chromium/ui/message_center/views/notification_view.h b/chromium/ui/message_center/views/notification_view.h
index 622e2c3bd69..5479939da8c 100644
--- a/chromium/ui/message_center/views/notification_view.h
+++ b/chromium/ui/message_center/views/notification_view.h
@@ -71,6 +71,7 @@ class MESSAGE_CENTER_EXPORT NotificationView : public MessageView {
views::View* top_view_;
BoundedLabel* title_view_;
BoundedLabel* message_view_;
+ BoundedLabel* context_message_view_;
std::vector<views::View*> item_views_;
views::View* icon_view_;
views::View* bottom_view_;
diff --git a/chromium/ui/message_center/views/notifier_settings_view.cc b/chromium/ui/message_center/views/notifier_settings_view.cc
index b4e18846a2b..40982748637 100644
--- a/chromium/ui/message_center/views/notifier_settings_view.cc
+++ b/chromium/ui/message_center/views/notifier_settings_view.cc
@@ -13,10 +13,10 @@
#include "grit/ui_strings.h"
#include "skia/ext/image_operations.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/models/simple_menu_model.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image.h"
#include "ui/gfx/size.h"
@@ -419,7 +419,7 @@ void NotifierSettingsView::UpdateContentsView(
contents_title_view->AddChildView(top_label);
string16 notifier_group_text;
- if (provider_) {
+ if (provider_ && provider_->GetNotifierGroupCount() > 0) {
const NotifierGroup& active_group = provider_->GetActiveNotifierGroup();
notifier_group_text = active_group.login_info.empty()
? active_group.name
@@ -478,7 +478,6 @@ gfx::Size NotifierSettingsView::GetMinimumSize() {
gfx::Size NotifierSettingsView::GetPreferredSize() {
gfx::Size preferred_size;
- std::vector<gfx::Size> child_sizes;
gfx::Size title_size = title_label_->GetPreferredSize();
gfx::Size content_size = scroller_->contents()->GetPreferredSize();
return gfx::Size(std::max(title_size.width(), content_size.width()),
diff --git a/chromium/ui/message_center/views/toast_contents_view.cc b/chromium/ui/message_center/views/toast_contents_view.cc
index b7dae986a20..645c654701c 100644
--- a/chromium/ui/message_center/views/toast_contents_view.cc
+++ b/chromium/ui/message_center/views/toast_contents_view.cc
@@ -11,8 +11,8 @@
#include "base/time/time.h"
#include "base/timer/timer.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/animation_delegate.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/gfx/display.h"
#include "ui/gfx/screen.h"
#include "ui/message_center/message_center.h"
@@ -59,7 +59,7 @@ ToastContentsView::ToastContentsView(
// remains. This is hacky but easier to keep the consistency.
set_background(views::Background::CreateSolidBackground(0, 0, 0, 0));
- fade_animation_.reset(new ui::SlideAnimation(this));
+ fade_animation_.reset(new gfx::SlideAnimation(this));
fade_animation_->SetSlideDuration(kFadeInOutDuration);
}
@@ -91,8 +91,22 @@ void ToastContentsView::SetContents(MessageView* view) {
Layout();
// If it has the contents already, this invocation means an update of the
// popup toast, and the new contents should be read through a11y feature.
- if (already_has_contents)
- NotifyAccessibilityEvent(ui::AccessibilityTypes::EVENT_FOCUS, false);
+ // The notification type should be ALERT, otherwise the accessibility message
+ // won't be read for this view which returns ROLE_WINDOW.
+ if (already_has_contents) {
+ const NotificationList::Notifications& notifications =
+ message_center_->GetNotifications();
+ for (NotificationList::Notifications::const_iterator iter =
+ notifications.begin(); iter != notifications.end(); ++iter) {
+ if ((*iter)->id() != id_)
+ continue;
+
+ const RichNotificationData& optional = (*iter)->rich_notification_data();
+ if (optional.should_make_spoken_feedback_for_popup_updates)
+ NotifyAccessibilityEvent(ui::AccessibilityTypes::EVENT_ALERT, false);
+ break;
+ }
+ }
}
void ToastContentsView::RevealWithAnimation(gfx::Point origin) {
@@ -153,7 +167,7 @@ void ToastContentsView::SetBoundsWithAnimation(gfx::Rect new_bounds) {
if (bounds_animation_.get())
bounds_animation_->Stop();
- bounds_animation_.reset(new ui::SlideAnimation(this));
+ bounds_animation_.reset(new gfx::SlideAnimation(this));
bounds_animation_->Show();
}
@@ -181,7 +195,7 @@ void ToastContentsView::StartFadeOut() {
}
void ToastContentsView::OnBoundsAnimationEndedOrCancelled(
- const ui::Animation* animation) {
+ const gfx::Animation* animation) {
if (is_closing_ && closing_animation_ == animation && GetWidget()) {
views::Widget* widget = GetWidget();
#if defined(USE_AURA)
@@ -205,8 +219,8 @@ void ToastContentsView::OnBoundsAnimationEndedOrCancelled(
collection_->DecrementDeferCounter();
}
-// ui::AnimationDelegate
-void ToastContentsView::AnimationProgressed(const ui::Animation* animation) {
+// gfx::AnimationDelegate
+void ToastContentsView::AnimationProgressed(const gfx::Animation* animation) {
if (animation == bounds_animation_.get()) {
gfx::Rect current(animation->CurrentValueBetween(
animated_bounds_start_, animated_bounds_end_));
@@ -218,12 +232,12 @@ void ToastContentsView::AnimationProgressed(const ui::Animation* animation) {
}
}
-void ToastContentsView::AnimationEnded(const ui::Animation* animation) {
+void ToastContentsView::AnimationEnded(const gfx::Animation* animation) {
OnBoundsAnimationEndedOrCancelled(animation);
}
void ToastContentsView::AnimationCanceled(
- const ui::Animation* animation) {
+ const gfx::Animation* animation) {
OnBoundsAnimationEndedOrCancelled(animation);
}
diff --git a/chromium/ui/message_center/views/toast_contents_view.h b/chromium/ui/message_center/views/toast_contents_view.h
index 4f26c6acb0c..6b79ac1336e 100644
--- a/chromium/ui/message_center/views/toast_contents_view.h
+++ b/chromium/ui/message_center/views/toast_contents_view.h
@@ -7,14 +7,14 @@
#include "base/compiler_specific.h"
#include "base/memory/weak_ptr.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/size.h"
#include "ui/views/widget/widget_delegate.h"
-namespace ui {
+namespace gfx {
class Animation;
class SlideAnimation;
}
@@ -32,7 +32,7 @@ class Notification;
class ToastContentsView : public views::WidgetDelegateView,
- public ui::AnimationDelegate {
+ public gfx::AnimationDelegate {
public:
ToastContentsView(const Notification* notification,
base::WeakPtr<MessagePopupCollection> collection,
@@ -71,10 +71,10 @@ class ToastContentsView : public views::WidgetDelegateView,
virtual void GetAccessibleState(ui::AccessibleViewState* state) OVERRIDE;
private:
- // Overridden from ui::AnimationDelegate:
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationCanceled(const ui::Animation* animation) OVERRIDE;
+ // Overridden from gfx::AnimationDelegate:
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationCanceled(const gfx::Animation* animation) OVERRIDE;
// Overridden from views::WidgetDelegate:
virtual views::View* GetContentsView() OVERRIDE;
@@ -90,7 +90,7 @@ class ToastContentsView : public views::WidgetDelegateView,
void StartFadeIn();
void StartFadeOut(); // Will call Widget::Close() when animation ends.
- void OnBoundsAnimationEndedOrCancelled(const ui::Animation* animation);
+ void OnBoundsAnimationEndedOrCancelled(const gfx::Animation* animation);
base::WeakPtr<MessagePopupCollection> collection_;
MessageCenter* message_center_;
@@ -98,8 +98,8 @@ class ToastContentsView : public views::WidgetDelegateView,
// Id if the corresponding Notification.
std::string id_;
- scoped_ptr<ui::SlideAnimation> bounds_animation_;
- scoped_ptr<ui::SlideAnimation> fade_animation_;
+ scoped_ptr<gfx::SlideAnimation> bounds_animation_;
+ scoped_ptr<gfx::SlideAnimation> fade_animation_;
bool is_animating_bounds_;
gfx::Rect animated_bounds_start_;
@@ -108,7 +108,7 @@ class ToastContentsView : public views::WidgetDelegateView,
bool is_closing_;
// Closing animation - when it ends, close the widget. Weak, only used
// for referential equality.
- ui::Animation* closing_animation_;
+ gfx::Animation* closing_animation_;
gfx::Point origin_;
gfx::Size preferred_size_;
diff --git a/chromium/ui/metro_viewer/metro_viewer_messages.h b/chromium/ui/metro_viewer/metro_viewer_messages.h
index 9108620653d..7d0bd14f368 100644
--- a/chromium/ui/metro_viewer/metro_viewer_messages.h
+++ b/chromium/ui/metro_viewer/metro_viewer_messages.h
@@ -8,7 +8,7 @@
#include "base/basictypes.h"
#include "ipc/ipc_message_macros.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/native_widget_types.h"
#define IPC_MESSAGE_START MetroViewerMsgStart
@@ -92,6 +92,11 @@ IPC_MESSAGE_CONTROL2(MetroViewerHostMsg_SelectFolderDone,
// Messages sent from the browser to the viewer:
+// Requests the viewer to open a URL in desktop mode.
+IPC_MESSAGE_CONTROL2(MetroViewerHostMsg_OpenURLOnDesktop,
+ base::FilePath, /* shortcut */
+ string16 /* url */);
+
// Requests the viewer to change the pointer to a new cursor.
IPC_MESSAGE_CONTROL1(MetroViewerHostMsg_SetCursor,
int64 /* cursor */);
@@ -132,11 +137,6 @@ IPC_MESSAGE_CONTROL4(MetroViewerHostMsg_DisplayFileOpen,
IPC_MESSAGE_CONTROL1(MetroViewerHostMsg_DisplaySelectFolder,
string16) /* title */
-// Informs the browser about the viewer activation state, i.e. active, lost
-// activation etc.
-IPC_MESSAGE_CONTROL1(MetroViewerHostMsg_WindowActivated,
- bool) /* active */
-
// Sent to the viewer process to set the cursor position.
IPC_MESSAGE_CONTROL2(MetroViewerHostMsg_SetCursorPos,
int, /* x */
diff --git a/chromium/ui/native_theme/common_theme.cc b/chromium/ui/native_theme/common_theme.cc
index b589c000b82..8c5a964e312 100644
--- a/chromium/ui/native_theme/common_theme.cc
+++ b/chromium/ui/native_theme/common_theme.cc
@@ -21,8 +21,7 @@ namespace {
// MenuItem:
const SkColor kMenuBackgroundColor = SK_ColorWHITE;
-const SkColor kMenuHighlightBackgroundColor = SkColorSetARGB(15, 0, 0, 0);
-const SkColor kMenuHighlightBackgroundColor2 = SkColorSetRGB(0x42, 0x81, 0xF4);
+const SkColor kMenuHighlightBackgroundColor = SkColorSetRGB(0x42, 0x81, 0xF4);
const SkColor kMenuInvertedSchemeHighlightBackgroundColor =
SkColorSetRGB(48, 48, 48);
const SkColor kMenuBorderColor = SkColorSetRGB(0xBA, 0xBA, 0xBA);
@@ -73,7 +72,7 @@ bool CommonThemeGetSystemColor(NativeTheme::ColorId color_id, SkColor* color) {
*color = kDisabledMenuItemForegroundColor;
break;
case NativeTheme::kColorId_SelectedMenuItemForegroundColor:
- *color = kEnabledMenuItemForegroundColor;
+ *color = SK_ColorWHITE;
break;
case NativeTheme::kColorId_ButtonDisabledColor:
*color = kDisabledMenuItemForegroundColor;
@@ -82,8 +81,6 @@ bool CommonThemeGetSystemColor(NativeTheme::ColorId color_id, SkColor* color) {
return false;
}
- *color = AdjustColorForMenuVariations(color_id, *color);
-
if (gfx::IsInvertedColorScheme()) {
switch (color_id) {
case NativeTheme::kColorId_FocusedMenuItemBackgroundColor:
@@ -168,19 +165,4 @@ void CommonThemePaintMenuItemBackground(SkCanvas* canvas,
canvas->drawRect(gfx::RectToSkRect(rect), paint);
}
-SkColor AdjustColorForMenuVariations(NativeTheme::ColorId color_id,
- SkColor color) {
- if (NativeTheme::GetMenuVariation() != NativeTheme::MENU_VARIATION_CONTRAST)
- return color;
-
- switch(color_id) {
- case NativeTheme::kColorId_FocusedMenuItemBackgroundColor:
- return kMenuHighlightBackgroundColor2;
- case NativeTheme::kColorId_SelectedMenuItemForegroundColor:
- return SK_ColorWHITE;
- default:
- return color;
- }
-}
-
} // namespace ui
diff --git a/chromium/ui/native_theme/common_theme.h b/chromium/ui/native_theme/common_theme.h
index 530032f8390..c91f4899c82 100644
--- a/chromium/ui/native_theme/common_theme.h
+++ b/chromium/ui/native_theme/common_theme.h
@@ -39,13 +39,6 @@ void NATIVE_THEME_EXPORT CommonThemePaintMenuItemBackground(
NativeTheme::State state,
const gfx::Rect& rect);
-// Adjust some colors for menu Finch experiments.
-// |color_id| id of a color to be adjusted.
-// |color| color before adjustment.
-// Returns adjusted color.
-SkColor AdjustColorForMenuVariations(NativeTheme::ColorId color_id,
- SkColor color);
-
} // namespace ui
#endif // UI_NATIVE_THEME_COMMON_THEME_H_
diff --git a/chromium/ui/native_theme/native_theme.cc b/chromium/ui/native_theme/native_theme.cc
index af44a7f9eb2..8cb845cc306 100644
--- a/chromium/ui/native_theme/native_theme.cc
+++ b/chromium/ui/native_theme/native_theme.cc
@@ -4,16 +4,6 @@
#include "ui/native_theme/native_theme.h"
-#include "base/command_line.h"
-#include "base/metrics/field_trial.h"
-
-
-// Constants for the new menu style field trial.
-const char kMenuVariationFieldTrialName[] = "NewMenuStyle";
-const char kMenuVariationFieldTrialGroupNameCompact1[] = "Compact1";
-const char kMenuVariationFieldTrialGroupNameCompact2[] = "Compact2";
-const char kMenuVariationFieldTrialGroupNameHigherContrast[] = "HigherContrast";
-
namespace ui {
void NativeTheme::SetScrollbarColors(unsigned inactive_color,
@@ -27,20 +17,6 @@ void NativeTheme::SetScrollbarColors(unsigned inactive_color,
// NativeTheme::instance() is implemented in the platform specific source files,
// such as native_theme_win.cc or native_theme_linux.cc
-// static
-NativeTheme::MenuVariation NativeTheme::GetMenuVariation() {
- std::string trial_group_name =
- base::FieldTrialList::FindFullName(kMenuVariationFieldTrialName);
- if (trial_group_name == kMenuVariationFieldTrialGroupNameCompact1)
- return MENU_VARIATION_COMPACT_1;
- if (trial_group_name == kMenuVariationFieldTrialGroupNameCompact2)
- return MENU_VARIATION_COMPACT_2;
- if (trial_group_name == kMenuVariationFieldTrialGroupNameHigherContrast)
- return MENU_VARIATION_CONTRAST;
-
- return MENU_VARIATION_NORMAL;
-}
-
NativeTheme::NativeTheme()
: thumb_inactive_color_(0xeaeaea),
thumb_active_color_(0xf4f4f4),
diff --git a/chromium/ui/native_theme/native_theme.h b/chromium/ui/native_theme/native_theme.h
index 30379169e37..98974145570 100644
--- a/chromium/ui/native_theme/native_theme.h
+++ b/chromium/ui/native_theme/native_theme.h
@@ -85,13 +85,6 @@ class NATIVE_THEME_EXPORT NativeTheme {
kMaxState,
};
- enum MenuVariation {
- MENU_VARIATION_NORMAL,
- MENU_VARIATION_COMPACT_1,
- MENU_VARIATION_COMPACT_2,
- MENU_VARIATION_CONTRAST
- };
-
// Each structure below holds extra information needed when painting a given
// part.
@@ -296,8 +289,6 @@ class NATIVE_THEME_EXPORT NativeTheme {
// function, returning the port's subclass.
static NativeTheme* instance();
- static MenuVariation GetMenuVariation();
-
protected:
NativeTheme();
virtual ~NativeTheme();
diff --git a/chromium/ui/native_theme/native_theme_win.cc b/chromium/ui/native_theme/native_theme_win.cc
index 1839de32263..74b4f14a261 100644
--- a/chromium/ui/native_theme/native_theme_win.cc
+++ b/chromium/ui/native_theme/native_theme_win.cc
@@ -23,12 +23,12 @@
#include "third_party/skia/include/core/SkCanvas.h"
#include "third_party/skia/include/core/SkColorPriv.h"
#include "third_party/skia/include/core/SkShader.h"
-#include "ui/base/win/dpi.h"
#include "ui/gfx/color_utils.h"
#include "ui/gfx/gdi_util.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/rect_conversions.h"
#include "ui/gfx/sys_color_change_listener.h"
+#include "ui/gfx/win/dpi.h"
#include "ui/native_theme/common_theme.h"
// This was removed from Winvers.h but is still used.
@@ -243,7 +243,7 @@ gfx::Size NativeThemeWin::GetPartSize(Part part,
case kScrollbarVerticalThumb:
case kScrollbarHorizontalTrack:
case kScrollbarVerticalTrack:
- size.cx = size.cy = ui::win::GetSystemMetricsInDIP(SM_CXVSCROLL);
+ size.cx = size.cy = gfx::win::GetSystemMetricsInDIP(SM_CXVSCROLL);
return gfx::Size(size.cx, size.cy);
}
diff --git a/chromium/ui/resources/default_100_percent/common/drag_tip_copy.png b/chromium/ui/resources/default_100_percent/common/drag_tip_copy.png
new file mode 100644
index 00000000000..349c7c6d9d3
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/drag_tip_copy.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/drag_tip_link.png b/chromium/ui/resources/default_100_percent/common/drag_tip_link.png
new file mode 100644
index 00000000000..8f61a39dd20
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/drag_tip_link.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/drag_tip_move.png b/chromium/ui/resources/default_100_percent/common/drag_tip_move.png
new file mode 100644
index 00000000000..a897ef4799a
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/drag_tip_move.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/drag_tip_nodrop.png b/chromium/ui/resources/default_100_percent/common/drag_tip_nodrop.png
new file mode 100644
index 00000000000..917cb5f1922
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/drag_tip_nodrop.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/notification_clear_all_disabled.png b/chromium/ui/resources/default_100_percent/common/notification_clear_all_disabled.png
index a15a261e027..1aa1857e0e9 100644
--- a/chromium/ui/resources/default_100_percent/common/notification_clear_all_disabled.png
+++ b/chromium/ui/resources/default_100_percent/common/notification_clear_all_disabled.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/alias_big.png b/chromium/ui/resources/default_100_percent/common/pointers/alias_big.png
new file mode 100644
index 00000000000..283bf7f48fe
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/alias_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/cell_big.png b/chromium/ui/resources/default_100_percent/common/pointers/cell_big.png
new file mode 100644
index 00000000000..3dec5e5d825
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/cell_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/context_menu_big.png b/chromium/ui/resources/default_100_percent/common/pointers/context_menu_big.png
new file mode 100644
index 00000000000..7c9e250d488
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/context_menu_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/copy_big.png b/chromium/ui/resources/default_100_percent/common/pointers/copy_big.png
new file mode 100644
index 00000000000..18f4696ffc2
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/copy_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/crosshair_big.png b/chromium/ui/resources/default_100_percent/common/pointers/crosshair_big.png
new file mode 100644
index 00000000000..ea1f5fc07ff
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/crosshair_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/fleur_big.png b/chromium/ui/resources/default_100_percent/common/pointers/fleur_big.png
new file mode 100644
index 00000000000..2e327661d68
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/fleur_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/hand2_big.png b/chromium/ui/resources/default_100_percent/common/pointers/hand2_big.png
new file mode 100644
index 00000000000..785047f7cdf
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/hand2_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/hand3_big.png b/chromium/ui/resources/default_100_percent/common/pointers/hand3_big.png
new file mode 100644
index 00000000000..3c547517392
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/hand3_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/help_big.png b/chromium/ui/resources/default_100_percent/common/pointers/help_big.png
new file mode 100644
index 00000000000..6552f9bb333
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/help_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/left_ptr_big.png b/chromium/ui/resources/default_100_percent/common/pointers/left_ptr_big.png
new file mode 100644
index 00000000000..c5604c74915
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/left_ptr_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/move_big.png b/chromium/ui/resources/default_100_percent/common/pointers/move_big.png
new file mode 100644
index 00000000000..c29db870273
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/move_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/nodrop_big.png b/chromium/ui/resources/default_100_percent/common/pointers/nodrop_big.png
new file mode 100644
index 00000000000..da981df3de2
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/nodrop_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/sb_h_double_arrow_big.png b/chromium/ui/resources/default_100_percent/common/pointers/sb_h_double_arrow_big.png
new file mode 100644
index 00000000000..49dc3d303bf
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/sb_h_double_arrow_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/sb_v_double_arrow_big.png b/chromium/ui/resources/default_100_percent/common/pointers/sb_v_double_arrow_big.png
new file mode 100644
index 00000000000..fd777b14bad
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/sb_v_double_arrow_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/top_left_corner_big.png b/chromium/ui/resources/default_100_percent/common/pointers/top_left_corner_big.png
new file mode 100644
index 00000000000..eecaa89204e
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/top_left_corner_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/top_right_corner_big.png b/chromium/ui/resources/default_100_percent/common/pointers/top_right_corner_big.png
new file mode 100644
index 00000000000..9d47ecf793e
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/top_right_corner_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/xterm_big.png b/chromium/ui/resources/default_100_percent/common/pointers/xterm_big.png
new file mode 100644
index 00000000000..2fba190552b
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/xterm_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/xterm_horiz_big.png b/chromium/ui/resources/default_100_percent/common/pointers/xterm_horiz_big.png
new file mode 100644
index 00000000000..94f5ddc59ac
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/xterm_horiz_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/zoom_in_big.png b/chromium/ui/resources/default_100_percent/common/pointers/zoom_in_big.png
new file mode 100644
index 00000000000..923ad792264
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/zoom_in_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/common/pointers/zoom_out_big.png b/chromium/ui/resources/default_100_percent/common/pointers/zoom_out_big.png
new file mode 100644
index 00000000000..aa47eb94fbc
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/common/pointers/zoom_out_big.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_attention.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_attention.png
index 6e4910943cb..f6fe8298b61 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_attention.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_attention.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_attention_pressed.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_attention_pressed.png
index 931a4abcaf2..e4f8cdb5dd9 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_attention_pressed.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_attention_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention.png
index 335a302712c..042673f535c 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention_pressed.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention_pressed.png
index 7ab9ee0b751..95a681ad4e8 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention_pressed.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_attention_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty.png
index 3c9149e6f12..84330824e72 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty_pressed.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty_pressed.png
index 87acf99e3d5..e0f7f234e52 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty_pressed.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_do_not_disturb_empty_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_empty.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_empty.png
index db17be92556..53ad499d459 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_empty.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_empty.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/mac/notification_tray_empty_pressed.png b/chromium/ui/resources/default_100_percent/mac/notification_tray_empty_pressed.png
index 2f3d8fca7c1..15d30bf68f6 100644
--- a/chromium/ui/resources/default_100_percent/mac/notification_tray_empty_pressed.png
+++ b/chromium/ui/resources/default_100_percent/mac/notification_tray_empty_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_100_percent/win/app_list_user_indicator.png b/chromium/ui/resources/default_100_percent/win/app_list_user_indicator.png
new file mode 100644
index 00000000000..77f58588790
--- /dev/null
+++ b/chromium/ui/resources/default_100_percent/win/app_list_user_indicator.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/common/drag_tip_copy.png b/chromium/ui/resources/default_200_percent/common/drag_tip_copy.png
new file mode 100644
index 00000000000..0c2d609f2ca
--- /dev/null
+++ b/chromium/ui/resources/default_200_percent/common/drag_tip_copy.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/common/drag_tip_link.png b/chromium/ui/resources/default_200_percent/common/drag_tip_link.png
new file mode 100644
index 00000000000..fe0fd25d144
--- /dev/null
+++ b/chromium/ui/resources/default_200_percent/common/drag_tip_link.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/common/drag_tip_move.png b/chromium/ui/resources/default_200_percent/common/drag_tip_move.png
new file mode 100644
index 00000000000..e2374ece106
--- /dev/null
+++ b/chromium/ui/resources/default_200_percent/common/drag_tip_move.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/common/drag_tip_nodrop.png b/chromium/ui/resources/default_200_percent/common/drag_tip_nodrop.png
new file mode 100644
index 00000000000..e735e422ef8
--- /dev/null
+++ b/chromium/ui/resources/default_200_percent/common/drag_tip_nodrop.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_attention.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_attention.png
index 6587f34bb8e..c0b374bd17a 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_attention.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_attention.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_attention_pressed.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_attention_pressed.png
index 7d2521c790b..5e12a8fe568 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_attention_pressed.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_attention_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention.png
index f0584e43351..804beb6f289 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention_pressed.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention_pressed.png
index 8f922347de3..e8e1e2454e9 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention_pressed.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_attention_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty.png
index 2370e7acdec..0d2e894db45 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty_pressed.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty_pressed.png
index 1c6a7af60e7..7376b2f2127 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty_pressed.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_do_not_disturb_empty_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_empty.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_empty.png
index e3fc1f3bfbe..f840d93a70e 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_empty.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_empty.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/mac/notification_tray_empty_pressed.png b/chromium/ui/resources/default_200_percent/mac/notification_tray_empty_pressed.png
index 21492e85dcf..f6f24b70f29 100644
--- a/chromium/ui/resources/default_200_percent/mac/notification_tray_empty_pressed.png
+++ b/chromium/ui/resources/default_200_percent/mac/notification_tray_empty_pressed.png
Binary files differ
diff --git a/chromium/ui/resources/default_200_percent/win/app_list_user_indicator.png b/chromium/ui/resources/default_200_percent/win/app_list_user_indicator.png
new file mode 100644
index 00000000000..9fb3a484c00
--- /dev/null
+++ b/chromium/ui/resources/default_200_percent/win/app_list_user_indicator.png
Binary files differ
diff --git a/chromium/ui/resources/resource_check/resource_scale_factors.py b/chromium/ui/resources/resource_check/resource_scale_factors.py
index f974447ccf2..9ddc70fda60 100644
--- a/chromium/ui/resources/resource_check/resource_scale_factors.py
+++ b/chromium/ui/resources/resource_check/resource_scale_factors.py
@@ -15,6 +15,10 @@ import os
import struct
+class InvalidPNGException(Exception):
+ pass
+
+
class ResourceScaleFactors(object):
"""Verifier of image dimensions for Chromium resources.
@@ -44,7 +48,8 @@ class ResourceScaleFactors(object):
def ImageSize(filename):
with open(filename, 'rb', buffering=0) as f:
data = f.read(24)
- assert data[:8] == '\x89PNG\r\n\x1A\n' and data[12:16] == 'IHDR'
+ if data[:8] != '\x89PNG\r\n\x1A\n' or data[12:16] != 'IHDR':
+ raise InvalidPNGException
return struct.unpack('>ii', data[16:24])
# Returns a list of valid scaled image sizes. The valid sizes are the
@@ -75,6 +80,9 @@ class ResourceScaleFactors(object):
if relative_path not in files:
files.append(relative_path)
+ corrupt_png_error = ('Corrupt PNG in file %s. Note that binaries are not '
+ 'correctly uploaded to the code review tool and must be directly '
+ 'submitted using the dcommit command.')
for f in files:
base_image = self.input_api.os_path.join(self.paths[0][1], f)
if not os.path.exists(base_image):
@@ -82,7 +90,12 @@ class ResourceScaleFactors(object):
'Base image %s does not exist' % self.input_api.os_path.join(
repository_path, base_image)))
continue
- base_dimensions = ImageSize(base_image)
+ try:
+ base_dimensions = ImageSize(base_image)
+ except InvalidPNGException:
+ results.append(self.output_api.PresubmitError(corrupt_png_error %
+ self.input_api.os_path.join(repository_path, base_image)))
+ continue
# Find all scaled versions of the base image and verify their sizes.
for i in range(1, len(self.paths)):
image_path = self.input_api.os_path.join(self.paths[i][1], f)
@@ -90,7 +103,12 @@ class ResourceScaleFactors(object):
continue
# Ensure that each image for a particular scale factor is the
# correct scale of the base image.
- scaled_dimensions = ImageSize(image_path)
+ try:
+ scaled_dimensions = ImageSize(image_path)
+ except InvalidPNGException:
+ results.append(self.output_api.PresubmitError(corrupt_png_error %
+ self.input_api.os_path.join(repository_path, image_path)))
+ continue
for dimension_name, base_size, scaled_size in zip(
('width', 'height'), base_dimensions, scaled_dimensions):
valid_sizes = ValidSizes(base_size, self.paths[i][0])
diff --git a/chromium/ui/resources/ui_resources.grd b/chromium/ui/resources/ui_resources.grd
index 067e2eaa925..06043de76f3 100644
--- a/chromium/ui/resources/ui_resources.grd
+++ b/chromium/ui/resources/ui_resources.grd
@@ -25,10 +25,12 @@
<structure type="chrome_scaled_image" name="IDR_APP_LIST_ITEM_PROGRESS_LEFT" file="common/app_list_progress_bar_left.png" />
<structure type="chrome_scaled_image" name="IDR_APP_LIST_ITEM_PROGRESS_CENTER" file="common/app_list_progress_bar_center.png" />
<structure type="chrome_scaled_image" name="IDR_APP_LIST_ITEM_PROGRESS_RIGHT" file="common/app_list_progress_bar_right.png" />
- <structure type="chrome_scaled_image" name="IDR_APP_LIST_USER_INDICATOR" file="common/app_list_user_indicator.png" />
<structure type="chrome_scaled_image" name="IDR_APP_LIST_TOOLS_HOVER" file="common/app_list_tools_hover.png" />
<structure type="chrome_scaled_image" name="IDR_APP_LIST_TOOLS_NORMAL" file="common/app_list_tools_normal.png" />
<structure type="chrome_scaled_image" name="IDR_APP_LIST_TOOLS_PRESSED" file="common/app_list_tools_pressed.png" />
+ <if expr="is_win">
+ <structure type="chrome_scaled_image" name="IDR_APP_LIST_USER_INDICATOR" file="win/app_list_user_indicator.png" />
+ </if>
</if>
<structure type="chrome_scaled_image" name="IDR_APP_TOP_CENTER" file="app_top_center.png" />
<if expr="pp_ifdef('toolkit_views')">
@@ -36,6 +38,37 @@
<structure type="chrome_scaled_image" name="IDR_APP_TOP_RIGHT" file="app_top_right.png" />
</if>
<if expr="is_linux and pp_ifdef('use_aura')">
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_ALIAS" file="common/pointers/alias_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_CELL" file="common/pointers/cell_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_COL_RESIZE" file="common/pointers/sb_h_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_CONTEXT_MENU" file="common/pointers/context_menu_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_COPY" file="common/pointers/copy_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_CROSSHAIR" file="common/pointers/crosshair_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_EAST_RESIZE" file="common/pointers/sb_h_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_EAST_WEST_RESIZE" file="common/pointers/sb_h_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_FLEUR" file="common/pointers/fleur_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_HAND" file="common/pointers/hand2_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_HELP" file="common/pointers/help_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_IBEAM" file="common/pointers/xterm_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_MOVE" file="common/pointers/move_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NORTH_EAST_RESIZE" file="common/pointers/top_right_corner_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NORTH_EAST_SOUTH_WEST_RESIZE" file="common/pointers/top_right_corner_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NORTH_RESIZE" file="common/pointers/sb_v_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NORTH_SOUTH_RESIZE" file="common/pointers/sb_v_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NORTH_WEST_RESIZE" file="common/pointers/top_left_corner_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NORTH_WEST_SOUTH_EAST_RESIZE" file="common/pointers/top_left_corner_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_NO_DROP" file="common/pointers/nodrop_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_PTR" file="common/pointers/left_ptr_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_ROW_RESIZE" file="common/pointers/sb_v_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_SOUTH_EAST_RESIZE" file="common/pointers/top_left_corner_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_SOUTH_RESIZE" file="common/pointers/sb_v_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_SOUTH_WEST_RESIZE" file="common/pointers/top_right_corner_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_WEST_RESIZE" file="common/pointers/sb_h_double_arrow_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_XTERM_HORIZ" file="common/pointers/xterm_horiz_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_ZOOM_IN" file="common/pointers/zoom_in_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_ZOOM_OUT" file="common/pointers/zoom_out_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_GRAB" file="common/pointers/fleur_big.png" />
+ <structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_BIG_GRABBING" file="common/pointers/hand3_big.png" />
<structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_ALIAS" file="common/pointers/alias.png" />
<structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_CELL" file="common/pointers/cell.png" />
<structure type="chrome_scaled_image" name="IDR_AURA_CURSOR_COL_RESIZE" file="common/pointers/sb_h_double_arrow.png" />
@@ -154,10 +187,10 @@
<structure type="chrome_scaled_image" name="IDR_RADIO_HOVER" file="common/radio_hover.png" />
<structure type="chrome_scaled_image" name="IDR_RADIO_PRESSED" file="common/radio_pressed.png" />
<structure type="chrome_scaled_image" name="IDR_TEXT_SELECTION_HANDLE" file="common/text_selection_handle_small.png" />
- <if expr="not pp_ifdef('toolkit_views') and is_posix and not is_macosx">
+ <if expr="pp_ifdef('desktop_linux')">
<structure type="chrome_scaled_image" name="IDR_CLOSE" file="linux/linux_close.png" />
</if>
- <if expr="pp_ifdef('toolkit_views')">
+ <if expr="not pp_ifdef('desktop_linux') and pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_CLOSE" file="close.png" />
</if>
<structure type="chrome_scaled_image" name="IDR_CLOSE_2" file="close_2.png" />
@@ -167,13 +200,15 @@
<structure type="chrome_scaled_image" name="IDR_CLOSE_DIALOG" file="close_dialog.png" />
<structure type="chrome_scaled_image" name="IDR_CLOSE_DIALOG_H" file="close_dialog_hover.png" />
<structure type="chrome_scaled_image" name="IDR_CLOSE_DIALOG_P" file="close_dialog_pressed.png" />
- <if expr="not pp_ifdef('toolkit_views') and is_posix and not is_macosx">
+ <if expr="pp_ifdef('desktop_linux')">
<structure type="chrome_scaled_image" name="IDR_CLOSE_H" file="linux/linux_close_hover.png" />
<structure type="chrome_scaled_image" name="IDR_CLOSE_P" file="linux/linux_close_pressed.png" />
</if>
- <if expr="pp_ifdef('toolkit_views')">
+ <if expr="not pp_ifdef('desktop_linux') and pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_CLOSE_H" file="close_hover.png" />
<structure type="chrome_scaled_image" name="IDR_CLOSE_P" file="close_pressed.png" />
+ </if>
+ <if expr="pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_CLOSE_SA" file="close_sa.png" />
<structure type="chrome_scaled_image" name="IDR_CLOSE_SA_H" file="close_sa_hover.png" />
<structure type="chrome_scaled_image" name="IDR_CLOSE_SA_P" file="close_sa_pressed.png" />
@@ -193,18 +228,20 @@
<structure type="chrome_scaled_image" name="IDR_FRAME" file="frame_default.png" />
<structure type="chrome_scaled_image" name="IDR_FRAME_APP_PANEL" file="frame_app_panel_default.png" />
<structure type="chrome_scaled_image" name="IDR_FRAME_INACTIVE" file="frame_default_inactive.png" />
- <if expr="not pp_ifdef('toolkit_views') and is_posix and not is_macosx">
+ <if expr="pp_ifdef('desktop_linux')">
<structure type="chrome_scaled_image" name="IDR_MAXIMIZE" file="linux/linux_maximize.png" />
<structure type="chrome_scaled_image" name="IDR_MAXIMIZE_H" file="linux/linux_maximize_hover.png" />
<structure type="chrome_scaled_image" name="IDR_MAXIMIZE_P" file="linux/linux_maximize_pressed.png" />
</if>
- <if expr="pp_ifdef('toolkit_views')">
+ <if expr="not pp_ifdef('desktop_linux') and pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_MAXIMIZE" file="maximize.png" />
<structure type="chrome_scaled_image" name="IDR_MAXIMIZE_H" file="maximize_hover.png" />
<structure type="chrome_scaled_image" name="IDR_MAXIMIZE_P" file="maximize_pressed.png" />
+ </if>
+ <if expr="pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_MENU_HIERARCHY_ARROW" file="common/menu_hierarchy_arrow.png" />
</if>
- <if expr="is_macosx">
+ <if expr="is_macosx or is_ios">
<structure type="chrome_scaled_image" name="IDR_MENU_HIERARCHY_ARROW" file="mac/menu_hierarchy_arrow.png" />
</if>
<if expr="pp_ifdef('toolkit_views')">
@@ -226,12 +263,12 @@
</if>
<structure type="chrome_scaled_image" name="IDR_MENU_DROPARROW" file="cros/menu_droparrow.png" />
<structure type="chrome_scaled_image" name="IDR_MESSAGE_CLOSE" file="common/message_close.png" />
- <if expr="not pp_ifdef('toolkit_views') and is_posix and not is_macosx">
+ <if expr="pp_ifdef('desktop_linux')">
<structure type="chrome_scaled_image" name="IDR_MINIMIZE" file="linux/linux_minimize.png" />
<structure type="chrome_scaled_image" name="IDR_MINIMIZE_H" file="linux/linux_minimize_hover.png" />
<structure type="chrome_scaled_image" name="IDR_MINIMIZE_P" file="linux/linux_minimize_pressed.png" />
</if>
- <if expr="pp_ifdef('toolkit_views')">
+ <if expr="not pp_ifdef('desktop_linux') and pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_MINIMIZE" file="minimize.png" />
<structure type="chrome_scaled_image" name="IDR_MINIMIZE_H" file="minimize_hover.png" />
<structure type="chrome_scaled_image" name="IDR_MINIMIZE_P" file="minimize_pressed.png" />
@@ -272,7 +309,7 @@
<structure type="chrome_scaled_image" name="IDR_PANEL_TOP_RIGHT_CORNER" file="panel_top_right_corner.png" />
<structure type="chrome_scaled_image" name="IDR_PANEL_BOTTOM_LEFT_CORNER" file="panel_bottom_left_corner.png" />
<structure type="chrome_scaled_image" name="IDR_PANEL_BOTTOM_RIGHT_CORNER" file="panel_bottom_right_corner.png" />
- <if expr="is_posix and not is_macosx and not pp_ifdef('use_aura')">
+ <if expr="is_posix and not is_macosx and not is_ios and not pp_ifdef('use_aura')">
<structure type="chrome_scaled_image" name="IDR_PROGRESS_BAR" file="linux/linux-progress-bar.png" />
<structure type="chrome_scaled_image" name="IDR_PROGRESS_BORDER_LEFT" file="linux/linux-progress-border-left.png" />
<structure type="chrome_scaled_image" name="IDR_PROGRESS_BORDER_RIGHT" file="linux/linux-progress-border-right.png" />
@@ -309,12 +346,12 @@
<structure type="chrome_scaled_image" name="IDR_SCROLL_THUMB_VERTICAL_TOP_H" file="cros/aura_scrollbar_thumb_vertical_hover_top.png" />
<structure type="chrome_scaled_image" name="IDR_SCROLL_THUMB_VERTICAL_TOP_P" file="cros/aura_scrollbar_thumb_vertical_pressed_top.png" />
</if>
- <if expr="not pp_ifdef('toolkit_views') and is_posix and not is_macosx">
+ <if expr="pp_ifdef('desktop_linux')">
<structure type="chrome_scaled_image" name="IDR_RESTORE" file="linux/linux_restore.png" />
<structure type="chrome_scaled_image" name="IDR_RESTORE_H" file="linux/linux_restore_hover.png" />
<structure type="chrome_scaled_image" name="IDR_RESTORE_P" file="linux/linux_restore_pressed.png" />
</if>
- <if expr="pp_ifdef('toolkit_views')">
+ <if expr="not pp_ifdef('desktop_linux') and pp_ifdef('toolkit_views')">
<structure type="chrome_scaled_image" name="IDR_RESTORE" file="restore.png" />
<structure type="chrome_scaled_image" name="IDR_RESTORE_H" file="restore_hover.png" />
<structure type="chrome_scaled_image" name="IDR_RESTORE_P" file="restore_pressed.png" />
@@ -338,7 +375,7 @@
<structure type="chrome_scaled_image" name="IDR_TEXTBUTTON_PRESSED_TOP_LEFT" file="common/textbutton_pressed_top_left.png" />
<structure type="chrome_scaled_image" name="IDR_TEXTBUTTON_PRESSED_TOP_RIGHT" file="common/textbutton_pressed_top_right.png" />
<structure type="chrome_scaled_image" name="IDR_THROBBER" file="throbber.png" />
- <if expr="is_macosx">
+ <if expr="is_macosx or is_ios">
<structure type="chrome_scaled_image" name="IDR_TRAY_ATTENTION" file="mac/notification_tray_attention.png"/>
<structure type="chrome_scaled_image" name="IDR_TRAY_ATTENTION_PRESSED" file="mac/notification_tray_attention_pressed.png"/>
<structure type="chrome_scaled_image" name="IDR_TRAY_DO_NOT_DISTURB_ATTENTION" file="mac/notification_tray_do_not_disturb_attention.png"/>
diff --git a/chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.cc b/chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.cc
deleted file mode 100644
index d62392ab478..00000000000
--- a/chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.cc
+++ /dev/null
@@ -1,24 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/shell_dialogs/android/shell_dialogs_jni_registrar.h"
-
-#include "base/android/jni_android.h"
-#include "base/android/jni_registrar.h"
-#include "ui/shell_dialogs/select_file_dialog_android.h"
-
-namespace ui {
-namespace shell_dialogs {
-
-static base::android::RegistrationMethod kUiRegisteredMethods[] = {
- { "SelectFileDialog", ui::SelectFileDialogImpl::RegisterSelectFileDialog },
-};
-
-bool RegisterJni(JNIEnv* env) {
- return RegisterNativeMethods(env, kUiRegisteredMethods,
- arraysize(kUiRegisteredMethods));
-}
-
-} // namespace shell_dialogs
-} // namespace ui
diff --git a/chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.h b/chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.h
deleted file mode 100644
index 59750801540..00000000000
--- a/chromium/ui/shell_dialogs/android/shell_dialogs_jni_registrar.h
+++ /dev/null
@@ -1,21 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_SHELL_DIALOGS_ANDROID_UI_SHELL_DIALOGS_JNI_REGISTRAR_H_
-#define UI_SHELL_DIALOGS_ANDROID_UI_SHELL_DIALOGS_JNI_REGISTRAR_H_
-
-#include <jni.h>
-
-#include "ui/shell_dialogs/shell_dialogs_export.h"
-
-namespace ui {
-namespace shell_dialogs {
-
-// Register all JNI bindings necessary for chrome.
-SHELL_DIALOGS_EXPORT bool RegisterJni(JNIEnv* env);
-
-} // namespace shell_dialogs
-} // namespace ui
-
-#endif // UI_SHELL_DIALOGS_ANDROID_UI_SHELL_DIALOGS_JNI_REGISTRAR_H_
diff --git a/chromium/ui/shell_dialogs/select_file_dialog_win.cc b/chromium/ui/shell_dialogs/select_file_dialog_win.cc
index eff7a493c19..c028d22c7ae 100644
--- a/chromium/ui/shell_dialogs/select_file_dialog_win.cc
+++ b/chromium/ui/shell_dialogs/select_file_dialog_win.cc
@@ -414,7 +414,7 @@ class SelectFileDialogImpl : public ui::SelectFileDialog,
ui::SelectFilePolicy* policy);
// BaseShellDialog implementation:
- virtual bool IsRunning(gfx::NativeWindow owning_hwnd) const OVERRIDE;
+ virtual bool IsRunning(gfx::NativeWindow owning_window) const OVERRIDE;
virtual void ListenerDestroyed() OVERRIDE;
protected:
@@ -598,7 +598,7 @@ void SelectFileDialogImpl::SelectFileImpl(
return;
}
}
- HWND owner = owning_window
+ HWND owner = owning_window && owning_window->GetRootWindow()
? owning_window->GetRootWindow()->GetAcceleratedWidget() : NULL;
#else
HWND owner = owning_window;
@@ -617,11 +617,13 @@ bool SelectFileDialogImpl::HasMultipleFileTypeChoicesImpl() {
return has_multiple_file_type_choices_;
}
-bool SelectFileDialogImpl::IsRunning(gfx::NativeWindow owning_hwnd) const {
+bool SelectFileDialogImpl::IsRunning(gfx::NativeWindow owning_window) const {
#if defined(USE_AURA)
- HWND owner = owning_hwnd->GetRootWindow()->GetAcceleratedWidget();
+ if (!owning_window->GetRootWindow())
+ return false;
+ HWND owner = owning_window->GetRootWindow()->GetAcceleratedWidget();
#else
- HWND owner = owning_hwnd;
+ HWND owner = owning_window;
#endif
return listener_ && IsRunningDialogForOwner(owner);
}
diff --git a/chromium/ui/snapshot/OWNERS b/chromium/ui/snapshot/OWNERS
new file mode 100644
index 00000000000..326ee949548
--- /dev/null
+++ b/chromium/ui/snapshot/OWNERS
@@ -0,0 +1,5 @@
+# Android
+per-file *android*=bulach@chromium.org
+per-file *android*=tedchoc@chromium.org
+per-file *android*=yfriedman@chromium.org
+per-file *android*=newt@chromium.org
diff --git a/chromium/ui/snapshot/snapshot_android.cc b/chromium/ui/snapshot/snapshot_android.cc
index 4e89c9da1ca..14c43ee9b46 100644
--- a/chromium/ui/snapshot/snapshot_android.cc
+++ b/chromium/ui/snapshot/snapshot_android.cc
@@ -4,22 +4,32 @@
#include "ui/snapshot/snapshot.h"
+#include "ui/android/view_android.h"
+#include "ui/android/window_android.h"
+#include "ui/gfx/display.h"
#include "ui/gfx/rect.h"
+#include "ui/gfx/screen.h"
namespace ui {
bool GrabViewSnapshot(gfx::NativeView view,
std::vector<unsigned char>* png_representation,
const gfx::Rect& snapshot_bounds) {
- // TODO(bajones): Implement Android snapshot functionality
- return false;
+ return GrabWindowSnapshot(
+ view->GetWindowAndroid(), png_representation, snapshot_bounds);
}
bool GrabWindowSnapshot(gfx::NativeWindow window,
std::vector<unsigned char>* png_representation,
const gfx::Rect& snapshot_bounds) {
- // TODO(bajones): Implement Android snapshot functionality
- return false;
+ gfx::Display display =
+ gfx::Screen::GetNativeScreen()->GetPrimaryDisplay();
+ gfx::Rect scaled_bounds =
+ gfx::ScaleToEnclosingRect(snapshot_bounds,
+ display.device_scale_factor());
+ return window->GrabSnapshot(
+ scaled_bounds.x(), scaled_bounds.y(), scaled_bounds.width(),
+ scaled_bounds.height(), png_representation);
}
} // namespace ui
diff --git a/chromium/ui/surface/accelerated_surface_win.cc b/chromium/ui/surface/accelerated_surface_win.cc
index 3b86db01ad4..15d78c00ac3 100644
--- a/chromium/ui/surface/accelerated_surface_win.cc
+++ b/chromium/ui/surface/accelerated_surface_win.cc
@@ -8,8 +8,8 @@
#include <algorithm>
#include "base/bind.h"
-#include "base/bind_helpers.h"
#include "base/callback.h"
+#include "base/callback_helpers.h"
#include "base/command_line.h"
#include "base/debug/trace_event.h"
#include "base/files/file_path.h"
@@ -25,11 +25,11 @@
#include "media/base/video_frame.h"
#include "media/base/video_util.h"
#include "third_party/skia/include/core/SkBitmap.h"
-#include "ui/base/latency_info.h"
-#include "ui/base/win/dpi.h"
-#include "ui/base/win/hwnd_util.h"
#include "ui/base/win/shell.h"
+#include "ui/events/latency_info.h"
#include "ui/gfx/rect.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/gl/gl_switches.h"
#include "ui/surface/accelerated_surface_transformer_win.h"
#include "ui/surface/d3d9_utils_win.h"
@@ -332,12 +332,6 @@ void AcceleratedPresenterMap::RemovePresenter(
scoped_refptr<AcceleratedPresenter> AcceleratedPresenterMap::GetPresenter(
gfx::PluginWindowHandle window) {
base::AutoLock locked(lock_);
-
-#if defined(USE_AURA)
- if (!window)
- return presenters_.begin()->second;
-#endif
-
PresenterMap::iterator it = presenters_.find(window);
if (it == presenters_.end())
return scoped_refptr<AcceleratedPresenter>();
@@ -672,13 +666,6 @@ void AcceleratedPresenter::ResetPresentThread(
quantized_size_ = gfx::Size();
}
-#if defined(USE_AURA)
-void AcceleratedPresenter::SetNewTargetWindow(gfx::PluginWindowHandle window) {
- window_ = window;
- swap_chain_ = NULL;
-}
-#endif
-
AcceleratedPresenter::~AcceleratedPresenter() {
}
@@ -728,15 +715,16 @@ void AcceleratedPresenter::DoPresentAndAcknowledge(
return;
}
+#if !defined(USE_AURA)
// If the window is a different size than the swap chain that is being
// presented then drop the frame.
gfx::Size window_size = GetWindowSize();
bool size_mismatch = size != window_size;
- if (ui::IsInHighDPIMode()) {
+ if (gfx::IsInHighDPIMode()) {
// Check if the size mismatch is within allowable round off or truncation
// error.
- gfx::Size dip_size = ui::win::ScreenToDIPSize(window_size);
- gfx::Size pixel_size = ui::win::DIPToScreenSize(dip_size);
+ gfx::Size dip_size = gfx::win::ScreenToDIPSize(window_size);
+ gfx::Size pixel_size = gfx::win::DIPToScreenSize(dip_size);
size_mismatch = abs(window_size.width() - size.width()) >
abs(window_size.width() - pixel_size.width()) ||
abs(window_size.height() - size.height()) >
@@ -750,7 +738,7 @@ void AcceleratedPresenter::DoPresentAndAcknowledge(
"windowheight", window_size.height());
return;
}
-
+#endif
// Round up size so the swap chain is not continuously resized with the
// surface, which could lead to memory fragmentation.
const int kRound = 64;
diff --git a/chromium/ui/surface/accelerated_surface_win.h b/chromium/ui/surface/accelerated_surface_win.h
index 357fff36733..7c4164b469b 100644
--- a/chromium/ui/surface/accelerated_surface_win.h
+++ b/chromium/ui/surface/accelerated_surface_win.h
@@ -14,7 +14,7 @@
#include "base/synchronization/waitable_event.h"
#include "base/time/time.h"
#include "base/win/scoped_comptr.h"
-#include "ui/base/latency_info.h"
+#include "ui/events/latency_info.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/size.h"
#include "ui/surface/surface_export.h"
@@ -89,12 +89,6 @@ class SURFACE_EXPORT AcceleratedPresenter
// the given present thread.
void ResetPresentThread(PresentThread* present_thread);
-#if defined(USE_AURA)
- // TODO(scottmg): This is a temporary hack until we have a two-worlds ash/aura
- // separation.
- void SetNewTargetWindow(gfx::PluginWindowHandle window);
-#endif
-
private:
friend class base::RefCountedThreadSafe<AcceleratedPresenter>;
diff --git a/chromium/ui/surface/transport_dib.h b/chromium/ui/surface/transport_dib.h
index 1d5410df25d..7ec7bb815f7 100644
--- a/chromium/ui/surface/transport_dib.h
+++ b/chromium/ui/surface/transport_dib.h
@@ -16,6 +16,7 @@
#include <windows.h>
#elif defined(TOOLKIT_GTK)
#include "ui/base/x/x11_util.h"
+#include "ui/gfx/x/x11_types.h"
#endif
class SkCanvas;
@@ -189,7 +190,7 @@ class SURFACE_EXPORT TransportDIB {
#if defined(TOOLKIT_GTK)
// Map the shared memory into the X server and return an id for the shared
// segment.
- XID MapToX(Display* connection);
+ XID MapToX(XDisplay* connection);
void IncreaseInFlightCounter() { inflight_counter_++; }
// Decreases the inflight counter, and deletes the transport DIB if it is
@@ -211,7 +212,7 @@ class SURFACE_EXPORT TransportDIB {
Id key_; // SysV shared memory id
void* address_; // mapped address
XSharedMemoryId x_shm_; // X id for the shared segment
- Display* display_; // connection to the X server
+ XDisplay* display_; // connection to the X server
size_t inflight_counter_; // How many requests to the X server are in flight
bool detached_; // If true, delete the transport DIB when it is idle
#else
diff --git a/chromium/ui/surface/transport_dib_gtk.cc b/chromium/ui/surface/transport_dib_gtk.cc
index 31f651328a0..61ec624c065 100644
--- a/chromium/ui/surface/transport_dib_gtk.cc
+++ b/chromium/ui/surface/transport_dib_gtk.cc
@@ -133,7 +133,7 @@ TransportDIB::Handle TransportDIB::handle() const {
return key_.shmkey;
}
-XID TransportDIB::MapToX(Display* display) {
+XID TransportDIB::MapToX(XDisplay* display) {
if (!x_shm_) {
x_shm_ = ui::AttachSharedMemory(display, key_.shmkey);
display_ = display;
diff --git a/chromium/ui/ui.gyp b/chromium/ui/ui.gyp
index b1e288098f5..4716f6c9cd0 100644
--- a/chromium/ui/ui.gyp
+++ b/chromium/ui/ui.gyp
@@ -31,6 +31,8 @@
'ui_resources',
],
'defines': [
+ # TODO(sky): remove once gfx dependencies are corrected.
+ 'GFX_IMPLEMENTATION',
'UI_IMPLEMENTATION',
],
# Export these dependencies since text_elider.h includes ICU headers.
@@ -62,23 +64,7 @@
'base/accessibility/accessible_text_utils.h',
'base/accessibility/accessible_view_state.cc',
'base/accessibility/accessible_view_state.h',
- 'base/animation/animation.cc',
- 'base/animation/animation.h',
- 'base/animation/animation_container.cc',
- 'base/animation/animation_container.h',
- 'base/animation/animation_container_element.h',
- 'base/animation/animation_container_observer.h',
- 'base/animation/animation_delegate.h',
- 'base/animation/linear_animation.cc',
- 'base/animation/linear_animation.h',
- 'base/animation/multi_animation.cc',
- 'base/animation/multi_animation.h',
- 'base/animation/slide_animation.cc',
- 'base/animation/slide_animation.h',
- 'base/animation/throb_animation.cc',
- 'base/animation/throb_animation.h',
- 'base/animation/tween.cc',
- 'base/animation/tween.h',
+ 'base/base_window.cc',
'base/base_window.h',
'base/clipboard/clipboard.cc',
'base/clipboard/clipboard.h',
@@ -99,6 +85,8 @@
'base/clipboard/scoped_clipboard_writer.cc',
'base/clipboard/scoped_clipboard_writer.h',
'base/cocoa/animation_utils.h',
+ 'base/cocoa/appkit_utils.h',
+ 'base/cocoa/appkit_utils.mm',
'base/cocoa/base_view.h',
'base/cocoa/base_view.mm',
'base/cocoa/cocoa_event_utils.h',
@@ -177,19 +165,6 @@
'base/dragdrop/os_exchange_data_provider_aura.h',
'base/dragdrop/os_exchange_data_provider_win.cc',
'base/dragdrop/os_exchange_data_provider_win.h',
- 'base/events/event.cc',
- 'base/events/event.h',
- 'base/events/event_constants.h',
- 'base/events/event_conversion_gtk.cc',
- 'base/events/event_conversion_gtk.h',
- 'base/events/event_dispatcher.cc',
- 'base/events/event_dispatcher.h',
- 'base/events/event_handler.cc',
- 'base/events/event_handler.h',
- 'base/events/event_target.cc',
- 'base/events/event_target.h',
- 'base/events/event_utils.cc',
- 'base/events/event_utils.h',
'base/gestures/gesture_configuration.cc',
'base/gestures/gesture_configuration.h',
'base/gestures/gesture_point.cc',
@@ -227,26 +202,9 @@
'base/gtk/gtk_windowing.h',
'base/gtk/owned_widget_gtk.cc',
'base/gtk/owned_widget_gtk.h',
- 'base/gtk/scoped_gobject.h',
'base/gtk/scoped_region.cc',
'base/gtk/scoped_region.h',
'base/hit_test.h',
- 'base/keycodes/keyboard_code_conversion.cc',
- 'base/keycodes/keyboard_code_conversion.h',
- 'base/keycodes/keyboard_code_conversion_android.cc',
- 'base/keycodes/keyboard_code_conversion_android.h',
- 'base/keycodes/keyboard_code_conversion_gtk.cc',
- 'base/keycodes/keyboard_code_conversion_gtk.h',
- 'base/keycodes/keyboard_code_conversion_mac.h',
- 'base/keycodes/keyboard_code_conversion_mac.mm',
- 'base/keycodes/keyboard_code_conversion_win.cc',
- 'base/keycodes/keyboard_code_conversion_win.h',
- 'base/keycodes/keyboard_code_conversion_x.cc',
- 'base/keycodes/keyboard_code_conversion_x.h',
- 'base/keycodes/keyboard_codes.h',
- 'base/keycodes/usb_keycode_map.h',
- 'base/latency_info.cc',
- 'base/latency_info.h',
'base/l10n/l10n_font_util.cc',
'base/l10n/l10n_font_util.h',
'base/l10n/l10n_util.cc',
@@ -256,6 +214,8 @@
'base/l10n/l10n_util_collator.h',
'base/l10n/l10n_util_mac.h',
'base/l10n/l10n_util_mac.mm',
+ 'base/l10n/l10n_util_plurals.cc',
+ 'base/l10n/l10n_util_plurals.h',
'base/l10n/l10n_util_posix.cc',
'base/l10n/l10n_util_win.cc',
'base/l10n/l10n_util_win.h',
@@ -287,22 +247,6 @@
'base/models/tree_model.h',
'base/models/tree_node_iterator.h',
'base/models/tree_node_model.h',
- 'base/ozone/evdev/key_event_converter_ozone.cc',
- 'base/ozone/evdev/key_event_converter_ozone.h',
- 'base/ozone/evdev/touch_event_converter_ozone.cc',
- 'base/ozone/evdev/touch_event_converter_ozone.h',
- 'base/ozone/event_converter_ozone.cc',
- 'base/ozone/event_converter_ozone.h',
- 'base/ozone/event_factory_delegate_ozone.h',
- 'base/ozone/event_factory_ozone.cc',
- 'base/ozone/event_factory_ozone.h',
- 'base/ozone/events_ozone.cc',
- 'base/ozone/surface_factory_ozone.cc',
- 'base/ozone/surface_factory_ozone.h',
- 'base/range/range.cc',
- 'base/range/range.h',
- 'base/range/range_mac.mm',
- 'base/range/range_win.cc',
'base/resource/data_pack.cc',
'base/resource/data_pack.h',
'base/resource/resource_bundle.cc',
@@ -317,12 +261,10 @@
'base/resource/resource_data_dll_win.cc',
'base/resource/resource_data_dll_win.h',
'base/resource/resource_handle.h',
+ 'base/sequential_id_generator.cc',
+ 'base/sequential_id_generator.h',
'base/text/bytes_formatting.cc',
'base/text/bytes_formatting.h',
- 'base/text/text_elider.cc',
- 'base/text/text_elider.h',
- 'base/text/utf16_indexing.cc',
- 'base/text/utf16_indexing.h',
'base/theme_provider.cc',
'base/theme_provider.h',
'base/touch/touch_device.cc',
@@ -353,8 +295,6 @@
'base/win/accessibility_misc_utils.cc',
'base/win/accessibility_misc_utils.h',
'base/win/atl_module.h',
- 'base/win/dpi.cc',
- 'base/win/dpi.h',
'base/win/events_win.cc',
'base/win/extra_sdk_defines.h',
'base/win/foreground_helper.cc',
@@ -363,23 +303,16 @@
'base/win/hidden_window.h',
'base/win/hwnd_subclass.cc',
'base/win/hwnd_subclass.h',
- 'base/win/hwnd_util.cc',
- 'base/win/hwnd_util.h',
'base/win/message_box_win.cc',
'base/win/message_box_win.h',
'base/win/mouse_wheel_util.cc',
'base/win/mouse_wheel_util.h',
'base/win/scoped_ole_initializer.cc',
'base/win/scoped_ole_initializer.h',
- 'base/win/scoped_set_map_mode.h',
'base/win/shell.cc',
'base/win/shell.h',
- 'base/win/singleton_hwnd.cc',
- 'base/win/singleton_hwnd.h',
'base/win/touch_input.cc',
'base/win/touch_input.h',
- 'base/win/window_impl.cc',
- 'base/win/window_impl.h',
'base/window_open_disposition.cc',
'base/window_open_disposition.h',
'base/work_area_watcher_observer.h',
@@ -403,13 +336,70 @@
'base/x/work_area_watcher_x.h',
'base/x/x11_atom_cache.cc',
'base/x/x11_atom_cache.h',
+ 'base/x/x11_error_tracker.cc',
+ 'base/x/x11_error_tracker.h',
+ 'base/x/x11_error_tracker_gtk.cc',
'base/x/x11_util.cc',
'base/x/x11_util.h',
'base/x/x11_util_internal.h',
+ 'events/event.cc',
+ 'events/event.h',
+ 'events/event_constants.h',
+ 'events/event_dispatcher.cc',
+ 'events/event_dispatcher.h',
+ 'events/event_handler.cc',
+ 'events/event_handler.h',
+ 'events/event_target.cc',
+ 'events/event_target.h',
+ 'events/event_utils.cc',
+ 'events/event_utils.h',
+ 'events/events_export.h',
+ 'events/keycodes/keyboard_code_conversion.cc',
+ 'events/keycodes/keyboard_code_conversion.h',
+ 'events/keycodes/keyboard_code_conversion_android.cc',
+ 'events/keycodes/keyboard_code_conversion_android.h',
+ 'events/keycodes/keyboard_code_conversion_gtk.cc',
+ 'events/keycodes/keyboard_code_conversion_gtk.h',
+ 'events/keycodes/keyboard_code_conversion_mac.h',
+ 'events/keycodes/keyboard_code_conversion_mac.mm',
+ 'events/keycodes/keyboard_code_conversion_win.cc',
+ 'events/keycodes/keyboard_code_conversion_win.h',
+ 'events/keycodes/keyboard_code_conversion_x.cc',
+ 'events/keycodes/keyboard_code_conversion_x.h',
+ 'events/keycodes/keyboard_codes.h',
+ 'events/latency_info.cc',
+ 'events/latency_info.h',
+ 'events/ozone/evdev/key_event_converter_ozone.cc',
+ 'events/ozone/evdev/key_event_converter_ozone.h',
+ 'events/ozone/evdev/touch_event_converter_ozone.cc',
+ 'events/ozone/evdev/touch_event_converter_ozone.h',
+ 'events/ozone/event_converter_ozone.cc',
+ 'events/ozone/event_converter_ozone.h',
+ 'events/ozone/event_factory_delegate_ozone.h',
+ 'events/ozone/event_factory_ozone.cc',
+ 'events/ozone/event_factory_ozone.h',
+ 'events/ozone/events_ozone.cc',
'gfx/android/device_display_info.cc',
'gfx/android/device_display_info.h',
'gfx/android/java_bitmap.cc',
'gfx/android/java_bitmap.h',
+ 'gfx/animation/animation.cc',
+ 'gfx/animation/animation.h',
+ 'gfx/animation/animation_container.cc',
+ 'gfx/animation/animation_container.h',
+ 'gfx/animation/animation_container_element.h',
+ 'gfx/animation/animation_container_observer.h',
+ 'gfx/animation/animation_delegate.h',
+ 'gfx/animation/linear_animation.cc',
+ 'gfx/animation/linear_animation.h',
+ 'gfx/animation/multi_animation.cc',
+ 'gfx/animation/multi_animation.h',
+ 'gfx/animation/slide_animation.cc',
+ 'gfx/animation/slide_animation.h',
+ 'gfx/animation/throb_animation.cc',
+ 'gfx/animation/throb_animation.h',
+ 'gfx/animation/tween.cc',
+ 'gfx/animation/tween.h',
'gfx/blit.cc',
'gfx/blit.h',
'gfx/box_f.cc',
@@ -418,13 +408,12 @@
'gfx/canvas.cc',
'gfx/canvas.h',
'gfx/canvas_android.cc',
- 'gfx/canvas_mac.mm',
+ 'gfx/canvas_paint_gtk.cc',
'gfx/canvas_paint_gtk.h',
'gfx/canvas_paint_mac.h',
- 'gfx/canvas_paint_win.h',
- 'gfx/canvas_paint_gtk.cc',
'gfx/canvas_paint_mac.mm',
'gfx/canvas_paint_win.cc',
+ 'gfx/canvas_paint_win.h',
'gfx/canvas_skia.cc',
'gfx/canvas_skia_paint.h',
'gfx/codec/jpeg_codec.cc',
@@ -456,6 +445,7 @@
'gfx/font_render_params_linux.h',
'gfx/font_smoothing_win.cc',
'gfx/font_smoothing_win.h',
+ 'gfx/gfx_export.h',
'gfx/gfx_paths.cc',
'gfx/gfx_paths.h',
'gfx/gpu_memory_buffer.cc',
@@ -495,6 +485,8 @@
'gfx/matrix3_f.cc',
'gfx/matrix3_f.h',
'gfx/native_widget_types.h',
+ 'gfx/ozone/surface_factory_ozone.cc',
+ 'gfx/ozone/surface_factory_ozone.h',
'gfx/pango_util.cc',
'gfx/pango_util.h',
'gfx/path.cc',
@@ -526,6 +518,10 @@
'gfx/point_f.h',
'gfx/quad_f.cc',
'gfx/quad_f.h',
+ 'gfx/range/range.cc',
+ 'gfx/range/range.h',
+ 'gfx/range/range_mac.mm',
+ 'gfx/range/range_win.cc',
'gfx/rect.cc',
'gfx/rect.h',
'gfx/rect_base.h',
@@ -581,12 +577,19 @@
'gfx/sys_color_change_listener.cc',
'gfx/sys_color_change_listener.h',
'gfx/text_constants.h',
+ 'gfx/text_elider.cc',
+ 'gfx/text_elider.h',
'gfx/text_utils.cc',
'gfx/text_utils.h',
+ 'gfx/text_utils_android.cc',
+ 'gfx/text_utils_ios.mm',
+ 'gfx/text_utils_skia.cc',
'gfx/transform.cc',
'gfx/transform.h',
'gfx/transform_util.cc',
'gfx/transform_util.h',
+ 'gfx/utf16_indexing.cc',
+ 'gfx/utf16_indexing.h',
'gfx/vector2d.cc',
'gfx/vector2d.h',
'gfx/vector2d_conversions.cc',
@@ -595,6 +598,17 @@
'gfx/vector2d_f.h',
'gfx/vector3d_f.cc',
'gfx/vector3d_f.h',
+ 'gfx/win/dpi.cc',
+ 'gfx/win/dpi.h',
+ 'gfx/win/hwnd_util.cc',
+ 'gfx/win/hwnd_util.h',
+ 'gfx/win/scoped_set_map_mode.h',
+ 'gfx/win/singleton_hwnd.cc',
+ 'gfx/win/singleton_hwnd.h',
+ 'gfx/win/window_impl.cc',
+ 'gfx/win/window_impl.h',
+ 'gfx/x/x11_types.cc',
+ 'gfx/x/x11_types.h',
'webui/jstemplate_builder.cc',
'webui/jstemplate_builder.h',
'webui/web_ui_util.cc',
@@ -622,13 +636,12 @@
['include', '_ios\\.(cc|mm)$'],
['include', '(^|/)ios/'],
['include', '^gfx/'],
+ ['include', '^gfx/animation/'],
['exclude', '^gfx/codec/jpeg_codec\\.cc$'],
- ['include', '^base/animation/'],
+ ['include', '^gfx/range/'],
['include', '^base/l10n/'],
['include', '^base/layout'],
- ['include', '^base/range/'],
['include', '^base/resource/'],
- ['include', '^base/text/text_elider\\.'],
['include', '^base/ui_base_'],
],
'link_settings': {
@@ -642,7 +655,6 @@
['use_canvas_skia==1', {
'sources!': [
'gfx/canvas_android.cc',
- 'gfx/canvas_mac.mm',
],
}, { # use_canvas_skia!=1
'sources!': [
@@ -740,10 +752,16 @@
'gfx/gtk_native_view_id_manager.h',
'gfx/gtk_preserve_window.cc',
'gfx/gtk_preserve_window.h',
+ 'gfx/gdk_compat.h',
+ 'gfx/gtk_compat.h',
'gfx/gtk_util.cc',
'gfx/gtk_util.h',
'gfx/image/cairo_cached_surface.cc',
'gfx/image/cairo_cached_surface.h',
+ 'gfx/scoped_gobject.h',
+ ],
+ 'sources!': [
+ 'base/x/x11_error_tracker.cc',
],
}],
['chromeos==1 or (use_aura==1 and OS=="linux" and use_x11==0)', {
@@ -857,7 +875,7 @@
],
}, { # use_x11==0
'sources/': [
- ['exclude', 'base/keycodes/keyboard_code_conversion_x.*'],
+ ['exclude', 'events/keycodes/keyboard_code_conversion_x.*'],
['exclude', 'base/x/*'],
],
}],
@@ -870,22 +888,37 @@
}],
['use_qt==0 and toolkit_views==0', {
'sources!': [
- 'base/events/event.cc',
- 'base/events/event.h',
- 'base/events/event_dispatcher.cc',
- 'base/events/event_dispatcher.h',
- 'base/events/event_handler.cc',
- 'base/events/event_handler.h',
- 'base/events/event_target.cc',
- 'base/events/event_target.h',
'base/x/events_x.cc',
+ 'events/event.cc',
+ 'events/event.h',
+ 'events/event_dispatcher.cc',
+ 'events/event_dispatcher.h',
+ 'events/event_handler.cc',
+ 'events/event_handler.h',
+ 'events/event_target.cc',
+ 'events/event_target.h',
],
}],
['OS=="android"', {
'sources!': [
+ 'base/accessibility/accessible_text_utils.cc',
+ 'base/accessibility/accessible_view_state.cc',
+ 'base/default_theme_provider.cc',
'base/dragdrop/drag_utils.cc',
'base/dragdrop/drag_utils.h',
+ 'events/event_utils.cc',
+ 'events/keycodes/keyboard_code_conversion.cc',
+ 'base/l10n/l10n_font_util.cc',
+ 'base/models/button_menu_item_model.cc',
+ 'base/models/dialog_model.cc',
+ 'base/theme_provider.cc',
'base/touch/touch_device.cc',
+ 'base/touch/touch_editing_controller.cc',
+ 'base/ui_base_types.cc',
+ 'gfx/animation/throb_animation.cc',
+ 'gfx/display_observer.cc',
+ 'gfx/path.cc',
+ 'gfx/selection_model.cc',
],
'dependencies': [
'ui_jni_headers',
@@ -908,6 +941,7 @@
'sources!': [
'gfx/render_text.cc',
'gfx/render_text.h',
+ 'gfx/text_utils_skia.cc',
],
}],
['OS=="linux"', {
@@ -931,6 +965,18 @@
'<(SHARED_INTERMEDIATE_DIR)/ui/ui_resources',
]
}
+ },
+ {
+ 'target_name': 'keycode_converter',
+ 'type': 'static_library',
+ 'dependencies': [
+ '../base/base.gyp:base',
+ ],
+ 'sources': [
+ 'base/keycodes/keycode_converter.cc',
+ 'base/keycodes/keycode_converter.h',
+ 'base/keycodes/keycode_converter_data.h',
+ ],
}
],
'conditions': [
diff --git a/chromium/ui/ui_unittests.gypi b/chromium/ui/ui_unittests.gypi
index e62af9376f8..ac73bfef4ff 100644
--- a/chromium/ui/ui_unittests.gypi
+++ b/chromium/ui/ui_unittests.gypi
@@ -82,6 +82,7 @@
'../third_party/libpng/libpng.gyp:libpng',
'../url/url.gyp:url_lib',
'base/strings/ui_strings.gyp:ui_strings',
+ 'keycode_converter',
'run_ui_unittests',
'shell_dialogs',
'ui',
@@ -91,23 +92,19 @@
# iOS uses a small subset of ui. common_sources are the only files that
# are built on iOS.
'common_sources' : [
- 'base/animation/animation_container_unittest.cc',
- 'base/animation/animation_unittest.cc',
- 'base/animation/multi_animation_unittest.cc',
- 'base/animation/slide_animation_unittest.cc',
'base/layout_unittest.cc',
'base/l10n/l10n_util_mac_unittest.mm',
'base/l10n/l10n_util_unittest.cc',
'base/l10n/l10n_util_win_unittest.cc',
'base/l10n/time_format_unittest.cc',
'base/models/tree_node_iterator_unittest.cc',
- 'base/range/range_mac_unittest.mm',
- 'base/range/range_unittest.cc',
- 'base/range/range_win_unittest.cc',
'base/resource/data_pack_literal.cc',
'base/resource/data_pack_unittest.cc',
'base/resource/resource_bundle_unittest.cc',
- 'base/text/text_elider_unittest.cc',
+ 'gfx/animation/animation_container_unittest.cc',
+ 'gfx/animation/animation_unittest.cc',
+ 'gfx/animation/multi_animation_unittest.cc',
+ 'gfx/animation/slide_animation_unittest.cc',
'gfx/box_unittest.cc',
'gfx/codec/png_codec_unittest.cc',
'gfx/color_utils_unittest.cc',
@@ -125,12 +122,16 @@
'gfx/point_unittest.cc',
'gfx/point3_unittest.cc',
'gfx/quad_unittest.cc',
+ 'gfx/range/range_mac_unittest.mm',
+ 'gfx/range/range_unittest.cc',
+ 'gfx/range/range_win_unittest.cc',
'gfx/rect_unittest.cc',
'gfx/safe_integer_conversions_unittest.cc',
'gfx/screen_unittest.cc',
'gfx/shadow_value_unittest.cc',
'gfx/size_unittest.cc',
'gfx/skbitmap_operations_unittest.cc',
+ 'gfx/text_elider_unittest.cc',
'gfx/text_utils_unittest.cc',
'gfx/vector2d_unittest.cc',
'gfx/vector3d_unittest.cc',
@@ -152,23 +153,25 @@
'base/cocoa/menu_controller_unittest.mm',
'base/cocoa/nsgraphics_context_additions_unittest.mm',
'base/cocoa/tracking_area_unittest.mm',
- 'base/events/event_dispatcher_unittest.cc',
- 'base/events/event_unittest.cc',
+ 'base/dragdrop/os_exchange_data_provider_aurax11_unittest.cc',
'base/gtk/gtk_expanded_container_unittest.cc',
'base/gtk/gtk_im_context_util_unittest.cc',
- 'base/keycodes/usb_keycode_map_unittest.cc',
- 'base/latency_info_unittest.cc',
+ 'base/keycodes/keycode_converter_unittest.cc',
'base/models/list_model_unittest.cc',
'base/models/list_selection_model_unittest.cc',
'base/models/tree_node_model_unittest.cc',
- 'base/ozone/evdev/touch_event_converter_ozone_unittest.cc',
+ 'base/sequential_id_generator_unittest.cc',
'base/test/data/resource.h',
'base/text/bytes_formatting_unittest.cc',
- 'base/text/utf16_indexing_unittest.cc',
'base/view_prop_unittest.cc',
+ 'events/event_dispatcher_unittest.cc',
+ 'events/event_unittest.cc',
+ 'events/latency_info_unittest.cc',
+ 'events/ozone/evdev/touch_event_converter_ozone_unittest.cc',
'gfx/blit_unittest.cc',
'gfx/break_list_unittest.cc',
'gfx/canvas_unittest.cc',
+ 'gfx/canvas_unittest_mac.mm',
'gfx/codec/jpeg_codec_unittest.cc',
'gfx/color_analysis_unittest.cc',
'gfx/font_list_unittest.cc',
@@ -177,6 +180,7 @@
'gfx/platform_font_mac_unittest.mm',
'gfx/render_text_unittest.cc',
'gfx/transform_util_unittest.cc',
+ 'gfx/utf16_indexing_unittest.cc',
'shell_dialogs/select_file_dialog_win_unittest.cc',
'webui/web_ui_util_unittest.cc',
],
@@ -311,8 +315,8 @@
],
}, {
'sources!': [
- 'base/events/event_dispatcher_unittest.cc',
- 'base/events/event_unittest.cc',
+ 'events/event_dispatcher_unittest.cc',
+ 'events/event_unittest.cc',
],
}],
['use_aura==1', {
@@ -322,6 +326,11 @@
'gfx/screen_unittest.cc',
],
}],
+ ['chromeos==1', {
+ 'sources!': [
+ 'base/dragdrop/os_exchange_data_provider_aurax11_unittest.cc',
+ ],
+ }],
],
'target_conditions': [
['OS == "ios"', {
diff --git a/chromium/ui/ui_unittests.isolate b/chromium/ui/ui_unittests.isolate
index 35f732b96ba..55ce04a9d47 100644
--- a/chromium/ui/ui_unittests.isolate
+++ b/chromium/ui/ui_unittests.isolate
@@ -7,7 +7,6 @@
'variables': {
'isolate_dependency_tracked': [
'base/test/data/data_pack_unittest/truncated-header.pak',
- '<(PRODUCT_DIR)/chrome.pak',
'<(PRODUCT_DIR)/locales/en-US.pak',
],
},
diff --git a/chromium/ui/views/accessibility/native_view_accessibility.cc b/chromium/ui/views/accessibility/native_view_accessibility.cc
index d94f05a0c0c..577ecfa41c2 100644
--- a/chromium/ui/views/accessibility/native_view_accessibility.cc
+++ b/chromium/ui/views/accessibility/native_view_accessibility.cc
@@ -29,11 +29,11 @@ void NativeViewAccessibility::Destroy() {
#if !defined(OS_WIN)
// static
-void NativeViewAccessibility::RegisterWebView(AccessibleWebView* web_view) {
+void NativeViewAccessibility::RegisterWebView(View* web_view) {
}
// static
-void NativeViewAccessibility::UnregisterWebView(AccessibleWebView* web_view) {
+void NativeViewAccessibility::UnregisterWebView(View* web_view) {
}
#endif
diff --git a/chromium/ui/views/accessibility/native_view_accessibility.h b/chromium/ui/views/accessibility/native_view_accessibility.h
index 688f34cc64e..2fc4c4423b6 100644
--- a/chromium/ui/views/accessibility/native_view_accessibility.h
+++ b/chromium/ui/views/accessibility/native_view_accessibility.h
@@ -13,13 +13,6 @@ namespace views {
class View;
-class AccessibleWebView {
- public:
- virtual gfx::NativeViewAccessible AccessibleObjectFromChildId(long child_id)
- = 0;
- virtual View* AsView() = 0;
-};
-
class VIEWS_EXPORT NativeViewAccessibility {
public:
static NativeViewAccessibility* Create(View* view);
@@ -33,9 +26,11 @@ class VIEWS_EXPORT NativeViewAccessibility {
// use reference counting.
virtual void Destroy();
- static void RegisterWebView(AccessibleWebView* web_view);
-
- static void UnregisterWebView(AccessibleWebView* web_view);
+ // WebViews need to be registered because they implement their own
+ // tree of accessibility objects, and we need to check them when
+ // mapping a child id to a NativeViewAccessible.
+ static void RegisterWebView(View* web_view);
+ static void UnregisterWebView(View* web_view);
protected:
NativeViewAccessibility();
diff --git a/chromium/ui/views/accessibility/native_view_accessibility_win.cc b/chromium/ui/views/accessibility/native_view_accessibility_win.cc
index 279c99d3d29..7aa92a2a13c 100644
--- a/chromium/ui/views/accessibility/native_view_accessibility_win.cc
+++ b/chromium/ui/views/accessibility/native_view_accessibility_win.cc
@@ -11,6 +11,8 @@
#include <vector>
#include "base/memory/singleton.h"
+#include "base/strings/utf_string_conversions.h"
+#include "base/win/scoped_comptr.h"
#include "base/win/windows_version.h"
#include "third_party/iaccessible2/ia2_api_all.h"
#include "ui/base/accessibility/accessible_text_utils.h"
@@ -21,6 +23,7 @@
#include "ui/views/controls/button/custom_button.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/focus/view_storage.h"
+#include "ui/views/widget/widget.h"
#include "ui/views/win/hwnd_util.h"
using ui::AccessibilityTypes;
@@ -32,9 +35,9 @@ class AccessibleWebViewRegistry {
public:
static AccessibleWebViewRegistry* GetInstance();
- void RegisterWebView(AccessibleWebView* web_view);
+ void RegisterWebView(View* web_view);
- void UnregisterWebView(AccessibleWebView* web_view);
+ void UnregisterWebView(View* web_view);
// Given the view that received the request for the accessible
// id in |top_view|, and the child id requested, return the native
@@ -42,40 +45,62 @@ class AccessibleWebViewRegistry {
// |top_view|'s view hierarchy, if any.
IAccessible* GetAccessibleFromWebView(View* top_view, long child_id);
+ // The system uses IAccessible APIs for many purposes, but only
+ // assistive technology like screen readers uses IAccessible2.
+ // Call this method to note that the IAccessible2 interface was queried and
+ // that WebViews should be proactively notified that this interface will be
+ // used. If this is enabled for the first time, this will explicitly call
+ // QueryService with an argument of IAccessible2 on all WebViews, otherwise
+ // it will just do it from now on.
+ void EnableIAccessible2Support();
+
private:
friend struct DefaultSingletonTraits<AccessibleWebViewRegistry>;
AccessibleWebViewRegistry();
~AccessibleWebViewRegistry() {}
+ IAccessible* AccessibleObjectFromChildId(View* web_view, long child_id);
+
+ void QueryIAccessible2Interface(View* web_view);
+
// Set of all web views. We check whether each one is contained in a
// top view dynamically rather than keeping track of a map.
- std::set<AccessibleWebView*> web_views_;
+ std::set<View*> web_views_;
// The most recent top view used in a call to GetAccessibleFromWebView.
View* last_top_view_;
// The most recent web view where an accessible object was found,
// corresponding to |last_top_view_|.
- AccessibleWebView* last_web_view_;
+ View* last_web_view_;
+
+ // If IAccessible2 support is enabled, we query the IAccessible2 interface
+ // of WebViews proactively when they're registered, so that they are
+ // aware that they need to support this interface.
+ bool iaccessible2_support_enabled_;
DISALLOW_COPY_AND_ASSIGN(AccessibleWebViewRegistry);
};
AccessibleWebViewRegistry::AccessibleWebViewRegistry()
: last_top_view_(NULL),
- last_web_view_(NULL) {
+ last_web_view_(NULL),
+ iaccessible2_support_enabled_(false) {
}
AccessibleWebViewRegistry* AccessibleWebViewRegistry::GetInstance() {
return Singleton<AccessibleWebViewRegistry>::get();
}
-void AccessibleWebViewRegistry::RegisterWebView(AccessibleWebView* web_view) {
+void AccessibleWebViewRegistry::RegisterWebView(View* web_view) {
DCHECK(web_views_.find(web_view) == web_views_.end());
web_views_.insert(web_view);
+
+ if (iaccessible2_support_enabled_)
+ QueryIAccessible2Interface(web_view);
}
-void AccessibleWebViewRegistry::UnregisterWebView(AccessibleWebView* web_view) {
+void AccessibleWebViewRegistry::UnregisterWebView(View* web_view) {
DCHECK(web_views_.find(web_view) != web_views_.end());
web_views_.erase(web_view);
if (last_web_view_ == web_view) {
@@ -91,7 +116,7 @@ IAccessible* AccessibleWebViewRegistry::GetAccessibleFromWebView(
// sent the last one.
if (last_top_view_ == top_view) {
IAccessible* accessible =
- last_web_view_->AccessibleObjectFromChildId(child_id);
+ AccessibleObjectFromChildId(last_web_view_, child_id);
if (accessible)
return accessible;
}
@@ -100,21 +125,65 @@ IAccessible* AccessibleWebViewRegistry::GetAccessibleFromWebView(
// of this view where the event was posted - and if so, see if it owns
// an accessible object with that child id. If so, save the view to speed
// up the next notification.
- for (std::set<AccessibleWebView*>::iterator iter = web_views_.begin();
+ for (std::set<View*>::iterator iter = web_views_.begin();
iter != web_views_.end(); ++iter) {
- AccessibleWebView* web_view = *iter;
- if (!top_view->Contains(web_view->AsView()))
+ View* web_view = *iter;
+ if (top_view == web_view || !top_view->Contains(web_view))
continue;
- IAccessible* accessible = web_view->AccessibleObjectFromChildId(child_id);
+ IAccessible* accessible = AccessibleObjectFromChildId(web_view, child_id);
if (accessible) {
last_top_view_ = top_view;
last_web_view_ = web_view;
return accessible;
}
}
+
+ return NULL;
+}
+
+void AccessibleWebViewRegistry::EnableIAccessible2Support() {
+ if (iaccessible2_support_enabled_)
+ return;
+ iaccessible2_support_enabled_ = true;
+ for (std::set<View*>::iterator iter = web_views_.begin();
+ iter != web_views_.end(); ++iter) {
+ QueryIAccessible2Interface(*iter);
+ }
+}
+
+IAccessible* AccessibleWebViewRegistry::AccessibleObjectFromChildId(
+ View* web_view,
+ long child_id) {
+ IAccessible* web_view_accessible = web_view->GetNativeViewAccessible();
+ if (web_view_accessible == NULL)
+ return NULL;
+
+ VARIANT var_child;
+ var_child.vt = VT_I4;
+ var_child.lVal = child_id;
+ IAccessible* result = NULL;
+ if (S_OK == web_view_accessible->get_accChild(
+ var_child, reinterpret_cast<IDispatch**>(&result))) {
+ return result;
+ }
+
return NULL;
}
+void AccessibleWebViewRegistry::QueryIAccessible2Interface(View* web_view) {
+ IAccessible* web_view_accessible = web_view->GetNativeViewAccessible();
+ if (!web_view_accessible)
+ return;
+
+ base::win::ScopedComPtr<IServiceProvider> service_provider;
+ if (S_OK != web_view_accessible->QueryInterface(service_provider.Receive()))
+ return;
+ base::win::ScopedComPtr<IAccessible2> iaccessible2;
+ service_provider->QueryService(
+ IID_IAccessible, IID_IAccessible2,
+ reinterpret_cast<void**>(iaccessible2.Receive()));
+}
+
} // anonymous namespace
// static
@@ -179,7 +248,6 @@ void NativeViewAccessibilityWin::Destroy() {
Release();
}
-// TODO(ctguil): Handle case where child View is not contained by parent.
STDMETHODIMP NativeViewAccessibilityWin::accHitTest(
LONG x_left, LONG y_top, VARIANT* child) {
if (!child)
@@ -188,25 +256,71 @@ STDMETHODIMP NativeViewAccessibilityWin::accHitTest(
if (!view_)
return E_FAIL;
+ // If this is a root view, our widget might have child widgets.
+ // Search child widgets first, since they're on top in the z-order.
+ if (view_->GetWidget()->GetRootView() == view_) {
+ std::vector<Widget*> child_widgets;
+ PopulateChildWidgetVector(&child_widgets);
+ for (size_t i = 0; i < child_widgets.size(); ++i) {
+ Widget* child_widget = child_widgets[i];
+ IAccessible* child_accessible =
+ child_widget->GetRootView()->GetNativeViewAccessible();
+ HRESULT result = child_accessible->accHitTest(x_left, y_top, child);
+ if (result == S_OK)
+ return result;
+ }
+ }
+
gfx::Point point(x_left, y_top);
View::ConvertPointToTarget(NULL, view_, &point);
+ // If the point is not inside this view, return false.
if (!view_->HitTestPoint(point)) {
- // If containing parent is not hit, return with failure.
child->vt = VT_EMPTY;
return S_FALSE;
}
- View* view = view_->GetEventHandlerForPoint(point);
- if (view == view_) {
- // No child hit, return parent id.
- child->vt = VT_I4;
- child->lVal = CHILDID_SELF;
- } else {
- child->vt = VT_DISPATCH;
- child->pdispVal = view->GetNativeViewAccessible();
- child->pdispVal->AddRef();
+ // Check if the point is within any of the immediate children of this
+ // view.
+ View* hit_child_view = NULL;
+ for (int i = view_->child_count() - 1; i >= 0; --i) {
+ View* child_view = view_->child_at(i);
+ if (!child_view->visible())
+ continue;
+
+ gfx::Point point_in_child_coords(point);
+ view_->ConvertPointToTarget(view_, child_view, &point_in_child_coords);
+ if (child_view->HitTestPoint(point_in_child_coords)) {
+ hit_child_view = child_view;
+ break;
+ }
}
+
+ // If the point was within one of this view's immediate children,
+ // call accHitTest recursively on that child's native view accessible -
+ // which may be a recursive call to this function or it may be overridden,
+ // for example in the case of a WebView.
+ if (hit_child_view) {
+ HRESULT result = hit_child_view->GetNativeViewAccessible()->accHitTest(
+ x_left, y_top, child);
+
+ // If the recursive call returned CHILDID_SELF, we have to convert that
+ // into a VT_DISPATCH for the return value to this call.
+ if (S_OK == result && child->vt == VT_I4 && child->lVal == CHILDID_SELF) {
+ child->vt = VT_DISPATCH;
+ child->pdispVal = hit_child_view->GetNativeViewAccessible();
+ // Always increment ref when returning a reference to a COM object.
+ child->pdispVal->AddRef();
+ }
+ return result;
+ }
+
+ // This object is the best match, so return CHILDID_SELF. It's tempting to
+ // simplify the logic and use VT_DISPATCH everywhere, but the Windows
+ // call AccessibleObjectFromPoint will keep calling accHitTest until some
+ // object returns CHILDID_SELF.
+ child->vt = VT_I4;
+ child->lVal = CHILDID_SELF;
return S_OK;
}
@@ -357,16 +471,37 @@ STDMETHODIMP NativeViewAccessibilityWin::get_accChild(VARIANT var_child,
return S_OK;
}
+ // If this is a root view, our widget might have child widgets. Include
+ std::vector<Widget*> child_widgets;
+ if (view_->GetWidget()->GetRootView() == view_)
+ PopulateChildWidgetVector(&child_widgets);
+ int child_widget_count = static_cast<int>(child_widgets.size());
+
View* child_view = NULL;
if (child_id > 0) {
// Positive child ids are a 1-based child index, used by clients
// that want to enumerate all immediate children.
int child_id_as_index = child_id - 1;
- if (child_id_as_index < view_->child_count())
+ if (child_id_as_index < view_->child_count()) {
child_view = view_->child_at(child_id_as_index);
+ } else if (child_id_as_index < view_->child_count() + child_widget_count) {
+ Widget* child_widget =
+ child_widgets[child_id_as_index - view_->child_count()];
+ child_view = child_widget->GetRootView();
+ }
} else {
- // Negative child ids can be used to map to any descendant;
- // we map child ids to a view storage id that can refer to a
+ // Negative child ids can be used to map to any descendant.
+ // Check child widget first.
+ for (int i = 0; i < child_widget_count; i++) {
+ Widget* child_widget = child_widgets[i];
+ IAccessible* child_accessible =
+ child_widget->GetRootView()->GetNativeViewAccessible();
+ HRESULT result = child_accessible->get_accChild(var_child, disp_child);
+ if (result == S_OK)
+ return result;
+ }
+
+ // We map child ids to a view storage id that can refer to a
// specific view (if that view still exists).
int view_storage_id_index =
base::win::kFirstViewsAccessibilityId - child_id;
@@ -378,10 +513,8 @@ STDMETHODIMP NativeViewAccessibilityWin::get_accChild(VARIANT var_child,
} else {
*disp_child = AccessibleWebViewRegistry::GetInstance()->
GetAccessibleFromWebView(view_, child_id);
- if (*disp_child) {
- (*disp_child)->AddRef();
+ if (*disp_child)
return S_OK;
- }
}
}
@@ -404,6 +537,15 @@ STDMETHODIMP NativeViewAccessibilityWin::get_accChildCount(LONG* child_count) {
return E_FAIL;
*child_count = view_->child_count();
+
+ // If this is a root view, our widget might have child widgets. Include
+ // them, too.
+ if (view_->GetWidget()->GetRootView() == view_) {
+ std::vector<Widget*> child_widgets;
+ PopulateChildWidgetVector(&child_widgets);
+ *child_count += child_widgets.size();
+ }
+
return S_OK;
}
@@ -929,6 +1071,9 @@ STDMETHODIMP NativeViewAccessibilityWin::QueryService(
if (!view_)
return E_FAIL;
+ if (riid == IID_IAccessible2)
+ AccessibleWebViewRegistry::GetInstance()->EnableIAccessible2Support();
+
if (guidService == IID_IAccessible ||
guidService == IID_IAccessible2 ||
guidService == IID_IAccessibleText) {
@@ -996,11 +1141,11 @@ STDMETHODIMP NativeViewAccessibilityWin::GetPropertyValue(PROPERTYID id,
// Static methods.
//
-void NativeViewAccessibility::RegisterWebView(AccessibleWebView* web_view) {
+void NativeViewAccessibility::RegisterWebView(View* web_view) {
AccessibleWebViewRegistry::GetInstance()->RegisterWebView(web_view);
}
-void NativeViewAccessibility::UnregisterWebView(AccessibleWebView* web_view) {
+void NativeViewAccessibility::UnregisterWebView(View* web_view) {
AccessibleWebViewRegistry::GetInstance()->UnregisterWebView(web_view);
}
@@ -1244,4 +1389,26 @@ LONG NativeViewAccessibilityWin::FindBoundary(
text, line_breaks, boundary, start_offset, direction);
}
+void NativeViewAccessibilityWin::PopulateChildWidgetVector(
+ std::vector<Widget*>* result_child_widgets) {
+ const Widget* widget = view()->GetWidget();
+ std::set<Widget*> child_widgets;
+ Widget::GetAllChildWidgets(widget->GetNativeView(), &child_widgets);
+ Widget::GetAllOwnedWidgets(widget->GetNativeView(), &child_widgets);
+ for (std::set<Widget*>::const_iterator iter = child_widgets.begin();
+ iter != child_widgets.end(); ++iter) {
+ Widget* child_widget = *iter;
+ if (child_widget == widget)
+ continue;
+
+ if (!child_widget->IsVisible())
+ continue;
+
+ if (widget->GetNativeWindowProperty(kWidgetNativeViewHostKey))
+ continue;
+
+ result_child_widgets->push_back(child_widget);
+ }
+}
+
} // namespace views
diff --git a/chromium/ui/views/accessibility/native_view_accessibility_win.h b/chromium/ui/views/accessibility/native_view_accessibility_win.h
index e616551b968..83d03dbe5d8 100644
--- a/chromium/ui/views/accessibility/native_view_accessibility_win.h
+++ b/chromium/ui/views/accessibility/native_view_accessibility_win.h
@@ -69,7 +69,7 @@ NativeViewAccessibilityWin
// Supported IAccessible methods.
// Retrieves the child element or child object at a given point on the screen.
- STDMETHODIMP accHitTest(LONG x_left, LONG y_top, VARIANT* child);
+ virtual STDMETHODIMP accHitTest(LONG x_left, LONG y_top, VARIANT* child);
// Performs the object's default action.
STDMETHODIMP accDoDefaultAction(VARIANT var_id);
@@ -85,10 +85,10 @@ NativeViewAccessibilityWin
STDMETHODIMP accNavigate(LONG nav_dir, VARIANT start, VARIANT* end);
// Retrieves an IDispatch interface pointer for the specified child.
- STDMETHODIMP get_accChild(VARIANT var_child, IDispatch** disp_child);
+ virtual STDMETHODIMP get_accChild(VARIANT var_child, IDispatch** disp_child);
// Retrieves the number of accessible children.
- STDMETHODIMP get_accChildCount(LONG* child_count);
+ virtual STDMETHODIMP get_accChildCount(LONG* child_count);
// Retrieves a string that describes the object's default action.
STDMETHODIMP get_accDefaultAction(VARIANT var_id, BSTR* default_action);
@@ -349,9 +349,12 @@ NativeViewAccessibilityWin
// to MSAA states set.
static int32 MSAAState(ui::AccessibilityTypes::State state);
- private:
+ protected:
NativeViewAccessibilityWin();
+ const View* view() const { return view_; }
+
+ private:
// Determines navigation direction for accNavigate, based on left, up and
// previous being mapped all to previous and right, down, next being mapped
// to next. Returns true if navigation direction is next, false otherwise.
@@ -388,7 +391,10 @@ NativeViewAccessibilityWin
LONG start_offset,
ui::TextBoundaryDirection direction);
- IAccessible* GetAccessibleFromWebView(long child_id);
+ // Populates the given vector with all widgets that are either a child
+ // or are owned by this view's widget, and who are not contained in a
+ // NativeViewHost.
+ void PopulateChildWidgetVector(std::vector<Widget*>* child_widgets);
// Give CComObject access to the class constructor.
template <class Base> friend class CComObject;
diff --git a/chromium/ui/views/accessibility/native_view_accessibility_win_unittest.cc b/chromium/ui/views/accessibility/native_view_accessibility_win_unittest.cc
index 7dcbac22145..5bd5bed7b91 100644
--- a/chromium/ui/views/accessibility/native_view_accessibility_win_unittest.cc
+++ b/chromium/ui/views/accessibility/native_view_accessibility_win_unittest.cc
@@ -7,6 +7,7 @@
#include "base/win/scoped_bstr.h"
#include "base/win/scoped_comptr.h"
#include "base/win/scoped_variant.h"
+#include "ui/views/accessibility/native_view_accessibility.h"
#include "ui/views/controls/textfield/textfield.h"
#include "ui/views/test/views_test_base.h"
@@ -61,5 +62,63 @@ TEST_F(NativeViewAcccessibilityWinTest, TextfieldAccessibility) {
ASSERT_STREQ(L"New value", textfield->text().c_str());
}
+TEST_F(NativeViewAcccessibilityWinTest, UnattachedWebView) {
+ // This is a regression test. Calling get_accChild on the native accessible
+ // object for a WebView with no attached WebContents was causing an
+ // infinite loop and crash. This test simulates that with an ordinary
+ // View that registers itself as a web view with NativeViewAcccessibility.
+
+ Widget widget;
+ Widget::InitParams init_params =
+ CreateParams(Widget::InitParams::TYPE_POPUP);
+ init_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ widget.Init(init_params);
+
+ View* content = new View;
+ widget.SetContentsView(content);
+
+ View* web_view = new View;
+ content->AddChildView(web_view);
+ NativeViewAccessibility::RegisterWebView(web_view);
+
+ base::win::ScopedComPtr<IAccessible> web_view_accessible(
+ web_view->GetNativeViewAccessible());
+ base::win::ScopedComPtr<IDispatch> result_dispatch;
+ base::win::ScopedVariant child_index(-999);
+ ASSERT_EQ(E_FAIL, web_view_accessible->get_accChild(
+ child_index, result_dispatch.Receive()));
+
+ NativeViewAccessibility::UnregisterWebView(web_view);
+}
+
+#if defined(USE_AURA)
+TEST_F(NativeViewAcccessibilityWinTest, AuraOwnedWidgets) {
+ Widget widget;
+ Widget::InitParams init_params =
+ CreateParams(Widget::InitParams::TYPE_WINDOW);
+ init_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ widget.Init(init_params);
+
+ base::win::ScopedComPtr<IAccessible> root_view_accessible(
+ widget.GetRootView()->GetNativeViewAccessible());
+
+ LONG child_count = 0;
+ ASSERT_EQ(S_OK, root_view_accessible->get_accChildCount(&child_count));
+ ASSERT_EQ(1L, child_count);
+
+ Widget owned_widget;
+ Widget::InitParams owned_init_params =
+ CreateParams(Widget::InitParams::TYPE_POPUP);
+ owned_init_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ owned_init_params.child = false;
+ owned_init_params.parent = widget.GetNativeView();
+ owned_widget.Init(owned_init_params);
+ owned_widget.Show();
+
+ ASSERT_EQ(S_OK, root_view_accessible->get_accChildCount(&child_count));
+ ASSERT_EQ(2L, child_count);
+}
+#endif
+
} // namespace test
} // namespace views
diff --git a/chromium/ui/views/animation/bounds_animator.cc b/chromium/ui/views/animation/bounds_animator.cc
index c064cc810f6..839294ff74c 100644
--- a/chromium/ui/views/animation/bounds_animator.cc
+++ b/chromium/ui/views/animation/bounds_animator.cc
@@ -5,18 +5,18 @@
#include "ui/views/animation/bounds_animator.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/animation/animation_container.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/animation_container.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/views/animation/bounds_animator_observer.h"
#include "ui/views/view.h"
// Duration in milliseconds for animations.
static const int kDefaultAnimationDuration = 200;
-using ui::Animation;
-using ui::AnimationContainer;
-using ui::SlideAnimation;
-using ui::Tween;
+using gfx::Animation;
+using gfx::AnimationContainer;
+using gfx::SlideAnimation;
+using gfx::Tween;
namespace views {
diff --git a/chromium/ui/views/animation/bounds_animator.h b/chromium/ui/views/animation/bounds_animator.h
index 4082b5c38d0..1688dd56235 100644
--- a/chromium/ui/views/animation/bounds_animator.h
+++ b/chromium/ui/views/animation/bounds_animator.h
@@ -10,13 +10,13 @@
#include "base/compiler_specific.h"
#include "base/memory/ref_counted.h"
#include "base/observer_list.h"
-#include "ui/base/animation/animation_container_observer.h"
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/animation/tween.h"
+#include "ui/gfx/animation/animation_container_observer.h"
+#include "ui/gfx/animation/animation_delegate.h"
+#include "ui/gfx/animation/tween.h"
#include "ui/gfx/rect.h"
#include "ui/views/views_export.h"
-namespace ui {
+namespace gfx {
class SlideAnimation;
}
@@ -35,12 +35,12 @@ class View;
// You can attach an AnimationDelegate to the individual animation for a view
// by way of SetAnimationDelegate. Additionally you can attach an observer to
// the BoundsAnimator that is notified when all animations are complete.
-class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
- public ui::AnimationContainerObserver {
+class VIEWS_EXPORT BoundsAnimator : public gfx::AnimationDelegate,
+ public gfx::AnimationContainerObserver {
public:
// If |delete_when_done| is set to true in |SetAnimationDelegate| the
// |AnimationDelegate| must subclass this class.
- class OwnedAnimationDelegate : public ui::AnimationDelegate {
+ class OwnedAnimationDelegate : public gfx::AnimationDelegate {
public:
virtual ~OwnedAnimationDelegate() {}
};
@@ -65,11 +65,11 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
// Sets the animation for the specified view. BoundsAnimator takes ownership
// of the specified animation.
- void SetAnimationForView(View* view, ui::SlideAnimation* animation);
+ void SetAnimationForView(View* view, gfx::SlideAnimation* animation);
// Returns the animation for the specified view. BoundsAnimator owns the
// returned Animation.
- const ui::SlideAnimation* GetAnimationForView(View* view);
+ const gfx::SlideAnimation* GetAnimationForView(View* view);
// Stops animating the specified view.
void StopAnimatingView(View* view);
@@ -78,7 +78,7 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
// |delete_when_done| is true the |delegate| is deleted when done and
// |delegate| must subclass OwnedAnimationDelegate.
void SetAnimationDelegate(View* view,
- ui::AnimationDelegate* delegate,
+ gfx::AnimationDelegate* delegate,
bool delete_when_done);
// Returns true if BoundsAnimator is animating the bounds of |view|.
@@ -96,14 +96,14 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
void SetAnimationDuration(int duration_ms);
// Sets the tween type for new animations. Default is EASE_OUT.
- void set_tween_type(ui::Tween::Type type) { tween_type_ = type; }
+ void set_tween_type(gfx::Tween::Type type) { tween_type_ = type; }
void AddObserver(BoundsAnimatorObserver* observer);
void RemoveObserver(BoundsAnimatorObserver* observer);
protected:
// Creates the animation to use for animating views.
- virtual ui::SlideAnimation* CreateAnimation();
+ virtual gfx::SlideAnimation* CreateAnimation();
private:
// Tracks data about the view being animated.
@@ -123,10 +123,10 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
gfx::Rect target_bounds;
// The animation. We own this.
- ui::SlideAnimation* animation;
+ gfx::SlideAnimation* animation;
// Additional delegate for the animation, may be null.
- ui::AnimationDelegate* delegate;
+ gfx::AnimationDelegate* delegate;
};
// Used by AnimationEndedOrCanceled.
@@ -137,7 +137,7 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
typedef std::map<View*, Data> ViewToDataMap;
- typedef std::map<const ui::Animation*, View*> AnimationToViewMap;
+ typedef std::map<const gfx::Animation*, View*> AnimationToViewMap;
// Removes references to |view| and its animation. This does NOT delete the
// animation or delegate.
@@ -150,22 +150,22 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
// Used when changing the animation for a view. This resets the maps for
// the animation used by view and returns the current animation. Ownership
// of the returned animation passes to the caller.
- ui::Animation* ResetAnimationForView(View* view);
+ gfx::Animation* ResetAnimationForView(View* view);
// Invoked from AnimationEnded and AnimationCanceled.
- void AnimationEndedOrCanceled(const ui::Animation* animation,
+ void AnimationEndedOrCanceled(const gfx::Animation* animation,
AnimationEndType type);
- // ui::AnimationDelegate overrides.
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationCanceled(const ui::Animation* animation) OVERRIDE;
+ // gfx::AnimationDelegate overrides.
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationCanceled(const gfx::Animation* animation) OVERRIDE;
- // ui::AnimationContainerObserver overrides.
+ // gfx::AnimationContainerObserver overrides.
virtual void AnimationContainerProgressed(
- ui::AnimationContainer* container) OVERRIDE;
+ gfx::AnimationContainer* container) OVERRIDE;
virtual void AnimationContainerEmpty(
- ui::AnimationContainer* container) OVERRIDE;
+ gfx::AnimationContainer* container) OVERRIDE;
// Parent of all views being animated.
View* parent_;
@@ -173,7 +173,7 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
ObserverList<BoundsAnimatorObserver> observers_;
// All animations we create up with the same container.
- scoped_refptr<ui::AnimationContainer> container_;
+ scoped_refptr<gfx::AnimationContainer> container_;
// Maps from view being animated to info about the view.
ViewToDataMap data_;
@@ -189,7 +189,7 @@ class VIEWS_EXPORT BoundsAnimator : public ui::AnimationDelegate,
int animation_duration_ms_;
- ui::Tween::Type tween_type_;
+ gfx::Tween::Type tween_type_;
DISALLOW_COPY_AND_ASSIGN(BoundsAnimator);
};
diff --git a/chromium/ui/views/animation/bounds_animator_unittest.cc b/chromium/ui/views/animation/bounds_animator_unittest.cc
index ed7dca590bf..0928fe665b0 100644
--- a/chromium/ui/views/animation/bounds_animator_unittest.cc
+++ b/chromium/ui/views/animation/bounds_animator_unittest.cc
@@ -5,13 +5,13 @@
#include "ui/views/animation/bounds_animator.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/animation/slide_animation.h"
-#include "ui/base/animation/test_animation_delegate.h"
+#include "ui/gfx/animation/slide_animation.h"
+#include "ui/gfx/animation/test_animation_delegate.h"
#include "ui/views/view.h"
-using ui::Animation;
-using ui::SlideAnimation;
-using ui::TestAnimationDelegate;
+using gfx::Animation;
+using gfx::SlideAnimation;
+using gfx::TestAnimationDelegate;
namespace views {
namespace {
@@ -52,7 +52,7 @@ class OwnedDelegate : public BoundsAnimator::OwnedAnimationDelegate {
return value;
}
- // Overridden from ui::AnimationDelegate:
+ // Overridden from gfx::AnimationDelegate:
virtual void AnimationCanceled(const Animation* animation) OVERRIDE {
canceled_ = true;
}
diff --git a/chromium/ui/views/animation/scroll_animator.cc b/chromium/ui/views/animation/scroll_animator.cc
index 1e484a37c80..7d689993f2b 100644
--- a/chromium/ui/views/animation/scroll_animator.cc
+++ b/chromium/ui/views/animation/scroll_animator.cc
@@ -8,7 +8,7 @@
#include <cmath>
#include "base/logging.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
namespace {
const float kDefaultAcceleration = -1500.0f; // in pixels per second^2
@@ -51,7 +51,7 @@ void ScrollAnimator::Start(float velocity_x, float velocity_y) {
velocity_x_ = velocity_x;
velocity_y_ = velocity_y;
duration_ = -v / acceleration_; // in seconds
- animation_.reset(new ui::SlideAnimation(this));
+ animation_.reset(new gfx::SlideAnimation(this));
animation_->SetSlideDuration(static_cast<int>(duration_ * 1000));
animation_->Show();
}
@@ -61,11 +61,11 @@ void ScrollAnimator::Stop() {
animation_.reset();
}
-void ScrollAnimator::AnimationEnded(const ui::Animation* animation) {
+void ScrollAnimator::AnimationEnded(const gfx::Animation* animation) {
Stop();
}
-void ScrollAnimator::AnimationProgressed(const ui::Animation* animation) {
+void ScrollAnimator::AnimationProgressed(const gfx::Animation* animation) {
float t = static_cast<float>(animation->GetCurrentValue()) * duration_;
float a_x = velocity_x_ > 0 ? acceleration_ : -acceleration_;
float a_y = velocity_y_ > 0 ? acceleration_ : -acceleration_;
@@ -75,7 +75,7 @@ void ScrollAnimator::AnimationProgressed(const ui::Animation* animation) {
delegate_->OnScroll(dx, dy);
}
-void ScrollAnimator::AnimationCanceled(const ui::Animation* animation) {
+void ScrollAnimator::AnimationCanceled(const gfx::Animation* animation) {
Stop();
}
diff --git a/chromium/ui/views/animation/scroll_animator.h b/chromium/ui/views/animation/scroll_animator.h
index 35e159bc552..525a99801f5 100644
--- a/chromium/ui/views/animation/scroll_animator.h
+++ b/chromium/ui/views/animation/scroll_animator.h
@@ -7,10 +7,10 @@
#include "base/basictypes.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
#include "ui/views/views_export.h"
-namespace ui {
+namespace gfx {
class SlideAnimation;
}
@@ -25,7 +25,7 @@ class VIEWS_EXPORT ScrollDelegate {
~ScrollDelegate() {}
};
-class VIEWS_EXPORT ScrollAnimator : public ui::AnimationDelegate {
+class VIEWS_EXPORT ScrollAnimator : public gfx::AnimationDelegate {
public:
// The ScrollAnimator does not own the delegate. Uses default acceleration.
explicit ScrollAnimator(ScrollDelegate* delegate);
@@ -40,10 +40,10 @@ class VIEWS_EXPORT ScrollAnimator : public ui::AnimationDelegate {
bool is_scrolling() const { return !!animation_.get(); }
private:
- // Implementation of ui::AnimationDelegate.
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationCanceled(const ui::Animation* animation) OVERRIDE;
+ // Implementation of gfx::AnimationDelegate.
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationCanceled(const gfx::Animation* animation) OVERRIDE;
ScrollDelegate* delegate_;
@@ -53,7 +53,7 @@ class VIEWS_EXPORT ScrollAnimator : public ui::AnimationDelegate {
float duration_;
float acceleration_;
- scoped_ptr<ui::SlideAnimation> animation_;
+ scoped_ptr<gfx::SlideAnimation> animation_;
DISALLOW_COPY_AND_ASSIGN(ScrollAnimator);
};
diff --git a/chromium/ui/views/bubble/bubble_border.cc b/chromium/ui/views/bubble/bubble_border.cc
index 3c9a3206df2..6494c7b2f40 100644
--- a/chromium/ui/views/bubble/bubble_border.cc
+++ b/chromium/ui/views/bubble/bubble_border.cc
@@ -73,25 +73,53 @@ namespace {
// The border and arrow stroke size used in image assets, in pixels.
const int kStroke = 1;
-// Macros to define arrays of IDR constants used with CreateImageGridPainter.
-#define IMAGE_BORDER(x) { x ## _TOP_LEFT, x ## _TOP, x ## _TOP_RIGHT, \
- x ## _LEFT, 0, x ## _RIGHT, \
- x ## _BOTTOM_LEFT, x ## _BOTTOM, x ## _BOTTOM_RIGHT, }
-#define IMAGE_BORDER_ACRONYM(x) { x ## _TL, x ## _T, x ## _TR, \
- x ## _L, 0, x ## _R, \
- x ## _BL, x ## _B, x ## _BR, }
-#define ARROWS(x) { x ## _LEFT, x ## _TOP, x ## _RIGHT, x ## _BOTTOM, }
-
-// Bubble border and arrow image resource ids.
-const int kShadowImages[] = IMAGE_BORDER_ACRONYM(IDR_BUBBLE_SHADOW);
+// Bubble border and arrow image resource ids. They don't use the IMAGE_GRID
+// macro because there is no center image.
+const int kShadowImages[] = {
+ IDR_BUBBLE_SHADOW_TL, IDR_BUBBLE_SHADOW_T, IDR_BUBBLE_SHADOW_TR,
+ IDR_BUBBLE_SHADOW_L, 0, IDR_BUBBLE_SHADOW_R,
+ IDR_BUBBLE_SHADOW_BL, IDR_BUBBLE_SHADOW_B, IDR_BUBBLE_SHADOW_BR };
const int kShadowArrows[] = { 0, 0, 0, 0 };
-const int kNoShadowImages[] = IMAGE_BORDER_ACRONYM(IDR_BUBBLE);
-const int kNoShadowArrows[] = { IDR_BUBBLE_L_ARROW, IDR_BUBBLE_T_ARROW,
- IDR_BUBBLE_R_ARROW, IDR_BUBBLE_B_ARROW, };
-const int kBigShadowImages[] = IMAGE_BORDER(IDR_WINDOW_BUBBLE_SHADOW_BIG);
-const int kBigShadowArrows[] = ARROWS(IDR_WINDOW_BUBBLE_SHADOW_SPIKE_BIG);
-const int kSmallShadowImages[] = IMAGE_BORDER(IDR_WINDOW_BUBBLE_SHADOW_SMALL);
-const int kSmallShadowArrows[] = ARROWS(IDR_WINDOW_BUBBLE_SHADOW_SPIKE_SMALL);
+
+const int kNoShadowImages[] = {
+ IDR_BUBBLE_TL, IDR_BUBBLE_T, IDR_BUBBLE_TR,
+ IDR_BUBBLE_L, 0, IDR_BUBBLE_R,
+ IDR_BUBBLE_BL, IDR_BUBBLE_B, IDR_BUBBLE_BR };
+const int kNoShadowArrows[] = {
+ IDR_BUBBLE_L_ARROW, IDR_BUBBLE_T_ARROW,
+ IDR_BUBBLE_R_ARROW, IDR_BUBBLE_B_ARROW, };
+
+const int kBigShadowImages[] = {
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_TOP_LEFT,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_TOP,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_TOP_RIGHT,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_LEFT,
+ 0,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_RIGHT,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_BOTTOM_LEFT,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_BOTTOM,
+ IDR_WINDOW_BUBBLE_SHADOW_BIG_BOTTOM_RIGHT };
+const int kBigShadowArrows[] = {
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_BIG_LEFT,
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_BIG_TOP,
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_BIG_RIGHT,
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_BIG_BOTTOM };
+
+const int kSmallShadowImages[] = {
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_TOP_LEFT,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_TOP,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_TOP_RIGHT,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_LEFT,
+ 0,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_RIGHT,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_BOTTOM_LEFT,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_BOTTOM,
+ IDR_WINDOW_BUBBLE_SHADOW_SMALL_BOTTOM_RIGHT };
+const int kSmallShadowArrows[] = {
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_SMALL_LEFT,
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_SMALL_TOP,
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_SMALL_RIGHT,
+ IDR_WINDOW_BUBBLE_SHADOW_SPIKE_SMALL_BOTTOM };
using internal::BorderImages;
diff --git a/chromium/ui/views/bubble/bubble_delegate.cc b/chromium/ui/views/bubble/bubble_delegate.cc
index 3987589f3fc..af08994d487 100644
--- a/chromium/ui/views/bubble/bubble_delegate.cc
+++ b/chromium/ui/views/bubble/bubble_delegate.cc
@@ -4,7 +4,7 @@
#include "ui/views/bubble/bubble_delegate.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/gfx/color_utils.h"
#include "ui/gfx/rect.h"
#include "ui/native_theme/native_theme.h"
@@ -46,6 +46,8 @@ Widget* CreateBubbleWidget(BubbleDelegateView* bubble) {
return bubble_widget;
}
+} // namespace
+
#if defined(OS_WIN) && !defined(USE_AURA)
// Windows uses two widgets and some extra complexity to host partially
// transparent native controls and use per-pixel HWND alpha on the border.
@@ -60,8 +62,7 @@ class BubbleBorderDelegate : public WidgetDelegate,
}
virtual ~BubbleBorderDelegate() {
- if (bubble_ && bubble_->GetWidget())
- bubble_->GetWidget()->RemoveObserver(this);
+ DetachFromBubble();
}
// WidgetDelegate overrides:
@@ -82,17 +83,30 @@ class BubbleBorderDelegate : public WidgetDelegate,
// WidgetObserver overrides:
virtual void OnWidgetDestroying(Widget* widget) OVERRIDE {
- bubble_ = NULL;
+ DetachFromBubble();
widget_->Close();
}
private:
+ // Removes state installed on |bubble_|, including references |bubble_| has to
+ // us.
+ void DetachFromBubble() {
+ if (!bubble_)
+ return;
+ if (bubble_->GetWidget())
+ bubble_->GetWidget()->RemoveObserver(this);
+ bubble_->border_widget_ = NULL;
+ bubble_ = NULL;
+ }
+
BubbleDelegateView* bubble_;
Widget* widget_;
DISALLOW_COPY_AND_ASSIGN(BubbleBorderDelegate);
};
+namespace {
+
// Create a widget to host the bubble's border.
Widget* CreateBorderWidget(BubbleDelegateView* bubble) {
Widget* border_widget = new Widget();
@@ -106,10 +120,11 @@ Widget* CreateBorderWidget(BubbleDelegateView* bubble) {
border_widget->set_focus_on_creation(false);
return border_widget;
}
-#endif
} // namespace
+#endif
+
BubbleDelegateView::BubbleDelegateView()
: close_on_esc_(true),
close_on_deactivate_(true),
@@ -223,20 +238,21 @@ void BubbleDelegateView::OnWidgetDestroying(Widget* widget) {
}
}
+void BubbleDelegateView::OnWidgetVisibilityChanging(Widget* widget,
+ bool visible) {
+#if defined(OS_WIN)
+ // On Windows we need to handle this before the bubble is visible or hidden.
+ // Please see the comment on the OnWidgetVisibilityChanging function. On
+ // other platforms it is fine to handle it after the bubble is shown/hidden.
+ HandleVisibilityChanged(widget, visible);
+#endif
+}
+
void BubbleDelegateView::OnWidgetVisibilityChanged(Widget* widget,
bool visible) {
- if (widget != GetWidget())
- return;
-
- if (visible) {
- if (border_widget_)
- border_widget_->ShowInactive();
- if (anchor_widget() && anchor_widget()->GetTopLevelWidget())
- anchor_widget()->GetTopLevelWidget()->DisableInactiveRendering();
- } else {
- if (border_widget_)
- border_widget_->Hide();
- }
+#if !defined(OS_WIN)
+ HandleVisibilityChanged(widget, visible);
+#endif
}
void BubbleDelegateView::OnWidgetActivationChanged(Widget* widget,
@@ -269,7 +285,7 @@ void BubbleDelegateView::StartFade(bool fade_in) {
else
GetWidget()->Close();
#else
- fade_animation_.reset(new ui::SlideAnimation(this));
+ fade_animation_.reset(new gfx::SlideAnimation(this));
fade_animation_->SetSlideDuration(GetFadeDuration());
fade_animation_->Reset(fade_in ? 0.0 : 1.0);
if (fade_in) {
@@ -322,7 +338,7 @@ void BubbleDelegateView::OnNativeThemeChanged(const ui::NativeTheme* theme) {
UpdateColorsFromTheme(theme);
}
-void BubbleDelegateView::AnimationEnded(const ui::Animation* animation) {
+void BubbleDelegateView::AnimationEnded(const gfx::Animation* animation) {
if (animation != fade_animation_.get())
return;
bool closed = fade_animation_->GetCurrentValue() == 0;
@@ -331,7 +347,7 @@ void BubbleDelegateView::AnimationEnded(const ui::Animation* animation) {
GetWidget()->Close();
}
-void BubbleDelegateView::AnimationProgressed(const ui::Animation* animation) {
+void BubbleDelegateView::AnimationProgressed(const gfx::Animation* animation) {
if (animation != fade_animation_.get())
return;
DCHECK(fade_animation_->is_animating());
@@ -405,4 +421,20 @@ gfx::Rect BubbleDelegateView::GetBubbleClientBounds() const {
}
#endif
+void BubbleDelegateView::HandleVisibilityChanged(Widget* widget,
+ bool visible) {
+ if (widget != GetWidget())
+ return;
+
+ if (visible) {
+ if (border_widget_)
+ border_widget_->ShowInactive();
+ if (anchor_widget() && anchor_widget()->GetTopLevelWidget())
+ anchor_widget()->GetTopLevelWidget()->DisableInactiveRendering();
+ } else {
+ if (border_widget_)
+ border_widget_->Hide();
+ }
+}
+
} // namespace views
diff --git a/chromium/ui/views/bubble/bubble_delegate.h b/chromium/ui/views/bubble/bubble_delegate.h
index c534273dd6f..4a0bb30ec01 100644
--- a/chromium/ui/views/bubble/bubble_delegate.h
+++ b/chromium/ui/views/bubble/bubble_delegate.h
@@ -6,21 +6,19 @@
#define UI_VIEWS_BUBBLE_BUBBLE_DELEGATE_H_
#include "base/gtest_prod_util.h"
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
#include "ui/views/bubble/bubble_border.h"
#include "ui/views/widget/widget_delegate.h"
#include "ui/views/widget/widget_observer.h"
namespace gfx {
class Rect;
-}
-
-namespace ui {
class SlideAnimation;
}
namespace views {
+class BubbleBorderDelegate;
class BubbleFrameView;
// BubbleDelegateView creates frame and client views for bubble Widgets.
@@ -28,7 +26,7 @@ class BubbleFrameView;
//
///////////////////////////////////////////////////////////////////////////////
class VIEWS_EXPORT BubbleDelegateView : public WidgetDelegateView,
- public ui::AnimationDelegate,
+ public gfx::AnimationDelegate,
public WidgetObserver {
public:
BubbleDelegateView();
@@ -47,7 +45,10 @@ class VIEWS_EXPORT BubbleDelegateView : public WidgetDelegateView,
// WidgetObserver overrides:
virtual void OnWidgetDestroying(Widget* widget) OVERRIDE;
- virtual void OnWidgetVisibilityChanged(Widget* widget, bool visible) OVERRIDE;
+ virtual void OnWidgetVisibilityChanging(Widget* widget, bool visible)
+ OVERRIDE;
+ virtual void OnWidgetVisibilityChanged(Widget* widget, bool visible)
+ OVERRIDE;
virtual void OnWidgetActivationChanged(Widget* widget, bool active) OVERRIDE;
virtual void OnWidgetBoundsChanged(Widget* widget,
const gfx::Rect& new_bounds) OVERRIDE;
@@ -133,9 +134,9 @@ class VIEWS_EXPORT BubbleDelegateView : public WidgetDelegateView,
virtual bool AcceleratorPressed(const ui::Accelerator& accelerator) OVERRIDE;
virtual void OnNativeThemeChanged(const ui::NativeTheme* theme) OVERRIDE;
- // ui::AnimationDelegate overrides:
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
+ // gfx::AnimationDelegate overrides:
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
// Perform view initialization on the contents for bubble sizing.
virtual void Init();
@@ -150,6 +151,8 @@ class VIEWS_EXPORT BubbleDelegateView : public WidgetDelegateView,
BubbleFrameView* GetBubbleFrameView() const;
private:
+ friend class BubbleBorderDelegate;
+
FRIEND_TEST_ALL_PREFIXES(BubbleDelegateTest, CreateDelegate);
FRIEND_TEST_ALL_PREFIXES(BubbleDelegateTest, NonClientHitTest);
@@ -161,8 +164,11 @@ class VIEWS_EXPORT BubbleDelegateView : public WidgetDelegateView,
gfx::Rect GetBubbleClientBounds() const;
#endif
+ // Handles widget visibility changes.
+ void HandleVisibilityChanged(Widget* widget, bool visible);
+
// Fade animation for bubble.
- scoped_ptr<ui::SlideAnimation> fade_animation_;
+ scoped_ptr<gfx::SlideAnimation> fade_animation_;
// Flags controlling bubble closure on the escape key and deactivation.
bool close_on_esc_;
diff --git a/chromium/ui/views/bubble/bubble_frame_view.cc b/chromium/ui/views/bubble/bubble_frame_view.cc
index 2bd579d79d9..dca1bc4b85b 100644
--- a/chromium/ui/views/bubble/bubble_frame_view.cc
+++ b/chromium/ui/views/bubble/bubble_frame_view.cc
@@ -168,18 +168,11 @@ gfx::Insets BubbleFrameView::GetInsets() const {
}
gfx::Size BubbleFrameView::GetPreferredSize() {
- const gfx::Size client(GetWidget()->client_view()->GetPreferredSize());
- gfx::Size size(GetUpdatedWindowBounds(gfx::Rect(), client, false).size());
- // Accommodate the width of the title bar elements.
- int title_bar_width = GetInsets().width() + border()->GetInsets().width();
- if (!title_->text().empty())
- title_bar_width += kTitleLeftInset + title_->GetPreferredSize().width();
- if (close_->visible())
- title_bar_width += close_->width() + 1;
- if (titlebar_extra_view_ != NULL)
- title_bar_width += titlebar_extra_view_->GetPreferredSize().width();
- size.SetToMax(gfx::Size(title_bar_width, 0));
- return size;
+ return GetSizeForClientSize(GetWidget()->client_view()->GetPreferredSize());
+}
+
+gfx::Size BubbleFrameView::GetMinimumSize() {
+ return GetSizeForClientSize(GetWidget()->client_view()->GetMinimumSize());
}
void BubbleFrameView::Layout() {
@@ -334,4 +327,19 @@ void BubbleFrameView::OffsetArrowIfOffScreen(const gfx::Rect& anchor_rect,
SchedulePaint();
}
+gfx::Size BubbleFrameView::GetSizeForClientSize(const gfx::Size& client_size) {
+ gfx::Size size(
+ GetUpdatedWindowBounds(gfx::Rect(), client_size, false).size());
+ // Accommodate the width of the title bar elements.
+ int title_bar_width = GetInsets().width() + border()->GetInsets().width();
+ if (!title_->text().empty())
+ title_bar_width += kTitleLeftInset + title_->GetPreferredSize().width();
+ if (close_->visible())
+ title_bar_width += close_->width() + 1;
+ if (titlebar_extra_view_ != NULL)
+ title_bar_width += titlebar_extra_view_->GetPreferredSize().width();
+ size.SetToMax(gfx::Size(title_bar_width, 0));
+ return size;
+}
+
} // namespace views
diff --git a/chromium/ui/views/bubble/bubble_frame_view.h b/chromium/ui/views/bubble/bubble_frame_view.h
index 7dc459623ba..48ef52dd347 100644
--- a/chromium/ui/views/bubble/bubble_frame_view.h
+++ b/chromium/ui/views/bubble/bubble_frame_view.h
@@ -46,6 +46,7 @@ class VIEWS_EXPORT BubbleFrameView : public NonClientFrameView,
// View overrides:
virtual gfx::Insets GetInsets() const OVERRIDE;
virtual gfx::Size GetPreferredSize() OVERRIDE;
+ virtual gfx::Size GetMinimumSize() OVERRIDE;
virtual void Layout() OVERRIDE;
virtual const char* GetClassName() const OVERRIDE;
virtual void ChildPreferredSizeChanged(View* child) OVERRIDE;
@@ -87,6 +88,9 @@ class VIEWS_EXPORT BubbleFrameView : public NonClientFrameView,
void OffsetArrowIfOffScreen(const gfx::Rect& anchor_rect,
const gfx::Size& client_size);
+ // Calculates the size needed to accommodate the given client area.
+ gfx::Size GetSizeForClientSize(const gfx::Size& client_size);
+
// The bubble border.
BubbleBorder* bubble_border_;
diff --git a/chromium/ui/views/bubble/tray_bubble_view.cc b/chromium/ui/views/bubble/tray_bubble_view.cc
index 0d8accdbdb5..6192e51c432 100644
--- a/chromium/ui/views/bubble/tray_bubble_view.cc
+++ b/chromium/ui/views/bubble/tray_bubble_view.cc
@@ -12,10 +12,10 @@
#include "third_party/skia/include/core/SkPath.h"
#include "third_party/skia/include/effects/SkBlurImageFilter.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_delegate.h"
+#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/path.h"
@@ -38,12 +38,40 @@ const int kArrowOffsetLeft = 9;
const int kArrowOffsetRight = -5;
const int kOffsetLeftRightForTopBottomOrientation = 5;
+// The sampling time for mouse position changes in ms - which is roughly a frame
+// time.
+const int kFrameTimeInMS = 30;
} // namespace
namespace views {
namespace internal {
+// Detects any mouse movement. This is needed to detect mouse movements by the
+// user over the bubble if the bubble got created underneath the cursor.
+class MouseMoveDetectorHost : public MouseWatcherHost {
+ public:
+ MouseMoveDetectorHost();
+ virtual ~MouseMoveDetectorHost();
+
+ virtual bool Contains(const gfx::Point& screen_point,
+ MouseEventType type) OVERRIDE;
+ private:
+
+ DISALLOW_COPY_AND_ASSIGN(MouseMoveDetectorHost);
+};
+
+MouseMoveDetectorHost::MouseMoveDetectorHost() {
+}
+
+MouseMoveDetectorHost::~MouseMoveDetectorHost() {
+}
+
+bool MouseMoveDetectorHost::Contains(const gfx::Point& screen_point,
+ MouseEventType type) {
+ return false;
+}
+
// Custom border for TrayBubbleView. Contains special logic for GetBounds()
// to stack bubbles with no arrows correctly. Also calculates the arrow offset.
class TrayBubbleBorder : public BubbleBorder {
@@ -293,7 +321,8 @@ TrayBubbleView::TrayBubbleView(gfx::NativeView parent_window,
delegate_(delegate),
preferred_width_(init_params.min_width),
bubble_border_(NULL),
- is_gesture_dragging_(false) {
+ is_gesture_dragging_(false),
+ mouse_actively_entered_(false) {
set_parent_window(parent_window);
set_notify_enter_exit_on_child(true);
set_close_on_deactivate(init_params.close_on_deactivate);
@@ -309,6 +338,7 @@ TrayBubbleView::TrayBubbleView(gfx::NativeView parent_window,
}
TrayBubbleView::~TrayBubbleView() {
+ mouse_watcher_.reset();
// Inform host items (models) that their views are being destroyed.
if (delegate_)
delegate_->BubbleViewDestroyed();
@@ -414,12 +444,36 @@ int TrayBubbleView::GetHeightForWidth(int width) {
}
void TrayBubbleView::OnMouseEntered(const ui::MouseEvent& event) {
- if (delegate_)
+ mouse_watcher_.reset();
+ if (delegate_ && !(event.flags() & ui::EF_IS_SYNTHESIZED)) {
+ // Coming here the user was actively moving the mouse over the bubble and
+ // we inform the delegate that we entered. This will prevent the bubble
+ // to auto close.
delegate_->OnMouseEnteredView();
+ mouse_actively_entered_ = true;
+ } else {
+ // Coming here the bubble got shown and the mouse was 'accidentally' over it
+ // which is not a reason to prevent the bubble to auto close. As such we
+ // do not call the delegate, but wait for the first mouse move within the
+ // bubble. The used MouseWatcher will notify use of a movement and call
+ // |MouseMovedOutOfHost|.
+ mouse_watcher_.reset(new MouseWatcher(
+ new views::internal::MouseMoveDetectorHost(),
+ this));
+ // Set the mouse sampling frequency to roughly a frame time so that the user
+ // cannot see a lag.
+ mouse_watcher_->set_notify_on_exit_time(
+ base::TimeDelta::FromMilliseconds(kFrameTimeInMS));
+ mouse_watcher_->Start();
+ }
}
void TrayBubbleView::OnMouseExited(const ui::MouseEvent& event) {
- if (delegate_)
+ // If there was a mouse watcher waiting for mouse movements we disable it
+ // immediately since we now leave the bubble.
+ mouse_watcher_.reset();
+ // Do not notify the delegate of an exit if we never told it that we entered.
+ if (delegate_ && mouse_actively_entered_)
delegate_->OnMouseExitedView();
}
@@ -430,6 +484,15 @@ void TrayBubbleView::GetAccessibleState(ui::AccessibleViewState* state) {
}
}
+void TrayBubbleView::MouseMovedOutOfHost() {
+ // The mouse was accidentally over the bubble when it opened and the AutoClose
+ // logic was not activated. Now that the user did move the mouse we tell the
+ // delegate to disable AutoClose.
+ delegate_->OnMouseEnteredView();
+ mouse_actively_entered_ = true;
+ mouse_watcher_->Stop();
+}
+
void TrayBubbleView::ChildPreferredSizeChanged(View* child) {
SizeToContents();
}
diff --git a/chromium/ui/views/bubble/tray_bubble_view.h b/chromium/ui/views/bubble/tray_bubble_view.h
index 9c96c5456b5..1e9d48298ea 100644
--- a/chromium/ui/views/bubble/tray_bubble_view.h
+++ b/chromium/ui/views/bubble/tray_bubble_view.h
@@ -7,6 +7,7 @@
#include "base/memory/scoped_ptr.h"
#include "ui/views/bubble/bubble_delegate.h"
+#include "ui/views/mouse_watcher.h"
#include "ui/views/views_export.h"
// Specialized bubble view for bubbles associated with a tray icon (e.g. the
@@ -30,7 +31,8 @@ class TrayBubbleBorder;
class TrayBubbleContentMask;
}
-class VIEWS_EXPORT TrayBubbleView : public views::BubbleDelegateView {
+class VIEWS_EXPORT TrayBubbleView : public views::BubbleDelegateView,
+ public views::MouseWatcherListener {
public:
// AnchorType differentiates between bubbles that are anchored on a tray
// element (ANCHOR_TYPE_TRAY) and display an arrow, or that are floating on
@@ -62,6 +64,8 @@ class VIEWS_EXPORT TrayBubbleView : public views::BubbleDelegateView {
virtual void BubbleViewDestroyed() = 0;
// Called when the mouse enters/exits the view.
+ // Note: This event will only be called if the mouse gets actively moved by
+ // the user to enter the view.
virtual void OnMouseEnteredView() = 0;
virtual void OnMouseExitedView() = 0;
@@ -159,6 +163,9 @@ class VIEWS_EXPORT TrayBubbleView : public views::BubbleDelegateView {
virtual void OnMouseExited(const ui::MouseEvent& event) OVERRIDE;
virtual void GetAccessibleState(ui::AccessibleViewState* state) OVERRIDE;
+ // Overridden from MouseWatcherListener
+ virtual void MouseMovedOutOfHost() OVERRIDE;
+
protected:
TrayBubbleView(gfx::NativeView parent_window,
views::View* anchor,
@@ -181,6 +188,13 @@ class VIEWS_EXPORT TrayBubbleView : public views::BubbleDelegateView {
scoped_ptr<internal::TrayBubbleContentMask> bubble_content_mask_;
bool is_gesture_dragging_;
+ // True once the mouse cursor was actively moved by the user over the bubble.
+ // Only then the OnMouseExitedView() event will get passed on to listeners.
+ bool mouse_actively_entered_;
+
+ // Used to find any mouse movements.
+ scoped_ptr<MouseWatcher> mouse_watcher_;
+
DISALLOW_COPY_AND_ASSIGN(TrayBubbleView);
};
diff --git a/chromium/ui/views/color_chooser/color_chooser_view.cc b/chromium/ui/views/color_chooser/color_chooser_view.cc
index 07a33a984a4..c4a136b6ea4 100644
--- a/chromium/ui/views/color_chooser/color_chooser_view.cc
+++ b/chromium/ui/views/color_chooser/color_chooser_view.cc
@@ -8,8 +8,8 @@
#include "base/strings/string_number_conversions.h"
#include "base/strings/stringprintf.h"
#include "base/strings/utf_string_conversions.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/views/background.h"
#include "ui/views/border.h"
diff --git a/chromium/ui/views/controls/button/blue_button.cc b/chromium/ui/views/controls/button/blue_button.cc
index a17441e1cbe..3e52afd896e 100644
--- a/chromium/ui/views/controls/button/blue_button.cc
+++ b/chromium/ui/views/controls/button/blue_button.cc
@@ -63,7 +63,12 @@ BlueButton::BlueButton(ButtonListener* listener, const string16& text)
button_border->SetPainter(true, STATE_DISABLED,
Painter::CreateImagePainter(
*rb.GetImageSkiaNamed(IDR_BLUE_BUTTON_DISABLED), insets));
+}
+
+BlueButton::~BlueButton() {}
+void BlueButton::ResetColorsFromNativeTheme() {
+ LabelButton::ResetColorsFromNativeTheme();
if (!gfx::IsInvertedColorScheme()) {
for (size_t state = STATE_NORMAL; state < STATE_COUNT; ++state)
SetTextColor(static_cast<ButtonState>(state), kBlueButtonTextColor);
@@ -72,15 +77,8 @@ BlueButton::BlueButton(ButtonListener* listener, const string16& text)
}
}
-BlueButton::~BlueButton() {}
-
const char* BlueButton::GetClassName() const {
return BlueButton::kViewClassName;
}
-// TODO(msw): Re-enable animations for blue buttons. See crbug.com/239121.
-const ui::Animation* BlueButton::GetThemeAnimation() const {
- return NULL;
-}
-
} // namespace views
diff --git a/chromium/ui/views/controls/button/blue_button.h b/chromium/ui/views/controls/button/blue_button.h
index 0415bf429c7..a169fba85d1 100644
--- a/chromium/ui/views/controls/button/blue_button.h
+++ b/chromium/ui/views/controls/button/blue_button.h
@@ -6,7 +6,6 @@
#define UI_VIEWS_CONTROLS_BUTTON_BLUE_BUTTON_H_
#include "base/compiler_specific.h"
-#include "base/strings/string16.h"
#include "ui/views/controls/button/label_button.h"
namespace views {
@@ -21,8 +20,8 @@ class VIEWS_EXPORT BlueButton : public LabelButton {
private:
// Overridden from LabelButton:
+ virtual void ResetColorsFromNativeTheme() OVERRIDE;
virtual const char* GetClassName() const OVERRIDE;
- virtual const ui::Animation* GetThemeAnimation() const OVERRIDE;
DISALLOW_COPY_AND_ASSIGN(BlueButton);
};
diff --git a/chromium/ui/views/controls/button/custom_button.cc b/chromium/ui/views/controls/button/custom_button.cc
index f8e8b58d2cf..4a15975d5b8 100644
--- a/chromium/ui/views/controls/button/custom_button.cc
+++ b/chromium/ui/views/controls/button/custom_button.cc
@@ -5,9 +5,9 @@
#include "ui/views/controls/button/custom_button.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/animation/throb_animation.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/gfx/animation/throb_animation.h"
#include "ui/gfx/screen.h"
#include "ui/views/widget/widget.h"
@@ -277,9 +277,9 @@ void CustomButton::VisibilityChanged(View* starting_from, bool visible) {
}
////////////////////////////////////////////////////////////////////////////////
-// CustomButton, ui::AnimationDelegate implementation:
+// CustomButton, gfx::AnimationDelegate implementation:
-void CustomButton::AnimationProgressed(const ui::Animation* animation) {
+void CustomButton::AnimationProgressed(const gfx::Animation* animation) {
SchedulePaint();
}
@@ -293,7 +293,7 @@ CustomButton::CustomButton(ButtonListener* listener)
is_throbbing_(false),
triggerable_event_flags_(ui::EF_LEFT_MOUSE_BUTTON),
request_focus_on_press_(true) {
- hover_animation_.reset(new ui::ThrobAnimation(this));
+ hover_animation_.reset(new gfx::ThrobAnimation(this));
hover_animation_->SetSlideDuration(kHoverFadeDurationMs);
}
diff --git a/chromium/ui/views/controls/button/custom_button.h b/chromium/ui/views/controls/button/custom_button.h
index 4d864b42abb..ecb49f60a3f 100644
--- a/chromium/ui/views/controls/button/custom_button.h
+++ b/chromium/ui/views/controls/button/custom_button.h
@@ -6,11 +6,11 @@
#define UI_VIEWS_CONTROLS_BUTTON_CUSTOM_BUTTON_H_
#include "base/memory/scoped_ptr.h"
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
+#include "ui/gfx/animation/animation_delegate.h"
#include "ui/views/controls/button/button.h"
-namespace ui {
+namespace gfx {
class ThrobAnimation;
}
@@ -24,7 +24,7 @@ class CustomButtonStateChangedDelegate;
// part of the focus chain. Call set_focusable(true) to make it part of the
// focus chain.
class VIEWS_EXPORT CustomButton : public Button,
- public ui::AnimationDelegate {
+ public gfx::AnimationDelegate {
public:
// The menu button's class name.
static const char kViewClassName[];
@@ -84,8 +84,8 @@ class VIEWS_EXPORT CustomButton : public Button,
virtual void GetAccessibleState(ui::AccessibleViewState* state) OVERRIDE;
virtual void VisibilityChanged(View* starting_from, bool is_visible) OVERRIDE;
- // Overridden from ui::AnimationDelegate:
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
+ // Overridden from gfx::AnimationDelegate:
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
// Takes ownership of the delegate.
void set_state_changed_delegate(CustomButtonStateChangedDelegate* delegate) {
@@ -120,7 +120,7 @@ class VIEWS_EXPORT CustomButton : public Button,
ButtonState state_;
// Hover animation.
- scoped_ptr<ui::ThrobAnimation> hover_animation_;
+ scoped_ptr<gfx::ThrobAnimation> hover_animation_;
private:
// Should we animate when the state changes? Defaults to true.
diff --git a/chromium/ui/views/controls/button/image_button.cc b/chromium/ui/views/controls/button/image_button.cc
index ff355ebd68e..17f74167c7c 100644
--- a/chromium/ui/views/controls/button/image_button.cc
+++ b/chromium/ui/views/controls/button/image_button.cc
@@ -6,7 +6,7 @@
#include "base/strings/utf_string_conversions.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/animation/throb_animation.h"
+#include "ui/gfx/animation/throb_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image_skia_operations.h"
#include "ui/views/widget/widget.h"
@@ -16,6 +16,8 @@ namespace views {
static const int kDefaultWidth = 16; // Default button width if no theme.
static const int kDefaultHeight = 14; // Default button height if no theme.
+const char ImageButton::kViewClassName[] = "ImageButton";
+
////////////////////////////////////////////////////////////////////////////////
// ImageButton, public:
@@ -84,6 +86,10 @@ gfx::Size ImageButton::GetPreferredSize() {
return size;
}
+const char* ImageButton::GetClassName() const {
+ return kViewClassName;
+}
+
void ImageButton::OnPaint(gfx::Canvas* canvas) {
// Call the base class first to paint any background/borders.
View::OnPaint(canvas);
diff --git a/chromium/ui/views/controls/button/image_button.h b/chromium/ui/views/controls/button/image_button.h
index 4015def5a6a..5ea0fa91ead 100644
--- a/chromium/ui/views/controls/button/image_button.h
+++ b/chromium/ui/views/controls/button/image_button.h
@@ -20,6 +20,8 @@ namespace views {
class VIEWS_EXPORT ImageButton : public CustomButton {
public:
+ static const char kViewClassName[];
+
enum HorizontalAlignment {
ALIGN_LEFT = 0,
ALIGN_CENTER,
@@ -56,6 +58,7 @@ class VIEWS_EXPORT ImageButton : public CustomButton {
// Overridden from View:
virtual gfx::Size GetPreferredSize() OVERRIDE;
+ virtual const char* GetClassName() const OVERRIDE;
virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE;
// Sets preferred size, so it could be correctly positioned in layout even if
diff --git a/chromium/ui/views/controls/button/label_button.cc b/chromium/ui/views/controls/button/label_button.cc
index 9fab63b0086..ae4ffe05311 100644
--- a/chromium/ui/views/controls/button/label_button.cc
+++ b/chromium/ui/views/controls/button/label_button.cc
@@ -6,8 +6,8 @@
#include "base/logging.h"
#include "grit/ui_resources.h"
-#include "ui/base/animation/throb_animation.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/gfx/animation/throb_animation.h"
#include "ui/gfx/sys_color_change_listener.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/controls/button/label_button_border.h"
@@ -128,7 +128,7 @@ void LabelButton::SetIsDefault(bool is_default) {
// STYLE_BUTTON uses bold text to indicate default buttons.
if (style_ == STYLE_BUTTON) {
int style = label_->font().GetStyle();
- style = is_default ? style | gfx::Font::BOLD : style & !gfx::Font::BOLD;
+ style = is_default ? style | gfx::Font::BOLD : style & ~gfx::Font::BOLD;
label_->SetFont(label_->font().DeriveFont(0, style));
}
}
@@ -257,10 +257,6 @@ void LabelButton::GetExtraParams(ui::NativeTheme::ExtraParams* params) const {
params->button.background_color = label()->background_color();
}
-void LabelButton::UpdateImage() {
- image_->SetImage(GetImage(state()));
-}
-
void LabelButton::ResetColorsFromNativeTheme() {
const ui::NativeTheme* theme = GetNativeTheme();
SkColor colors[STATE_COUNT] = {
@@ -277,9 +273,6 @@ void LabelButton::ResetColorsFromNativeTheme() {
theme == ui::NativeThemeWin::instance());
#endif
- label_->SetBackgroundColor(theme->GetSystemColor(
- ui::NativeTheme::kColorId_ButtonBackgroundColor));
-
// Use hardcoded colors for inverted color scheme support and STYLE_BUTTON.
if (gfx::IsInvertedColorScheme()) {
constant_text_color = true;
@@ -290,6 +283,8 @@ void LabelButton::ResetColorsFromNativeTheme() {
} else if (style() == STYLE_BUTTON) {
constant_text_color = true;
colors[STATE_NORMAL] = kStyleButtonTextColor;
+ label_->SetBackgroundColor(theme->GetSystemColor(
+ ui::NativeTheme::kColorId_ButtonBackgroundColor));
label_->SetAutoColorReadabilityEnabled(false);
label_->SetShadowColors(kStyleButtonShadowColor, kStyleButtonShadowColor);
label_->SetShadowOffset(0, 1);
@@ -306,6 +301,10 @@ void LabelButton::ResetColorsFromNativeTheme() {
}
}
+void LabelButton::UpdateImage() {
+ image_->SetImage(GetImage(state()));
+}
+
void LabelButton::StateChanged() {
const gfx::Size previous_image_size(image_->GetPreferredSize());
UpdateImage();
@@ -346,7 +345,7 @@ ui::NativeTheme::State LabelButton::GetThemeState(
return ui::NativeTheme::kNormal;
}
-const ui::Animation* LabelButton::GetThemeAnimation() const {
+const gfx::Animation* LabelButton::GetThemeAnimation() const {
#if defined(OS_WIN)
if (style() == STYLE_NATIVE_TEXTBUTTON &&
GetNativeTheme() == ui::NativeThemeWin::instance()) {
diff --git a/chromium/ui/views/controls/button/label_button.h b/chromium/ui/views/controls/button/label_button.h
index 0f501914dc3..f48e9a8e2eb 100644
--- a/chromium/ui/views/controls/button/label_button.h
+++ b/chromium/ui/views/controls/button/label_button.h
@@ -73,6 +73,9 @@ class VIEWS_EXPORT LabelButton : public CustomButton,
// Fill |params| with information about the button.
virtual void GetExtraParams(ui::NativeTheme::ExtraParams* params) const;
+ // Resets colors from the NativeTheme, explicitly set colors are unchanged.
+ virtual void ResetColorsFromNativeTheme();
+
// Updates the image view to contain the appropriate button state image.
void UpdateImage();
@@ -83,9 +86,6 @@ class VIEWS_EXPORT LabelButton : public CustomButton,
FRIEND_TEST_ALL_PREFIXES(LabelButtonTest, LabelAndImage);
FRIEND_TEST_ALL_PREFIXES(LabelButtonTest, Font);
- // Resets colors from the NativeTheme, explicitly set colors are unchanged.
- void ResetColorsFromNativeTheme();
-
// Overridden from CustomButton:
virtual void StateChanged() OVERRIDE;
@@ -98,7 +98,7 @@ class VIEWS_EXPORT LabelButton : public CustomButton,
virtual gfx::Rect GetThemePaintRect() const OVERRIDE;
virtual ui::NativeTheme::State GetThemeState(
ui::NativeTheme::ExtraParams* params) const OVERRIDE;
- virtual const ui::Animation* GetThemeAnimation() const OVERRIDE;
+ virtual const gfx::Animation* GetThemeAnimation() const OVERRIDE;
virtual ui::NativeTheme::State GetBackgroundThemeState(
ui::NativeTheme::ExtraParams* params) const OVERRIDE;
virtual ui::NativeTheme::State GetForegroundThemeState(
diff --git a/chromium/ui/views/controls/button/label_button_border.cc b/chromium/ui/views/controls/button/label_button_border.cc
index efb80df3a1b..fb6ea0695b8 100644
--- a/chromium/ui/views/controls/button/label_button_border.cc
+++ b/chromium/ui/views/controls/button/label_button_border.cc
@@ -6,10 +6,13 @@
#include "base/logging.h"
#include "grit/ui_resources.h"
-#include "ui/base/animation/animation.h"
+#include "third_party/skia/include/core/SkPaint.h"
+#include "third_party/skia/include/effects/SkLerpXfermode.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/gfx/animation/animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/rect.h"
+#include "ui/gfx/skia_util.h"
#include "ui/gfx/sys_color_change_listener.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/controls/button/label_button.h"
@@ -115,21 +118,26 @@ void LabelButtonBorder::Paint(const View& view, gfx::Canvas* canvas) {
gfx::Rect rect(native_theme_delegate->GetThemePaintRect());
ui::NativeTheme::ExtraParams extra;
const ui::NativeTheme* theme = view.GetNativeTheme();
- const ui::Animation* animation = native_theme_delegate->GetThemeAnimation();
+ const gfx::Animation* animation = native_theme_delegate->GetThemeAnimation();
ui::NativeTheme::State state = native_theme_delegate->GetThemeState(&extra);
if (animation && animation->is_animating()) {
- // Composite the background and foreground painters during state animations.
- int alpha = animation->CurrentValueBetween(0, 0xff);
+ // Linearly interpolate background and foreground painters during animation.
+ const SkRect sk_rect = gfx::RectToSkRect(rect);
+ canvas->sk_canvas()->saveLayer(&sk_rect, NULL);
state = native_theme_delegate->GetBackgroundThemeState(&extra);
- canvas->SaveLayerAlpha(static_cast<uint8>(0xff - alpha));
PaintHelper(this, canvas, theme, part, state, rect, extra);
- canvas->Restore();
+ SkPaint paint;
+ skia::RefPtr<SkXfermode> sk_lerp_xfer =
+ skia::AdoptRef(SkLerpXfermode::Create(animation->GetCurrentValue()));
+ paint.setXfermode(sk_lerp_xfer.get());
+ canvas->sk_canvas()->saveLayer(&sk_rect, &paint);
state = native_theme_delegate->GetForegroundThemeState(&extra);
- canvas->SaveLayerAlpha(static_cast<uint8>(alpha));
PaintHelper(this, canvas, theme, part, state, rect, extra);
- canvas->Restore();
+ canvas->sk_canvas()->restore();
+
+ canvas->sk_canvas()->restore();
} else {
PaintHelper(this, canvas, theme, part, state, rect, extra);
}
diff --git a/chromium/ui/views/controls/button/menu_button.cc b/chromium/ui/views/controls/button/menu_button.cc
index 5a20d52b12a..b2e70377281 100644
--- a/chromium/ui/views/controls/button/menu_button.cc
+++ b/chromium/ui/views/controls/button/menu_button.cc
@@ -9,15 +9,16 @@
#include "grit/ui_strings.h"
#include "ui/base/accessibility/accessible_view_state.h"
#include "ui/base/dragdrop/drag_drop_types.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image.h"
#include "ui/gfx/screen.h"
#include "ui/views/controls/button/button.h"
#include "ui/views/controls/button/menu_button_listener.h"
+#include "ui/views/mouse_constants.h"
#include "ui/views/widget/root_view.h"
#include "ui/views/widget/widget.h"
@@ -32,7 +33,6 @@ static const int kDefaultMenuOffsetY = -4;
// static
const char MenuButton::kViewClassName[] = "MenuButton";
-const int64 MenuButton::kMinimumTimeBetweenButtonClicks = 100;
const int MenuButton::kMenuMarkerPaddingLeft = 3;
const int MenuButton::kMenuMarkerPaddingRight = -1;
@@ -182,10 +182,8 @@ bool MenuButton::OnMousePressed(const ui::MouseEvent& event) {
HitTestPoint(event.location()) &&
GetDragOperations(event.location()) == ui::DragDropTypes::DRAG_NONE) {
TimeDelta delta = Time::Now() - menu_closed_time_;
- int64 delta_in_milliseconds = delta.InMilliseconds();
- if (delta_in_milliseconds > kMinimumTimeBetweenButtonClicks) {
+ if (delta.InMilliseconds() > kMinimumMsBetweenButtonClicks)
return Activate();
- }
}
}
return true;
diff --git a/chromium/ui/views/controls/button/menu_button.h b/chromium/ui/views/controls/button/menu_button.h
index 575942b1589..20cdb83316b 100644
--- a/chromium/ui/views/controls/button/menu_button.h
+++ b/chromium/ui/views/controls/button/menu_button.h
@@ -28,10 +28,6 @@ class VIEWS_EXPORT MenuButton : public TextButton {
public:
static const char kViewClassName[];
- // The amount of time, in milliseconds, we wait before allowing another mouse
- // pressed event to show the menu.
- static const int64 kMinimumTimeBetweenButtonClicks;
-
// How much padding to put on the left and right of the menu marker.
static const int kMenuMarkerPaddingLeft;
static const int kMenuMarkerPaddingRight;
diff --git a/chromium/ui/views/controls/button/text_button.cc b/chromium/ui/views/controls/button/text_button.cc
index a02d6b2b0fd..38e9691b19a 100644
--- a/chromium/ui/views/controls/button/text_button.cc
+++ b/chromium/ui/views/controls/button/text_button.cc
@@ -8,8 +8,8 @@
#include "base/logging.h"
#include "grit/ui_resources.h"
-#include "ui/base/animation/throb_animation.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/gfx/animation/throb_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image.h"
#include "ui/views/controls/button/button.h"
@@ -345,7 +345,7 @@ void TextButtonBase::OnBoundsChanged(const gfx::Rect& previous_bounds) {
UpdateTextSize();
}
-const ui::Animation* TextButtonBase::GetAnimation() const {
+const gfx::Animation* TextButtonBase::GetAnimation() const {
return hover_animation_.get();
}
@@ -570,7 +570,7 @@ ui::NativeTheme::State TextButtonBase::GetThemeState(
}
}
-const ui::Animation* TextButtonBase::GetThemeAnimation() const {
+const gfx::Animation* TextButtonBase::GetThemeAnimation() const {
#if defined(OS_WIN)
if (GetNativeTheme() == ui::NativeThemeWin::instance()) {
return ui::NativeThemeWin::instance()->IsThemingActive() ?
diff --git a/chromium/ui/views/controls/button/text_button.h b/chromium/ui/views/controls/button/text_button.h
index c66f288a241..5dccaa2ad11 100644
--- a/chromium/ui/views/controls/button/text_button.h
+++ b/chromium/ui/views/controls/button/text_button.h
@@ -142,7 +142,7 @@ class VIEWS_EXPORT TextButtonBase : public CustomButton,
void set_alignment(TextAlignment alignment) { alignment_ = alignment; }
- const ui::Animation* GetAnimation() const;
+ const gfx::Animation* GetAnimation() const;
void SetIsDefault(bool is_default);
bool is_default() const { return is_default_; }
@@ -234,7 +234,7 @@ class VIEWS_EXPORT TextButtonBase : public CustomButton,
virtual gfx::Rect GetThemePaintRect() const OVERRIDE;
virtual ui::NativeTheme::State GetThemeState(
ui::NativeTheme::ExtraParams* params) const OVERRIDE;
- virtual const ui::Animation* GetThemeAnimation() const OVERRIDE;
+ virtual const gfx::Animation* GetThemeAnimation() const OVERRIDE;
virtual ui::NativeTheme::State GetBackgroundThemeState(
ui::NativeTheme::ExtraParams* params) const OVERRIDE;
virtual ui::NativeTheme::State GetForegroundThemeState(
diff --git a/chromium/ui/views/controls/combobox/combobox.cc b/chromium/ui/views/controls/combobox/combobox.cc
index 34f48484755..8ef7b365e75 100644
--- a/chromium/ui/views/controls/combobox/combobox.cc
+++ b/chromium/ui/views/controls/combobox/combobox.cc
@@ -6,32 +6,101 @@
#include "base/logging.h"
#include "base/strings/utf_string_conversions.h"
+#include "grit/ui_resources.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/models/combobox_model.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/gfx/canvas.h"
+#include "ui/native_theme/native_theme.h"
+#include "ui/views/color_constants.h"
#include "ui/views/controls/combobox/combobox_listener.h"
-#include "ui/views/controls/native/native_view_host.h"
+#include "ui/views/controls/focusable_border.h"
+#include "ui/views/controls/menu/menu_runner.h"
+#include "ui/views/controls/menu/submenu_view.h"
#include "ui/views/controls/prefix_selector.h"
#include "ui/views/ime/input_method.h"
+#include "ui/views/mouse_constants.h"
#include "ui/views/widget/widget.h"
namespace views {
+namespace {
+
+// Menu border widths
+const int kMenuBorderWidthLeft = 1;
+const int kMenuBorderWidthTop = 1;
+const int kMenuBorderWidthRight = 1;
+const int kMenuBorderWidthBottom = 2;
+
+// Limit how small a combobox can be.
+const int kMinComboboxWidth = 25;
+
+// Size of the combobox arrow margins
+const int kDisclosureArrowLeftPadding = 7;
+const int kDisclosureArrowRightPadding = 7;
+
+// Define the id of the first item in the menu (since it needs to be > 0)
+const int kFirstMenuItemId = 1000;
+
+const SkColor kInvalidTextColor = SK_ColorWHITE;
+
+// Used to indicate that no item is currently selected by the user.
+const int kNoSelection = -1;
+
+// The background to use for invalid comboboxes.
+class InvalidBackground : public Background {
+ public:
+ InvalidBackground() {}
+ virtual ~InvalidBackground() {}
+
+ // Overridden from Background:
+ virtual void Paint(gfx::Canvas* canvas, View* view) const OVERRIDE {
+ gfx::Rect bounds(view->GetLocalBounds());
+ // Inset by 2 to leave 1 empty pixel between background and border.
+ bounds.Inset(2, 2, 2, 2);
+ canvas->FillRect(bounds, kWarningColor);
+ }
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(InvalidBackground);
+};
+
+// Returns the next or previous valid index (depending on |increment|'s value).
+// Skips separator indices. Returns -1 if there is no valid adjacent index.
+int GetAdjacentIndex(ui::ComboboxModel* model, int increment, int index) {
+ DCHECK(increment == -1 || increment == 1);
+
+ index += increment;
+ while (index >= 0 && index < model->GetItemCount()) {
+ if (!model->IsItemSeparatorAt(index))
+ return index;
+ index += increment;
+ }
+ return kNoSelection;
+}
+
+} // namespace
+
// static
-const char Combobox::kViewClassName[] = "Combobox";
+const char Combobox::kViewClassName[] = "views/Combobox";
////////////////////////////////////////////////////////////////////////////////
// Combobox, public:
Combobox::Combobox(ui::ComboboxModel* model)
- : native_wrapper_(NULL),
- model_(model),
+ : model_(model),
listener_(NULL),
selected_index_(model_->GetDefaultIndex()),
- invalid_(false) {
+ invalid_(false),
+ text_border_(new FocusableBorder()),
+ disclosure_arrow_(ui::ResourceBundle::GetSharedInstance().GetImageNamed(
+ IDR_MENU_DROPARROW).ToImageSkia()),
+ dropdown_open_(false) {
+ UpdateFromModel();
set_focusable(true);
+ set_border(text_border_);
}
Combobox::~Combobox() {
@@ -45,22 +114,13 @@ const gfx::Font& Combobox::GetFont() {
void Combobox::ModelChanged() {
selected_index_ = std::min(0, model_->GetItemCount());
- if (native_wrapper_)
- native_wrapper_->UpdateFromModel();
+ UpdateFromModel();
PreferredSizeChanged();
}
void Combobox::SetSelectedIndex(int index) {
selected_index_ = index;
- if (native_wrapper_)
- native_wrapper_->UpdateSelectedIndex();
-}
-
-void Combobox::SelectionChanged() {
- selected_index_ = native_wrapper_->GetSelectedIndex();
- if (listener_)
- listener_->OnSelectedIndexChanged(this);
- NotifyAccessibilityEvent(ui::AccessibilityTypes::EVENT_VALUE_CHANGED, false);
+ SchedulePaint();
}
void Combobox::SetAccessibleName(const string16& name) {
@@ -69,8 +129,13 @@ void Combobox::SetAccessibleName(const string16& name) {
void Combobox::SetInvalid(bool invalid) {
invalid_ = invalid;
- if (native_wrapper_)
- native_wrapper_->ValidityStateChanged();
+ if (invalid) {
+ text_border_->SetColor(kWarningColor);
+ set_background(new InvalidBackground());
+ } else {
+ text_border_->UseDefaultColor();
+ set_background(NULL);
+ }
}
ui::TextInputClient* Combobox::GetTextInputClient() {
@@ -79,6 +144,28 @@ ui::TextInputClient* Combobox::GetTextInputClient() {
return selector_.get();
}
+
+bool Combobox::IsItemChecked(int id) const {
+ return false;
+}
+
+bool Combobox::IsCommandEnabled(int id) const {
+ return true;
+}
+
+void Combobox::ExecuteCommand(int id) {
+ // (note that the id received is offset by kFirstMenuItemId)
+ // Revert menu ID offset to map back to combobox model.
+ id -= kFirstMenuItemId;
+ DCHECK_LT(id, model()->GetItemCount());
+ selected_index_ = id;
+ OnSelectionChanged();
+}
+
+bool Combobox::GetAccelerator(int id, ui::Accelerator* accel) {
+ return false;
+}
+
int Combobox::GetRowCount() {
return model()->GetItemCount();
}
@@ -99,65 +186,137 @@ string16 Combobox::GetTextForRow(int row) {
// Combobox, View overrides:
gfx::Size Combobox::GetPreferredSize() {
- if (native_wrapper_)
- return native_wrapper_->GetPreferredSize();
- return gfx::Size();
-}
+ if (content_size_.IsEmpty())
+ UpdateFromModel();
-void Combobox::Layout() {
- if (native_wrapper_) {
- native_wrapper_->GetView()->SetBounds(0, 0, width(), height());
- native_wrapper_->GetView()->Layout();
- }
+ // The preferred size will drive the local bounds which in turn is used to set
+ // the minimum width for the dropdown list.
+ gfx::Insets insets = GetInsets();
+ int total_width = std::max(kMinComboboxWidth, content_size_.width()) +
+ insets.width() + kDisclosureArrowLeftPadding +
+ disclosure_arrow_->width() + kDisclosureArrowRightPadding;
+
+ return gfx::Size(total_width, content_size_.height() + insets.height());
}
-void Combobox::OnEnabledChanged() {
- View::OnEnabledChanged();
- if (native_wrapper_)
- native_wrapper_->UpdateEnabled();
+const char* Combobox::GetClassName() const {
+ return kViewClassName;
}
-// VKEY_ESCAPE should be handled by this view when the drop down list is active.
-// In other words, the list should be closed instead of the dialog.
bool Combobox::SkipDefaultKeyEventProcessing(const ui::KeyEvent& e) {
+ // Escape should close the drop down list when it is active, not host UI.
if (e.key_code() != ui::VKEY_ESCAPE ||
e.IsShiftDown() || e.IsControlDown() || e.IsAltDown()) {
return false;
}
- return native_wrapper_ && native_wrapper_->IsDropdownOpen();
+ return dropdown_open_;
}
-void Combobox::OnPaintFocusBorder(gfx::Canvas* canvas) {
- if (NativeViewHost::kRenderNativeControlFocus)
- View::OnPaintFocusBorder(canvas);
+bool Combobox::OnMousePressed(const ui::MouseEvent& mouse_event) {
+ RequestFocus();
+ const base::TimeDelta delta = base::Time::Now() - closed_time_;
+ if (mouse_event.IsLeftMouseButton() &&
+ (delta.InMilliseconds() > kMinimumMsBetweenButtonClicks)) {
+ UpdateFromModel();
+ ShowDropDownMenu(ui::MENU_SOURCE_MOUSE);
+ }
+
+ return true;
+}
+
+bool Combobox::OnMouseDragged(const ui::MouseEvent& mouse_event) {
+ return true;
}
bool Combobox::OnKeyPressed(const ui::KeyEvent& e) {
- return native_wrapper_ && native_wrapper_->HandleKeyPressed(e);
+ // TODO(oshima): handle IME.
+ DCHECK_EQ(e.type(), ui::ET_KEY_PRESSED);
+
+ DCHECK_GE(selected_index_, 0);
+ DCHECK_LT(selected_index_, model()->GetItemCount());
+ if (selected_index_ < 0 || selected_index_ > model()->GetItemCount())
+ selected_index_ = 0;
+
+ bool show_menu = false;
+ int new_index = kNoSelection;
+ switch (e.key_code()) {
+ // Show the menu on Space.
+ case ui::VKEY_SPACE:
+ show_menu = true;
+ break;
+
+ // Show the menu on Alt+Down (like Windows) or move to the next item if any.
+ case ui::VKEY_DOWN:
+ if (e.IsAltDown())
+ show_menu = true;
+ else
+ new_index = GetAdjacentIndex(model(), 1, selected_index_);
+ break;
+
+ // Move to the end of the list.
+ case ui::VKEY_END:
+ case ui::VKEY_NEXT: // Page down.
+ new_index = GetAdjacentIndex(model(), -1, model()->GetItemCount());
+ break;
+
+ // Move to the beginning of the list.
+ case ui::VKEY_HOME:
+ case ui::VKEY_PRIOR: // Page up.
+ new_index = GetAdjacentIndex(model(), 1, -1);
+ break;
+
+ // Move to the previous item if any.
+ case ui::VKEY_UP:
+ new_index = GetAdjacentIndex(model(), -1, selected_index_);
+ break;
+
+ default:
+ return false;
+ }
+
+ if (show_menu) {
+ UpdateFromModel();
+ ShowDropDownMenu(ui::MENU_SOURCE_KEYBOARD);
+ } else if (new_index != selected_index_ && new_index != kNoSelection) {
+ DCHECK(!model()->IsItemSeparatorAt(new_index));
+ selected_index_ = new_index;
+ OnSelectionChanged();
+ }
+
+ return true;
}
bool Combobox::OnKeyReleased(const ui::KeyEvent& e) {
- return native_wrapper_ && native_wrapper_->HandleKeyReleased(e);
+ return false; // crbug.com/127520
+}
+
+void Combobox::OnGestureEvent(ui::GestureEvent* gesture) {
+ if (gesture->type() == ui::ET_GESTURE_TAP) {
+ UpdateFromModel();
+ ShowDropDownMenu(ui::MENU_SOURCE_TOUCH);
+ gesture->StopPropagation();
+ return;
+ }
+ View::OnGestureEvent(gesture);
+}
+
+void Combobox::OnPaint(gfx::Canvas* canvas) {
+ OnPaintBackground(canvas);
+ PaintText(canvas);
+ OnPaintBorder(canvas);
}
void Combobox::OnFocus() {
GetInputMethod()->OnFocus();
- // Forward the focus to the wrapper.
- if (native_wrapper_) {
- native_wrapper_->SetFocus();
- NotifyAccessibilityEvent(ui::AccessibilityTypes::EVENT_FOCUS, true);
- } else {
- View::OnFocus(); // Will focus the RootView window (so we still get
- // keyboard messages).
- }
+ text_border_->set_has_focus(true);
+ View::OnFocus();
}
void Combobox::OnBlur() {
GetInputMethod()->OnBlur();
if (selector_)
selector_->OnViewBlur();
- if (native_wrapper_)
- native_wrapper_->HandleBlur();
+ text_border_->set_has_focus(false);
}
void Combobox::GetAccessibleState(ui::AccessibleViewState* state) {
@@ -168,24 +327,129 @@ void Combobox::GetAccessibleState(ui::AccessibleViewState* state) {
state->count = model_->GetItemCount();
}
-void Combobox::ViewHierarchyChanged(
- const ViewHierarchyChangedDetails& details) {
- if (details.is_add && !native_wrapper_ && GetWidget()) {
- // The native wrapper's lifetime will be managed by the view hierarchy after
- // we call AddChildView.
- native_wrapper_ = NativeComboboxWrapper::CreateWrapper(this);
- AddChildView(native_wrapper_->GetView());
- // The underlying native widget may not be created until the wrapper is
- // parented. For this reason the wrapper is only updated after adding its
- // view.
- native_wrapper_->UpdateFromModel();
- native_wrapper_->UpdateSelectedIndex();
- native_wrapper_->UpdateEnabled();
+void Combobox::UpdateFromModel() {
+ int max_width = 0;
+ const gfx::Font& font = Combobox::GetFont();
+
+ MenuItemView* menu = new MenuItemView(this);
+ // MenuRunner owns |menu|.
+ dropdown_list_menu_runner_.reset(new MenuRunner(menu));
+
+ int num_items = model()->GetItemCount();
+ for (int i = 0; i < num_items; ++i) {
+ if (model()->IsItemSeparatorAt(i)) {
+ menu->AppendSeparator();
+ continue;
+ }
+
+ string16 text = model()->GetItemAt(i);
+
+ // Inserting the Unicode formatting characters if necessary so that the
+ // text is displayed correctly in right-to-left UIs.
+ base::i18n::AdjustStringForLocaleDirection(&text);
+
+ menu->AppendMenuItem(i + kFirstMenuItemId, text, MenuItemView::NORMAL);
+ max_width = std::max(max_width, font.GetStringWidth(text));
}
+
+ content_size_.SetSize(max_width, font.GetHeight());
}
-const char* Combobox::GetClassName() const {
- return kViewClassName;
+void Combobox::AdjustBoundsForRTLUI(gfx::Rect* rect) const {
+ rect->set_x(GetMirroredXForRect(*rect));
+}
+
+void Combobox::PaintText(gfx::Canvas* canvas) {
+ gfx::Insets insets = GetInsets();
+
+ canvas->Save();
+ canvas->ClipRect(GetContentsBounds());
+
+ int x = insets.left();
+ int y = insets.top();
+ int text_height = height() - insets.height();
+ SkColor text_color = invalid() ? kInvalidTextColor :
+ GetNativeTheme()->GetSystemColor(
+ ui::NativeTheme::kColorId_LabelEnabledColor);
+
+ DCHECK_GE(selected_index_, 0);
+ DCHECK_LT(selected_index_, model()->GetItemCount());
+ if (selected_index_ < 0 || selected_index_ > model()->GetItemCount())
+ selected_index_ = 0;
+ string16 text = model()->GetItemAt(selected_index_);
+
+ int disclosure_arrow_offset = width() - disclosure_arrow_->width()
+ - kDisclosureArrowLeftPadding - kDisclosureArrowRightPadding;
+
+ const gfx::Font& font = Combobox::GetFont();
+ int text_width = font.GetStringWidth(text);
+ if ((text_width + insets.width()) > disclosure_arrow_offset)
+ text_width = disclosure_arrow_offset - insets.width();
+
+ gfx::Rect text_bounds(x, y, text_width, text_height);
+ AdjustBoundsForRTLUI(&text_bounds);
+ canvas->DrawStringInt(text, font, text_color, text_bounds);
+
+ gfx::Rect arrow_bounds(disclosure_arrow_offset + kDisclosureArrowLeftPadding,
+ height() / 2 - disclosure_arrow_->height() / 2,
+ disclosure_arrow_->width(),
+ disclosure_arrow_->height());
+ AdjustBoundsForRTLUI(&arrow_bounds);
+
+ SkPaint paint;
+ // This makes the arrow subtractive.
+ if (invalid())
+ paint.setXfermodeMode(SkXfermode::kDstOut_Mode);
+ canvas->DrawImageInt(*disclosure_arrow_, arrow_bounds.x(), arrow_bounds.y(),
+ paint);
+
+ canvas->Restore();
+}
+
+void Combobox::ShowDropDownMenu(ui::MenuSourceType source_type) {
+ if (!dropdown_list_menu_runner_.get())
+ UpdateFromModel();
+
+ // Extend the menu to the width of the combobox.
+ MenuItemView* menu = dropdown_list_menu_runner_->GetMenu();
+ SubmenuView* submenu = menu->CreateSubmenu();
+ submenu->set_minimum_preferred_width(size().width() -
+ (kMenuBorderWidthLeft + kMenuBorderWidthRight));
+
+ gfx::Rect lb = GetLocalBounds();
+ gfx::Point menu_position(lb.origin());
+
+ // Inset the menu's requested position so the border of the menu lines up
+ // with the border of the combobox.
+ menu_position.set_x(menu_position.x() + kMenuBorderWidthLeft);
+ menu_position.set_y(menu_position.y() + kMenuBorderWidthTop);
+ lb.set_width(lb.width() - (kMenuBorderWidthLeft + kMenuBorderWidthRight));
+
+ View::ConvertPointToScreen(this, &menu_position);
+ if (menu_position.x() < 0)
+ menu_position.set_x(0);
+
+ gfx::Rect bounds(menu_position, lb.size());
+
+ dropdown_open_ = true;
+ if (dropdown_list_menu_runner_->RunMenuAt(
+ GetWidget(), NULL, bounds, MenuItemView::TOPLEFT, source_type, 0) ==
+ MenuRunner::MENU_DELETED)
+ return;
+ dropdown_open_ = false;
+ closed_time_ = base::Time::Now();
+
+ // Need to explicitly clear mouse handler so that events get sent
+ // properly after the menu finishes running. If we don't do this, then
+ // the first click to other parts of the UI is eaten.
+ SetMouseHandler(NULL);
+}
+
+void Combobox::OnSelectionChanged() {
+ if (listener_)
+ listener_->OnSelectedIndexChanged(this);
+ NotifyAccessibilityEvent(ui::AccessibilityTypes::EVENT_VALUE_CHANGED, false);
+ SchedulePaint();
}
} // namespace views
diff --git a/chromium/ui/views/controls/combobox/combobox.h b/chromium/ui/views/controls/combobox/combobox.h
index e71604e4238..09188e8e967 100644
--- a/chromium/ui/views/controls/combobox/combobox.h
+++ b/chromium/ui/views/controls/combobox/combobox.h
@@ -7,10 +7,10 @@
#include <string>
+#include "base/time/time.h"
#include "ui/gfx/native_widget_types.h"
-#include "ui/views/controls/combobox/native_combobox_wrapper.h"
+#include "ui/views/controls/menu/menu_delegate.h"
#include "ui/views/controls/prefix_delegate.h"
-#include "ui/views/view.h"
namespace gfx {
class Font;
@@ -23,10 +23,12 @@ class ComboboxModel;
namespace views {
class ComboboxListener;
+class FocusableBorder;
+class MenuRunner;
class PrefixSelector;
-// A non-editable combobox (aka a drop-down list).
-class VIEWS_EXPORT Combobox : public PrefixDelegate {
+// A non-editable combobox (aka a drop-down list or selector).
+class VIEWS_EXPORT Combobox : public MenuDelegate, public PrefixDelegate {
public:
// The combobox's class name.
static const char kViewClassName[];
@@ -38,9 +40,7 @@ class VIEWS_EXPORT Combobox : public PrefixDelegate {
static const gfx::Font& GetFont();
// Sets the listener which will be called when a selection has been made.
- void set_listener(ComboboxListener* listener) {
- listener_ = listener;
- }
+ void set_listener(ComboboxListener* listener) { listener_ = listener; }
// Informs the combobox that its model changed.
void ModelChanged();
@@ -49,66 +49,67 @@ class VIEWS_EXPORT Combobox : public PrefixDelegate {
int selected_index() const { return selected_index_; }
void SetSelectedIndex(int index);
- // Called when the combobox's selection is changed by the user.
- void SelectionChanged();
-
ui::ComboboxModel* model() const { return model_; }
// Set the accessible name of the combobox.
void SetAccessibleName(const string16& name);
- // Provided only for testing:
- gfx::NativeView GetTestingHandle() const {
- return native_wrapper_ ? native_wrapper_->GetTestingHandle() : NULL;
- }
- NativeComboboxWrapper* GetNativeWrapperForTesting() const {
- return native_wrapper_;
- }
-
- // Visually marks the combobox as having an invalid value selected. The caller
- // is responsible for flipping it back to valid if the selection changes.
+ // Visually marks the combobox as having an invalid value selected.
+ // When invalid, it paints with white text on a red background.
+ // Callers are responsible for restoring validity with selection changes.
void SetInvalid(bool invalid);
-
- bool invalid() const {
- return invalid_;
- }
+ bool invalid() const { return invalid_; }
// Overridden from View:
virtual gfx::Size GetPreferredSize() OVERRIDE;
- virtual void Layout() OVERRIDE;
- virtual void OnEnabledChanged() OVERRIDE;
+ virtual const char* GetClassName() const OVERRIDE;
virtual bool SkipDefaultKeyEventProcessing(const ui::KeyEvent& e) OVERRIDE;
- virtual void OnPaintFocusBorder(gfx::Canvas* canvas) OVERRIDE;
+ virtual bool OnMousePressed(const ui::MouseEvent& mouse_event) OVERRIDE;
+ virtual bool OnMouseDragged(const ui::MouseEvent& mouse_event) OVERRIDE;
virtual bool OnKeyPressed(const ui::KeyEvent& e) OVERRIDE;
virtual bool OnKeyReleased(const ui::KeyEvent& e) OVERRIDE;
+ virtual void OnGestureEvent(ui::GestureEvent* gesture) OVERRIDE;
+ virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE;
virtual void OnFocus() OVERRIDE;
virtual void OnBlur() OVERRIDE;
virtual void GetAccessibleState(ui::AccessibleViewState* state) OVERRIDE;
virtual ui::TextInputClient* GetTextInputClient() OVERRIDE;
+ // Overridden from MenuDelegate:
+ virtual bool IsItemChecked(int id) const OVERRIDE;
+ virtual bool IsCommandEnabled(int id) const OVERRIDE;
+ virtual void ExecuteCommand(int id) OVERRIDE;
+ virtual bool GetAccelerator(int id, ui::Accelerator* accelerator) OVERRIDE;
+
// Overridden from PrefixDelegate:
virtual int GetRowCount() OVERRIDE;
virtual int GetSelectedRow() OVERRIDE;
virtual void SetSelectedRow(int row) OVERRIDE;
virtual string16 GetTextForRow(int row) OVERRIDE;
- protected:
- // Overridden from View:
- virtual void ViewHierarchyChanged(
- const ViewHierarchyChangedDetails& details) OVERRIDE;
- virtual const char* GetClassName() const OVERRIDE;
+ private:
+ // Updates the combobox's content from its model.
+ void UpdateFromModel();
- // The object that actually implements the native combobox.
- NativeComboboxWrapper* native_wrapper_;
+ // Given bounds within our View, this helper mirrors the bounds if necessary.
+ void AdjustBoundsForRTLUI(gfx::Rect* rect) const;
+
+ // Draw the selected value of the drop down list
+ void PaintText(gfx::Canvas* canvas);
+
+ // Show the drop down list
+ void ShowDropDownMenu(ui::MenuSourceType source_type);
+
+ // Called when the selection is changed by the user.
+ void OnSelectionChanged();
- private:
// Our model. Not owned.
ui::ComboboxModel* model_;
// Our listener. Not owned. Notified when the selected index change.
ComboboxListener* listener_;
- // The current selected index.
+ // The current selected index; -1 and means no selection.
int selected_index_;
// True when the selection is visually denoted as invalid.
@@ -117,8 +118,32 @@ class VIEWS_EXPORT Combobox : public PrefixDelegate {
// The accessible name of this combobox.
string16 accessible_name_;
+ // A helper used to select entries by keyboard input.
scoped_ptr<PrefixSelector> selector_;
+ // The reference to the border class. The object is owned by View::border_.
+ FocusableBorder* text_border_;
+
+ // The disclosure arrow next to the currently selected item from the list.
+ const gfx::ImageSkia* disclosure_arrow_;
+
+ // Responsible for showing the context menu.
+ scoped_ptr<MenuRunner> dropdown_list_menu_runner_;
+
+ // Is the drop down list showing
+ bool dropdown_open_;
+
+ // Like MenuButton, we use a time object in order to keep track of when the
+ // combobox was closed. The time is used for simulating menu behavior; that
+ // is, if the menu is shown and the button is pressed, we need to close the
+ // menu. There is no clean way to get the second click event because the
+ // menu is displayed using a modal loop and, unlike regular menus in Windows,
+ // the button is not part of the displayed menu.
+ base::Time closed_time_;
+
+ // The maximum dimensions of the content in the dropdown
+ gfx::Size content_size_;
+
DISALLOW_COPY_AND_ASSIGN(Combobox);
};
diff --git a/chromium/ui/views/controls/combobox/combobox_unittest.cc b/chromium/ui/views/controls/combobox/combobox_unittest.cc
new file mode 100644
index 00000000000..ea8d8f537bc
--- /dev/null
+++ b/chromium/ui/views/controls/combobox/combobox_unittest.cc
@@ -0,0 +1,310 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/controls/combobox/combobox.h"
+
+#include <set>
+
+#include "base/strings/utf_string_conversions.h"
+#include "ui/base/models/combobox_model.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/views/ime/mock_input_method.h"
+#include "ui/views/test/views_test_base.h"
+#include "ui/views/widget/widget.h"
+
+namespace {
+
+// A wrapper of Combobox to intercept the result of OnKeyPressed() and
+// OnKeyReleased() methods.
+class TestCombobox : public views::Combobox {
+ public:
+ explicit TestCombobox(ui::ComboboxModel* model)
+ : Combobox(model),
+ key_handled_(false),
+ key_received_(false) {
+ }
+
+ virtual bool OnKeyPressed(const ui::KeyEvent& e) OVERRIDE {
+ key_received_ = true;
+ key_handled_ = views::Combobox::OnKeyPressed(e);
+ return key_handled_;
+ }
+
+ virtual bool OnKeyReleased(const ui::KeyEvent& e) OVERRIDE {
+ key_received_ = true;
+ key_handled_ = views::Combobox::OnKeyReleased(e);
+ return key_handled_;
+ }
+
+ bool key_handled() const { return key_handled_; }
+ bool key_received() const { return key_received_; }
+
+ void clear() {
+ key_received_ = key_handled_ = false;
+ }
+
+ private:
+ bool key_handled_;
+ bool key_received_;
+
+ DISALLOW_COPY_AND_ASSIGN(TestCombobox);
+};
+
+// A concrete class is needed to test the combobox.
+class TestComboboxModel : public ui::ComboboxModel {
+ public:
+ TestComboboxModel() {}
+ virtual ~TestComboboxModel() {}
+
+ // ui::ComboboxModel:
+ virtual int GetItemCount() const OVERRIDE {
+ return 10;
+ }
+ virtual string16 GetItemAt(int index) OVERRIDE {
+ return string16();
+ }
+ virtual bool IsItemSeparatorAt(int index) OVERRIDE {
+ return separators_.find(index) != separators_.end();
+ }
+
+ void SetSeparators(const std::set<int>& separators) {
+ separators_ = separators;
+ }
+
+ private:
+ std::set<int> separators_;
+
+ DISALLOW_COPY_AND_ASSIGN(TestComboboxModel);
+};
+
+} // namespace
+
+namespace views {
+
+class ComboboxTest : public ViewsTestBase {
+ public:
+ ComboboxTest() : widget_(NULL), combobox_(NULL), input_method_(NULL) {}
+
+ virtual void TearDown() OVERRIDE {
+ if (widget_)
+ widget_->Close();
+ ViewsTestBase::TearDown();
+ }
+
+ void InitCombobox() {
+ model_.reset(new TestComboboxModel());
+
+ ASSERT_FALSE(combobox_);
+ combobox_ = new TestCombobox(model_.get());
+ combobox_->set_id(1);
+
+ widget_ = new Widget;
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
+ params.bounds = gfx::Rect(100, 100, 100, 100);
+ widget_->Init(params);
+ View* container = new View();
+ widget_->SetContentsView(container);
+ container->AddChildView(combobox_);
+
+ input_method_ = new MockInputMethod();
+ widget_->ReplaceInputMethod(input_method_);
+
+ // Assumes the Widget is always focused.
+ input_method_->OnFocus();
+
+ combobox_->RequestFocus();
+ }
+
+ protected:
+ void SendKeyEvent(ui::KeyboardCode key_code) {
+ ui::KeyEvent event(ui::ET_KEY_PRESSED, key_code, 0, false);
+ input_method_->DispatchKeyEvent(event);
+ }
+
+ View* GetFocusedView() {
+ return widget_->GetFocusManager()->GetFocusedView();
+ }
+
+ // We need widget to populate wrapper class.
+ Widget* widget_;
+
+ // |combobox_| will be allocated InitCombobox() and then owned by |widget_|.
+ TestCombobox* combobox_;
+
+ // Combobox does not take ownership of the model, hence it needs to be scoped.
+ scoped_ptr<TestComboboxModel> model_;
+
+ // For testing input method related behaviors.
+ MockInputMethod* input_method_;
+};
+
+TEST_F(ComboboxTest, KeyTest) {
+ InitCombobox();
+ SendKeyEvent(ui::VKEY_END);
+ EXPECT_EQ(combobox_->selected_index() + 1, model_->GetItemCount());
+ SendKeyEvent(ui::VKEY_HOME);
+ EXPECT_EQ(combobox_->selected_index(), 0);
+ SendKeyEvent(ui::VKEY_DOWN);
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(combobox_->selected_index(), 2);
+ SendKeyEvent(ui::VKEY_RIGHT);
+ EXPECT_EQ(combobox_->selected_index(), 2);
+ SendKeyEvent(ui::VKEY_LEFT);
+ EXPECT_EQ(combobox_->selected_index(), 2);
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(combobox_->selected_index(), 1);
+ SendKeyEvent(ui::VKEY_PRIOR);
+ EXPECT_EQ(combobox_->selected_index(), 0);
+ SendKeyEvent(ui::VKEY_NEXT);
+ EXPECT_EQ(combobox_->selected_index(), model_->GetItemCount() - 1);
+}
+
+// Check that if a combobox is disabled before it has a native wrapper, then the
+// native wrapper inherits the disabled state when it gets created.
+TEST_F(ComboboxTest, DisabilityTest) {
+ model_.reset(new TestComboboxModel());
+
+ ASSERT_FALSE(combobox_);
+ combobox_ = new TestCombobox(model_.get());
+ combobox_->SetEnabled(false);
+
+ widget_ = new Widget;
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
+ params.bounds = gfx::Rect(100, 100, 100, 100);
+ widget_->Init(params);
+ View* container = new View();
+ widget_->SetContentsView(container);
+ container->AddChildView(combobox_);
+ EXPECT_FALSE(combobox_->enabled());
+}
+
+// Verifies that we don't select a separator line in combobox when navigating
+// through keyboard.
+TEST_F(ComboboxTest, SkipSeparatorSimple) {
+ InitCombobox();
+ std::set<int> separators;
+ separators.insert(2);
+ model_->SetSeparators(separators);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(1, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(3, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(1, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_HOME);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_PRIOR);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_END);
+ EXPECT_EQ(9, combobox_->selected_index());
+}
+
+// Verifies that we never select the separator that is in the beginning of the
+// combobox list when navigating through keyboard.
+TEST_F(ComboboxTest, SkipSeparatorBeginning) {
+ InitCombobox();
+ std::set<int> separators;
+ separators.insert(0);
+ model_->SetSeparators(separators);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(1, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(2, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(1, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_HOME);
+ EXPECT_EQ(1, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_PRIOR);
+ EXPECT_EQ(1, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_END);
+ EXPECT_EQ(9, combobox_->selected_index());
+}
+
+// Verifies that we never select the separator that is in the end of the
+// combobox list when navigating through keyboard.
+TEST_F(ComboboxTest, SkipSeparatorEnd) {
+ InitCombobox();
+ std::set<int> separators;
+ separators.insert(model_->GetItemCount() - 1);
+ model_->SetSeparators(separators);
+ combobox_->SetSelectedIndex(8);
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(8, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(7, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_END);
+ EXPECT_EQ(8, combobox_->selected_index());
+}
+
+// Verifies that we never select any of the adjacent separators (multiple
+// consecutive) that appear in the beginning of the combobox list when
+// navigating through keyboard.
+TEST_F(ComboboxTest, SkipMultipleSeparatorsAtBeginning) {
+ InitCombobox();
+ std::set<int> separators;
+ separators.insert(0);
+ separators.insert(1);
+ separators.insert(2);
+ model_->SetSeparators(separators);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(3, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(3, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_NEXT);
+ EXPECT_EQ(9, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_HOME);
+ EXPECT_EQ(3, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_END);
+ EXPECT_EQ(9, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_PRIOR);
+ EXPECT_EQ(3, combobox_->selected_index());
+}
+
+// Verifies that we never select any of the adjacent separators (multiple
+// consecutive) that appear in the middle of the combobox list when navigating
+// through keyboard.
+TEST_F(ComboboxTest, SkipMultipleAdjacentSeparatorsAtMiddle) {
+ InitCombobox();
+ std::set<int> separators;
+ separators.insert(4);
+ separators.insert(5);
+ separators.insert(6);
+ model_->SetSeparators(separators);
+ combobox_->SetSelectedIndex(3);
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(7, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(3, combobox_->selected_index());
+}
+
+// Verifies that we never select any of the adjacent separators (multiple
+// consecutive) that appear in the end of the combobox list when navigating
+// through keyboard.
+TEST_F(ComboboxTest, SkipMultipleSeparatorsAtEnd) {
+ InitCombobox();
+ std::set<int> separators;
+ separators.insert(7);
+ separators.insert(8);
+ separators.insert(9);
+ model_->SetSeparators(separators);
+ combobox_->SetSelectedIndex(6);
+ SendKeyEvent(ui::VKEY_DOWN);
+ EXPECT_EQ(6, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_UP);
+ EXPECT_EQ(5, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_HOME);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_NEXT);
+ EXPECT_EQ(6, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_PRIOR);
+ EXPECT_EQ(0, combobox_->selected_index());
+ SendKeyEvent(ui::VKEY_END);
+ EXPECT_EQ(6, combobox_->selected_index());
+}
+
+} // namespace views
diff --git a/chromium/ui/views/controls/combobox/native_combobox_views.cc b/chromium/ui/views/controls/combobox/native_combobox_views.cc
deleted file mode 100644
index 3cb3a5c52a8..00000000000
--- a/chromium/ui/views/controls/combobox/native_combobox_views.cc
+++ /dev/null
@@ -1,435 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/views/controls/combobox/native_combobox_views.h"
-
-#include <algorithm>
-
-#include "grit/ui_resources.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/models/combobox_model.h"
-#include "ui/base/resource/resource_bundle.h"
-#include "ui/gfx/canvas.h"
-#include "ui/gfx/font.h"
-#include "ui/gfx/image/image.h"
-#include "ui/gfx/path.h"
-#include "ui/native_theme/native_theme.h"
-#include "ui/views/background.h"
-#include "ui/views/border.h"
-#include "ui/views/color_constants.h"
-#include "ui/views/controls/button/menu_button.h"
-#include "ui/views/controls/combobox/combobox.h"
-#include "ui/views/controls/focusable_border.h"
-#include "ui/views/controls/menu/menu_runner.h"
-#include "ui/views/controls/menu/submenu_view.h"
-#include "ui/views/widget/root_view.h"
-#include "ui/views/widget/widget.h"
-
-namespace views {
-
-namespace {
-
-// Define the size of the insets.
-const int kTopInsetSize = 4;
-const int kLeftInsetSize = 4;
-const int kBottomInsetSize = 4;
-const int kRightInsetSize = 4;
-
-// Menu border widths
-const int kMenuBorderWidthLeft = 1;
-const int kMenuBorderWidthTop = 1;
-const int kMenuBorderWidthRight = 1;
-const int kMenuBorderWidthBottom = 2;
-
-// Limit how small a combobox can be.
-const int kMinComboboxWidth = 25;
-
-// Size of the combobox arrow margins
-const int kDisclosureArrowLeftPadding = 7;
-const int kDisclosureArrowRightPadding = 7;
-
-// Define the id of the first item in the menu (since it needs to be > 0)
-const int kFirstMenuItemId = 1000;
-
-const SkColor kInvalidTextColor = SK_ColorWHITE;
-
-// The background to use for invalid comboboxes.
-class InvalidBackground : public Background {
- public:
- InvalidBackground() {}
- virtual ~InvalidBackground() {}
-
- // Overridden from Background:
- virtual void Paint(gfx::Canvas* canvas, View* view) const OVERRIDE {
- gfx::Rect bounds(view->GetLocalBounds());
- // Inset by 2 to leave 1 empty pixel between background and border.
- bounds.Inset(2, 2, 2, 2);
- canvas->FillRect(bounds, kWarningColor);
- }
-
- private:
- DISALLOW_COPY_AND_ASSIGN(InvalidBackground);
-};
-
-} // namespace
-
-const char NativeComboboxViews::kViewClassName[] =
- "views/NativeComboboxViews";
-
-NativeComboboxViews::NativeComboboxViews(Combobox* combobox)
- : combobox_(combobox),
- text_border_(new FocusableBorder()),
- disclosure_arrow_(ui::ResourceBundle::GetSharedInstance().GetImageNamed(
- IDR_MENU_DROPARROW).ToImageSkia()),
- dropdown_open_(false),
- selected_index_(-1),
- content_width_(0),
- content_height_(0) {
- set_border(text_border_);
-}
-
-NativeComboboxViews::~NativeComboboxViews() {
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxViews, View overrides:
-
-bool NativeComboboxViews::OnMousePressed(const ui::MouseEvent& mouse_event) {
- combobox_->RequestFocus();
- const base::TimeDelta delta = base::Time::Now() - closed_time_;
- if (mouse_event.IsLeftMouseButton() &&
- (delta.InMilliseconds() > MenuButton::kMinimumTimeBetweenButtonClicks)) {
- UpdateFromModel();
- ShowDropDownMenu(ui::MENU_SOURCE_MOUSE);
- }
-
- return true;
-}
-
-bool NativeComboboxViews::OnMouseDragged(const ui::MouseEvent& mouse_event) {
- return true;
-}
-
-bool NativeComboboxViews::OnKeyPressed(const ui::KeyEvent& key_event) {
- // TODO(oshima): handle IME.
- DCHECK_EQ(key_event.type(), ui::ET_KEY_PRESSED);
-
- // Check if we are in the default state (-1) and set to first item.
- if (selected_index_ == -1)
- selected_index_ = 0;
-
- bool show_menu = false;
- int new_index = selected_index_;
- switch (key_event.key_code()) {
- // Show the menu on Space.
- case ui::VKEY_SPACE:
- show_menu = true;
- break;
-
- // Show the menu on Alt+Down (like Windows) or move to the next item if any.
- case ui::VKEY_DOWN:
- if (key_event.IsAltDown())
- show_menu = true;
- else if (new_index < (combobox_->model()->GetItemCount() - 1))
- new_index++;
- break;
-
- // Move to the end of the list.
- case ui::VKEY_END:
- case ui::VKEY_NEXT:
- new_index = combobox_->model()->GetItemCount() - 1;
- break;
-
- // Move to the beginning of the list.
- case ui::VKEY_HOME:
- case ui::VKEY_PRIOR:
- new_index = 0;
- break;
-
- // Move to the previous item if any.
- case ui::VKEY_UP:
- if (new_index > 0)
- new_index--;
- break;
-
- default:
- return false;
- }
-
- if (show_menu) {
- UpdateFromModel();
- ShowDropDownMenu(ui::MENU_SOURCE_KEYBOARD);
- } else if (new_index != selected_index_) {
- selected_index_ = new_index;
- combobox_->SelectionChanged();
- SchedulePaint();
- }
-
- return true;
-}
-
-bool NativeComboboxViews::OnKeyReleased(const ui::KeyEvent& key_event) {
- return true;
-}
-
-void NativeComboboxViews::OnPaint(gfx::Canvas* canvas) {
- text_border_->set_has_focus(combobox_->HasFocus());
- OnPaintBackground(canvas);
- PaintText(canvas);
- OnPaintBorder(canvas);
-}
-
-void NativeComboboxViews::OnFocus() {
- NOTREACHED();
-}
-
-void NativeComboboxViews::OnBlur() {
- NOTREACHED();
-}
-
-/////////////////////////////////////////////////////////////////
-// NativeComboboxViews, ui::EventHandler overrides:
-
-void NativeComboboxViews::OnGestureEvent(ui::GestureEvent* gesture) {
- if (gesture->type() == ui::ET_GESTURE_TAP) {
- UpdateFromModel();
- ShowDropDownMenu(ui::MENU_SOURCE_TOUCH);
- gesture->StopPropagation();
- return;
- }
- View::OnGestureEvent(gesture);
-}
-
-/////////////////////////////////////////////////////////////////
-// NativeComboboxViews, NativeComboboxWrapper overrides:
-
-void NativeComboboxViews::UpdateFromModel() {
- int max_width = 0;
- const gfx::Font& font = Combobox::GetFont();
-
- MenuItemView* menu = new MenuItemView(this);
- // MenuRunner owns |menu|.
- dropdown_list_menu_runner_.reset(new MenuRunner(menu));
-
- int num_items = combobox_->model()->GetItemCount();
- for (int i = 0; i < num_items; ++i) {
- if (combobox_->model()->IsItemSeparatorAt(i)) {
- menu->AppendSeparator();
- continue;
- }
-
- string16 text = combobox_->model()->GetItemAt(i);
-
- // Inserting the Unicode formatting characters if necessary so that the
- // text is displayed correctly in right-to-left UIs.
- base::i18n::AdjustStringForLocaleDirection(&text);
-
- menu->AppendMenuItem(i + kFirstMenuItemId, text, MenuItemView::NORMAL);
- max_width = std::max(max_width, font.GetStringWidth(text));
- }
-
- content_width_ = max_width;
- content_height_ = font.GetHeight();
-}
-
-void NativeComboboxViews::UpdateSelectedIndex() {
- selected_index_ = combobox_->selected_index();
- SchedulePaint();
-}
-
-void NativeComboboxViews::UpdateEnabled() {
- SetEnabled(combobox_->enabled());
-}
-
-int NativeComboboxViews::GetSelectedIndex() const {
- return selected_index_;
-}
-
-bool NativeComboboxViews::IsDropdownOpen() const {
- return dropdown_open_;
-}
-
-gfx::Size NativeComboboxViews::GetPreferredSize() {
- if (content_width_ == 0)
- UpdateFromModel();
-
- // The preferred size will drive the local bounds which in turn is used to set
- // the minimum width for the dropdown list.
- gfx::Insets insets = GetInsets();
- int total_width = std::max(kMinComboboxWidth, content_width_) +
- insets.width() + kDisclosureArrowLeftPadding +
- disclosure_arrow_->width() + kDisclosureArrowRightPadding;
-
- return gfx::Size(total_width, content_height_ + insets.height());
-}
-
-View* NativeComboboxViews::GetView() {
- return this;
-}
-
-void NativeComboboxViews::SetFocus() {
- text_border_->set_has_focus(true);
-}
-
-void NativeComboboxViews::ValidityStateChanged() {
- if (combobox_->invalid()) {
- text_border_->SetColor(kWarningColor);
- set_background(new InvalidBackground());
- } else {
- text_border_->UseDefaultColor();
- set_background(NULL);
- }
- SchedulePaint();
-}
-
-bool NativeComboboxViews::HandleKeyPressed(const ui::KeyEvent& e) {
- return OnKeyPressed(e);
-}
-
-bool NativeComboboxViews::HandleKeyReleased(const ui::KeyEvent& e) {
- return false; // crbug.com/127520
-}
-
-void NativeComboboxViews::HandleFocus() {
- SchedulePaint();
-}
-
-void NativeComboboxViews::HandleBlur() {
-}
-
-gfx::NativeView NativeComboboxViews::GetTestingHandle() const {
- NOTREACHED();
- return NULL;
-}
-
-/////////////////////////////////////////////////////////////////
-// NativeComboboxViews, views::MenuDelegate overrides:
-// (note that the id received is offset by kFirstMenuItemId)
-
-bool NativeComboboxViews::IsItemChecked(int id) const {
- return false;
-}
-
-bool NativeComboboxViews::IsCommandEnabled(int id) const {
- return true;
-}
-
-void NativeComboboxViews::ExecuteCommand(int id) {
- // Revert menu offset to map back to combobox model.
- id -= kFirstMenuItemId;
- DCHECK_LT(id, combobox_->model()->GetItemCount());
- selected_index_ = id;
- combobox_->SelectionChanged();
- SchedulePaint();
-}
-
-bool NativeComboboxViews::GetAccelerator(int id, ui::Accelerator* accel) {
- return false;
-}
-
-/////////////////////////////////////////////////////////////////
-// NativeComboboxViews private methods:
-
-void NativeComboboxViews::AdjustBoundsForRTLUI(gfx::Rect* rect) const {
- rect->set_x(GetMirroredXForRect(*rect));
-}
-
-void NativeComboboxViews::PaintText(gfx::Canvas* canvas) {
- gfx::Insets insets = GetInsets();
-
- canvas->Save();
- canvas->ClipRect(GetContentsBounds());
-
- int x = insets.left();
- int y = insets.top();
- int text_height = height() - insets.height();
- SkColor text_color = combobox_->invalid() ? kInvalidTextColor :
- GetNativeTheme()->GetSystemColor(
- ui::NativeTheme::kColorId_LabelEnabledColor);
-
- int index = GetSelectedIndex();
- if (index < 0 || index > combobox_->model()->GetItemCount())
- index = 0;
- string16 text = combobox_->model()->GetItemAt(index);
-
- int disclosure_arrow_offset = width() - disclosure_arrow_->width()
- - kDisclosureArrowLeftPadding - kDisclosureArrowRightPadding;
-
- const gfx::Font& font = Combobox::GetFont();
- int text_width = font.GetStringWidth(text);
- if ((text_width + insets.width()) > disclosure_arrow_offset)
- text_width = disclosure_arrow_offset - insets.width();
-
- gfx::Rect text_bounds(x, y, text_width, text_height);
- AdjustBoundsForRTLUI(&text_bounds);
- canvas->DrawStringInt(text, font, text_color, text_bounds);
-
- gfx::Rect arrow_bounds(disclosure_arrow_offset + kDisclosureArrowLeftPadding,
- height() / 2 - disclosure_arrow_->height() / 2,
- disclosure_arrow_->width(),
- disclosure_arrow_->height());
- AdjustBoundsForRTLUI(&arrow_bounds);
-
- SkPaint paint;
- // This makes the arrow subtractive.
- if (combobox_->invalid())
- paint.setXfermodeMode(SkXfermode::kDstOut_Mode);
- canvas->DrawImageInt(*disclosure_arrow_, arrow_bounds.x(), arrow_bounds.y(),
- paint);
-
- canvas->Restore();
-}
-
-void NativeComboboxViews::ShowDropDownMenu(ui::MenuSourceType source_type) {
- if (!dropdown_list_menu_runner_.get())
- UpdateFromModel();
-
- // Extend the menu to the width of the combobox.
- MenuItemView* menu = dropdown_list_menu_runner_->GetMenu();
- SubmenuView* submenu = menu->CreateSubmenu();
- submenu->set_minimum_preferred_width(size().width() -
- (kMenuBorderWidthLeft + kMenuBorderWidthRight));
-
- gfx::Rect lb = GetLocalBounds();
- gfx::Point menu_position(lb.origin());
-
- // Inset the menu's requested position so the border of the menu lines up
- // with the border of the combobox.
- menu_position.set_x(menu_position.x() + kMenuBorderWidthLeft);
- menu_position.set_y(menu_position.y() + kMenuBorderWidthTop);
- lb.set_width(lb.width() - (kMenuBorderWidthLeft + kMenuBorderWidthRight));
-
- View::ConvertPointToScreen(this, &menu_position);
- if (menu_position.x() < 0)
- menu_position.set_x(0);
-
- gfx::Rect bounds(menu_position, lb.size());
-
- dropdown_open_ = true;
- if (dropdown_list_menu_runner_->RunMenuAt(
- GetWidget(), NULL, bounds, MenuItemView::TOPLEFT, source_type, 0) ==
- MenuRunner::MENU_DELETED)
- return;
- dropdown_open_ = false;
- closed_time_ = base::Time::Now();
-
- // Need to explicitly clear mouse handler so that events get sent
- // properly after the menu finishes running. If we don't do this, then
- // the first click to other parts of the UI is eaten.
- SetMouseHandler(NULL);
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxWrapper, public:
-
-#if defined(USE_AURA)
-// static
-NativeComboboxWrapper* NativeComboboxWrapper::CreateWrapper(
- Combobox* combobox) {
- return new NativeComboboxViews(combobox);
-}
-#endif
-
-} // namespace views
diff --git a/chromium/ui/views/controls/combobox/native_combobox_views.h b/chromium/ui/views/controls/combobox/native_combobox_views.h
deleted file mode 100644
index bdf70339acf..00000000000
--- a/chromium/ui/views/controls/combobox/native_combobox_views.h
+++ /dev/null
@@ -1,115 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_VIEWS_H_
-#define UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_VIEWS_H_
-
-#include "base/time/time.h"
-#include "ui/views/controls/combobox/native_combobox_wrapper.h"
-#include "ui/views/controls/menu/menu_delegate.h"
-#include "ui/views/view.h"
-
-namespace gfx {
-class Canvas;
-class Font;
-}
-
-namespace views {
-
-class FocusableBorder;
-class MenuRunner;
-
-// A views/skia only implementation of NativeComboboxWrapper.
-// No platform specific code is used.
-class NativeComboboxViews : public views::View,
- public NativeComboboxWrapper,
- public views::MenuDelegate {
- public:
- static const char kViewClassName[];
-
- explicit NativeComboboxViews(Combobox* combobox);
- virtual ~NativeComboboxViews();
-
- // views::View overrides:
- virtual bool OnMousePressed(const ui::MouseEvent& mouse_event) OVERRIDE;
- virtual bool OnMouseDragged(const ui::MouseEvent& mouse_event) OVERRIDE;
- virtual bool OnKeyPressed(const ui::KeyEvent& key_event) OVERRIDE;
- virtual bool OnKeyReleased(const ui::KeyEvent& key_event) OVERRIDE;
- virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE;
- virtual void OnFocus() OVERRIDE;
- virtual void OnBlur() OVERRIDE;
-
- // ui::EventHandler overrides:
- virtual void OnGestureEvent(ui::GestureEvent* gesture) OVERRIDE;
-
- // NativeComboboxWrapper overrides:
- virtual void UpdateFromModel() OVERRIDE;
- virtual void UpdateSelectedIndex() OVERRIDE;
- virtual void UpdateEnabled() OVERRIDE;
- virtual int GetSelectedIndex() const OVERRIDE;
- virtual bool IsDropdownOpen() const OVERRIDE;
- virtual gfx::Size GetPreferredSize() OVERRIDE;
- virtual View* GetView() OVERRIDE;
- virtual void SetFocus() OVERRIDE;
- virtual void ValidityStateChanged() OVERRIDE;
- virtual bool HandleKeyPressed(const ui::KeyEvent& event) OVERRIDE;
- virtual bool HandleKeyReleased(const ui::KeyEvent& event) OVERRIDE;
- virtual void HandleFocus() OVERRIDE;
- virtual void HandleBlur() OVERRIDE;
- virtual gfx::NativeView GetTestingHandle() const OVERRIDE;
-
- // MenuDelegate overrides:
- virtual bool IsItemChecked(int id) const OVERRIDE;
- virtual bool IsCommandEnabled(int id) const OVERRIDE;
- virtual void ExecuteCommand(int id) OVERRIDE;
- virtual bool GetAccelerator(int id, ui::Accelerator* accelerator) OVERRIDE;
-
- private:
- // Given bounds within our View, this helper routine mirrors the bounds if
- // necessary.
- void AdjustBoundsForRTLUI(gfx::Rect* rect) const;
-
- // Draw the selected value of the drop down list
- void PaintText(gfx::Canvas* canvas);
-
- // Show the drop down list
- void ShowDropDownMenu(ui::MenuSourceType source_type);
-
- // The parent combobox, the owner of this object.
- Combobox* combobox_;
-
- // The reference to the border class. The object is owned by View::border_.
- FocusableBorder* text_border_;
-
- // The disclosure arrow next to the currently selected item from the list.
- const gfx::ImageSkia* disclosure_arrow_;
-
- // Responsible for showing the context menu.
- scoped_ptr<MenuRunner> dropdown_list_menu_runner_;
-
- // Is the drop down list showing
- bool dropdown_open_;
-
- // Like MenuButton, we use a time object in order to keep track of when the
- // combobox was closed. The time is used for simulating menu behavior; that
- // is, if the menu is shown and the button is pressed, we need to close the
- // menu. There is no clean way to get the second click event because the
- // menu is displayed using a modal loop and, unlike regular menus in Windows,
- // the button is not part of the displayed menu.
- base::Time closed_time_;
-
- // The selected index in the model. The default value is -1, which means no
- // selection.
- int selected_index_;
-
- // The maximum dimensions of the content in the dropdown
- int content_width_;
- int content_height_;
-
- DISALLOW_COPY_AND_ASSIGN(NativeComboboxViews);
-};
-
-} // namespace views
-
-#endif // UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_VIEWS_H_
diff --git a/chromium/ui/views/controls/combobox/native_combobox_views_unittest.cc b/chromium/ui/views/controls/combobox/native_combobox_views_unittest.cc
deleted file mode 100644
index 66811dd19a2..00000000000
--- a/chromium/ui/views/controls/combobox/native_combobox_views_unittest.cc
+++ /dev/null
@@ -1,194 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/strings/utf_string_conversions.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/models/combobox_model.h"
-#include "ui/views/controls/combobox/combobox.h"
-#include "ui/views/controls/combobox/native_combobox_views.h"
-#include "ui/views/ime/mock_input_method.h"
-#include "ui/views/test/views_test_base.h"
-#include "ui/views/widget/native_widget_private.h"
-#include "ui/views/widget/widget.h"
-
-namespace {
-
-// A wrapper of Combobox to intercept the result of OnKeyPressed() and
-// OnKeyReleased() methods.
-class TestCombobox : public views::Combobox {
- public:
- explicit TestCombobox(ui::ComboboxModel* model)
- : Combobox(model),
- key_handled_(false),
- key_received_(false) {
- }
-
- virtual bool OnKeyPressed(const ui::KeyEvent& e) OVERRIDE {
- key_received_ = true;
- key_handled_ = views::Combobox::OnKeyPressed(e);
- return key_handled_;
- }
-
- virtual bool OnKeyReleased(const ui::KeyEvent& e) OVERRIDE {
- key_received_ = true;
- key_handled_ = views::Combobox::OnKeyReleased(e);
- return key_handled_;
- }
-
- bool key_handled() const { return key_handled_; }
- bool key_received() const { return key_received_; }
-
- void clear() {
- key_received_ = key_handled_ = false;
- }
-
- private:
- bool key_handled_;
- bool key_received_;
-
- DISALLOW_COPY_AND_ASSIGN(TestCombobox);
-};
-
-// A concrete class is needed to test the combobox.
-class TestComboboxModel : public ui::ComboboxModel {
- public:
- TestComboboxModel() {}
- virtual ~TestComboboxModel() {}
-
- // Overridden from ui::ComboboxModel:
- virtual int GetItemCount() const OVERRIDE {
- return 4;
- }
- virtual string16 GetItemAt(int index) OVERRIDE {
- return string16();
- }
-
- private:
- DISALLOW_COPY_AND_ASSIGN(TestComboboxModel);
-};
-
-} // namespace
-
-namespace views {
-
-class NativeComboboxViewsTest : public ViewsTestBase {
- public:
- NativeComboboxViewsTest()
- : widget_(NULL),
- combobox_(NULL),
- combobox_view_(NULL),
- input_method_(NULL) {}
-
- // ::testing::Test:
- virtual void SetUp() {
- ViewsTestBase::SetUp();
- }
-
- virtual void TearDown() {
- if (widget_)
- widget_->Close();
- ViewsTestBase::TearDown();
- }
-
- void InitCombobox() {
- model_.reset(new TestComboboxModel());
-
- ASSERT_FALSE(combobox_);
- combobox_ = new TestCombobox(model_.get());
- combobox_->set_id(1);
-
- widget_ = new Widget;
- Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
- params.bounds = gfx::Rect(100, 100, 100, 100);
- widget_->Init(params);
- View* container = new View();
- widget_->SetContentsView(container);
- container->AddChildView(combobox_);
-
- combobox_view_ = static_cast<NativeComboboxViews*>(
- combobox_->GetNativeWrapperForTesting());
- ASSERT_TRUE(combobox_view_);
-
- input_method_ = new MockInputMethod();
- widget_->ReplaceInputMethod(input_method_);
-
- // Assumes the Widget is always focused.
- input_method_->OnFocus();
-
- combobox_->RequestFocus();
- }
-
- protected:
- void SendKeyEvent(ui::KeyboardCode key_code) {
- ui::KeyEvent event(ui::ET_KEY_PRESSED, key_code, 0, false);
- input_method_->DispatchKeyEvent(event);
- }
-
- View* GetFocusedView() {
- return widget_->GetFocusManager()->GetFocusedView();
- }
-
- // We need widget to populate wrapper class.
- Widget* widget_;
-
- // |combobox_| will be allocated InitCombobox() and then owned by |widget_|.
- TestCombobox* combobox_;
-
- // |combobox_view_| is the pointer to the pure Views interface of |combobox_|.
- NativeComboboxViews* combobox_view_;
-
- // Combobox does not take ownership of the model, hence it needs to be scoped.
- scoped_ptr<TestComboboxModel> model_;
-
- // For testing input method related behaviors.
- MockInputMethod* input_method_;
-};
-
-TEST_F(NativeComboboxViewsTest, KeyTest) {
- InitCombobox();
- SendKeyEvent(ui::VKEY_END);
- EXPECT_EQ(combobox_->selected_index() + 1, model_->GetItemCount());
- SendKeyEvent(ui::VKEY_HOME);
- EXPECT_EQ(combobox_->selected_index(), 0);
- SendKeyEvent(ui::VKEY_DOWN);
- SendKeyEvent(ui::VKEY_DOWN);
- EXPECT_EQ(combobox_->selected_index(), 2);
- SendKeyEvent(ui::VKEY_RIGHT);
- EXPECT_EQ(combobox_->selected_index(), 2);
- SendKeyEvent(ui::VKEY_LEFT);
- EXPECT_EQ(combobox_->selected_index(), 2);
- SendKeyEvent(ui::VKEY_UP);
- EXPECT_EQ(combobox_->selected_index(), 1);
- SendKeyEvent(ui::VKEY_PRIOR);
- EXPECT_EQ(combobox_->selected_index(), 0);
- SendKeyEvent(ui::VKEY_NEXT);
- EXPECT_EQ(combobox_->selected_index(), model_->GetItemCount() - 1);
-}
-
-// Check that if a combobox is disabled before it has a native wrapper, then the
-// native wrapper inherits the disabled state when it gets created.
-TEST_F(NativeComboboxViewsTest, DisabilityTest) {
- model_.reset(new TestComboboxModel());
-
- ASSERT_FALSE(combobox_);
- combobox_ = new TestCombobox(model_.get());
- combobox_->SetEnabled(false);
- ASSERT_FALSE(combobox_->GetNativeWrapperForTesting());
-
- widget_ = new Widget;
- Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
- params.bounds = gfx::Rect(100, 100, 100, 100);
- widget_->Init(params);
- View* container = new View();
- widget_->SetContentsView(container);
- container->AddChildView(combobox_);
-
- combobox_view_ = static_cast<NativeComboboxViews*>(
- combobox_->GetNativeWrapperForTesting());
- ASSERT_TRUE(combobox_view_);
- ASSERT_FALSE(combobox_view_->enabled());
-}
-
-} // namespace views
diff --git a/chromium/ui/views/controls/combobox/native_combobox_win.cc b/chromium/ui/views/controls/combobox/native_combobox_win.cc
deleted file mode 100644
index 3093c53bc22..00000000000
--- a/chromium/ui/views/controls/combobox/native_combobox_win.cc
+++ /dev/null
@@ -1,218 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/views/controls/combobox/native_combobox_win.h"
-
-#include "base/i18n/rtl.h"
-#include "base/strings/utf_string_conversions.h"
-#include "ui/base/events/event.h"
-#include "ui/base/models/combobox_model.h"
-#include "ui/base/resource/resource_bundle.h"
-#include "ui/base/win/hwnd_util.h"
-#include "ui/gfx/font.h"
-#include "ui/native_theme/native_theme_win.h"
-#include "ui/views/controls/combobox/combobox.h"
-#include "ui/views/controls/combobox/native_combobox_views.h"
-#include "ui/views/widget/widget.h"
-
-namespace {
-
-// Limit how small a combobox can be.
-const int kMinComboboxWidth = 148;
-
-// Add a couple extra pixels to the widths of comboboxes and combobox
-// dropdowns so that text isn't too crowded.
-const int kComboboxExtraPaddingX = 6;
-
-} // namespace
-
-namespace views {
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxWin, public:
-
-NativeComboboxWin::NativeComboboxWin(Combobox* combobox)
- : combobox_(combobox),
- content_width_(0) {
- // Associates the actual HWND with the combobox so it is the one considered as
- // having the focus (not the wrapper) when the HWND is focused directly (with
- // a click for example).
- set_focus_view(combobox);
-}
-
-NativeComboboxWin::~NativeComboboxWin() {
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxWin, NativeComboboxWrapper implementation:
-
-void NativeComboboxWin::UpdateFromModel() {
- SendMessage(native_view(), CB_RESETCONTENT, 0, 0);
- const gfx::Font& font = Combobox::GetFont();
- int max_width = 0;
- int num_items = combobox_->model()->GetItemCount();
- for (int i = 0; i < num_items; ++i) {
- string16 text = combobox_->model()->GetItemAt(i);
-
- // Inserting the Unicode formatting characters if necessary so that the
- // text is displayed correctly in right-to-left UIs.
- base::i18n::AdjustStringForLocaleDirection(&text);
-
- SendMessage(native_view(), CB_ADDSTRING, 0,
- reinterpret_cast<LPARAM>(UTF16ToWide(text).c_str()));
- max_width = std::max(max_width, font.GetStringWidth(text));
- }
- content_width_ = max_width;
-
- if (num_items > 0) {
- SendMessage(native_view(), CB_SETCURSEL, combobox_->selected_index(), 0);
-
- // Set the width for the drop down while accounting for the scrollbar and
- // borders.
- if (num_items > ComboBox_GetMinVisible(native_view()))
- max_width += GetSystemMetrics(SM_CXVSCROLL);
- // SM_CXEDGE would not be correct here, since the dropdown is flat, not 3D.
- int kComboboxDropdownBorderSize = 1;
- max_width += 2 * kComboboxDropdownBorderSize + kComboboxExtraPaddingX;
- SendMessage(native_view(), CB_SETDROPPEDWIDTH, max_width, 0);
- }
-}
-
-void NativeComboboxWin::UpdateSelectedIndex() {
- // Note that we use CB_SETCURSEL and not CB_SELECTSTRING because on RTL
- // locales the strings we get from our ComboBox::Model might be augmented
- // with Unicode directionality marks before we insert them into the combobox
- // and therefore we can not assume that the string we get from
- // ui::ComboboxModel can be safely searched for and selected (which is what
- // CB_SELECTSTRING does).
- SendMessage(native_view(), CB_SETCURSEL, combobox_->selected_index(), 0);
-}
-
-void NativeComboboxWin::UpdateEnabled() {
- SetEnabled(combobox_->enabled());
-}
-
-int NativeComboboxWin::GetSelectedIndex() const {
- LRESULT selected_index = SendMessage(native_view(), CB_GETCURSEL, 0, 0);
- return selected_index != CB_ERR ? selected_index : -1;
-}
-
-bool NativeComboboxWin::IsDropdownOpen() const {
- return SendMessage(native_view(), CB_GETDROPPEDSTATE, 0, 0) != 0;
-}
-
-gfx::Size NativeComboboxWin::GetPreferredSize() {
- COMBOBOXINFO cbi = { 0 };
- cbi.cbSize = sizeof(cbi);
- // Note: Don't use CB_GETCOMBOBOXINFO since that crashes on WOW64 systems
- // when you have a global message hook installed.
- GetComboBoxInfo(native_view(), &cbi);
- gfx::Rect rect_item(cbi.rcItem);
- gfx::Rect rect_button(cbi.rcButton);
- gfx::Size border = ui::NativeThemeWin::instance()->GetThemeBorderSize(
- ui::NativeThemeWin::MENULIST);
-
- // The padding value of '3' is the xy offset from the corner of the control
- // to the corner of rcItem. It does not seem to be queryable from the theme.
- // It is consistent on all versions of Windows from 2K to Vista, and is
- // invariant with respect to the combobox border size. We could conceivably
- // get this number from rect_item.x, but it seems fragile to depend on
- // position here, inside of the layout code.
- const int kItemOffset = 3;
- int item_to_button_distance = std::max(kItemOffset - border.width(), 0);
-
- // The cx computation can be read as measuring from left to right.
- int pref_width = std::max(kItemOffset + content_width_ +
- kComboboxExtraPaddingX +
- item_to_button_distance + rect_button.width() +
- border.width(), kMinComboboxWidth);
- // The two arguments to ::max below should be typically be equal.
- int pref_height = std::max(rect_item.height() + 2 * kItemOffset,
- rect_button.height() + 2 * border.height());
- return gfx::Size(pref_width, pref_height);
-}
-
-View* NativeComboboxWin::GetView() {
- return this;
-}
-
-void NativeComboboxWin::SetFocus() {
- OnFocus();
-}
-
-void NativeComboboxWin::ValidityStateChanged() {
- // TODO(estade): implement.
-}
-
-bool NativeComboboxWin::HandleKeyPressed(const ui::KeyEvent& event) {
- return false;
-}
-
-bool NativeComboboxWin::HandleKeyReleased(const ui::KeyEvent& event) {
- return false;
-}
-
-void NativeComboboxWin::HandleFocus() {
-}
-
-void NativeComboboxWin::HandleBlur() {
-}
-
-gfx::NativeView NativeComboboxWin::GetTestingHandle() const {
- return native_view();
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxWin, NativeControlWin overrides:
-
-bool NativeComboboxWin::ProcessMessage(UINT message,
- WPARAM w_param,
- LPARAM l_param,
- LRESULT* result) {
- if (message == WM_COMMAND && HIWORD(w_param) == CBN_SELCHANGE) {
- combobox_->SelectionChanged();
- *result = 0;
- return true;
- }
- return NativeControlWin::ProcessMessage(message, w_param, l_param, result);
-}
-
-void NativeComboboxWin::CreateNativeControl() {
- // It's ok to add WS_VSCROLL. The scrollbar will show up only when necessary
- // as long as we don't use CBS_DISABLENOSCROLL.
- // See http://msdn.microsoft.com/en-us/library/7h63bxbe(VS.80).aspx
- DWORD flags = WS_CHILD | WS_CLIPSIBLINGS | WS_CLIPCHILDREN |
- CBS_DROPDOWNLIST | WS_VSCROLL;
- HWND control_hwnd = ::CreateWindowEx(GetAdditionalExStyle(), L"COMBOBOX", L"",
- flags, 0, 0, width(), height(),
- GetWidget()->GetNativeView(), NULL, NULL,
- NULL);
- ui::CheckWindowCreated(control_hwnd);
- NativeControlCreated(control_hwnd);
-}
-
-void NativeComboboxWin::NativeControlCreated(HWND native_control) {
- NativeControlWin::NativeControlCreated(native_control);
-
- UpdateFont();
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxWin, private:
-
-void NativeComboboxWin::UpdateFont() {
- HFONT font = Combobox::GetFont().GetNativeFont();
- SendMessage(native_view(), WM_SETFONT, reinterpret_cast<WPARAM>(font), FALSE);
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// NativeComboboxWrapper, public:
-
-// static
-NativeComboboxWrapper* NativeComboboxWrapper::CreateWrapper(
- Combobox* combobox) {
- return new NativeComboboxViews(combobox);
-}
-
-} // namespace views
diff --git a/chromium/ui/views/controls/combobox/native_combobox_win.h b/chromium/ui/views/controls/combobox/native_combobox_win.h
deleted file mode 100644
index 534946009a4..00000000000
--- a/chromium/ui/views/controls/combobox/native_combobox_win.h
+++ /dev/null
@@ -1,58 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_WIN_H_
-#define UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_WIN_H_
-
-#include "ui/views/controls/combobox/native_combobox_wrapper.h"
-#include "ui/views/controls/native_control_win.h"
-
-namespace views {
-
-class NativeComboboxWin : public NativeControlWin,
- public NativeComboboxWrapper {
- public:
- explicit NativeComboboxWin(Combobox* combobox);
- virtual ~NativeComboboxWin();
-
- // Overridden from NativeComboboxWrapper:
- virtual void UpdateFromModel() OVERRIDE;
- virtual void UpdateSelectedIndex() OVERRIDE;
- virtual void UpdateEnabled() OVERRIDE;
- virtual int GetSelectedIndex() const OVERRIDE;
- virtual bool IsDropdownOpen() const OVERRIDE;
- virtual gfx::Size GetPreferredSize() OVERRIDE;
- virtual View* GetView() OVERRIDE;
- virtual void SetFocus() OVERRIDE;
- virtual void ValidityStateChanged() OVERRIDE;
- virtual bool HandleKeyPressed(const ui::KeyEvent& event) OVERRIDE;
- virtual bool HandleKeyReleased(const ui::KeyEvent& event) OVERRIDE;
- virtual void HandleFocus() OVERRIDE;
- virtual void HandleBlur() OVERRIDE;
- virtual gfx::NativeView GetTestingHandle() const OVERRIDE;
-
- protected:
- // Overridden from NativeControlWin:
- virtual bool ProcessMessage(UINT message,
- WPARAM w_param,
- LPARAM l_param,
- LRESULT* result) OVERRIDE;
- virtual void CreateNativeControl() OVERRIDE;
- virtual void NativeControlCreated(HWND native_control) OVERRIDE;
-
- private:
- void UpdateFont();
-
- // The combobox we are bound to.
- Combobox* combobox_;
-
- // The min width, in pixels, for the text content.
- int content_width_;
-
- DISALLOW_COPY_AND_ASSIGN(NativeComboboxWin);
-};
-
-} // namespace views
-
-#endif // UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_WIN_H_
diff --git a/chromium/ui/views/controls/combobox/native_combobox_wrapper.h b/chromium/ui/views/controls/combobox/native_combobox_wrapper.h
deleted file mode 100644
index 539812fb472..00000000000
--- a/chromium/ui/views/controls/combobox/native_combobox_wrapper.h
+++ /dev/null
@@ -1,76 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_WRAPPER_H_
-#define UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_WRAPPER_H_
-
-#include "ui/gfx/native_widget_types.h"
-#include "ui/views/views_export.h"
-
-namespace gfx {
-class Size;
-}
-
-namespace ui {
-class KeyEvent;
-}
-
-namespace views {
-
-class Combobox;
-class View;
-
-class VIEWS_EXPORT NativeComboboxWrapper {
- public:
- // Updates the combobox's content from its model.
- virtual void UpdateFromModel() = 0;
-
- // Updates the selected index from the associated combobox.
- virtual void UpdateSelectedIndex() = 0;
-
- // Updates the enabled state of the combobox from the associated view.
- virtual void UpdateEnabled() = 0;
-
- // Returns the selected index.
- virtual int GetSelectedIndex() const = 0;
-
- // Returns true if the combobox dropdown is open.
- virtual bool IsDropdownOpen() const = 0;
-
- // Returns the preferred size of the combobox.
- virtual gfx::Size GetPreferredSize() = 0;
-
- // Retrieves the view that hosts the native control.
- virtual View* GetView() = 0;
-
- // Sets the focus to the button.
- virtual void SetFocus() = 0;
-
- // Called when the combobox flipped validity. When invalid, it paints
- // with white text on a red background.
- virtual void ValidityStateChanged() = 0;
-
- // Invoked when a key is pressed/release on combobox. Subclasser should
- // return true if the event has been processed and false otherwise.
- // See also View::OnKeyPressed/OnKeyReleased.
- virtual bool HandleKeyPressed(const ui::KeyEvent& e) = 0;
- virtual bool HandleKeyReleased(const ui::KeyEvent& e) = 0;
-
- // Invoked when focus is being moved from or to the combobox.
- // See also View::OnFocus/OnBlur.
- virtual void HandleFocus() = 0;
- virtual void HandleBlur() = 0;
-
- // Returns a handle to the underlying native view for testing.
- virtual gfx::NativeView GetTestingHandle() const = 0;
-
- static NativeComboboxWrapper* CreateWrapper(Combobox* combobox);
-
- protected:
- virtual ~NativeComboboxWrapper() {}
-};
-
-} // namespace views
-
-#endif // UI_VIEWS_CONTROLS_COMBOBOX_NATIVE_COMBOBOX_WRAPPER_H_
diff --git a/chromium/ui/views/controls/glow_hover_controller.cc b/chromium/ui/views/controls/glow_hover_controller.cc
index f2e3bf26f30..f7fcd3fdd03 100644
--- a/chromium/ui/views/controls/glow_hover_controller.cc
+++ b/chromium/ui/views/controls/glow_hover_controller.cc
@@ -30,7 +30,7 @@ GlowHoverController::~GlowHoverController() {
}
void GlowHoverController::SetAnimationContainer(
- ui::AnimationContainer* container) {
+ gfx::AnimationContainer* container) {
animation_.SetContainer(container);
}
@@ -45,7 +45,7 @@ void GlowHoverController::Show(Style style) {
case SUBTLE:
opacity_scale_ = kTrackOpacityScale;
animation_.SetSlideDuration(kTrackHoverDurationMs);
- animation_.SetTweenType(ui::Tween::EASE_OUT);
+ animation_.SetTweenType(gfx::Tween::EASE_OUT);
animation_.Show();
break;
case PRONOUNCED:
@@ -58,7 +58,7 @@ void GlowHoverController::Show(Style style) {
}
void GlowHoverController::Hide() {
- animation_.SetTweenType(ui::Tween::EASE_IN);
+ animation_.SetTweenType(gfx::Tween::EASE_IN);
animation_.Hide();
}
@@ -117,11 +117,11 @@ void GlowHoverController::Draw(gfx::Canvas* canvas,
(view_->height() - mask_image.height()) / 2);
}
-void GlowHoverController::AnimationEnded(const ui::Animation* animation) {
+void GlowHoverController::AnimationEnded(const gfx::Animation* animation) {
view_->SchedulePaint();
}
-void GlowHoverController::AnimationProgressed(const ui::Animation* animation) {
+void GlowHoverController::AnimationProgressed(const gfx::Animation* animation) {
view_->SchedulePaint();
}
diff --git a/chromium/ui/views/controls/glow_hover_controller.h b/chromium/ui/views/controls/glow_hover_controller.h
index 7d8e62ce2bd..2ac423e42d5 100644
--- a/chromium/ui/views/controls/glow_hover_controller.h
+++ b/chromium/ui/views/controls/glow_hover_controller.h
@@ -5,8 +5,8 @@
#ifndef UI_VIEWS_CONTROLS_GLOW_HOVER_CONTROLLER_H_
#define UI_VIEWS_CONTROLS_GLOW_HOVER_CONTROLLER_H_
-#include "ui/base/animation/animation_delegate.h"
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/animation_delegate.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/views/views_export.h"
namespace gfx {
@@ -27,7 +27,7 @@ class View;
// OnPaint() -> if ShouldDraw() returns true invoke Draw().
// Internally GlowHoverController uses an animation to animate the glow and
// invokes SchedulePaint() back on the View as necessary.
-class VIEWS_EXPORT GlowHoverController : public ui::AnimationDelegate {
+class VIEWS_EXPORT GlowHoverController : public gfx::AnimationDelegate {
public:
enum Style {
SUBTLE,
@@ -38,7 +38,7 @@ class VIEWS_EXPORT GlowHoverController : public ui::AnimationDelegate {
virtual ~GlowHoverController();
// Sets the AnimationContainer used by the animation.
- void SetAnimationContainer(ui::AnimationContainer* container);
+ void SetAnimationContainer(gfx::AnimationContainer* container);
// Sets the location of the hover, relative to the View passed to the
// constructor.
@@ -64,16 +64,16 @@ class VIEWS_EXPORT GlowHoverController : public ui::AnimationDelegate {
// |mask_image| is used to determine what parts of the canvas to draw on.
void Draw(gfx::Canvas* canvas, const gfx::ImageSkia& mask_image) const;
- // ui::AnimationDelegate overrides:
- virtual void AnimationEnded(const ui::Animation* animation) OVERRIDE;
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
+ // gfx::AnimationDelegate overrides:
+ virtual void AnimationEnded(const gfx::Animation* animation) OVERRIDE;
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
private:
// View we're drawing to.
views::View* view_;
// Opacity of the glow ramps up over time.
- ui::SlideAnimation animation_;
+ gfx::SlideAnimation animation_;
// Location of the glow, relative to view.
gfx::Point location_;
diff --git a/chromium/ui/views/controls/label.cc b/chromium/ui/views/controls/label.cc
index 3e81ce5451c..7d4bc7e8470 100644
--- a/chromium/ui/views/controls/label.cc
+++ b/chromium/ui/views/controls/label.cc
@@ -16,12 +16,12 @@
#include "base/strings/utf_string_conversions.h"
#include "ui/base/accessibility/accessible_view_state.h"
#include "ui/base/resource/resource_bundle.h"
-#include "ui/base/text/text_elider.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/color_utils.h"
-#include "ui/gfx/font.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/shadow_value.h"
+#include "ui/gfx/text_elider.h"
+#include "ui/gfx/text_utils.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/background.h"
@@ -31,6 +31,11 @@ namespace {
const int kFocusBorderPadding = 1;
const int kCachedSizeLimit = 10;
+gfx::FontList GetDefaultFontList() {
+ return ui::ResourceBundle::GetSharedInstance().GetFontList(
+ ui::ResourceBundle::BaseFont);
+}
+
} // namespace
namespace views {
@@ -39,27 +44,39 @@ namespace views {
const char Label::kViewClassName[] = "Label";
Label::Label() {
- Init(string16(), GetDefaultFont());
+ Init(string16(), GetDefaultFontList());
}
Label::Label(const string16& text) {
- Init(text, GetDefaultFont());
+ Init(text, GetDefaultFontList());
+}
+
+Label::Label(const string16& text, const gfx::FontList& font_list) {
+ Init(text, font_list);
}
Label::Label(const string16& text, const gfx::Font& font) {
- Init(text, font);
+ Init(text, gfx::FontList(font));
}
Label::~Label() {
}
-void Label::SetFont(const gfx::Font& font) {
- font_ = font;
+void Label::SetFontList(const gfx::FontList& font_list) {
+ font_list_ = font_list;
ResetCachedSize();
PreferredSizeChanged();
SchedulePaint();
}
+const gfx::Font& Label::font() const {
+ return font_list_.GetPrimaryFont();
+}
+
+void Label::SetFont(const gfx::Font& font) {
+ SetFontList(gfx::FontList(font));
+}
+
void Label::SetText(const string16& text) {
if (text == text_)
return;
@@ -172,7 +189,7 @@ void Label::SizeToFit(int max_width) {
int label_width = 0;
for (std::vector<string16>::const_iterator iter = lines.begin();
iter != lines.end(); ++iter) {
- label_width = std::max(label_width, font_.GetStringWidth(*iter));
+ label_width = std::max(label_width, gfx::GetStringWidth(*iter, font_list_));
}
label_width += GetInsets().width();
@@ -202,7 +219,7 @@ gfx::Insets Label::GetInsets() const {
}
int Label::GetBaseline() const {
- return GetInsets().top() + font_.GetBaseline();
+ return GetInsets().top() + font_list_.GetBaseline();
}
gfx::Size Label::GetPreferredSize() {
@@ -234,9 +251,9 @@ int Label::GetHeightForWidth(int w) {
int cache_width = w;
- int h = font_.GetHeight();
+ int h = font_list_.GetHeight();
const int flags = ComputeDrawStringFlags();
- gfx::Canvas::SizeStringInt(text_, font_, &w, &h, line_height_, flags);
+ gfx::Canvas::SizeStringInt(text_, font_list_, &w, &h, line_height_, flags);
cached_heights_[cached_heights_cursor_] = gfx::Size(cache_width, h);
cached_heights_cursor_ = (cached_heights_cursor_ + 1) % kCachedSizeLimit;
return h + GetInsets().height();
@@ -297,7 +314,7 @@ void Label::PaintText(gfx::Canvas* canvas,
if (has_shadow_)
shadows.push_back(gfx::ShadowValue(shadow_offset_, 0,
enabled() ? enabled_shadow_color_ : disabled_shadow_color_));
- canvas->DrawStringWithShadows(text, font_,
+ canvas->DrawStringRectWithShadows(text, font_list_,
enabled() ? actual_enabled_color_ : actual_disabled_color_,
text_bounds, line_height_, flags, shadows);
@@ -316,13 +333,13 @@ gfx::Size Label::GetTextSize() const {
// on Linux.
int w = is_multi_line_ ?
GetAvailableRect().width() : std::numeric_limits<int>::max();
- int h = font_.GetHeight();
+ int h = font_list_.GetHeight();
// For single-line strings, ignore the available width and calculate how
// wide the text wants to be.
int flags = ComputeDrawStringFlags();
if (!is_multi_line_)
flags |= gfx::Canvas::NO_ELLIPSIS;
- gfx::Canvas::SizeStringInt(text_, font_, &w, &h, line_height_, flags);
+ gfx::Canvas::SizeStringInt(text_, font_list_, &w, &h, line_height_, flags);
text_size_.SetSize(w, h);
text_size_valid_ = true;
}
@@ -352,13 +369,8 @@ void Label::OnNativeThemeChanged(const ui::NativeTheme* theme) {
UpdateColorsFromTheme(theme);
}
-// static
-gfx::Font Label::GetDefaultFont() {
- return ResourceBundle::GetSharedInstance().GetFont(ResourceBundle::BaseFont);
-}
-
-void Label::Init(const string16& text, const gfx::Font& font) {
- font_ = font;
+void Label::Init(const string16& text, const gfx::FontList& font_list) {
+ font_list_ = font_list;
enabled_color_set_ = disabled_color_set_ = background_color_set_ = false;
auto_color_readability_ = true;
UpdateColorsFromTheme(ui::NativeTheme::instance());
@@ -483,14 +495,15 @@ void Label::CalculateDrawStringParams(string16* paint_text,
if (is_multi_line_ || (elide_behavior_ == NO_ELIDE)) {
*paint_text = text_;
} else if (elide_behavior_ == ELIDE_IN_MIDDLE) {
- *paint_text = ui::ElideText(text_, font_, GetAvailableRect().width(),
- ui::ELIDE_IN_MIDDLE);
+ *paint_text = gfx::ElideText(text_, font_list_, GetAvailableRect().width(),
+ gfx::ELIDE_IN_MIDDLE);
} else if (elide_behavior_ == ELIDE_AT_END) {
- *paint_text = ui::ElideText(text_, font_, GetAvailableRect().width(),
- ui::ELIDE_AT_END);
+ *paint_text = gfx::ElideText(text_, font_list_, GetAvailableRect().width(),
+ gfx::ELIDE_AT_END);
} else {
DCHECK_EQ(ELIDE_AS_EMAIL, elide_behavior_);
- *paint_text = ui::ElideEmail(text_, font_, GetAvailableRect().width());
+ *paint_text = gfx::ElideEmail(text_, font_list_,
+ GetAvailableRect().width());
}
*text_bounds = GetTextBounds();
@@ -524,7 +537,7 @@ void Label::ResetCachedSize() {
bool Label::ShouldShowDefaultTooltip() const {
return !is_multi_line_ &&
- font_.GetStringWidth(text_) > GetAvailableRect().width();
+ gfx::GetStringWidth(text_, font_list_) > GetAvailableRect().width();
}
} // namespace views
diff --git a/chromium/ui/views/controls/label.h b/chromium/ui/views/controls/label.h
index d637d7fb39e..40534ff654f 100644
--- a/chromium/ui/views/controls/label.h
+++ b/chromium/ui/views/controls/label.h
@@ -12,7 +12,7 @@
#include "base/gtest_prod_util.h"
#include "base/strings/string16.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/gfx/font.h"
+#include "ui/gfx/font_list.h"
#include "ui/gfx/text_constants.h"
#include "ui/views/view.h"
@@ -54,12 +54,16 @@ class VIEWS_EXPORT Label : public View {
Label();
explicit Label(const string16& text);
- Label(const string16& text, const gfx::Font& font);
+ Label(const string16& text, const gfx::FontList& font_list);
+ Label(const string16& text, const gfx::Font& font); // OBSOLETE
virtual ~Label();
- // Get or set the font used by this label.
- const gfx::Font& font() const { return font_; }
- virtual void SetFont(const gfx::Font& font);
+ // Gets or sets the fonts used by this label.
+ const gfx::FontList& font_list() const { return font_list_; }
+ virtual void SetFontList(const gfx::FontList& font_list);
+ // Obsolete gfx::Font version. Should use gfx::FontList version instead.
+ const gfx::Font& font() const; // OBSOLETE
+ virtual void SetFont(const gfx::Font& font); // OBSOLETE
// Get or set the label text.
const string16& text() const { return text_; }
@@ -119,7 +123,7 @@ class VIEWS_EXPORT Label : public View {
// Get or set the distance in pixels between baselines of multi-line text.
// Default is 0, indicating the distance between lines should be the standard
- // one for the label's text, font, and platform.
+ // one for the label's text, font list, and platform.
int line_height() const { return line_height_; }
void SetLineHeight(int height);
@@ -208,9 +212,7 @@ class VIEWS_EXPORT Label : public View {
// Calls ComputeDrawStringFlags().
FRIEND_TEST_ALL_PREFIXES(LabelTest, DisableSubpixelRendering);
- static gfx::Font GetDefaultFont();
-
- void Init(const string16& text, const gfx::Font& font);
+ void Init(const string16& text, const gfx::FontList& font_list);
void RecalculateColors();
@@ -236,7 +238,7 @@ class VIEWS_EXPORT Label : public View {
bool ShouldShowDefaultTooltip() const;
string16 text_;
- gfx::Font font_;
+ gfx::FontList font_list_;
SkColor requested_enabled_color_;
SkColor actual_enabled_color_;
SkColor requested_disabled_color_;
diff --git a/chromium/ui/views/controls/label_unittest.cc b/chromium/ui/views/controls/label_unittest.cc
index 134a05d7ee0..be752810f3b 100644
--- a/chromium/ui/views/controls/label_unittest.cc
+++ b/chromium/ui/views/controls/label_unittest.cc
@@ -16,17 +16,13 @@ namespace views {
// All text sizing measurements (width and height) should be greater than this.
const int kMinTextDimension = 4;
-TEST(LabelTest, FontPropertyCourier) {
+TEST(LabelTest, FontPropertySymbol) {
Label label;
- std::string font_name("courier");
- // Note: This test is size dependent since Courier does not support all sizes.
+ std::string font_name("symbol");
gfx::Font font(font_name, 26);
- label.SetFont(font);
- gfx::Font font_used = label.font();
-#if defined(OS_WIN)
- // On Linux, this results in "Sans" instead of "courier".
+ label.SetFontList(gfx::FontList(font));
+ gfx::Font font_used = label.font_list().GetPrimaryFont();
EXPECT_EQ(font_name, font_used.GetFontName());
-#endif
EXPECT_EQ(26, font_used.GetFontSize());
}
@@ -34,8 +30,8 @@ TEST(LabelTest, FontPropertyArial) {
Label label;
std::string font_name("arial");
gfx::Font font(font_name, 30);
- label.SetFont(font);
- gfx::Font font_used = label.font();
+ label.SetFontList(gfx::FontList(font));
+ gfx::Font font_used = label.font_list().GetPrimaryFont();
EXPECT_EQ(font_name, font_used.GetFontName());
EXPECT_EQ(30, font_used.GetFontSize());
}
diff --git a/chromium/ui/views/controls/link.cc b/chromium/ui/views/controls/link.cc
index b82cd51533f..b2bcc8f692b 100644
--- a/chromium/ui/views/controls/link.cc
+++ b/chromium/ui/views/controls/link.cc
@@ -9,8 +9,8 @@
#include "base/logging.h"
#include "base/strings/utf_string_conversions.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/color_utils.h"
#include "ui/gfx/font.h"
#include "ui/views/controls/link_listener.h"
diff --git a/chromium/ui/views/controls/menu/menu_config.cc b/chromium/ui/views/controls/menu/menu_config.cc
index 16570855e30..1c34ac0b3e0 100644
--- a/chromium/ui/views/controls/menu/menu_config.cc
+++ b/chromium/ui/views/controls/menu/menu_config.cc
@@ -13,13 +13,13 @@ namespace views {
MenuConfig::MenuConfig(const ui::NativeTheme* theme)
: text_color(SK_ColorBLACK),
arrow_color(SK_ColorBLACK),
- menu_vertical_border_size(7),
+ menu_vertical_border_size(3),
menu_horizontal_border_size(0),
submenu_horizontal_inset(3),
- item_top_margin(7),
- item_bottom_margin(6),
- item_no_icon_top_margin(7),
- item_no_icon_bottom_margin(7),
+ item_top_margin(4),
+ item_bottom_margin(3),
+ item_no_icon_top_margin(4),
+ item_no_icon_bottom_margin(4),
item_left_margin(10),
label_to_arrow_padding(10),
arrow_to_edge_padding(5),
@@ -32,7 +32,7 @@ MenuConfig::MenuConfig(const ui::NativeTheme* theme)
arrow_height(9),
arrow_width(9),
gutter_width(0),
- separator_height(15),
+ separator_height(11),
separator_upper_height(3),
separator_lower_height(4),
separator_spacing_height(3),
@@ -48,7 +48,6 @@ MenuConfig::MenuConfig(const ui::NativeTheme* theme)
native_theme(theme),
show_delay(400),
corner_radius(0) {
- AdjustForMenuVariations();
// Use 40px tall menu items when running in touch optimized mode.
// For Windows use 40px tall menu items when running in touch optimized mode.
if (ui::GetDisplayLayout() == ui::LAYOUT_TOUCH) {
@@ -60,28 +59,4 @@ MenuConfig::MenuConfig(const ui::NativeTheme* theme)
MenuConfig::~MenuConfig() {}
-void MenuConfig::AdjustForMenuVariations() {
- switch (ui::NativeTheme::GetMenuVariation()) {
- case ui::NativeTheme::MENU_VARIATION_COMPACT_1:
- case ui::NativeTheme::MENU_VARIATION_CONTRAST:
- item_top_margin = 5;
- item_bottom_margin = 4;
- item_no_icon_top_margin = 5;
- item_no_icon_bottom_margin = 5;
- separator_height = 11;
- menu_vertical_border_size = 5;
- break;
- case ui::NativeTheme::MENU_VARIATION_COMPACT_2:
- item_top_margin = 4;
- item_bottom_margin = 3;
- item_no_icon_top_margin = 4;
- item_no_icon_bottom_margin = 4;
- separator_height = 11;
- menu_vertical_border_size = 3;
- break;
- default:
- break;
- }
-}
-
} // namespace views
diff --git a/chromium/ui/views/controls/menu/menu_config.h b/chromium/ui/views/controls/menu/menu_config.h
index ac947823321..96eb21ac219 100644
--- a/chromium/ui/views/controls/menu/menu_config.h
+++ b/chromium/ui/views/controls/menu/menu_config.h
@@ -139,9 +139,6 @@ struct VIEWS_EXPORT MenuConfig {
#if defined(USE_AURA)
void InitAura(const ui::NativeTheme* theme);
#endif
-
- // Adjust some menu values for different menu variations.
- void AdjustForMenuVariations();
};
} // namespace views
diff --git a/chromium/ui/views/controls/menu/menu_controller.cc b/chromium/ui/views/controls/menu/menu_controller.cc
index 960130da9ad..fe203dd0e98 100644
--- a/chromium/ui/views/controls/menu/menu_controller.cc
+++ b/chromium/ui/views/controls/menu/menu_controller.cc
@@ -15,19 +15,25 @@
#include "base/time/time.h"
#include "ui/base/dragdrop/drag_utils.h"
#include "ui/base/dragdrop/os_exchange_data.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
+#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/screen.h"
+#include "ui/gfx/vector2d.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/controls/button/menu_button.h"
#include "ui/views/controls/menu/menu_config.h"
#include "ui/views/controls/menu/menu_controller_delegate.h"
+#include "ui/views/controls/menu/menu_host_root_view.h"
#include "ui/views/controls/menu/menu_scroll_view_container.h"
#include "ui/views/controls/menu/submenu_view.h"
#include "ui/views/drag_utils.h"
+#include "ui/views/event_utils.h"
+#include "ui/views/focus/view_storage.h"
+#include "ui/views/mouse_constants.h"
#include "ui/views/view_constants.h"
#include "ui/views/views_delegate.h"
#include "ui/views/widget/root_view.h"
@@ -36,7 +42,6 @@
#if defined(USE_AURA)
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
-#include "ui/aura/window.h"
#endif
#if defined(OS_WIN)
@@ -68,12 +73,17 @@ namespace {
// When showing context menu on mouse down, the user might accidentally select
// the menu item on the subsequent mouse up. To prevent this, we add the
// following delay before the user is able to select an item.
-static int context_menu_selection_hold_time_ms = 200;
+static int menu_selection_hold_time_ms = kMinimumMsPressedToActivate;
// The spacing offset for the bubble tip.
const int kBubbleTipSizeLeftRight = 12;
const int kBubbleTipSizeTopBottom = 11;
+// The maximum distance (in DIPS) that the mouse can be moved before it should
+// trigger a mouse menu item activation (regardless of how long the menu has
+// been showing).
+const float kMaximumLengthMovedToActivate = 4.0f;
+
// Returns true if the mnemonic of |menu| matches key.
bool MatchesMnemonic(MenuItemView* menu, char16 key) {
return menu->GetMnemonic() == key;
@@ -268,7 +278,7 @@ struct MenuController::SelectByCharDetails {
MenuController::State::State()
: item(NULL),
submenu_open(false),
- anchor(views::MenuItemView::TOPLEFT),
+ anchor(MenuItemView::TOPLEFT),
context_menu(false) {}
MenuController::State::~State() {}
@@ -295,12 +305,26 @@ MenuItemView* MenuController::Run(Widget* parent,
drag_in_progress_ = false;
closing_event_time_ = base::TimeDelta();
menu_start_time_ = base::TimeTicks::Now();
+ menu_start_mouse_press_loc_ = gfx::Point();
// If we are shown on mouse press, we will eat the subsequent mouse down and
// the parent widget will not be able to reset its state (it might have mouse
// capture from the mouse down). So we clear its state here.
- if (parent && parent->GetRootView())
- parent->GetRootView()->SetMouseHandler(NULL);
+ if (parent) {
+ View* root_view = parent->GetRootView();
+ if (root_view) {
+ root_view->SetMouseHandler(NULL);
+ const ui::Event* event =
+ static_cast<internal::RootView*>(root_view)->current_event();
+ if (event && event->type() == ui::ET_MOUSE_PRESSED) {
+ gfx::Point screen_loc(
+ static_cast<const ui::MouseEvent*>(event)->location());
+ View::ConvertPointToScreen(
+ static_cast<View*>(event->target()), &screen_loc);
+ menu_start_mouse_press_loc_ = screen_loc;
+ }
+ }
+ }
bool nested_menu = showing_;
if (showing_) {
@@ -485,9 +509,9 @@ void MenuController::OnMouseReleased(SubmenuView* source,
// If it is from an empty menu, use parent context menu instead of that.
if (menu == NULL &&
part.submenu->child_count() == 1 &&
- part.submenu->child_at(0)->id()
- == views::MenuItemView::kEmptyMenuItemViewID)
+ part.submenu->child_at(0)->id() == MenuItemView::kEmptyMenuItemViewID) {
menu = part.parent;
+ }
if (menu != NULL && ShowContextMenu(menu, source, event,
ui::MENU_SOURCE_MOUSE))
@@ -500,10 +524,23 @@ void MenuController::OnMouseReleased(SubmenuView* source,
if (!part.is_scroll() && part.menu &&
!(part.menu->HasSubmenu() &&
(event.flags() & ui::EF_LEFT_MOUSE_BUTTON))) {
- if (active_mouse_view_) {
+ if (GetActiveMouseView()) {
SendMouseReleaseToActiveView(source, event);
return;
}
+ // If a mouse release was received quickly after showing.
+ base::TimeDelta time_shown = base::TimeTicks::Now() - menu_start_time_;
+ if (time_shown.InMilliseconds() < menu_selection_hold_time_ms) {
+ // And it wasn't far from the mouse press location.
+ gfx::Point screen_loc(event.location());
+ View::ConvertPointToScreen(source->GetScrollViewContainer(), &screen_loc);
+ gfx::Vector2d moved = screen_loc - menu_start_mouse_press_loc_;
+ if (moved.Length() < kMaximumLengthMovedToActivate) {
+ // Ignore the mouse release as it was likely this menu was shown under
+ // the mouse and the action was just a normal click.
+ return;
+ }
+ }
if (part.menu->GetDelegate()->ShouldExecuteCommandWithoutClosingMenu(
part.menu->GetCommand(), event)) {
part.menu->GetDelegate()->ExecuteCommand(part.menu->GetCommand(),
@@ -512,11 +549,11 @@ void MenuController::OnMouseReleased(SubmenuView* source,
}
if (!part.menu->NonIconChildViewsCount() &&
part.menu->GetDelegate()->IsTriggerableEvent(part.menu, event)) {
- int64 time_since_menu_start =
- (base::TimeTicks::Now() - menu_start_time_).InMilliseconds();
+ base::TimeDelta shown_time = base::TimeTicks::Now() - menu_start_time_;
if (!state_.context_menu || !View::ShouldShowContextMenuOnMousePress() ||
- time_since_menu_start > context_menu_selection_hold_time_ms)
+ shown_time.InMilliseconds() > menu_selection_hold_time_ms) {
Accept(part.menu, event.flags());
+ }
return;
}
} else if (part.type == MenuPart::MENU_ITEM) {
@@ -740,7 +777,7 @@ void MenuController::UpdateSubmenuSelection(SubmenuView* submenu) {
gfx::Point point = GetScreen()->GetCursorScreenPoint();
const SubmenuView* root_submenu =
submenu->GetMenuItem()->GetRootMenuItem()->GetSubmenu();
- views::View::ConvertPointFromScreen(
+ View::ConvertPointFromScreen(
root_submenu->GetWidget()->GetRootView(), &point);
HandleMouseLocation(submenu, point);
}
@@ -753,8 +790,8 @@ void MenuController::OnWidgetDestroying(Widget* widget) {
}
// static
-void MenuController::TurnOffContextMenuSelectionHoldForTest() {
- context_menu_selection_hold_time_ms = -1;
+void MenuController::TurnOffMenuSelectionHoldForTest() {
+ menu_selection_hold_time_ms = -1;
}
void MenuController::SetSelection(MenuItemView* menu_item,
@@ -828,7 +865,7 @@ void MenuController::SetSelectionOnPointerDown(SubmenuView* source,
if (!blocking_run_)
return;
- DCHECK(!active_mouse_view_);
+ DCHECK(!GetActiveMouseView());
MenuPart part = GetMenuPart(source, event.location());
if (part.is_scroll())
@@ -855,9 +892,15 @@ void MenuController::SetSelectionOnPointerDown(SubmenuView* source,
#if defined(OS_WIN)
// We're going to close and we own the mouse capture. We need to repost the
- // mouse down, otherwise the window the user clicked on won't get the
- // event.
- RepostEvent(source, event);
+ // mouse down, otherwise the window the user clicked on won't get the event.
+ if (!state_.item) {
+ // We some times get an event after closing all the menus. Ignore it. Make
+ // sure the menu is in fact not visible. If the menu is visible, then
+ // we're in a bad state where we think the menu isn't visibile but it is.
+ DCHECK(!source->GetWidget()->IsVisible());
+ } else {
+ RepostEvent(source, event);
+ }
#endif
// And close.
@@ -914,7 +957,7 @@ void MenuController::StartDrag(SubmenuView* source,
View::ConvertPointToTarget(NULL, item, &press_loc);
gfx::Point widget_loc(press_loc);
View::ConvertPointToWidget(item, &widget_loc);
- scoped_ptr<gfx::Canvas> canvas(views::GetCanvasForDragImage(
+ scoped_ptr<gfx::Canvas> canvas(GetCanvasForDragImage(
source->GetWidget(), gfx::Size(item->width(), item->height())));
item->PaintButton(canvas.get(), MenuItemView::PB_FOR_DRAG);
@@ -1119,7 +1162,7 @@ MenuController::MenuController(ui::NativeTheme* theme,
last_drop_operation_(MenuDelegate::DROP_UNKNOWN),
showing_submenu_(false),
menu_button_(NULL),
- active_mouse_view_(NULL),
+ active_mouse_view_id_(ViewStorage::GetInstance()->CreateStorageID()),
delegate_(delegate),
message_loop_depth_(0),
menu_config_(theme),
@@ -1218,8 +1261,7 @@ bool MenuController::ShowSiblingMenu(SubmenuView* source,
return false;
}
- gfx::NativeWindow window_under_mouse =
- GetScreen()->GetWindowAtCursorScreenPoint();
+ gfx::NativeWindow window_under_mouse = GetScreen()->GetWindowUnderCursor();
// TODO(oshima): Replace with views only API.
if (!owner_ || window_under_mouse != owner_->GetNativeWindow())
return false;
@@ -1541,7 +1583,7 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) {
void MenuController::MenuChildrenChanged(MenuItemView* item) {
DCHECK(item);
// Menu shouldn't be updated during drag operation.
- DCHECK(!active_mouse_view_);
+ DCHECK(!GetActiveMouseView());
// If the current item or pending item is a descendant of the item
// that changed, move the selection back to the changed item.
@@ -2058,85 +2100,53 @@ bool MenuController::SelectByChar(char16 character) {
return false;
}
-#if defined(OS_WIN)
void MenuController::RepostEvent(SubmenuView* source,
const ui::LocatedEvent& event) {
- if (!state_.item) {
- // We some times get an event after closing all the menus. Ignore it.
- // Make sure the menu is in fact not visible. If the menu is visible, then
- // we're in a bad state where we think the menu isn't visibile but it is.
- DCHECK(!source->GetWidget()->IsVisible());
- return;
- }
-
gfx::Point screen_loc(event.location());
View::ConvertPointToScreen(source->GetScrollViewContainer(), &screen_loc);
- HWND window = WindowFromPoint(screen_loc.ToPOINT());
- if (window) {
- // Release the capture.
- SubmenuView* submenu = state_.item->GetRootMenuItem()->GetSubmenu();
- submenu->ReleaseCapture();
-
- if (submenu->GetWidget()->GetNativeView() &&
- GetWindowThreadProcessId(
- views::HWNDForNativeView(submenu->GetWidget()->GetNativeView()),
- NULL) != GetWindowThreadProcessId(window, NULL)) {
- // Even though we have mouse capture, windows generates a mouse event
- // if the other window is in a separate thread. Don't generate an event in
- // this case else the target window can get double events leading to bad
- // behavior.
- return;
- }
- // Convert the coordinates to the target window.
- RECT window_bounds;
- GetWindowRect(window, &window_bounds);
- int window_x = screen_loc.x() - window_bounds.left;
- int window_y = screen_loc.y() - window_bounds.top;
-
- // Determine whether the click was in the client area or not.
- // NOTE: WM_NCHITTEST coordinates are relative to the screen.
- LRESULT nc_hit_result = SendMessage(window, WM_NCHITTEST, 0,
- MAKELPARAM(screen_loc.x(),
- screen_loc.y()));
- const bool in_client_area = (nc_hit_result == HTCLIENT);
-
- // TODO(sky): this isn't right. The event to generate should correspond
- // with the event we just got. MouseEvent only tells us what is down,
- // which may differ. Need to add ability to get changed button from
- // MouseEvent.
- int event_type;
- int flags = event.flags();
- if (flags & ui::EF_LEFT_MOUSE_BUTTON)
- event_type = in_client_area ? WM_LBUTTONDOWN : WM_NCLBUTTONDOWN;
- else if (flags & ui::EF_MIDDLE_MOUSE_BUTTON)
- event_type = in_client_area ? WM_MBUTTONDOWN : WM_NCMBUTTONDOWN;
- else if (flags & ui::EF_RIGHT_MOUSE_BUTTON)
- event_type = in_client_area ? WM_RBUTTONDOWN : WM_NCRBUTTONDOWN;
- else
- event_type = 0; // Unknown mouse press.
+ gfx::NativeView native_view = source->GetWidget()->GetNativeView();
+ gfx::Screen* screen = gfx::Screen::GetScreenFor(native_view);
+ gfx::NativeWindow window = screen->GetWindowAtScreenPoint(screen_loc);
- if (event_type) {
- if (in_client_area) {
- PostMessage(window, event_type, event.native_event().wParam,
- MAKELPARAM(window_x, window_y));
- } else {
- PostMessage(window, event_type, nc_hit_result,
- MAKELPARAM(screen_loc.x(), screen_loc.y()));
- }
+ if (!window)
+ return;
+
+#if defined(OS_WIN)
+ // Release the capture.
+ SubmenuView* submenu = state_.item->GetRootMenuItem()->GetSubmenu();
+ submenu->ReleaseCapture();
+
+ gfx::NativeView view = submenu->GetWidget()->GetNativeView();
+ if (view) {
+ DWORD view_tid = GetWindowThreadProcessId(HWNDForNativeView(view), NULL);
+ if (view_tid != GetWindowThreadProcessId(HWNDForNativeView(window), NULL)) {
+ // Even though we have mouse capture, windows generates a mouse event if
+ // the other window is in a separate thread. Only repost an event if
+ // |view| was created on the same thread, else the target window can get
+ // double events leading to bad behavior.
+ return;
}
}
-}
-#elif defined(USE_AURA)
-void MenuController::RepostEvent(SubmenuView* source,
- const ui::LocatedEvent& event) {
- aura::RootWindow* root_window =
- source->GetWidget()->GetNativeWindow()->GetRootWindow();
- DCHECK(root_window);
- root_window->RepostEvent(event);
-}
#endif
+ scoped_ptr<ui::LocatedEvent> clone;
+ if (event.IsMouseEvent()) {
+ clone.reset(new ui::MouseEvent(static_cast<const ui::MouseEvent&>(event)));
+ } else if (event.IsGestureEvent()) {
+ // TODO(rbyers): Gesture event repost is tricky to get right
+ // crbug.com/170987.
+ return;
+ } else {
+ NOTREACHED();
+ return;
+ }
+ clone->set_location(screen_loc);
+
+ RepostLocatedEvent(window, *clone);
+}
+
+
void MenuController::SetDropMenuItem(
MenuItemView* new_target,
MenuDelegate::DropPosition new_position) {
@@ -2185,63 +2195,75 @@ void MenuController::UpdateActiveMouseView(SubmenuView* event_source,
if (target == target_menu || !target->enabled())
target = NULL;
}
- if (target != active_mouse_view_) {
+ View* active_mouse_view = GetActiveMouseView();
+ if (target != active_mouse_view) {
SendMouseCaptureLostToActiveView();
- active_mouse_view_ = target;
- if (active_mouse_view_) {
+ active_mouse_view = target;
+ SetActiveMouseView(active_mouse_view);
+ if (active_mouse_view) {
gfx::Point target_point(target_menu_loc);
View::ConvertPointToTarget(
- target_menu, active_mouse_view_, &target_point);
+ target_menu, active_mouse_view, &target_point);
ui::MouseEvent mouse_entered_event(ui::ET_MOUSE_ENTERED,
target_point, target_point,
0);
- active_mouse_view_->OnMouseEntered(mouse_entered_event);
+ active_mouse_view->OnMouseEntered(mouse_entered_event);
ui::MouseEvent mouse_pressed_event(ui::ET_MOUSE_PRESSED,
target_point, target_point,
event.flags());
- active_mouse_view_->OnMousePressed(mouse_pressed_event);
+ active_mouse_view->OnMousePressed(mouse_pressed_event);
}
}
- if (active_mouse_view_) {
+ if (active_mouse_view) {
gfx::Point target_point(target_menu_loc);
- View::ConvertPointToTarget(target_menu, active_mouse_view_, &target_point);
+ View::ConvertPointToTarget(target_menu, active_mouse_view, &target_point);
ui::MouseEvent mouse_dragged_event(ui::ET_MOUSE_DRAGGED,
target_point, target_point,
event.flags());
- active_mouse_view_->OnMouseDragged(mouse_dragged_event);
+ active_mouse_view->OnMouseDragged(mouse_dragged_event);
}
}
void MenuController::SendMouseReleaseToActiveView(SubmenuView* event_source,
const ui::MouseEvent& event) {
- if (!active_mouse_view_)
+ View* active_mouse_view = GetActiveMouseView();
+ if (!active_mouse_view)
return;
gfx::Point target_loc(event.location());
View::ConvertPointToScreen(event_source->GetScrollViewContainer(),
&target_loc);
- View::ConvertPointToTarget(NULL, active_mouse_view_, &target_loc);
- ui::MouseEvent release_event(ui::ET_MOUSE_RELEASED,
- target_loc, target_loc,
- event.flags());
- // Reset the active_mouse_view_ before sending mouse released. That way if it
- // calls back to us, we aren't in a weird state.
- View* active_view = active_mouse_view_;
- active_mouse_view_ = NULL;
- active_view->OnMouseReleased(release_event);
+ View::ConvertPointToTarget(NULL, active_mouse_view, &target_loc);
+ ui::MouseEvent release_event(ui::ET_MOUSE_RELEASED, target_loc, target_loc,
+ event.flags());
+ // Reset active mouse view before sending mouse released. That way if it calls
+ // back to us, we aren't in a weird state.
+ SetActiveMouseView(NULL);
+ active_mouse_view->OnMouseReleased(release_event);
}
void MenuController::SendMouseCaptureLostToActiveView() {
- if (!active_mouse_view_)
+ View* active_mouse_view = GetActiveMouseView();
+ if (!active_mouse_view)
return;
// Reset the active_mouse_view_ before sending mouse capture lost. That way if
// it calls back to us, we aren't in a weird state.
- View* active_view = active_mouse_view_;
- active_mouse_view_ = NULL;
- active_view->OnMouseCaptureLost();
+ SetActiveMouseView(NULL);
+ active_mouse_view->OnMouseCaptureLost();
+}
+
+void MenuController::SetActiveMouseView(View* view) {
+ if (view)
+ ViewStorage::GetInstance()->StoreView(active_mouse_view_id_, view);
+ else
+ ViewStorage::GetInstance()->RemoveView(active_mouse_view_id_);
+}
+
+View* MenuController::GetActiveMouseView() {
+ return ViewStorage::GetInstance()->RetrieveView(active_mouse_view_id_);
}
void MenuController::SetExitType(ExitType type) {
diff --git a/chromium/ui/views/controls/menu/menu_controller.h b/chromium/ui/views/controls/menu/menu_controller.h
index 6dfdd528e9f..1bd571aa043 100644
--- a/chromium/ui/views/controls/menu/menu_controller.h
+++ b/chromium/ui/views/controls/menu/menu_controller.h
@@ -15,7 +15,7 @@
#include "base/memory/scoped_ptr.h"
#include "base/message_loop/message_loop.h"
#include "base/timer/timer.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "ui/views/controls/menu/menu_delegate.h"
#include "ui/views/controls/menu/menu_item_view.h"
#include "ui/views/widget/widget_observer.h"
@@ -137,7 +137,7 @@ class VIEWS_EXPORT MenuController : public base::MessageLoop::Dispatcher,
virtual void OnWidgetDestroying(Widget* widget) OVERRIDE;
// Only used for testing.
- static void TurnOffContextMenuSelectionHoldForTest();
+ static void TurnOffMenuSelectionHoldForTest();
private:
friend class internal::MenuRunnerImpl;
@@ -445,7 +445,7 @@ class VIEWS_EXPORT MenuController : public base::MessageLoop::Dispatcher,
// Stops scrolling.
void StopScrolling();
- // Updates |active_mouse_view_| from the location of the event and sends it
+ // Updates active mouse view from the location of the event and sends it
// the appropriate events. This is used to send mouse events to child views so
// that they react to click-drag-release as if the user clicked on the view
// itself.
@@ -453,15 +453,19 @@ class VIEWS_EXPORT MenuController : public base::MessageLoop::Dispatcher,
const ui::MouseEvent& event,
View* target_menu);
- // Sends a mouse release event to the current |active_mouse_view_| and sets
+ // Sends a mouse release event to the current active mouse view and sets
// it to null.
void SendMouseReleaseToActiveView(SubmenuView* event_source,
const ui::MouseEvent& event);
- // Sends a mouse capture lost event to the current |active_mouse_view_| and
- // sets it to null.
+ // Sends a mouse capture lost event to the current active mouse view and sets
+ // it to null.
void SendMouseCaptureLostToActiveView();
+ // Sets/gets the active mouse view. See UpdateActiveMouseView() for details.
+ void SetActiveMouseView(View* view);
+ View* GetActiveMouseView();
+
// Sets exit type.
void SetExitType(ExitType type);
@@ -556,9 +560,9 @@ class VIEWS_EXPORT MenuController : public base::MessageLoop::Dispatcher,
MenuButton* menu_button_;
- // If non-null mouse drag events are forwarded to this view. See
- // UpdateActiveMouseView for details.
- View* active_mouse_view_;
+ // ViewStorage id used to store the view mouse drag events are forwarded to.
+ // See UpdateActiveMouseView() for details.
+ const int active_mouse_view_id_;
internal::MenuControllerDelegate* delegate_;
@@ -574,6 +578,10 @@ class VIEWS_EXPORT MenuController : public base::MessageLoop::Dispatcher,
// Time when the menu is first shown.
base::TimeTicks menu_start_time_;
+ // If a mouse press triggered this menu, this will have its location (in
+ // screen coordinates). Otherwise this will be (0, 0).
+ gfx::Point menu_start_mouse_press_loc_;
+
DISALLOW_COPY_AND_ASSIGN(MenuController);
};
diff --git a/chromium/ui/views/controls/menu/menu_host.cc b/chromium/ui/views/controls/menu/menu_host.cc
index 6dea62c6560..f9dd5b2a550 100644
--- a/chromium/ui/views/controls/menu/menu_host.cc
+++ b/chromium/ui/views/controls/menu/menu_host.cc
@@ -29,6 +29,7 @@ MenuHost::MenuHost(SubmenuView* submenu)
: submenu_(submenu),
destroying_(false),
ignore_capture_lost_(false) {
+ set_auto_release_capture(false);
}
MenuHost::~MenuHost() {
@@ -109,10 +110,6 @@ internal::RootView* MenuHost::CreateRootView() {
return new MenuHostRootView(this, submenu_);
}
-bool MenuHost::ShouldReleaseCaptureOnMouseReleased() const {
- return false;
-}
-
void MenuHost::OnMouseCaptureLost() {
if (destroying_ || ignore_capture_lost_)
return;
diff --git a/chromium/ui/views/controls/menu/menu_host.h b/chromium/ui/views/controls/menu/menu_host.h
index 1255a52ef5e..e38cab52b7d 100644
--- a/chromium/ui/views/controls/menu/menu_host.h
+++ b/chromium/ui/views/controls/menu/menu_host.h
@@ -57,7 +57,6 @@ class MenuHost : public Widget {
private:
// Overridden from Widget:
virtual internal::RootView* CreateRootView() OVERRIDE;
- virtual bool ShouldReleaseCaptureOnMouseReleased() const OVERRIDE;
virtual void OnMouseCaptureLost() OVERRIDE;
virtual void OnNativeWidgetDestroyed() OVERRIDE;
virtual void OnOwnerClosing() OVERRIDE;
diff --git a/chromium/ui/views/controls/menu/menu_item_view.cc b/chromium/ui/views/controls/menu/menu_item_view.cc
index 8d706819875..040cd898616 100644
--- a/chromium/ui/views/controls/menu/menu_item_view.cc
+++ b/chromium/ui/views/controls/menu/menu_item_view.cc
@@ -227,6 +227,7 @@ MenuItemView* MenuItemView::AddMenuItemAt(
int item_id,
const string16& label,
const string16& sublabel,
+ const string16& minor_text,
const gfx::ImageSkia& icon,
Type type,
ui::MenuSeparatorType separator_style) {
@@ -245,6 +246,7 @@ MenuItemView* MenuItemView::AddMenuItemAt(
else
item->SetTitle(label);
item->SetSubtitle(sublabel);
+ item->SetMinorText(minor_text);
if (!icon.isNull())
item->SetIcon(icon);
if (type == SUBMENU)
@@ -271,21 +273,21 @@ void MenuItemView::RemoveMenuItemAt(int index) {
MenuItemView* MenuItemView::AppendMenuItem(int item_id,
const string16& label,
Type type) {
- return AppendMenuItemImpl(item_id, label, string16(), gfx::ImageSkia(), type,
- ui::NORMAL_SEPARATOR);
+ return AppendMenuItemImpl(item_id, label, string16(), string16(),
+ gfx::ImageSkia(), type, ui::NORMAL_SEPARATOR);
}
MenuItemView* MenuItemView::AppendSubMenu(int item_id,
const string16& label) {
- return AppendMenuItemImpl(item_id, label, string16(), gfx::ImageSkia(),
- SUBMENU, ui::NORMAL_SEPARATOR);
+ return AppendMenuItemImpl(item_id, label, string16(), string16(),
+ gfx::ImageSkia(), SUBMENU, ui::NORMAL_SEPARATOR);
}
MenuItemView* MenuItemView::AppendSubMenuWithIcon(int item_id,
const string16& label,
const gfx::ImageSkia& icon) {
- return AppendMenuItemImpl(
- item_id, label, string16(), icon, SUBMENU, ui::NORMAL_SEPARATOR);
+ return AppendMenuItemImpl(item_id, label, string16(), string16(), icon,
+ SUBMENU, ui::NORMAL_SEPARATOR);
}
MenuItemView* MenuItemView::AppendMenuItemWithLabel(int item_id,
@@ -298,15 +300,15 @@ MenuItemView* MenuItemView::AppendDelegateMenuItem(int item_id) {
}
void MenuItemView::AppendSeparator() {
- AppendMenuItemImpl(0, string16(), string16(), gfx::ImageSkia(), SEPARATOR,
- ui::NORMAL_SEPARATOR);
+ AppendMenuItemImpl(0, string16(), string16(), string16(), gfx::ImageSkia(),
+ SEPARATOR, ui::NORMAL_SEPARATOR);
}
MenuItemView* MenuItemView::AppendMenuItemWithIcon(int item_id,
const string16& label,
const gfx::ImageSkia& icon) {
- return AppendMenuItemImpl(
- item_id, label, string16(), icon, NORMAL, ui::NORMAL_SEPARATOR);
+ return AppendMenuItemImpl(item_id, label, string16(), string16(), icon,
+ NORMAL, ui::NORMAL_SEPARATOR);
}
MenuItemView* MenuItemView::AppendMenuItemFromModel(ui::MenuModel* model,
@@ -314,7 +316,7 @@ MenuItemView* MenuItemView::AppendMenuItemFromModel(ui::MenuModel* model,
int id) {
gfx::Image icon;
model->GetIconAt(index, &icon);
- string16 label, sublabel;
+ string16 label, sublabel, minor_text;
ui::MenuSeparatorType separator_style = ui::NORMAL_SEPARATOR;
MenuItemView::Type type;
ui::MenuModel::ItemType menu_type = model->GetTypeAt(index);
@@ -323,16 +325,19 @@ MenuItemView* MenuItemView::AppendMenuItemFromModel(ui::MenuModel* model,
type = MenuItemView::NORMAL;
label = model->GetLabelAt(index);
sublabel = model->GetSublabelAt(index);
+ minor_text = model->GetMinorTextAt(index);
break;
case ui::MenuModel::TYPE_CHECK:
type = MenuItemView::CHECKBOX;
label = model->GetLabelAt(index);
sublabel = model->GetSublabelAt(index);
+ minor_text = model->GetMinorTextAt(index);
break;
case ui::MenuModel::TYPE_RADIO:
type = MenuItemView::RADIO;
label = model->GetLabelAt(index);
sublabel = model->GetSublabelAt(index);
+ minor_text = model->GetMinorTextAt(index);
break;
case ui::MenuModel::TYPE_SEPARATOR:
icon = gfx::Image();
@@ -343,6 +348,7 @@ MenuItemView* MenuItemView::AppendMenuItemFromModel(ui::MenuModel* model,
type = MenuItemView::SUBMENU;
label = model->GetLabelAt(index);
sublabel = model->GetSublabelAt(index);
+ minor_text = model->GetMinorTextAt(index);
break;
default:
NOTREACHED();
@@ -353,6 +359,7 @@ MenuItemView* MenuItemView::AppendMenuItemFromModel(ui::MenuModel* model,
return AppendMenuItemImpl(id,
label,
sublabel,
+ minor_text,
icon.IsEmpty() ? gfx::ImageSkia() : *icon.ToImageSkia(),
type,
separator_style);
@@ -362,11 +369,12 @@ MenuItemView* MenuItemView::AppendMenuItemImpl(
int item_id,
const string16& label,
const string16& sublabel,
+ const string16& minor_text,
const gfx::ImageSkia& icon,
Type type,
ui::MenuSeparatorType separator_style) {
const int index = submenu_ ? submenu_->child_count() : 0;
- return AddMenuItemAt(index, item_id, label, sublabel, icon, type,
+ return AddMenuItemAt(index, item_id, label, sublabel, minor_text, icon, type,
separator_style);
}
@@ -394,6 +402,11 @@ void MenuItemView::SetSubtitle(const string16& subtitle) {
invalidate_dimensions(); // Triggers preferred size recalculation.
}
+void MenuItemView::SetMinorText(const string16& minor_text) {
+ minor_text_ = minor_text;
+ invalidate_dimensions(); // Triggers preferred size recalculation.
+}
+
void MenuItemView::SetSelected(bool selected) {
selected_ = selected;
SchedulePaint();
@@ -851,7 +864,9 @@ void MenuItemView::PaintButton(gfx::Canvas* canvas, PaintButtonMode mode) {
(!delegate ||
delegate->ShouldReserveSpaceForSubmenuIndicator() ?
item_right_margin_ : config.arrow_to_edge_padding);
- gfx::Rect text_bounds(label_start, top_margin, width, available_height);
+ gfx::Rect text_bounds(label_start, top_margin, width,
+ subtitle_.empty() ? available_height
+ : available_height / 2);
text_bounds.set_x(GetMirroredXForRect(text_bounds));
int flags = GetDrawStringFlags();
if (mode == PB_FOR_DRAG)
@@ -859,6 +874,18 @@ void MenuItemView::PaintButton(gfx::Canvas* canvas, PaintButtonMode mode) {
canvas->DrawStringInt(title(), font, fg_color,
text_bounds.x(), text_bounds.y(), text_bounds.width(),
text_bounds.height(), flags);
+ if (!subtitle_.empty()) {
+ canvas->DrawStringInt(
+ subtitle_,
+ font,
+ GetNativeTheme()->GetSystemColor(
+ ui::NativeTheme::kColorId_ButtonDisabledColor),
+ text_bounds.x(),
+ text_bounds.y() + GetFont().GetHeight(),
+ text_bounds.width(),
+ text_bounds.height(),
+ flags);
+ }
PaintMinorText(canvas, render_selection);
@@ -1003,7 +1030,11 @@ MenuItemView::MenuItemDimensions MenuItemView::CalculateDimensions() {
}
int label_start = GetLabelStartForThisItem();
- dimensions.standard_width = font.GetStringWidth(title_) + label_start +
+ int string_width = font.GetStringWidth(title_);
+ if (!subtitle_.empty())
+ string_width = std::max(string_width, font.GetStringWidth(subtitle_));
+
+ dimensions.standard_width = string_width + label_start +
item_right_margin_;
// Determine the length of the right-side text.
string16 minor_text = GetMinorText();
@@ -1012,6 +1043,7 @@ MenuItemView::MenuItemDimensions MenuItemView::CalculateDimensions() {
// Determine the height to use.
dimensions.height = std::max(dimensions.height,
+ (subtitle_.empty() ? 0 : font.GetHeight()) +
font.GetHeight() + GetBottomMargin() + GetTopMargin());
dimensions.height = std::max(dimensions.height,
GetMenuConfig().item_min_height);
@@ -1039,7 +1071,7 @@ string16 MenuItemView::GetMinorText() {
return accelerator.GetShortcutText();
}
- return subtitle_;
+ return minor_text_;
}
bool MenuItemView::IsContainer() const {
diff --git a/chromium/ui/views/controls/menu/menu_item_view.h b/chromium/ui/views/controls/menu/menu_item_view.h
index e625592c30d..9d641fda56f 100644
--- a/chromium/ui/views/controls/menu/menu_item_view.h
+++ b/chromium/ui/views/controls/menu/menu_item_view.h
@@ -164,6 +164,7 @@ class VIEWS_EXPORT MenuItemView : public View {
int item_id,
const string16& label,
const string16& sublabel,
+ const string16& minor_text,
const gfx::ImageSkia& icon,
Type type,
ui::MenuSeparatorType separator_style);
@@ -224,6 +225,7 @@ class VIEWS_EXPORT MenuItemView : public View {
MenuItemView* AppendMenuItemImpl(int item_id,
const string16& label,
const string16& sublabel,
+ const string16& minor_text,
const gfx::ImageSkia& icon,
Type type,
ui::MenuSeparatorType separator_style);
@@ -249,6 +251,9 @@ class VIEWS_EXPORT MenuItemView : public View {
// Sets the subtitle.
void SetSubtitle(const string16& subtitle);
+ // Sets the minor text.
+ void SetMinorText(const string16& minor_text);
+
// Returns the type of this menu.
const Type& GetType() const { return type_; }
@@ -475,6 +480,9 @@ class VIEWS_EXPORT MenuItemView : public View {
// Subtitle/sublabel.
string16 subtitle_;
+ // Minor text.
+ string16 minor_text_;
+
// Does the title have a mnemonic? Only useful on the root menu item.
bool has_mnemonics_;
diff --git a/chromium/ui/views/controls/menu/menu_win.cc b/chromium/ui/views/controls/menu/menu_win.cc
index 3ff01b878c8..ac08ec7fb5b 100644
--- a/chromium/ui/views/controls/menu/menu_win.cc
+++ b/chromium/ui/views/controls/menu/menu_win.cc
@@ -10,13 +10,13 @@
#include "base/stl_util.h"
#include "base/strings/string_util.h"
#include "ui/base/accelerators/accelerator.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/l10n/l10n_util_win.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/gfx/rect.h"
+#include "ui/gfx/win/window_impl.h"
namespace views {
@@ -62,7 +62,7 @@ static int ChromeGetMenuItemID(HMENU hMenu, int pos) {
// to intercept right clicks on the HMENU and notify the delegate as well as
// for drawing icons.
//
-class MenuHostWindow : public ui::WindowImpl {
+class MenuHostWindow : public gfx::WindowImpl {
public:
MenuHostWindow(MenuWin* menu, HWND parent_window) : menu_(menu) {
int extended_style = 0;
diff --git a/chromium/ui/views/controls/menu/native_menu_win.cc b/chromium/ui/views/controls/menu/native_menu_win.cc
index e357b1ef3e4..c48a98c5f20 100644
--- a/chromium/ui/views/controls/menu/native_menu_win.cc
+++ b/chromium/ui/views/controls/menu/native_menu_win.cc
@@ -13,16 +13,16 @@
#include "base/strings/string_util.h"
#include "base/win/wrapped_window_proc.h"
#include "ui/base/accelerators/accelerator.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/l10n/l10n_util_win.h"
#include "ui/base/models/menu_model.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/gfx/image/image.h"
#include "ui/gfx/image/image_skia.h"
#include "ui/gfx/rect.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/native_theme/native_theme.h"
#include "ui/native_theme/native_theme_win.h"
#include "ui/views/controls/menu/menu_2.h"
@@ -81,8 +81,8 @@ class NativeMenuWin::MenuHostWindow {
RegisterClass();
hwnd_ = CreateWindowEx(l10n_util::GetExtendedStyles(), kWindowClassName,
L"", 0, 0, 0, 0, 0, HWND_MESSAGE, NULL, NULL, NULL);
- ui::CheckWindowCreated(hwnd_);
- ui::SetWindowUserData(hwnd_, this);
+ gfx::CheckWindowCreated(hwnd_);
+ gfx::SetWindowUserData(hwnd_, this);
}
~MenuHostWindow() {
@@ -350,7 +350,7 @@ class NativeMenuWin::MenuHostWindow {
WPARAM w_param,
LPARAM l_param) {
MenuHostWindow* host =
- reinterpret_cast<MenuHostWindow*>(ui::GetWindowUserData(window));
+ reinterpret_cast<MenuHostWindow*>(gfx::GetWindowUserData(window));
// host is null during initial construction.
LRESULT l_result = 0;
if (!host || !host->ProcessWindowMessage(window, message, w_param, l_param,
diff --git a/chromium/ui/views/controls/menu/submenu_view.cc b/chromium/ui/views/controls/menu/submenu_view.cc
index fce2983b59c..9184ca9abfb 100644
--- a/chromium/ui/views/controls/menu/submenu_view.cc
+++ b/chromium/ui/views/controls/menu/submenu_view.cc
@@ -8,7 +8,7 @@
#include "base/compiler_specific.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/views/controls/menu/menu_config.h"
#include "ui/views/controls/menu/menu_controller.h"
diff --git a/chromium/ui/views/controls/native/native_view_host.cc b/chromium/ui/views/controls/native/native_view_host.cc
index a5ae61d33ae..7ec512a5e50 100644
--- a/chromium/ui/views/controls/native/native_view_host.cc
+++ b/chromium/ui/views/controls/native/native_view_host.cc
@@ -6,6 +6,7 @@
#include "base/logging.h"
#include "ui/gfx/canvas.h"
+#include "ui/views/accessibility/native_view_accessibility.h"
#include "ui/views/controls/native/native_view_host_wrapper.h"
#include "ui/views/widget/widget.h"
@@ -13,6 +14,7 @@ namespace views {
// static
const char NativeViewHost::kViewClassName[] = "NativeViewHost";
+const char kWidgetNativeViewHostKey[] = "WidgetNativeViewHost";
#if defined(USE_AURA)
// Views implmenetatxion draws the focus.
@@ -48,6 +50,10 @@ void NativeViewHost::Attach(gfx::NativeView native_view) {
native_wrapper_->NativeViewWillAttach();
Widget::ReparentNativeView(native_view_, GetWidget()->GetNativeView());
Layout();
+
+ Widget* widget = Widget::GetWidgetForNativeView(native_view);
+ if (widget)
+ widget->SetNativeWindowProperty(kWidgetNativeViewHostKey, this);
}
void NativeViewHost::Detach() {
@@ -195,8 +201,12 @@ gfx::NativeViewAccessible NativeViewHost::GetNativeViewAccessible() {
void NativeViewHost::Detach(bool destroyed) {
if (native_view_) {
- if (!destroyed)
+ if (!destroyed) {
+ Widget* widget = Widget::GetWidgetForNativeView(native_view_);
+ if (widget)
+ widget->SetNativeWindowProperty(kWidgetNativeViewHostKey, NULL);
ClearFocus();
+ }
native_wrapper_->NativeViewDetaching(destroyed);
native_view_ = NULL;
}
diff --git a/chromium/ui/views/controls/native/native_view_host.h b/chromium/ui/views/controls/native/native_view_host.h
index c1738f8d789..bdc51510550 100644
--- a/chromium/ui/views/controls/native/native_view_host.h
+++ b/chromium/ui/views/controls/native/native_view_host.h
@@ -15,6 +15,10 @@ namespace views {
class NativeViewHostAuraTest;
class NativeViewHostWrapper;
+// If a NativeViewHost's native view is a Widget, this native window
+// property is set on the widget, pointing to the owning NativeViewHost.
+extern const char kWidgetNativeViewHostKey[];
+
// A View type that hosts a gfx::NativeView. The bounds of the native view are
// kept in sync with the bounds of this view as it is moved and sized.
// Under the hood, a platform-specific NativeViewHostWrapper implementation does
diff --git a/chromium/ui/views/controls/native/native_view_host_aura.cc b/chromium/ui/views/controls/native/native_view_host_aura.cc
index 3a3ed14f80c..444f5803e68 100644
--- a/chromium/ui/views/controls/native/native_view_host_aura.cc
+++ b/chromium/ui/views/controls/native/native_view_host_aura.cc
@@ -66,7 +66,9 @@ void NativeViewHostAura::RemovedFromWidget() {
}
void NativeViewHostAura::InstallClip(int x, int y, int w, int h) {
- NOTIMPLEMENTED();
+ // Note that this does not pose a problem functionality wise - it might
+ // however pose a speed degradation if not implemented.
+ LOG(WARNING) << "NativeViewHostAura::InstallClip is not implemented yet.";
}
bool NativeViewHostAura::HasInstalledClip() {
diff --git a/chromium/ui/views/controls/native/native_view_host_unittest.cc b/chromium/ui/views/controls/native/native_view_host_unittest.cc
index 0f8eca122b2..f30980bca8b 100644
--- a/chromium/ui/views/controls/native/native_view_host_unittest.cc
+++ b/chromium/ui/views/controls/native/native_view_host_unittest.cc
@@ -72,33 +72,23 @@ namespace {
// times NativeViewHierarchyChanged() is invoked.
class NativeViewHierarchyChangedTestView : public View {
public:
- NativeViewHierarchyChangedTestView()
- : attached_count_(0),
- detached_count_(0) {
+ NativeViewHierarchyChangedTestView() : notification_count_(0) {
}
- void ResetCounts() {
- attached_count_ = detached_count_ = 0;
+ void ResetCount() {
+ notification_count_ = 0;
}
- int attached_count() const { return attached_count_; }
- int detached_count() const { return detached_count_; }
+ int notification_count() const { return notification_count_; }
// Overriden from View:
- virtual void NativeViewHierarchyChanged(
- bool attached,
- gfx::NativeView native_view,
- internal::RootView* root_view) OVERRIDE {
- if (attached)
- attached_count_++;
- else
- detached_count_++;
- View::NativeViewHierarchyChanged(attached, native_view, root_view);
+ virtual void NativeViewHierarchyChanged() OVERRIDE {
+ ++notification_count_;
+ View::NativeViewHierarchyChanged();
}
private:
- int attached_count_;
- int detached_count_;
+ int notification_count_;
DISALLOW_COPY_AND_ASSIGN(NativeViewHierarchyChangedTestView);
};
@@ -158,22 +148,21 @@ TEST_F(NativeViewHostTest, NativeViewHierarchyChanged) {
test_view,
host));
- EXPECT_EQ(0, test_view->attached_count());
- EXPECT_EQ(0, test_view->detached_count());
- test_view->ResetCounts();
+ EXPECT_EQ(0, test_view->notification_count());
+ test_view->ResetCount();
- // Detach should send both an attach and detach as well as changing parent.
+ // Detaching should send a NativeViewHierarchyChanged() notification and
+ // change the parent.
host->Detach();
- EXPECT_EQ(1, test_view->attached_count());
- EXPECT_EQ(1, test_view->detached_count());
+ EXPECT_EQ(1, test_view->notification_count());
EXPECT_NE(toplevel()->GetNativeView(),
GetNativeParent(child->GetNativeView()));
- test_view->ResetCounts();
+ test_view->ResetCount();
- // Attaching should send both an attach and detach and reset parent.
+ // Attaching should send a NativeViewHierarchyChanged() notification and
+ // reset the parent.
host->Attach(child->GetNativeView());
- EXPECT_EQ(1, test_view->attached_count());
- EXPECT_EQ(1, test_view->detached_count());
+ EXPECT_EQ(1, test_view->notification_count());
EXPECT_EQ(toplevel()->GetNativeView(),
GetNativeParent(child->GetNativeView()));
}
diff --git a/chromium/ui/views/controls/native/native_view_host_win.cc b/chromium/ui/views/controls/native/native_view_host_win.cc
index 24ea19e7ca6..e7b74c3c7a1 100644
--- a/chromium/ui/views/controls/native/native_view_host_win.cc
+++ b/chromium/ui/views/controls/native/native_view_host_win.cc
@@ -7,10 +7,10 @@
#include <oleacc.h>
#include "base/logging.h"
-#include "ui/base/win/dpi.h"
#include "ui/base/win/hidden_window.h"
-#include "ui/base/win/window_impl.h"
#include "ui/gfx/canvas.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/window_impl.h"
#include "ui/views/controls/native/native_view_host.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/widget/native_widget.h"
@@ -91,7 +91,7 @@ void NativeViewHostWin::ShowWidget(int x, int y, int w, int h) {
SWP_NOCOPYBITS |
SWP_NOOWNERZORDER |
SWP_NOZORDER;
- gfx::Rect bounds = ui::win::DIPToScreenRect(gfx::Rect(x,y,w,h));
+ gfx::Rect bounds = gfx::win::DIPToScreenRect(gfx::Rect(x,y,w,h));
// Only send the SHOWWINDOW flag if we're invisible, to avoid flashing.
if (!IsWindowVisible(host_->native_view()))
diff --git a/chromium/ui/views/controls/native_control.cc b/chromium/ui/views/controls/native_control.cc
index e6219e74a1c..3a1fe581016 100644
--- a/chromium/ui/views/controls/native_control.cc
+++ b/chromium/ui/views/controls/native_control.cc
@@ -13,11 +13,11 @@
#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
#include "ui/base/accessibility/accessibility_types.h"
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util_win.h"
#include "ui/base/view_prop.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/views/background.h"
#include "ui/views/controls/native/native_view_host.h"
#include "ui/views/focus/focus_manager.h"
@@ -88,7 +88,7 @@ class NativeControlContainer : public CWindowImpl<NativeControlContainer,
control_ = parent_->CreateNativeControl(m_hWnd);
// We subclass the control hwnd so we get the WM_KEYDOWN messages.
- original_handler_ = ui::SetWindowProc(
+ original_handler_ = gfx::SetWindowProc(
control_, &NativeControl::NativeControlWndProc);
prop_.reset(new ViewProp(control_, kNativeControlKey , parent_));
@@ -378,7 +378,7 @@ LRESULT CALLBACK NativeControl::NativeControlWndProc(HWND window,
NOTREACHED();
}
} else if (message == WM_DESTROY) {
- ui::SetWindowProc(window, reinterpret_cast<WNDPROC>(original_handler));
+ gfx::SetWindowProc(window, reinterpret_cast<WNDPROC>(original_handler));
native_control->container_->prop_.reset();
}
diff --git a/chromium/ui/views/controls/native_control.h b/chromium/ui/views/controls/native_control.h
index 2ec731e278a..80aa5887cf1 100644
--- a/chromium/ui/views/controls/native_control.h
+++ b/chromium/ui/views/controls/native_control.h
@@ -7,7 +7,7 @@
#include <windows.h>
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/view.h"
namespace views {
diff --git a/chromium/ui/views/controls/native_control_win.cc b/chromium/ui/views/controls/native_control_win.cc
index 2b6c6d42571..c50411d13f5 100644
--- a/chromium/ui/views/controls/native_control_win.cc
+++ b/chromium/ui/views/controls/native_control_win.cc
@@ -10,7 +10,7 @@
#include "ui/base/accessibility/accessibility_types.h"
#include "ui/base/l10n/l10n_util_win.h"
#include "ui/base/view_prop.h"
-#include "ui/base/win/hwnd_util.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/views/controls/combobox/combobox.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/widget/widget.h"
@@ -139,7 +139,7 @@ void NativeControlWin::NativeControlCreated(HWND native_control) {
props_.push_back(ChildWindowMessageProcessor::Register(native_control, this));
// Subclass so we get WM_KEYDOWN and WM_SETFOCUS messages.
- original_wndproc_ = ui::SetWindowProc(
+ original_wndproc_ = gfx::SetWindowProc(
native_control, &NativeControlWin::NativeControlWndProc);
Attach(native_control);
@@ -216,7 +216,7 @@ LRESULT NativeControlWin::NativeControlWndProc(HWND window,
}
} else if (message == WM_DESTROY) {
native_control->props_.clear();
- ui::SetWindowProc(window, native_control->original_wndproc_);
+ gfx::SetWindowProc(window, native_control->original_wndproc_);
}
return CallWindowProc(native_control->original_wndproc_, window, message,
diff --git a/chromium/ui/views/controls/prefix_selector.cc b/chromium/ui/views/controls/prefix_selector.cc
index 6d6e0809c8b..91659bc2a29 100644
--- a/chromium/ui/views/controls/prefix_selector.cc
+++ b/chromium/ui/views/controls/prefix_selector.cc
@@ -6,7 +6,7 @@
#include "base/i18n/case_conversion.h"
#include "ui/base/ime/text_input_type.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
#include "ui/views/controls/prefix_delegate.h"
#include "ui/views/widget/widget.h"
@@ -91,30 +91,30 @@ bool PrefixSelector::HasCompositionText() {
return false;
}
-bool PrefixSelector::GetTextRange(ui::Range* range) {
- *range = ui::Range();
+bool PrefixSelector::GetTextRange(gfx::Range* range) {
+ *range = gfx::Range();
return false;
}
-bool PrefixSelector::GetCompositionTextRange(ui::Range* range) {
- *range = ui::Range();
+bool PrefixSelector::GetCompositionTextRange(gfx::Range* range) {
+ *range = gfx::Range();
return false;
}
-bool PrefixSelector::GetSelectionRange(ui::Range* range) {
- *range = ui::Range();
+bool PrefixSelector::GetSelectionRange(gfx::Range* range) {
+ *range = gfx::Range();
return false;
}
-bool PrefixSelector::SetSelectionRange(const ui::Range& range) {
+bool PrefixSelector::SetSelectionRange(const gfx::Range& range) {
return false;
}
-bool PrefixSelector::DeleteRange(const ui::Range& range) {
+bool PrefixSelector::DeleteRange(const gfx::Range& range) {
return false;
}
-bool PrefixSelector::GetTextFromRange(const ui::Range& range,
+bool PrefixSelector::GetTextFromRange(const gfx::Range& range,
string16* text) {
return false;
}
@@ -135,9 +135,11 @@ void PrefixSelector::EnsureCaretInRect(const gfx::Rect& rect) {
}
void PrefixSelector::OnTextInput(const string16& text) {
- // Small hack to filter out 'tab' input, as the expectation is that tabs
- // should cycle input elements, not influence selection.
- if (text.length() == 1 && text.at(0) == 0x09)
+ // Small hack to filter out 'tab' and 'enter' input, as the expectation is
+ // that they are control characters and will not affect the currently-active
+ // prefix.
+ if (text.length() == 1 &&
+ (text[0] == L'\t' || text[0] == L'\r' || text[0] == L'\n'))
return;
const int row_count = prefix_delegate_->GetRowCount();
diff --git a/chromium/ui/views/controls/prefix_selector.h b/chromium/ui/views/controls/prefix_selector.h
index 629c306449b..2c580086441 100644
--- a/chromium/ui/views/controls/prefix_selector.h
+++ b/chromium/ui/views/controls/prefix_selector.h
@@ -39,12 +39,12 @@ class VIEWS_EXPORT PrefixSelector : public ui::TextInputClient {
virtual bool GetCompositionCharacterBounds(uint32 index,
gfx::Rect* rect) OVERRIDE;
virtual bool HasCompositionText() OVERRIDE;
- virtual bool GetTextRange(ui::Range* range) OVERRIDE;
- virtual bool GetCompositionTextRange(ui::Range* range) OVERRIDE;
- virtual bool GetSelectionRange(ui::Range* range) OVERRIDE;
- virtual bool SetSelectionRange(const ui::Range& range) OVERRIDE;
- virtual bool DeleteRange(const ui::Range& range) OVERRIDE;
- virtual bool GetTextFromRange(const ui::Range& range,
+ virtual bool GetTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetCompositionTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetSelectionRange(gfx::Range* range) OVERRIDE;
+ virtual bool SetSelectionRange(const gfx::Range& range) OVERRIDE;
+ virtual bool DeleteRange(const gfx::Range& range) OVERRIDE;
+ virtual bool GetTextFromRange(const gfx::Range& range,
string16* text) OVERRIDE;
virtual void OnInputMethodChanged() OVERRIDE;
virtual bool ChangeTextDirectionAndLayoutAlignment(
diff --git a/chromium/ui/views/controls/scroll_view.cc b/chromium/ui/views/controls/scroll_view.cc
index 11ffc020ea7..d835c1ebdf8 100644
--- a/chromium/ui/views/controls/scroll_view.cc
+++ b/chromium/ui/views/controls/scroll_view.cc
@@ -5,7 +5,7 @@
#include "ui/views/controls/scroll_view.h"
#include "base/logging.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/border.h"
#include "ui/views/controls/scrollbar/native_scroll_bar.h"
diff --git a/chromium/ui/views/controls/scrollbar/base_scroll_bar.cc b/chromium/ui/views/controls/scrollbar/base_scroll_bar.cc
index 38c025676e0..6271c2e1bfe 100644
--- a/chromium/ui/views/controls/scrollbar/base_scroll_bar.cc
+++ b/chromium/ui/views/controls/scrollbar/base_scroll_bar.cc
@@ -13,9 +13,9 @@
#include "base/strings/utf_string_conversions.h"
#include "build/build_config.h"
#include "grit/ui_strings.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/views/controls/menu/menu_item_view.h"
#include "ui/views/controls/menu/menu_runner.h"
diff --git a/chromium/ui/views/controls/scrollbar/bitmap_scroll_bar.cc b/chromium/ui/views/controls/scrollbar/bitmap_scroll_bar.cc
index 7ba82e41140..2597cee0b78 100644
--- a/chromium/ui/views/controls/scrollbar/bitmap_scroll_bar.cc
+++ b/chromium/ui/views/controls/scrollbar/bitmap_scroll_bar.cc
@@ -13,8 +13,8 @@
#include "base/strings/utf_string_conversions.h"
#include "build/build_config.h"
#include "grit/ui_strings.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image_skia.h"
#include "ui/views/controls/menu/menu.h"
diff --git a/chromium/ui/views/controls/scrollbar/native_scroll_bar.cc b/chromium/ui/views/controls/scrollbar/native_scroll_bar.cc
index de2ec37bba5..9a913709a4b 100644
--- a/chromium/ui/views/controls/scrollbar/native_scroll_bar.cc
+++ b/chromium/ui/views/controls/scrollbar/native_scroll_bar.cc
@@ -8,7 +8,7 @@
#include <string>
#include "base/message_loop/message_loop.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/controls/scrollbar/native_scroll_bar_wrapper.h"
#include "ui/views/widget/widget.h"
diff --git a/chromium/ui/views/controls/scrollbar/native_scroll_bar_views.cc b/chromium/ui/views/controls/scrollbar/native_scroll_bar_views.cc
index aa812a894e5..6c3506f515c 100644
--- a/chromium/ui/views/controls/scrollbar/native_scroll_bar_views.cc
+++ b/chromium/ui/views/controls/scrollbar/native_scroll_bar_views.cc
@@ -5,7 +5,7 @@
#include "ui/views/controls/scrollbar/native_scroll_bar_views.h"
#include "base/logging.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/path.h"
#include "ui/views/controls/button/custom_button.h"
diff --git a/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.cc b/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.cc
index 25228e45a4d..176f7b9554e 100644
--- a/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.cc
+++ b/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.cc
@@ -23,7 +23,7 @@ const int kThumbHoverAlpha = 128;
const int kThumbDefaultAlpha = 64;
class OverlayScrollBarThumb : public BaseScrollBarThumb,
- public ui::AnimationDelegate {
+ public gfx::AnimationDelegate {
public:
explicit OverlayScrollBarThumb(BaseScrollBar* scroll_bar);
virtual ~OverlayScrollBarThumb();
@@ -33,8 +33,8 @@ class OverlayScrollBarThumb : public BaseScrollBarThumb,
virtual gfx::Size GetPreferredSize() OVERRIDE;
virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE;
- // ui::AnimationDelegate overrides:
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
+ // gfx::AnimationDelegate overrides:
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
private:
double animation_opacity_;
@@ -77,7 +77,7 @@ void OverlayScrollBarThumb::OnPaint(gfx::Canvas* canvas) {
}
void OverlayScrollBarThumb::AnimationProgressed(
- const ui::Animation* animation) {
+ const gfx::Animation* animation) {
animation_opacity_ = animation->GetCurrentValue();
SchedulePaint();
}
diff --git a/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.h b/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.h
index ac64d356097..b061da08586 100644
--- a/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.h
+++ b/chromium/ui/views/controls/scrollbar/overlay_scroll_bar.h
@@ -5,7 +5,7 @@
#ifndef UI_VIEWS_CONTROLS_SCROLLBAR_OVERLAY_SCROLL_BAR_H_
#define UI_VIEWS_CONTROLS_SCROLLBAR_OVERLAY_SCROLL_BAR_H_
-#include "ui/base/animation/slide_animation.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/views/controls/scrollbar/base_scroll_bar.h"
namespace views {
@@ -33,7 +33,7 @@ class VIEWS_EXPORT OverlayScrollBar : public BaseScrollBar {
virtual void OnPaint(gfx::Canvas* canvas) OVERRIDE;
private:
- ui::SlideAnimation animation_;
+ gfx::SlideAnimation animation_;
DISALLOW_COPY_AND_ASSIGN(OverlayScrollBar);
};
diff --git a/chromium/ui/views/controls/slider.cc b/chromium/ui/views/controls/slider.cc
index 2b74121c1e4..0a5c7f050cb 100644
--- a/chromium/ui/views/controls/slider.cc
+++ b/chromium/ui/views/controls/slider.cc
@@ -13,9 +13,9 @@
#include "third_party/skia/include/core/SkColor.h"
#include "third_party/skia/include/core/SkPaint.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/animation/slide_animation.h"
-#include "ui/base/events/event.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/events/event.h"
+#include "ui/gfx/animation/slide_animation.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
@@ -95,7 +95,7 @@ void Slider::SetValueInternal(float value, SliderChangeReason reason) {
// Do not animate when setting the value of the slider for the first time.
// There is no message-loop when running tests. So we cannot animate then.
animating_value_ = old_value;
- move_animation_.reset(new ui::SlideAnimation(this));
+ move_animation_.reset(new gfx::SlideAnimation(this));
move_animation_->SetSlideDuration(kSlideValueChangeDurationMS);
move_animation_->Show();
AnimationProgressed(move_animation_.get());
@@ -304,7 +304,7 @@ void Slider::OnGestureEvent(ui::GestureEvent* event) {
}
}
-void Slider::AnimationProgressed(const ui::Animation* animation) {
+void Slider::AnimationProgressed(const gfx::Animation* animation) {
animating_value_ = animation->CurrentValueBetween(animating_value_, value_);
SchedulePaint();
}
diff --git a/chromium/ui/views/controls/slider.h b/chromium/ui/views/controls/slider.h
index 5cfd3f5aaec..3c17e94af25 100644
--- a/chromium/ui/views/controls/slider.h
+++ b/chromium/ui/views/controls/slider.h
@@ -5,7 +5,7 @@
#ifndef UI_VIEWS_CONTROLS_SLIDER_H_
#define UI_VIEWS_CONTROLS_SLIDER_H_
-#include "ui/base/animation/animation_delegate.h"
+#include "ui/gfx/animation/animation_delegate.h"
#include "ui/views/view.h"
#include "ui/views/views_export.h"
@@ -13,9 +13,6 @@ typedef unsigned int SkColor;
namespace gfx {
class ImageSkia;
-}
-
-namespace ui {
class SlideAnimation;
}
@@ -45,7 +42,7 @@ class VIEWS_EXPORT SliderListener {
};
class VIEWS_EXPORT Slider : public View,
- public ui::AnimationDelegate {
+ public gfx::AnimationDelegate {
public:
enum Orientation {
HORIZONTAL,
@@ -96,13 +93,13 @@ class VIEWS_EXPORT Slider : public View,
// ui::EventHandler overrides:
virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE;
- // ui::AnimationDelegate overrides:
- virtual void AnimationProgressed(const ui::Animation* animation) OVERRIDE;
+ // gfx::AnimationDelegate overrides:
+ virtual void AnimationProgressed(const gfx::Animation* animation) OVERRIDE;
SliderListener* listener_;
Orientation orientation_;
- scoped_ptr<ui::SlideAnimation> move_animation_;
+ scoped_ptr<gfx::SlideAnimation> move_animation_;
float value_;
float keyboard_increment_;
diff --git a/chromium/ui/views/controls/styled_label.cc b/chromium/ui/views/controls/styled_label.cc
index d679ac13ee5..e23e40c4628 100644
--- a/chromium/ui/views/controls/styled_label.cc
+++ b/chromium/ui/views/controls/styled_label.cc
@@ -7,7 +7,7 @@
#include <vector>
#include "base/strings/string_util.h"
-#include "ui/base/text/text_elider.h"
+#include "ui/gfx/text_elider.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/controls/label.h"
#include "ui/views/controls/link.h"
@@ -82,7 +82,8 @@ bool StyledLabel::StyleRange::operator<(
StyledLabel::StyledLabel(const string16& text, StyledLabelListener* listener)
: listener_(listener),
- displayed_on_background_color_set_(false) {
+ displayed_on_background_color_set_(false),
+ auto_color_readability_enabled_(true) {
TrimWhitespace(text, TRIM_TRAILING, &text_);
}
@@ -95,11 +96,11 @@ void StyledLabel::SetText(const string16& text) {
PreferredSizeChanged();
}
-void StyledLabel::AddStyleRange(const ui::Range& range,
+void StyledLabel::AddStyleRange(const gfx::Range& range,
const RangeStyleInfo& style_info) {
DCHECK(!range.is_reversed());
DCHECK(!range.is_empty());
- DCHECK(ui::Range(0, text_.size()).Contains(range));
+ DCHECK(gfx::Range(0, text_.size()).Contains(range));
style_ranges_.push(StyleRange(range, style_info));
@@ -172,7 +173,7 @@ int StyledLabel::CalculateAndDoLayout(int width, bool dry_run) {
if (x == 0 && line > 0)
TrimWhitespace(remaining_string, TRIM_LEADING, &remaining_string);
- ui::Range range(ui::Range::InvalidRange());
+ gfx::Range range(gfx::Range::InvalidRange());
if (!style_ranges.empty())
range = style_ranges.top().range;
@@ -188,11 +189,11 @@ int StyledLabel::CalculateAndDoLayout(int width, bool dry_run) {
text_font =
text_font.DeriveFont(0, style_ranges.top().style_info.font_style);
}
- ui::ElideRectangleText(remaining_string,
+ gfx::ElideRectangleText(remaining_string,
text_font,
chunk_bounds.width(),
chunk_bounds.height(),
- ui::IGNORE_LONG_WORDS,
+ gfx::IGNORE_LONG_WORDS,
&substrings);
DCHECK(!substrings.empty());
@@ -246,6 +247,7 @@ int StyledLabel::CalculateAndDoLayout(int width, bool dry_run) {
if (displayed_on_background_color_set_)
label->SetBackgroundColor(displayed_on_background_color_);
+ label->SetAutoColorReadabilityEnabled(auto_color_readability_enabled_);
// Lay out the views to overlap by 1 pixel to compensate for their border
// spacing. Otherwise, "<a>link</a>," will render as "link ,".
diff --git a/chromium/ui/views/controls/styled_label.h b/chromium/ui/views/controls/styled_label.h
index bc22a18ea1f..adf5993a767 100644
--- a/chromium/ui/views/controls/styled_label.h
+++ b/chromium/ui/views/controls/styled_label.h
@@ -11,7 +11,7 @@
#include "base/basictypes.h"
#include "base/strings/string16.h"
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/size.h"
#include "ui/views/controls/link_listener.h"
#include "ui/views/view.h"
@@ -62,7 +62,7 @@ class VIEWS_EXPORT StyledLabel : public View, public LinkListener {
// Marks the given range within |text_| with style defined by |style_info|.
// |range| must be contained in |text_|.
- void AddStyleRange(const ui::Range& range, const RangeStyleInfo& style_info);
+ void AddStyleRange(const gfx::Range& range, const RangeStyleInfo& style_info);
// Sets the default style to use for any part of the text that isn't within
// a range set by AddStyleRange.
@@ -76,6 +76,10 @@ class VIEWS_EXPORT StyledLabel : public View, public LinkListener {
return displayed_on_background_color_;
}
+ void set_auto_color_readability_enabled(bool auto_color_readability) {
+ auto_color_readability_enabled_ = auto_color_readability;
+ }
+
// View implementation:
virtual gfx::Insets GetInsets() const OVERRIDE;
virtual int GetHeightForWidth(int w) OVERRIDE;
@@ -87,7 +91,7 @@ class VIEWS_EXPORT StyledLabel : public View, public LinkListener {
private:
struct StyleRange {
- StyleRange(const ui::Range& range,
+ StyleRange(const gfx::Range& range,
const RangeStyleInfo& style_info)
: range(range),
style_info(style_info) {
@@ -96,7 +100,7 @@ class VIEWS_EXPORT StyledLabel : public View, public LinkListener {
bool operator<(const StyleRange& other) const;
- ui::Range range;
+ gfx::Range range;
RangeStyleInfo style_info;
};
@@ -121,7 +125,7 @@ class VIEWS_EXPORT StyledLabel : public View, public LinkListener {
// A mapping from a view to the range it corresponds to in |text_|. Only views
// that correspond to ranges with is_link style set will be added to the map.
- std::map<View*, ui::Range> link_targets_;
+ std::map<View*, gfx::Range> link_targets_;
// This variable saves the result of the last GetHeightForWidth call in order
// to avoid repeated calculation.
@@ -131,6 +135,10 @@ class VIEWS_EXPORT StyledLabel : public View, public LinkListener {
SkColor displayed_on_background_color_;
bool displayed_on_background_color_set_;
+ // Controls whether the text is automatically re-colored to be readable on the
+ // background.
+ bool auto_color_readability_enabled_;
+
DISALLOW_COPY_AND_ASSIGN(StyledLabel);
};
diff --git a/chromium/ui/views/controls/styled_label_listener.h b/chromium/ui/views/controls/styled_label_listener.h
index 390865c797f..13c08fd6e97 100644
--- a/chromium/ui/views/controls/styled_label_listener.h
+++ b/chromium/ui/views/controls/styled_label_listener.h
@@ -7,7 +7,7 @@
#include "ui/views/views_export.h"
-namespace ui {
+namespace gfx {
class Range;
}
@@ -16,7 +16,7 @@ namespace views {
// A listener interface for StyledLabel.
class VIEWS_EXPORT StyledLabelListener {
public:
- virtual void StyledLabelLinkClicked(const ui::Range& range,
+ virtual void StyledLabelLinkClicked(const gfx::Range& range,
int event_flags) = 0;
protected:
diff --git a/chromium/ui/views/controls/styled_label_unittest.cc b/chromium/ui/views/controls/styled_label_unittest.cc
index 3e2b15354b6..dac53930f2f 100644
--- a/chromium/ui/views/controls/styled_label_unittest.cc
+++ b/chromium/ui/views/controls/styled_label_unittest.cc
@@ -21,7 +21,7 @@ class StyledLabelTest : public testing::Test, public StyledLabelListener {
virtual ~StyledLabelTest() {}
// StyledLabelListener implementation.
- virtual void StyledLabelLinkClicked(const ui::Range& range,
+ virtual void StyledLabelLinkClicked(const gfx::Range& range,
int event_flags) OVERRIDE {}
protected:
@@ -121,13 +121,13 @@ TEST_F(StyledLabelTest, BasicWrapping) {
TEST_F(StyledLabelTest, CreateLinks) {
const std::string text("This is a test block of text.");
InitStyledLabel(text);
- styled()->AddStyleRange(ui::Range(0, 1),
+ styled()->AddStyleRange(gfx::Range(0, 1),
StyledLabel::RangeStyleInfo::CreateForLink());
- styled()->AddStyleRange(ui::Range(1, 2),
+ styled()->AddStyleRange(gfx::Range(1, 2),
StyledLabel::RangeStyleInfo::CreateForLink());
- styled()->AddStyleRange(ui::Range(10, 11),
+ styled()->AddStyleRange(gfx::Range(10, 11),
StyledLabel::RangeStyleInfo::CreateForLink());
- styled()->AddStyleRange(ui::Range(12, 13),
+ styled()->AddStyleRange(gfx::Range(12, 13),
StyledLabel::RangeStyleInfo::CreateForLink());
styled()->SetBounds(0, 0, 1000, 1000);
@@ -140,7 +140,7 @@ TEST_F(StyledLabelTest, DontBreakLinks) {
const std::string link_text("and this should be a link");
InitStyledLabel(text + link_text);
styled()->AddStyleRange(
- ui::Range(text.size(), text.size() + link_text.size()),
+ gfx::Range(text.size(), text.size() + link_text.size()),
StyledLabel::RangeStyleInfo::CreateForLink());
Label label(ASCIIToUTF16(text + link_text.substr(0, link_text.size() / 2)));
@@ -163,7 +163,7 @@ TEST_F(StyledLabelTest, StyledRangeWithDisabledLineWrapping) {
StyledLabel::RangeStyleInfo style_info;
style_info.disable_line_wrapping = true;
styled()->AddStyleRange(
- ui::Range(text.size(), text.size() + unbreakable_text.size()),
+ gfx::Range(text.size(), text.size() + unbreakable_text.size()),
style_info);
Label label(ASCIIToUTF16(
@@ -187,7 +187,7 @@ TEST_F(StyledLabelTest, StyledRangeUnderlined) {
StyledLabel::RangeStyleInfo style_info;
style_info.font_style = gfx::Font::UNDERLINE;
styled()->AddStyleRange(
- ui::Range(text.size(), text.size() + underlined_text.size()),
+ gfx::Range(text.size(), text.size() + underlined_text.size()),
style_info);
styled()->SetBounds(0, 0, 1000, 1000);
@@ -208,7 +208,7 @@ TEST_F(StyledLabelTest, StyledRangeBold) {
StyledLabel::RangeStyleInfo style_info;
style_info.font_style = gfx::Font::BOLD;
- styled()->AddStyleRange(ui::Range(0, bold_text.size()), style_info);
+ styled()->AddStyleRange(gfx::Range(0, bold_text.size()), style_info);
// Calculate the bold text width if it were a pure label view, both with bold
// and normal style.
@@ -265,11 +265,11 @@ TEST_F(StyledLabelTest, Color) {
StyledLabel::RangeStyleInfo style_info_red;
style_info_red.color = SK_ColorRED;
- styled()->AddStyleRange(ui::Range(0, text_red.size()), style_info_red);
+ styled()->AddStyleRange(gfx::Range(0, text_red.size()), style_info_red);
StyledLabel::RangeStyleInfo style_info_link =
StyledLabel::RangeStyleInfo::CreateForLink();
- styled()->AddStyleRange(ui::Range(text_red.size(),
+ styled()->AddStyleRange(gfx::Range(text_red.size(),
text_red.size() + text_link.size()),
style_info_link);
@@ -323,9 +323,9 @@ TEST_F(StyledLabelTest, StyledRangeWithTooltip) {
StyledLabel::RangeStyleInfo tooltip_style;
tooltip_style.tooltip = ASCIIToUTF16("tooltip");
styled()->AddStyleRange(
- ui::Range(tooltip_start, tooltip_start + tooltip_text.size()),
+ gfx::Range(tooltip_start, tooltip_start + tooltip_text.size()),
tooltip_style);
- styled()->AddStyleRange(ui::Range(link_start, link_start + link_text.size()),
+ styled()->AddStyleRange(gfx::Range(link_start, link_start + link_text.size()),
StyledLabel::RangeStyleInfo::CreateForLink());
// Break line inside the range with the tooltip.
diff --git a/chromium/ui/views/controls/tabbed_pane/tabbed_pane.cc b/chromium/ui/views/controls/tabbed_pane/tabbed_pane.cc
index cb2b595294f..65021d240cb 100644
--- a/chromium/ui/views/controls/tabbed_pane/tabbed_pane.cc
+++ b/chromium/ui/views/controls/tabbed_pane/tabbed_pane.cc
@@ -6,7 +6,7 @@
#include "base/logging.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/views/controls/label.h"
@@ -230,7 +230,7 @@ void TabStrip::OnPaint(gfx::Canvas* canvas) {
SkIntToScalar(selected_tab->height()) - kTabBorderThickness;
SkScalar tab_width =
SkIntToScalar(selected_tab->width()) - kTabBorderThickness;
- SkScalar tab_start = SkIntToScalar(selected_tab->x());
+ SkScalar tab_start = SkIntToScalar(selected_tab->GetMirroredX());
path.moveTo(0, line_y);
path.rLineTo(tab_start, 0);
path.rLineTo(0, -tab_height);
diff --git a/chromium/ui/views/controls/table/table_view.cc b/chromium/ui/views/controls/table/table_view.cc
index 48dd4c48776..c655eb686ad 100644
--- a/chromium/ui/views/controls/table/table_view.cc
+++ b/chromium/ui/views/controls/table/table_view.cc
@@ -8,7 +8,7 @@
#include "base/auto_reset.h"
#include "base/i18n/rtl.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image_skia.h"
#include "ui/gfx/rect_conversions.h"
diff --git a/chromium/ui/views/controls/table/table_view_observer.h b/chromium/ui/views/controls/table/table_view_observer.h
index bd2ff367ab4..44400eee1c7 100644
--- a/chromium/ui/views/controls/table/table_view_observer.h
+++ b/chromium/ui/views/controls/table/table_view_observer.h
@@ -5,7 +5,7 @@
#ifndef UI_VIEWS_CONTROLS_TABLE_TABLE_VIEW_OBSERVER_H_
#define UI_VIEWS_CONTROLS_TABLE_TABLE_VIEW_OBSERVER_H_
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
namespace views {
diff --git a/chromium/ui/views/controls/textfield/native_textfield_views.cc b/chromium/ui/views/controls/textfield/native_textfield_views.cc
index 822bbdf5fb0..3f74efcccd2 100644
--- a/chromium/ui/views/controls/textfield/native_textfield_views.cc
+++ b/chromium/ui/views/controls/textfield/native_textfield_views.cc
@@ -19,13 +19,13 @@
#include "ui/base/clipboard/clipboard.h"
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/base/dragdrop/drag_utils.h"
-#include "ui/base/events/event.h"
#include "ui/base/l10n/l10n_util.h"
-#include "ui/base/range/range.h"
#include "ui/base/ui_base_switches_util.h"
#include "ui/compositor/layer.h"
+#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/insets.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/render_text.h"
#include "ui/gfx/text_constants.h"
#include "ui/native_theme/native_theme.h"
@@ -130,7 +130,7 @@ bool NativeTextfieldViews::OnMouseDragged(const ui::MouseEvent& event) {
if (aggregated_clicks_ == 1) {
model_->SelectWord();
// Expand the selection so the initially selected word remains selected.
- ui::Range selection = GetRenderText()->selection();
+ gfx::Range selection = GetRenderText()->selection();
const size_t min = std::min(selection.GetMin(),
double_click_word_.GetMin());
const size_t max = std::max(selection.GetMax(),
@@ -273,10 +273,10 @@ bool NativeTextfieldViews::CanDrop(const OSExchangeData& data) {
int NativeTextfieldViews::OnDragUpdated(const ui::DropTargetEvent& event) {
DCHECK(CanDrop(event.data()));
- const ui::Range& selection = GetRenderText()->selection();
+ const gfx::Range& selection = GetRenderText()->selection();
drop_cursor_position_ = GetRenderText()->FindCursorPosition(event.location());
bool in_selection = !selection.is_empty() &&
- selection.Contains(ui::Range(drop_cursor_position_.caret_pos()));
+ selection.Contains(gfx::Range(drop_cursor_position_.caret_pos()));
is_drop_cursor_visible_ = !in_selection;
// TODO(msw): Pan over text when the user drags to the visible text edge.
OnCaretBoundsChanged();
@@ -325,7 +325,7 @@ int NativeTextfieldViews::OnPerformDrop(const ui::DropTargetEvent& event) {
if (move) {
// Adjust the drop destination if it is on or after the current selection.
size_t drop = drop_destination_model.caret_pos();
- drop -= GetSelectedRange().Intersect(ui::Range(0, drop)).length();
+ drop -= GetSelectedRange().Intersect(gfx::Range(0, drop)).length();
model_->DeleteSelectionAndInsertTextAt(text, drop);
} else {
model_->MoveCursorTo(drop_destination_model);
@@ -371,7 +371,7 @@ void NativeTextfieldViews::SelectRect(const gfx::Point& start,
gfx::SelectionModel start_caret = GetRenderText()->FindCursorPosition(start);
gfx::SelectionModel end_caret = GetRenderText()->FindCursorPosition(end);
gfx::SelectionModel selection(
- ui::Range(start_caret.caret_pos(), end_caret.caret_pos()),
+ gfx::Range(start_caret.caret_pos(), end_caret.caret_pos()),
end_caret.caret_affinity());
OnBeforeUserAction();
@@ -629,11 +629,11 @@ bool NativeTextfieldViews::IsIMEComposing() const {
return model_->HasCompositionText();
}
-ui::Range NativeTextfieldViews::GetSelectedRange() const {
+gfx::Range NativeTextfieldViews::GetSelectedRange() const {
return GetRenderText()->selection();
}
-void NativeTextfieldViews::SelectRange(const ui::Range& range) {
+void NativeTextfieldViews::SelectRange(const gfx::Range& range) {
model_->SelectRange(range);
OnCaretBoundsChanged();
SchedulePaint();
@@ -719,7 +719,7 @@ int NativeTextfieldViews::GetFontHeight() {
}
int NativeTextfieldViews::GetTextfieldBaseline() const {
- return GetRenderText()->font_list().GetBaseline();
+ return GetRenderText()->GetBaseline();
}
int NativeTextfieldViews::GetWidthNeededForText() const {
@@ -734,6 +734,10 @@ bool NativeTextfieldViews::HasTextBeingDragged() {
return initiating_drag_;
}
+gfx::Point NativeTextfieldViews::GetContextMenuLocation() {
+ return GetCaretBounds().bottom_right();
+}
+
/////////////////////////////////////////////////////////////////
// NativeTextfieldViews, ui::SimpleMenuModel::Delegate overrides:
@@ -745,6 +749,8 @@ bool NativeTextfieldViews::IsCommandIdEnabled(int command_id) const {
bool editable = !textfield_->read_only();
string16 result;
switch (command_id) {
+ case IDS_APP_UNDO:
+ return editable && model_->CanUndo();
case IDS_APP_CUT:
return editable && model_->HasSelection() && !textfield_->IsObscured();
case IDS_APP_COPY:
@@ -788,6 +794,12 @@ void NativeTextfieldViews::ExecuteCommand(int command_id, int event_flags) {
} else {
bool text_changed = false;
switch (command_id) {
+ case IDS_APP_UNDO:
+ OnBeforeUserAction();
+ text_changed = model_->Undo();
+ UpdateAfterChange(text_changed, text_changed);
+ OnAfterUserAction();
+ break;
case IDS_APP_CUT:
OnBeforeUserAction();
text_changed = Cut();
@@ -829,7 +841,7 @@ void NativeTextfieldViews::SetColor(SkColor value) {
SchedulePaint();
}
-void NativeTextfieldViews::ApplyColor(SkColor value, const ui::Range& range) {
+void NativeTextfieldViews::ApplyColor(SkColor value, const gfx::Range& range) {
GetRenderText()->ApplyColor(value, range);
SchedulePaint();
}
@@ -841,7 +853,7 @@ void NativeTextfieldViews::SetStyle(gfx::TextStyle style, bool value) {
void NativeTextfieldViews::ApplyStyle(gfx::TextStyle style,
bool value,
- const ui::Range& range) {
+ const gfx::Range& range) {
GetRenderText()->ApplyStyle(style, value, range);
SchedulePaint();
}
@@ -983,7 +995,7 @@ bool NativeTextfieldViews::GetCompositionCharacterBounds(uint32 index,
DCHECK(rect);
if (!HasCompositionText())
return false;
- const ui::Range& composition_range = GetRenderText()->GetCompositionRange();
+ const gfx::Range& composition_range = GetRenderText()->GetCompositionRange();
const uint32 left_cursor_pos = composition_range.start() + index;
const uint32 right_cursor_pos = composition_range.start() + index + 1;
DCHECK(!composition_range.is_empty());
@@ -1012,7 +1024,7 @@ bool NativeTextfieldViews::HasCompositionText() {
return model_->HasCompositionText();
}
-bool NativeTextfieldViews::GetTextRange(ui::Range* range) {
+bool NativeTextfieldViews::GetTextRange(gfx::Range* range) {
if (!ImeEditingAllowed())
return false;
@@ -1020,7 +1032,7 @@ bool NativeTextfieldViews::GetTextRange(ui::Range* range) {
return true;
}
-bool NativeTextfieldViews::GetCompositionTextRange(ui::Range* range) {
+bool NativeTextfieldViews::GetCompositionTextRange(gfx::Range* range) {
if (!ImeEditingAllowed())
return false;
@@ -1028,14 +1040,14 @@ bool NativeTextfieldViews::GetCompositionTextRange(ui::Range* range) {
return true;
}
-bool NativeTextfieldViews::GetSelectionRange(ui::Range* range) {
+bool NativeTextfieldViews::GetSelectionRange(gfx::Range* range) {
if (!ImeEditingAllowed())
return false;
*range = GetSelectedRange();
return true;
}
-bool NativeTextfieldViews::SetSelectionRange(const ui::Range& range) {
+bool NativeTextfieldViews::SetSelectionRange(const gfx::Range& range) {
if (!ImeEditingAllowed() || !range.IsValid())
return false;
@@ -1045,7 +1057,7 @@ bool NativeTextfieldViews::SetSelectionRange(const ui::Range& range) {
return true;
}
-bool NativeTextfieldViews::DeleteRange(const ui::Range& range) {
+bool NativeTextfieldViews::DeleteRange(const gfx::Range& range) {
if (!ImeEditingAllowed() || range.is_empty())
return false;
@@ -1060,12 +1072,12 @@ bool NativeTextfieldViews::DeleteRange(const ui::Range& range) {
}
bool NativeTextfieldViews::GetTextFromRange(
- const ui::Range& range,
+ const gfx::Range& range,
string16* text) {
if (!ImeEditingAllowed() || !range.IsValid())
return false;
- ui::Range text_range;
+ gfx::Range text_range;
if (!GetTextRange(&text_range) || !text_range.Contains(range))
return false;
@@ -1086,12 +1098,12 @@ bool NativeTextfieldViews::ChangeTextDirectionAndLayoutAlignment(
void NativeTextfieldViews::ExtendSelectionAndDelete(
size_t before,
size_t after) {
- ui::Range range = GetSelectedRange();
+ gfx::Range range = GetSelectedRange();
DCHECK_GE(range.start(), before);
range.set_start(range.start() - before);
range.set_end(range.end() + after);
- ui::Range text_range;
+ gfx::Range text_range;
if (GetTextRange(&text_range) && text_range.Contains(range))
DeleteRange(range);
}
@@ -1178,7 +1190,7 @@ bool NativeTextfieldViews::HandleKeyEvent(const ui::KeyEvent& key_event) {
const bool readable = !textfield_->IsObscured();
const bool shift = key_event.IsShiftDown();
const bool control = key_event.IsControlDown();
- const bool alt = key_event.IsAltDown();
+ const bool alt = key_event.IsAltDown() || key_event.IsAltGrDown();
bool text_changed = false;
bool cursor_changed = false;
switch (key_code) {
@@ -1217,7 +1229,7 @@ bool NativeTextfieldViews::HandleKeyEvent(const ui::KeyEvent& key_event) {
// forward/back of the browser history.
if (alt)
break;
- const ui::Range selection_range = GetSelectedRange();
+ const gfx::Range selection_range = GetSelectedRange();
model_->MoveCursor(
control ? gfx::WORD_BREAK : gfx::CHARACTER_BREAK,
(key_code == ui::VKEY_RIGHT) ? gfx::CURSOR_RIGHT : gfx::CURSOR_LEFT,
@@ -1322,6 +1334,8 @@ void NativeTextfieldViews::UpdateAfterChange(bool text_changed,
void NativeTextfieldViews::UpdateContextMenu() {
if (!context_menu_contents_.get()) {
context_menu_contents_.reset(new ui::SimpleMenuModel(this));
+ context_menu_contents_->AddItemWithStringId(IDS_APP_UNDO, IDS_APP_UNDO);
+ context_menu_contents_->AddSeparator(ui::NORMAL_SEPARATOR);
context_menu_contents_->AddItemWithStringId(IDS_APP_CUT, IDS_APP_CUT);
context_menu_contents_->AddItemWithStringId(IDS_APP_COPY, IDS_APP_COPY);
context_menu_contents_->AddItemWithStringId(IDS_APP_PASTE, IDS_APP_PASTE);
diff --git a/chromium/ui/views/controls/textfield/native_textfield_views.h b/chromium/ui/views/controls/textfield/native_textfield_views.h
index 3230fb4d6c8..6b1c2de3724 100644
--- a/chromium/ui/views/controls/textfield/native_textfield_views.h
+++ b/chromium/ui/views/controls/textfield/native_textfield_views.h
@@ -8,10 +8,10 @@
#include "base/memory/weak_ptr.h"
#include "base/strings/string16.h"
#include "base/timer/timer.h"
-#include "ui/base/events/event_constants.h"
#include "ui/base/ime/text_input_client.h"
#include "ui/base/models/simple_menu_model.h"
#include "ui/base/touch/touch_editing_controller.h"
+#include "ui/events/event_constants.h"
#include "ui/gfx/font.h"
#include "ui/views/border.h"
#include "ui/views/context_menu_controller.h"
@@ -130,8 +130,8 @@ class VIEWS_EXPORT NativeTextfieldViews : public View,
virtual View* GetView() OVERRIDE;
virtual gfx::NativeView GetTestingHandle() const OVERRIDE;
virtual bool IsIMEComposing() const OVERRIDE;
- virtual ui::Range GetSelectedRange() const OVERRIDE;
- virtual void SelectRange(const ui::Range& range) OVERRIDE;
+ virtual gfx::Range GetSelectedRange() const OVERRIDE;
+ virtual void SelectRange(const gfx::Range& range) OVERRIDE;
virtual gfx::SelectionModel GetSelectionModel() const OVERRIDE;
virtual void SelectSelectionModel(const gfx::SelectionModel& sel) OVERRIDE;
virtual size_t GetCursorPosition() const OVERRIDE;
@@ -143,17 +143,18 @@ class VIEWS_EXPORT NativeTextfieldViews : public View,
virtual void HandleBlur() OVERRIDE;
virtual ui::TextInputClient* GetTextInputClient() OVERRIDE;
virtual void SetColor(SkColor value) OVERRIDE;
- virtual void ApplyColor(SkColor value, const ui::Range& range) OVERRIDE;
+ virtual void ApplyColor(SkColor value, const gfx::Range& range) OVERRIDE;
virtual void SetStyle(gfx::TextStyle style, bool value) OVERRIDE;
virtual void ApplyStyle(gfx::TextStyle style,
bool value,
- const ui::Range& range) OVERRIDE;
+ const gfx::Range& range) OVERRIDE;
virtual void ClearEditHistory() OVERRIDE;
virtual int GetFontHeight() OVERRIDE;
virtual int GetTextfieldBaseline() const OVERRIDE;
virtual int GetWidthNeededForText() const OVERRIDE;
virtual void ExecuteTextCommand(int command_id) OVERRIDE;
virtual bool HasTextBeingDragged() OVERRIDE;
+ virtual gfx::Point GetContextMenuLocation() OVERRIDE;
// ui::SimpleMenuModel::Delegate overrides
virtual bool IsCommandIdChecked(int command_id) const OVERRIDE;
@@ -191,12 +192,12 @@ class VIEWS_EXPORT NativeTextfieldViews : public View,
virtual bool GetCompositionCharacterBounds(uint32 index,
gfx::Rect* rect) OVERRIDE;
virtual bool HasCompositionText() OVERRIDE;
- virtual bool GetTextRange(ui::Range* range) OVERRIDE;
- virtual bool GetCompositionTextRange(ui::Range* range) OVERRIDE;
- virtual bool GetSelectionRange(ui::Range* range) OVERRIDE;
- virtual bool SetSelectionRange(const ui::Range& range) OVERRIDE;
- virtual bool DeleteRange(const ui::Range& range) OVERRIDE;
- virtual bool GetTextFromRange(const ui::Range& range,
+ virtual bool GetTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetCompositionTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetSelectionRange(gfx::Range* range) OVERRIDE;
+ virtual bool SetSelectionRange(const gfx::Range& range) OVERRIDE;
+ virtual bool DeleteRange(const gfx::Range& range) OVERRIDE;
+ virtual bool GetTextFromRange(const gfx::Range& range,
string16* text) OVERRIDE;
virtual void OnInputMethodChanged() OVERRIDE;
virtual bool ChangeTextDirectionAndLayoutAlignment(
@@ -325,7 +326,7 @@ class VIEWS_EXPORT NativeTextfieldViews : public View,
size_t aggregated_clicks_;
base::TimeDelta last_click_time_;
gfx::Point last_click_location_;
- ui::Range double_click_word_;
+ gfx::Range double_click_word_;
// Context menu and its content list for the textfield.
scoped_ptr<ui::SimpleMenuModel> context_menu_contents_;
diff --git a/chromium/ui/views/controls/textfield/native_textfield_views_unittest.cc b/chromium/ui/views/controls/textfield/native_textfield_views_unittest.cc
index c2e32c998a4..54873d95b64 100644
--- a/chromium/ui/views/controls/textfield/native_textfield_views_unittest.cc
+++ b/chromium/ui/views/controls/textfield/native_textfield_views_unittest.cc
@@ -2,6 +2,8 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include "ui/views/controls/textfield/native_textfield_views.h"
+
#include <set>
#include <string>
#include <vector>
@@ -20,13 +22,12 @@
#include "ui/base/clipboard/clipboard.h"
#include "ui/base/clipboard/scoped_clipboard_writer.h"
#include "ui/base/dragdrop/drag_drop_types.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/text_input_client.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/ui_base_switches.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/render_text.h"
-#include "ui/views/controls/textfield/native_textfield_views.h"
#include "ui/views/controls/textfield/textfield.h"
#include "ui/views/controls/textfield/textfield_controller.h"
#include "ui/views/controls/textfield/textfield_views_model.h"
@@ -38,6 +39,10 @@
#include "ui/views/widget/widget.h"
#include "url/gurl.h"
+#if defined(OS_WIN)
+#include "base/win/windows_version.h"
+#endif
+
#define EXPECT_STR_EQ(ascii, utf16) EXPECT_EQ(ASCIIToUTF16(ascii), utf16)
namespace {
@@ -179,6 +184,7 @@ class NativeTextfieldViewsTest : public ViewsTestBase,
textfield_view_ = static_cast<NativeTextfieldViews*>(
textfield_->GetNativeWrapperForTesting());
+ DCHECK(textfield_view_);
textfield_view_->SetBoundsRect(params.bounds);
textfield_->set_id(1);
@@ -188,7 +194,6 @@ class NativeTextfieldViewsTest : public ViewsTestBase,
textfield->set_id(i + 1);
}
- DCHECK(textfield_view_);
model_ = textfield_view_->model_.get();
model_->ClearEditHistory();
@@ -314,14 +319,16 @@ class NativeTextfieldViewsTest : public ViewsTestBase,
}
void VerifyTextfieldContextMenuContents(bool textfield_has_selection,
- ui::MenuModel* menu_model) {
- EXPECT_TRUE(menu_model->IsEnabledAt(4 /* Separator */));
- EXPECT_TRUE(menu_model->IsEnabledAt(5 /* SELECT ALL */));
- EXPECT_EQ(textfield_has_selection, menu_model->IsEnabledAt(0 /* CUT */));
- EXPECT_EQ(textfield_has_selection, menu_model->IsEnabledAt(1 /* COPY */));
- EXPECT_EQ(textfield_has_selection, menu_model->IsEnabledAt(3 /* DELETE */));
- string16 str(GetClipboardText());
- EXPECT_NE(str.empty(), menu_model->IsEnabledAt(2 /* PASTE */));
+ bool can_undo,
+ ui::MenuModel* menu) {
+ EXPECT_EQ(can_undo, menu->IsEnabledAt(0 /* UNDO */));
+ EXPECT_TRUE(menu->IsEnabledAt(1 /* Separator */));
+ EXPECT_EQ(textfield_has_selection, menu->IsEnabledAt(2 /* CUT */));
+ EXPECT_EQ(textfield_has_selection, menu->IsEnabledAt(3 /* COPY */));
+ EXPECT_NE(GetClipboardText().empty(), menu->IsEnabledAt(4 /* PASTE */));
+ EXPECT_EQ(textfield_has_selection, menu->IsEnabledAt(5 /* DELETE */));
+ EXPECT_TRUE(menu->IsEnabledAt(6 /* Separator */));
+ EXPECT_TRUE(menu->IsEnabledAt(7 /* SELECT ALL */));
}
// We need widget to populate wrapper class.
@@ -505,7 +512,7 @@ TEST_F(NativeTextfieldViewsTest, InsertionDeletionTest) {
EXPECT_STR_EQ("abcdefghij", textfield_->text());
// Test the delete and backspace keys.
- textfield_->SelectRange(ui::Range(5));
+ textfield_->SelectRange(gfx::Range(5));
for (int i = 0; i < 3; i++)
SendKeyEvent(ui::VKEY_BACK);
EXPECT_STR_EQ("abfghij", textfield_->text());
@@ -786,11 +793,23 @@ TEST_F(NativeTextfieldViewsTest, ContextMenuDisplayTest) {
InitTextfield(Textfield::STYLE_DEFAULT);
EXPECT_TRUE(textfield_->context_menu_controller());
textfield_->SetText(ASCIIToUTF16("hello world"));
+ ui::Clipboard::GetForCurrentThread()->Clear(ui::Clipboard::BUFFER_STANDARD);
+ textfield_view_->ClearEditHistory();
EXPECT_TRUE(GetContextMenuModel());
- VerifyTextfieldContextMenuContents(false, GetContextMenuModel());
+ VerifyTextfieldContextMenuContents(false, false, GetContextMenuModel());
+
+ textfield_->SelectAll(false);
+ VerifyTextfieldContextMenuContents(true, false, GetContextMenuModel());
+
+ SendKeyEvent(ui::VKEY_T);
+ VerifyTextfieldContextMenuContents(false, true, GetContextMenuModel());
textfield_->SelectAll(false);
- VerifyTextfieldContextMenuContents(true, GetContextMenuModel());
+ VerifyTextfieldContextMenuContents(true, true, GetContextMenuModel());
+
+ // Exercise the "paste enabled?" check in the verifier.
+ SetClipboardText("Test");
+ VerifyTextfieldContextMenuContents(true, true, GetContextMenuModel());
}
TEST_F(NativeTextfieldViewsTest, DoubleAndTripleClickTest) {
@@ -922,7 +941,7 @@ TEST_F(NativeTextfieldViewsTest, DragAndDrop_InitiateDrag) {
// Ensure the textfield will provide selected text for drag data.
string16 string;
ui::OSExchangeData data;
- const ui::Range kStringRange(6, 12);
+ const gfx::Range kStringRange(6, 12);
textfield_->SelectRange(kStringRange);
const gfx::Point kStringPoint(GetCursorPositionX(9), 0);
textfield_view_->WriteDragDataForView(NULL, kStringPoint, &data);
@@ -972,7 +991,7 @@ TEST_F(NativeTextfieldViewsTest, DragAndDrop_ToTheRight) {
std::set<OSExchangeData::CustomFormat> custom_formats;
// Start dragging "ello".
- textfield_->SelectRange(ui::Range(1, 5));
+ textfield_->SelectRange(gfx::Range(1, 5));
gfx::Point point(GetCursorPositionX(3), 0);
ui::MouseEvent click_a(ui::ET_MOUSE_PRESSED, point, point,
ui::EF_LEFT_MOUSE_BUTTON);
@@ -1027,7 +1046,7 @@ TEST_F(NativeTextfieldViewsTest, DragAndDrop_ToTheLeft) {
std::set<OSExchangeData::CustomFormat> custom_formats;
// Start dragging " worl".
- textfield_->SelectRange(ui::Range(5, 10));
+ textfield_->SelectRange(gfx::Range(5, 10));
gfx::Point point(GetCursorPositionX(7), 0);
ui::MouseEvent click_a(ui::ET_MOUSE_PRESSED, point, point,
ui::EF_LEFT_MOUSE_BUTTON);
@@ -1076,7 +1095,7 @@ TEST_F(NativeTextfieldViewsTest, DragAndDrop_Canceled) {
textfield_->SetText(ASCIIToUTF16("hello world"));
// Start dragging "worl".
- textfield_->SelectRange(ui::Range(6, 10));
+ textfield_->SelectRange(gfx::Range(6, 10));
gfx::Point point(GetCursorPositionX(8), 0);
ui::MouseEvent click(ui::ET_MOUSE_PRESSED, point, point,
ui::EF_LEFT_MOUSE_BUTTON);
@@ -1174,14 +1193,14 @@ TEST_F(NativeTextfieldViewsTest, TextInputClientTest) {
EXPECT_EQ(ui::TEXT_INPUT_TYPE_TEXT, client->GetTextInputType());
textfield_->SetText(ASCIIToUTF16("0123456789"));
- ui::Range range;
+ gfx::Range range;
EXPECT_TRUE(client->GetTextRange(&range));
EXPECT_EQ(0U, range.start());
EXPECT_EQ(10U, range.end());
- EXPECT_TRUE(client->SetSelectionRange(ui::Range(1, 4)));
+ EXPECT_TRUE(client->SetSelectionRange(gfx::Range(1, 4)));
EXPECT_TRUE(client->GetSelectionRange(&range));
- EXPECT_EQ(ui::Range(1, 4), range);
+ EXPECT_EQ(gfx::Range(1, 4), range);
// This code can't be compiled because of a bug in base::Callback.
#if 0
@@ -1210,7 +1229,7 @@ TEST_F(NativeTextfieldViewsTest, TextInputClientTest) {
EXPECT_TRUE(client->HasCompositionText());
EXPECT_TRUE(client->GetCompositionTextRange(&range));
EXPECT_STR_EQ("0321456789", textfield_->text());
- EXPECT_EQ(ui::Range(1, 4), range);
+ EXPECT_EQ(gfx::Range(1, 4), range);
EXPECT_EQ(2, on_before_user_action_);
EXPECT_EQ(2, on_after_user_action_);
@@ -1247,7 +1266,7 @@ TEST_F(NativeTextfieldViewsTest, TextInputClientTest) {
textfield_->clear();
textfield_->SetText(ASCIIToUTF16("0123456789"));
- EXPECT_TRUE(client->SetSelectionRange(ui::Range(5, 5)));
+ EXPECT_TRUE(client->SetSelectionRange(gfx::Range(5, 5)));
client->ExtendSelectionAndDelete(4, 2);
EXPECT_STR_EQ("0789", textfield_->text());
@@ -1755,7 +1774,7 @@ TEST_F(NativeTextfieldViewsTest, GetCompositionCharacterBoundsTest) {
gfx::Rect char_rect_in_screen_coord[char_count];
gfx::Rect prev_cursor = GetCursorBounds();
for (uint32 i = 0; i < char_count; ++i) {
- composition.selection = ui::Range(0, i+1);
+ composition.selection = gfx::Range(0, i+1);
client->SetCompositionText(composition);
EXPECT_TRUE(client->HasCompositionText()) << " i=" << i;
gfx::Rect cursor_bounds = GetCursorBounds();
@@ -1789,9 +1808,9 @@ TEST_F(NativeTextfieldViewsTest, KeepInitiallySelectedWord) {
textfield_->SetText(ASCIIToUTF16("abc def ghi"));
- textfield_->SelectRange(ui::Range(5, 5));
+ textfield_->SelectRange(gfx::Range(5, 5));
const gfx::Rect middle_cursor = GetCursorBounds();
- textfield_->SelectRange(ui::Range(0, 0));
+ textfield_->SelectRange(gfx::Range(0, 0));
const gfx::Point beginning = GetCursorBounds().origin();
// Double click, but do not release the left button.
@@ -1801,13 +1820,13 @@ TEST_F(NativeTextfieldViewsTest, KeepInitiallySelectedWord) {
ui::MouseEvent press_event(ui::ET_MOUSE_PRESSED, middle, middle,
ui::EF_LEFT_MOUSE_BUTTON);
textfield_view_->OnMousePressed(press_event);
- EXPECT_EQ(ui::Range(4, 7), textfield_->GetSelectedRange());
+ EXPECT_EQ(gfx::Range(4, 7), textfield_->GetSelectedRange());
// Drag the mouse to the beginning of the textfield.
ui::MouseEvent drag_event(ui::ET_MOUSE_DRAGGED, beginning, beginning,
ui::EF_LEFT_MOUSE_BUTTON);
textfield_view_->OnMouseDragged(drag_event);
- EXPECT_EQ(ui::Range(7, 0), textfield_->GetSelectedRange());
+ EXPECT_EQ(gfx::Range(7, 0), textfield_->GetSelectedRange());
}
// Touch selection and draggin currently only works for chromeos.
@@ -1868,7 +1887,7 @@ TEST_F(NativeTextfieldViewsTest, TestLongPressInitiatesDragDrop) {
textfield_->SetText(ASCIIToUTF16("Hello string world"));
// Ensure the textfield will provide selected text for drag data.
- textfield_->SelectRange(ui::Range(6, 12));
+ textfield_->SelectRange(gfx::Range(6, 12));
const gfx::Point kStringPoint(GetCursorPositionX(9), 0);
// Enable touch-drag-drop to make long press effective.
@@ -1882,4 +1901,26 @@ TEST_F(NativeTextfieldViewsTest, TestLongPressInitiatesDragDrop) {
EXPECT_TRUE(textfield_view_->CanStartDragForView(NULL,
kStringPoint, kStringPoint));
}
+
+TEST_F(NativeTextfieldViewsTest, GetTextfieldBaseline_FontFallbackTest) {
+#if defined(OS_WIN)
+ // This test fails on some versions of Windows because two different strings
+ // have the same baseline.
+ if (base::win::GetVersion() <= base::win::VERSION_XP ||
+ base::win::VERSION_WIN8 <= base::win::GetVersion())
+ return;
+#endif
+
+ InitTextfield(Textfield::STYLE_DEFAULT);
+ textfield_->SetText(UTF8ToUTF16("abc"));
+ const int old_baseline = textfield_->GetBaseline();
+
+ // Set text which may fall back to a font which has taller baseline than
+ // the default font. |new_baseline| will be greater than |old_baseline|.
+ textfield_->SetText(UTF8ToUTF16("\xE0\xB9\x91"));
+ const int new_baseline = textfield_->GetBaseline();
+
+ EXPECT_GT(new_baseline, old_baseline);
+}
+
} // namespace views
diff --git a/chromium/ui/views/controls/textfield/native_textfield_win.cc b/chromium/ui/views/controls/textfield/native_textfield_win.cc
index defe632cf80..f98c0ad75d2 100644
--- a/chromium/ui/views/controls/textfield/native_textfield_win.cc
+++ b/chromium/ui/views/controls/textfield/native_textfield_win.cc
@@ -17,14 +17,14 @@
#include "ui/base/accessibility/accessible_view_state.h"
#include "ui/base/clipboard/clipboard.h"
#include "ui/base/clipboard/scoped_clipboard_writer.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/win/tsf_bridge.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/l10n/l10n_util_win.h"
-#include "ui/base/range/range.h"
-#include "ui/base/win/hwnd_util.h"
#include "ui/base/win/mouse_wheel_util.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
+#include "ui/gfx/range/range.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/native_theme/native_theme_win.h"
#include "ui/views/controls/label.h"
#include "ui/views/controls/menu/menu_item_view.h"
@@ -340,13 +340,13 @@ bool NativeTextfieldWin::IsIMEComposing() const {
return composition_size > 0;
}
-ui::Range NativeTextfieldWin::GetSelectedRange() const {
+gfx::Range NativeTextfieldWin::GetSelectedRange() const {
// TODO(tommi): Implement.
NOTIMPLEMENTED();
- return ui::Range();
+ return gfx::Range();
}
-void NativeTextfieldWin::SelectRange(const ui::Range& range) {
+void NativeTextfieldWin::SelectRange(const gfx::Range& range) {
// TODO(tommi): Implement.
NOTIMPLEMENTED();
}
@@ -401,7 +401,7 @@ void NativeTextfieldWin::SetColor(SkColor value) {
NOTREACHED();
}
-void NativeTextfieldWin::ApplyColor(SkColor value, const ui::Range& range) {
+void NativeTextfieldWin::ApplyColor(SkColor value, const gfx::Range& range) {
NOTREACHED();
}
@@ -411,7 +411,7 @@ void NativeTextfieldWin::SetStyle(gfx::TextStyle style, bool value) {
void NativeTextfieldWin::ApplyStyle(gfx::TextStyle style,
bool value,
- const ui::Range& range) {
+ const gfx::Range& range) {
NOTREACHED();
}
@@ -441,6 +441,11 @@ bool NativeTextfieldWin::HasTextBeingDragged() {
return false;
}
+gfx::Point NativeTextfieldWin::GetContextMenuLocation() {
+ NOTIMPLEMENTED();
+ return gfx::Point();
+}
+
////////////////////////////////////////////////////////////////////////////////
// NativeTextfieldWin, ui::SimpleMenuModel::Delegate implementation:
@@ -493,7 +498,7 @@ void NativeTextfieldWin::ExecuteCommand(int command_id, int event_flags) {
OnAfterPossibleChange(true);
}
-void NativeTextfieldWin::OnTextUpdated(const ui::Range& composition_range) {
+void NativeTextfieldWin::OnTextUpdated(const gfx::Range& composition_range) {
if (ime_discard_composition_) {
ime_composition_start_ = composition_range.start();
ime_composition_length_ = composition_range.length();
@@ -1103,7 +1108,7 @@ void NativeTextfieldWin::OnSysChar(TCHAR ch, UINT repeat_count, UINT flags) {
// something useful, so discard those. Note that [Ctrl]+[Alt]+<xxx> generates
// WM_CHAR instead of WM_SYSCHAR, so it is not handled here.
if (ch == VK_SPACE) {
- ui::ShowSystemMenu(
+ gfx::ShowSystemMenu(
container_view_->GetWidget()->GetTopLevelWidget()->GetNativeWindow());
}
}
diff --git a/chromium/ui/views/controls/textfield/native_textfield_win.h b/chromium/ui/views/controls/textfield/native_textfield_win.h
index 6e119b11a60..6939a093f32 100644
--- a/chromium/ui/views/controls/textfield/native_textfield_win.h
+++ b/chromium/ui/views/controls/textfield/native_textfield_win.h
@@ -21,6 +21,7 @@
#include "ui/base/models/simple_menu_model.h"
#include "ui/base/win/extra_sdk_defines.h"
#include "ui/gfx/insets.h"
+#include "ui/gfx/point.h"
#include "ui/views/controls/textfield/native_textfield_wrapper.h"
namespace views {
@@ -79,8 +80,8 @@ class NativeTextfieldWin
virtual View* GetView() OVERRIDE;
virtual gfx::NativeView GetTestingHandle() const OVERRIDE;
virtual bool IsIMEComposing() const OVERRIDE;
- virtual ui::Range GetSelectedRange() const OVERRIDE;
- virtual void SelectRange(const ui::Range& range) OVERRIDE;
+ virtual gfx::Range GetSelectedRange() const OVERRIDE;
+ virtual void SelectRange(const gfx::Range& range) OVERRIDE;
virtual gfx::SelectionModel GetSelectionModel() const OVERRIDE;
virtual void SelectSelectionModel(const gfx::SelectionModel& sel) OVERRIDE;
virtual size_t GetCursorPosition() const OVERRIDE;
@@ -92,17 +93,18 @@ class NativeTextfieldWin
virtual void HandleBlur() OVERRIDE;
virtual ui::TextInputClient* GetTextInputClient() OVERRIDE;
virtual void SetColor(SkColor value) OVERRIDE;
- virtual void ApplyColor(SkColor value, const ui::Range& range) OVERRIDE;
+ virtual void ApplyColor(SkColor value, const gfx::Range& range) OVERRIDE;
virtual void SetStyle(gfx::TextStyle style, bool value) OVERRIDE;
virtual void ApplyStyle(gfx::TextStyle style,
bool value,
- const ui::Range& range) OVERRIDE;
+ const gfx::Range& range) OVERRIDE;
virtual void ClearEditHistory() OVERRIDE;
virtual int GetFontHeight() OVERRIDE;
virtual int GetTextfieldBaseline() const OVERRIDE;
virtual int GetWidthNeededForText() const OVERRIDE;
virtual void ExecuteTextCommand(int command_id) OVERRIDE;
virtual bool HasTextBeingDragged() OVERRIDE;
+ virtual gfx::Point GetContextMenuLocation() OVERRIDE;
// ui::SimpleMenuModel::Delegate:
virtual bool IsCommandIdChecked(int command_id) const OVERRIDE;
@@ -113,7 +115,7 @@ class NativeTextfieldWin
virtual void ExecuteCommand(int command_id, int event_flags) OVERRIDE;
// ui::TSFEventRouterObserver:
- virtual void OnTextUpdated(const ui::Range& composition_range) OVERRIDE;
+ virtual void OnTextUpdated(const gfx::Range& composition_range) OVERRIDE;
virtual void OnTSFStartComposition() OVERRIDE;
virtual void OnTSFEndComposition() OVERRIDE;
diff --git a/chromium/ui/views/controls/textfield/native_textfield_wrapper.h b/chromium/ui/views/controls/textfield/native_textfield_wrapper.h
index 82e75b381b9..3d8938e3286 100644
--- a/chromium/ui/views/controls/textfield/native_textfield_wrapper.h
+++ b/chromium/ui/views/controls/textfield/native_textfield_wrapper.h
@@ -7,14 +7,15 @@
#include "base/i18n/rtl.h"
#include "base/strings/string16.h"
-#include "ui/base/range/range.h"
#include "ui/gfx/native_widget_types.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/selection_model.h"
#include "ui/gfx/text_constants.h"
#include "ui/views/views_export.h"
namespace gfx {
class Insets;
+class Point;
} // namespace gfx
namespace ui {
@@ -109,10 +110,10 @@ class VIEWS_EXPORT NativeTextfieldWrapper {
virtual bool IsIMEComposing() const = 0;
// Gets the selected range.
- virtual ui::Range GetSelectedRange() const = 0;
+ virtual gfx::Range GetSelectedRange() const = 0;
// Selects the text given by |range|.
- virtual void SelectRange(const ui::Range& range) = 0;
+ virtual void SelectRange(const gfx::Range& range) = 0;
// Gets the selection model.
virtual gfx::SelectionModel GetSelectionModel() const = 0;
@@ -149,13 +150,13 @@ class VIEWS_EXPORT NativeTextfieldWrapper {
// Set the text colors; see the corresponding Textfield functions for details.
virtual void SetColor(SkColor value) = 0;
- virtual void ApplyColor(SkColor value, const ui::Range& range) = 0;
+ virtual void ApplyColor(SkColor value, const gfx::Range& range) = 0;
// Set the text styles; see the corresponding Textfield functions for details.
virtual void SetStyle(gfx::TextStyle style, bool value) = 0;
virtual void ApplyStyle(gfx::TextStyle style,
bool value,
- const ui::Range& range) = 0;
+ const gfx::Range& range) = 0;
// Clears Edit history.
virtual void ClearEditHistory() = 0;
@@ -178,6 +179,9 @@ class VIEWS_EXPORT NativeTextfieldWrapper {
// Returns whether there is a drag operation originating from the textfield.
virtual bool HasTextBeingDragged() = 0;
+ // Returns the location for keyboard-triggered context menus.
+ virtual gfx::Point GetContextMenuLocation() = 0;
+
// Creates an appropriate NativeTextfieldWrapper for the platform.
static NativeTextfieldWrapper* CreateWrapper(Textfield* field);
};
diff --git a/chromium/ui/views/controls/textfield/textfield.cc b/chromium/ui/views/controls/textfield/textfield.cc
index b76c20c8ac8..b26aa37120a 100644
--- a/chromium/ui/views/controls/textfield/textfield.cc
+++ b/chromium/ui/views/controls/textfield/textfield.cc
@@ -10,14 +10,13 @@
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/text_input_type.h"
-#include "ui/base/keycodes/keyboard_codes.h"
-#include "ui/base/range/range.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/base/ui_base_switches.h"
-#include "ui/base/ui_base_switches_util.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/insets.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/selection_model.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/controls/native/native_view_host.h"
@@ -62,9 +61,6 @@ bool Textfield::IsViewsTextfieldEnabled() {
return false;
if (command_line->HasSwitch(switches::kEnableViewsTextfield))
return true;
- // The new dialog style cannot host native Windows textfield controls.
- if (switches::IsNewDialogStyleEnabled())
- return true;
// Avoid native Windows Textfields if the RichEdit library is not available.
static const HMODULE loaded_msftedit_dll = LoadLibrary(L"msftedit.dll");
if (!loaded_msftedit_dll)
@@ -367,11 +363,11 @@ bool Textfield::IsIMEComposing() const {
return native_wrapper_ && native_wrapper_->IsIMEComposing();
}
-ui::Range Textfield::GetSelectedRange() const {
+gfx::Range Textfield::GetSelectedRange() const {
return native_wrapper_->GetSelectedRange();
}
-void Textfield::SelectRange(const ui::Range& range) {
+void Textfield::SelectRange(const gfx::Range& range) {
native_wrapper_->SelectRange(range);
}
@@ -391,7 +387,7 @@ void Textfield::SetColor(SkColor value) {
return native_wrapper_->SetColor(value);
}
-void Textfield::ApplyColor(SkColor value, const ui::Range& range) {
+void Textfield::ApplyColor(SkColor value, const gfx::Range& range) {
return native_wrapper_->ApplyColor(value, range);
}
@@ -401,7 +397,7 @@ void Textfield::SetStyle(gfx::TextStyle style, bool value) {
void Textfield::ApplyStyle(gfx::TextStyle style,
bool value,
- const ui::Range& range) {
+ const gfx::Range& range) {
return native_wrapper_->ApplyStyle(style, value, range);
}
@@ -505,7 +501,7 @@ void Textfield::GetAccessibleState(ui::AccessibleViewState* state) {
state->state |= ui::AccessibilityTypes::STATE_PROTECTED;
state->value = text_;
- const ui::Range range = native_wrapper_->GetSelectedRange();
+ const gfx::Range range = native_wrapper_->GetSelectedRange();
state->selection_start = range.start();
state->selection_end = range.end();
@@ -520,6 +516,11 @@ ui::TextInputClient* Textfield::GetTextInputClient() {
return native_wrapper_ ? native_wrapper_->GetTextInputClient() : NULL;
}
+gfx::Point Textfield::GetKeyboardContextMenuLocation() {
+ return native_wrapper_ ? native_wrapper_->GetContextMenuLocation() :
+ View::GetKeyboardContextMenuLocation();
+}
+
void Textfield::OnEnabledChanged() {
View::OnEnabledChanged();
if (native_wrapper_)
diff --git a/chromium/ui/views/controls/textfield/textfield.h b/chromium/ui/views/controls/textfield/textfield.h
index 71b663bd2e5..3f796357b0d 100644
--- a/chromium/ui/views/controls/textfield/textfield.h
+++ b/chromium/ui/views/controls/textfield/textfield.h
@@ -15,7 +15,7 @@
#include "build/build_config.h"
#include "third_party/skia/include/core/SkColor.h"
#include "ui/base/ime/text_input_type.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/font_list.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/text_constants.h"
@@ -27,11 +27,11 @@
#endif
namespace gfx {
+class Range;
class ImageSkia;
}
namespace ui {
-class Range;
class TextInputClient;
} // namespace ui
@@ -172,9 +172,6 @@ class VIEWS_EXPORT Textfield : public View {
// Sets the text to display when empty.
void set_placeholder_text(const string16& text) {
placeholder_text_ = text;
-#if !defined(OS_LINUX)
- NOTIMPLEMENTED();
-#endif
}
const string16& placeholder_text() const {
return placeholder_text_;
@@ -209,11 +206,11 @@ class VIEWS_EXPORT Textfield : public View {
// Gets the selected range. This is views-implementation only and
// has to be called after the wrapper is created.
// TODO(msw): Return a const reference when NativeTextfieldWin is gone.
- ui::Range GetSelectedRange() const;
+ gfx::Range GetSelectedRange() const;
// Selects the text given by |range|. This is views-implementation only and
// has to be called after the wrapper is created.
- void SelectRange(const ui::Range& range);
+ void SelectRange(const gfx::Range& range);
// Gets the selection model. This is views-implementation only and
// has to be called after the wrapper is created.
@@ -232,14 +229,14 @@ class VIEWS_EXPORT Textfield : public View {
// Empty and invalid ranges are ignored. This is views-implementation only and
// has to be called after the wrapper is created.
void SetColor(SkColor value);
- void ApplyColor(SkColor value, const ui::Range& range);
+ void ApplyColor(SkColor value, const gfx::Range& range);
// Set various text styles over the entire text or a logical character range.
// The respective |style| is applied if |value| is true, or removed if false.
// Empty and invalid ranges are ignored. This is views-implementation only and
// has to be called after the wrapper is created.
void SetStyle(gfx::TextStyle style, bool value);
- void ApplyStyle(gfx::TextStyle style, bool value, const ui::Range& range);
+ void ApplyStyle(gfx::TextStyle style, bool value, const gfx::Range& range);
// Clears Edit history.
void ClearEditHistory();
@@ -276,6 +273,7 @@ class VIEWS_EXPORT Textfield : public View {
virtual void OnBlur() OVERRIDE;
virtual void GetAccessibleState(ui::AccessibleViewState* state) OVERRIDE;
virtual ui::TextInputClient* GetTextInputClient() OVERRIDE;
+ virtual gfx::Point GetKeyboardContextMenuLocation() OVERRIDE;
protected:
virtual void ViewHierarchyChanged(
diff --git a/chromium/ui/views/controls/textfield/textfield_controller.cc b/chromium/ui/views/controls/textfield/textfield_controller.cc
index d9899d2e59a..8f72be8a1c4 100644
--- a/chromium/ui/views/controls/textfield/textfield_controller.cc
+++ b/chromium/ui/views/controls/textfield/textfield_controller.cc
@@ -5,7 +5,7 @@
#include "ui/views/controls/textfield/textfield_controller.h"
#include "ui/base/dragdrop/drag_drop_types.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
namespace views {
diff --git a/chromium/ui/views/controls/textfield/textfield_views_model.cc b/chromium/ui/views/controls/textfield/textfield_views_model.cc
index 5ff20a5422a..dae5684889c 100644
--- a/chromium/ui/views/controls/textfield/textfield_views_model.cc
+++ b/chromium/ui/views/controls/textfield/textfield_views_model.cc
@@ -12,12 +12,12 @@
#include "base/strings/utf_string_conversions.h"
#include "ui/base/clipboard/clipboard.h"
#include "ui/base/clipboard/scoped_clipboard_writer.h"
-#include "ui/base/range/range.h"
-#include "ui/base/text/utf16_indexing.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/render_text.h"
#include "ui/gfx/text_constants.h"
+#include "ui/gfx/utf16_indexing.h"
#include "ui/views/controls/textfield/textfield.h"
namespace views {
@@ -269,13 +269,13 @@ namespace {
// Returns the first segment that is visually emphasized. Usually it's used for
// representing the target clause (on Windows). Returns an invalid range if
// there is no such a range.
-ui::Range GetFirstEmphasizedRange(const ui::CompositionText& composition) {
+gfx::Range GetFirstEmphasizedRange(const ui::CompositionText& composition) {
for (size_t i = 0; i < composition.underlines.size(); ++i) {
const ui::CompositionUnderline& underline = composition.underlines[i];
if (underline.thick)
- return ui::Range(underline.start_offset, underline.end_offset);
+ return gfx::Range(underline.start_offset, underline.end_offset);
}
- return ui::Range::InvalidRange();
+ return gfx::Range::InvalidRange();
}
} // namespace
@@ -363,7 +363,7 @@ bool TextfieldViewsModel::Delete() {
size_t cursor_position = GetCursorPosition();
size_t next_grapheme_index = render_text_->IndexOfAdjacentGrapheme(
cursor_position, gfx::CURSOR_FORWARD);
- ExecuteAndRecordDelete(ui::Range(cursor_position, next_grapheme_index),
+ ExecuteAndRecordDelete(gfx::Range(cursor_position, next_grapheme_index),
true);
return true;
}
@@ -384,8 +384,8 @@ bool TextfieldViewsModel::Backspace() {
if (cursor_position > 0) {
// Delete one code point, which may be two UTF-16 words.
size_t previous_char =
- ui::UTF16OffsetToIndex(GetText(), cursor_position, -1);
- ExecuteAndRecordDelete(ui::Range(cursor_position, previous_char), true);
+ gfx::UTF16OffsetToIndex(GetText(), cursor_position, -1);
+ ExecuteAndRecordDelete(gfx::Range(cursor_position, previous_char), true);
return true;
}
return false;
@@ -408,7 +408,7 @@ bool TextfieldViewsModel::MoveCursorTo(const gfx::SelectionModel& model) {
ConfirmCompositionText();
// ConfirmCompositionText() updates cursor position. Need to reflect it in
// the SelectionModel parameter of MoveCursorTo().
- ui::Range range(render_text_->selection().start(), model.caret_pos());
+ gfx::Range range(render_text_->selection().start(), model.caret_pos());
if (!range.is_empty())
return render_text_->SelectRange(range);
return render_text_->MoveCursorTo(
@@ -428,7 +428,7 @@ string16 TextfieldViewsModel::GetSelectedText() const {
render_text_->selection().length());
}
-void TextfieldViewsModel::SelectRange(const ui::Range& range) {
+void TextfieldViewsModel::SelectRange(const gfx::Range& range) {
if (HasCompositionText())
ConfirmCompositionText();
render_text_->SelectRange(range);
@@ -518,8 +518,8 @@ bool TextfieldViewsModel::Cut() {
// than beginning, unlike Delete/Backspace.
// TODO(oshima): Change Delete/Backspace to use DeleteSelection,
// update DeleteEdit and remove this trick.
- const ui::Range& selection = render_text_->selection();
- render_text_->SelectRange(ui::Range(selection.end(), selection.start()));
+ const gfx::Range& selection = render_text_->selection();
+ render_text_->SelectRange(gfx::Range(selection.end(), selection.start()));
DeleteSelection();
return true;
}
@@ -568,14 +568,14 @@ void TextfieldViewsModel::DeleteSelectionAndInsertTextAt(
position);
}
-string16 TextfieldViewsModel::GetTextFromRange(const ui::Range& range) const {
+string16 TextfieldViewsModel::GetTextFromRange(const gfx::Range& range) const {
if (range.IsValid() && range.GetMin() < GetText().length())
return GetText().substr(range.GetMin(), range.length());
return string16();
}
-void TextfieldViewsModel::GetTextRange(ui::Range* range) const {
- *range = ui::Range(0, GetText().length());
+void TextfieldViewsModel::GetTextRange(gfx::Range* range) const {
+ *range = gfx::Range(0, GetText().length());
}
void TextfieldViewsModel::SetCompositionText(
@@ -591,9 +591,9 @@ void TextfieldViewsModel::SetCompositionText(
size_t cursor = GetCursorPosition();
string16 new_text = GetText();
render_text_->SetText(new_text.insert(cursor, composition.text));
- ui::Range range(cursor, cursor + composition.text.length());
+ gfx::Range range(cursor, cursor + composition.text.length());
render_text_->SetCompositionRange(range);
- ui::Range emphasized_range = GetFirstEmphasizedRange(composition);
+ gfx::Range emphasized_range = GetFirstEmphasizedRange(composition);
if (emphasized_range.IsValid()) {
// This is a workaround due to the lack of support in RenderText to draw
// a thick underline. In a composition returned from an IME, the segment
@@ -603,11 +603,11 @@ void TextfieldViewsModel::SetCompositionText(
// marker instead to show this range.
// TODO(yukawa, msw): Support thick underline in RenderText and remove
// this workaround.
- render_text_->SelectRange(ui::Range(
+ render_text_->SelectRange(gfx::Range(
cursor + emphasized_range.GetMin(),
cursor + emphasized_range.GetMax()));
} else if (!composition.selection.is_empty()) {
- render_text_->SelectRange(ui::Range(
+ render_text_->SelectRange(gfx::Range(
cursor + composition.selection.GetMin(),
cursor + composition.selection.GetMax()));
} else {
@@ -617,7 +617,7 @@ void TextfieldViewsModel::SetCompositionText(
void TextfieldViewsModel::ConfirmCompositionText() {
DCHECK(HasCompositionText());
- ui::Range range = render_text_->GetCompositionRange();
+ gfx::Range range = render_text_->GetCompositionRange();
string16 text = GetText().substr(range.start(), range.length());
// TODO(oshima): current behavior on ChromeOS is a bit weird and not
// sure exactly how this should work. Find out and fix if necessary.
@@ -630,7 +630,7 @@ void TextfieldViewsModel::ConfirmCompositionText() {
void TextfieldViewsModel::CancelCompositionText() {
DCHECK(HasCompositionText());
- ui::Range range = render_text_->GetCompositionRange();
+ gfx::Range range = render_text_->GetCompositionRange();
ClearComposition();
string16 new_text = GetText();
render_text_->SetText(new_text.erase(range.start(), range.length()));
@@ -640,11 +640,11 @@ void TextfieldViewsModel::CancelCompositionText() {
}
void TextfieldViewsModel::ClearComposition() {
- render_text_->SetCompositionRange(ui::Range::InvalidRange());
+ render_text_->SetCompositionRange(gfx::Range::InvalidRange());
}
-void TextfieldViewsModel::GetCompositionTextRange(ui::Range* range) const {
- *range = ui::Range(render_text_->GetCompositionRange());
+void TextfieldViewsModel::GetCompositionTextRange(gfx::Range* range) const {
+ *range = gfx::Range(render_text_->GetCompositionRange());
}
bool TextfieldViewsModel::HasCompositionText() const {
@@ -681,7 +681,7 @@ void TextfieldViewsModel::ReplaceTextInternal(const string16& text,
if (next == model.caret_pos())
render_text_->MoveCursorTo(model);
else
- render_text_->SelectRange(ui::Range(next, model.caret_pos()));
+ render_text_->SelectRange(gfx::Range(next, model.caret_pos()));
}
// Edit history is recorded in InsertText.
InsertTextInternal(text, mergeable);
@@ -705,7 +705,7 @@ void TextfieldViewsModel::ClearRedoHistory() {
edit_history_.erase(delete_start, edit_history_.end());
}
-void TextfieldViewsModel::ExecuteAndRecordDelete(ui::Range range,
+void TextfieldViewsModel::ExecuteAndRecordDelete(gfx::Range range,
bool mergeable) {
size_t old_text_start = range.GetMin();
const string16 text = GetText().substr(old_text_start, range.length());
diff --git a/chromium/ui/views/controls/textfield/textfield_views_model.h b/chromium/ui/views/controls/textfield/textfield_views_model.h
index ddbdd72e7dc..1af734054a9 100644
--- a/chromium/ui/views/controls/textfield/textfield_views_model.h
+++ b/chromium/ui/views/controls/textfield/textfield_views_model.h
@@ -19,13 +19,10 @@
#include "ui/views/views_export.h"
namespace gfx {
+class Range;
class RenderText;
} // namespace gfx
-namespace ui {
-class Range;
-} // namespace ui
-
namespace views {
namespace internal {
@@ -144,7 +141,7 @@ class VIEWS_EXPORT TextfieldViewsModel {
// The current composition text will be confirmed. The selection starts with
// the range's start position, and ends with the range's end position,
// therefore the cursor position becomes the end position.
- void SelectRange(const ui::Range& range);
+ void SelectRange(const gfx::Range& range);
// The current composition text will be confirmed.
// render_text_'s selection model is set to |sel|.
@@ -204,10 +201,10 @@ class VIEWS_EXPORT TextfieldViewsModel {
const string16& text, size_t position);
// Retrieves the text content in a given range.
- string16 GetTextFromRange(const ui::Range& range) const;
+ string16 GetTextFromRange(const gfx::Range& range) const;
// Retrieves the range containing all text in the model.
- void GetTextRange(ui::Range* range) const;
+ void GetTextRange(gfx::Range* range) const;
// Sets composition text and attributes. If there is composition text already,
// it'll be replaced by the new one. Otherwise, current selection will be
@@ -224,7 +221,7 @@ class VIEWS_EXPORT TextfieldViewsModel {
void CancelCompositionText();
// Retrieves the range of current composition text.
- void GetCompositionTextRange(ui::Range* range) const;
+ void GetCompositionTextRange(gfx::Range* range) const;
// Returns true if there is composition text.
bool HasCompositionText() const;
@@ -258,7 +255,7 @@ class VIEWS_EXPORT TextfieldViewsModel {
void ClearRedoHistory();
// Executes and records edit operations.
- void ExecuteAndRecordDelete(ui::Range range, bool mergeable);
+ void ExecuteAndRecordDelete(gfx::Range range, bool mergeable);
void ExecuteAndRecordReplaceSelection(internal::MergeType merge_type,
const string16& text);
void ExecuteAndRecordReplace(internal::MergeType merge_type,
diff --git a/chromium/ui/views/controls/textfield/textfield_views_model_unittest.cc b/chromium/ui/views/controls/textfield/textfield_views_model_unittest.cc
index 2b2d546a89a..f78ffba1ac1 100644
--- a/chromium/ui/views/controls/textfield/textfield_views_model_unittest.cc
+++ b/chromium/ui/views/controls/textfield/textfield_views_model_unittest.cc
@@ -12,7 +12,7 @@
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/base/clipboard/clipboard.h"
#include "ui/base/clipboard/scoped_clipboard_writer.h"
-#include "ui/base/range/range.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/render_text.h"
#include "ui/views/controls/textfield/textfield.h"
#include "ui/views/controls/textfield/textfield_views_model.h"
@@ -276,19 +276,19 @@ TEST_F(TextfieldViewsModelTest, Selection) {
// SelectAll(false) selects towards the end.
model.SelectAll(false);
EXPECT_STR_EQ("HELLO", model.GetSelectedText());
- EXPECT_EQ(ui::Range(0, 5), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(0, 5), model.render_text()->selection());
// SelectAll(true) selects towards the beginning.
model.SelectAll(true);
EXPECT_STR_EQ("HELLO", model.GetSelectedText());
- EXPECT_EQ(ui::Range(5, 0), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(5, 0), model.render_text()->selection());
// Select and move cursor.
- model.SelectRange(ui::Range(1U, 3U));
+ model.SelectRange(gfx::Range(1U, 3U));
EXPECT_STR_EQ("EL", model.GetSelectedText());
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_LEFT, false);
EXPECT_EQ(1U, model.GetCursorPosition());
- model.SelectRange(ui::Range(1U, 3U));
+ model.SelectRange(gfx::Range(1U, 3U));
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, false);
EXPECT_EQ(3U, model.GetCursorPosition());
@@ -318,20 +318,20 @@ TEST_F(TextfieldViewsModelTest, Selection_BidiWithNonSpacingMarks) {
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, false);
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, true);
- EXPECT_EQ(ui::Range(2, 3), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(2, 3), model.render_text()->selection());
EXPECT_EQ(WideToUTF16(L"c"), model.GetSelectedText());
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, true);
- EXPECT_EQ(ui::Range(2, 7), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(2, 7), model.render_text()->selection());
EXPECT_EQ(WideToUTF16(L"c\x05E9\x05BC\x05C1\x05B8"),
model.GetSelectedText());
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, true);
- EXPECT_EQ(ui::Range(2, 3), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(2, 3), model.render_text()->selection());
EXPECT_EQ(WideToUTF16(L"c"), model.GetSelectedText());
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, true);
- EXPECT_EQ(ui::Range(2, 10), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(2, 10), model.render_text()->selection());
EXPECT_EQ(WideToUTF16(L"c\x05E9\x05BC\x05C1\x05B8\x05E0\x05B8" L"d"),
model.GetSelectedText());
@@ -634,7 +634,7 @@ TEST_F(TextfieldViewsModelTest, RangeTest) {
TextfieldViewsModel model(NULL);
model.Append(ASCIIToUTF16("HELLO WORLD"));
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_LEFT, false);
- ui::Range range = model.render_text()->selection();
+ gfx::Range range = model.render_text()->selection();
EXPECT_TRUE(range.is_empty());
EXPECT_EQ(0U, range.start());
EXPECT_EQ(0U, range.end());
@@ -697,42 +697,42 @@ TEST_F(TextfieldViewsModelTest, RangeTest) {
TEST_F(TextfieldViewsModelTest, SelectRangeTest) {
TextfieldViewsModel model(NULL);
model.Append(ASCIIToUTF16("HELLO WORLD"));
- ui::Range range(0, 6);
+ gfx::Range range(0, 6);
EXPECT_FALSE(range.is_reversed());
model.SelectRange(range);
EXPECT_STR_EQ("HELLO ", model.GetSelectedText());
- range = ui::Range(6, 1);
+ range = gfx::Range(6, 1);
EXPECT_TRUE(range.is_reversed());
model.SelectRange(range);
EXPECT_STR_EQ("ELLO ", model.GetSelectedText());
- range = ui::Range(2, 1000);
+ range = gfx::Range(2, 1000);
EXPECT_FALSE(range.is_reversed());
model.SelectRange(range);
EXPECT_STR_EQ("LLO WORLD", model.GetSelectedText());
- range = ui::Range(1000, 3);
+ range = gfx::Range(1000, 3);
EXPECT_TRUE(range.is_reversed());
model.SelectRange(range);
EXPECT_STR_EQ("LO WORLD", model.GetSelectedText());
- range = ui::Range(0, 0);
+ range = gfx::Range(0, 0);
EXPECT_TRUE(range.is_empty());
model.SelectRange(range);
EXPECT_TRUE(model.GetSelectedText().empty());
- range = ui::Range(3, 3);
+ range = gfx::Range(3, 3);
EXPECT_TRUE(range.is_empty());
model.SelectRange(range);
EXPECT_TRUE(model.GetSelectedText().empty());
- range = ui::Range(1000, 100);
+ range = gfx::Range(1000, 100);
EXPECT_FALSE(range.is_empty());
model.SelectRange(range);
EXPECT_TRUE(model.GetSelectedText().empty());
- range = ui::Range(1000, 1000);
+ range = gfx::Range(1000, 1000);
EXPECT_TRUE(range.is_empty());
model.SelectRange(range);
EXPECT_TRUE(model.GetSelectedText().empty());
@@ -742,60 +742,60 @@ TEST_F(TextfieldViewsModelTest, SelectionTest) {
TextfieldViewsModel model(NULL);
model.Append(ASCIIToUTF16("HELLO WORLD"));
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_LEFT, false);
- ui::Range selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(0), selection);
+ gfx::Range selection = model.render_text()->selection();
+ EXPECT_EQ(gfx::Range(0), selection);
model.MoveCursor(gfx::WORD_BREAK, gfx::CURSOR_RIGHT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(0, 5), selection);
+ EXPECT_EQ(gfx::Range(0, 5), selection);
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_LEFT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(0, 4), selection);
+ EXPECT_EQ(gfx::Range(0, 4), selection);
model.MoveCursor(gfx::WORD_BREAK, gfx::CURSOR_LEFT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(0), selection);
+ EXPECT_EQ(gfx::Range(0), selection);
// now from the end.
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_RIGHT, false);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(11), selection);
+ EXPECT_EQ(gfx::Range(11), selection);
model.MoveCursor(gfx::WORD_BREAK, gfx::CURSOR_LEFT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(11, 6), selection);
+ EXPECT_EQ(gfx::Range(11, 6), selection);
model.MoveCursor(gfx::CHARACTER_BREAK, gfx::CURSOR_RIGHT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(11, 7), selection);
+ EXPECT_EQ(gfx::Range(11, 7), selection);
model.MoveCursor(gfx::WORD_BREAK, gfx::CURSOR_RIGHT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(11), selection);
+ EXPECT_EQ(gfx::Range(11), selection);
// Select All
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_LEFT, true);
selection = model.render_text()->selection();
- EXPECT_EQ(ui::Range(11, 0), selection);
+ EXPECT_EQ(gfx::Range(11, 0), selection);
}
TEST_F(TextfieldViewsModelTest, SelectSelectionModelTest) {
TextfieldViewsModel model(NULL);
model.Append(ASCIIToUTF16("HELLO WORLD"));
- model.SelectSelectionModel(gfx::SelectionModel(ui::Range(0, 6),
+ model.SelectSelectionModel(gfx::SelectionModel(gfx::Range(0, 6),
gfx::CURSOR_BACKWARD));
EXPECT_STR_EQ("HELLO ", model.GetSelectedText());
- model.SelectSelectionModel(gfx::SelectionModel(ui::Range(6, 1),
+ model.SelectSelectionModel(gfx::SelectionModel(gfx::Range(6, 1),
gfx::CURSOR_FORWARD));
EXPECT_STR_EQ("ELLO ", model.GetSelectedText());
- model.SelectSelectionModel(gfx::SelectionModel(ui::Range(2, 1000),
+ model.SelectSelectionModel(gfx::SelectionModel(gfx::Range(2, 1000),
gfx::CURSOR_BACKWARD));
EXPECT_STR_EQ("LLO WORLD", model.GetSelectedText());
- model.SelectSelectionModel(gfx::SelectionModel(ui::Range(1000, 3),
+ model.SelectSelectionModel(gfx::SelectionModel(gfx::Range(1000, 3),
gfx::CURSOR_FORWARD));
EXPECT_STR_EQ("LO WORLD", model.GetSelectedText());
@@ -805,7 +805,7 @@ TEST_F(TextfieldViewsModelTest, SelectSelectionModelTest) {
model.SelectSelectionModel(gfx::SelectionModel(3, gfx::CURSOR_FORWARD));
EXPECT_TRUE(model.GetSelectedText().empty());
- model.SelectSelectionModel(gfx::SelectionModel(ui::Range(1000, 100),
+ model.SelectSelectionModel(gfx::SelectionModel(gfx::Range(1000, 100),
gfx::CURSOR_FORWARD));
EXPECT_TRUE(model.GetSelectedText().empty());
@@ -816,20 +816,20 @@ TEST_F(TextfieldViewsModelTest, SelectSelectionModelTest) {
TEST_F(TextfieldViewsModelTest, CompositionTextTest) {
TextfieldViewsModel model(this);
model.Append(ASCIIToUTF16("1234590"));
- model.SelectRange(ui::Range(5, 5));
+ model.SelectRange(gfx::Range(5, 5));
EXPECT_FALSE(model.HasSelection());
EXPECT_EQ(5U, model.GetCursorPosition());
- ui::Range range;
+ gfx::Range range;
model.GetTextRange(&range);
- EXPECT_EQ(ui::Range(0, 7), range);
+ EXPECT_EQ(gfx::Range(0, 7), range);
ui::CompositionText composition;
composition.text = ASCIIToUTF16("678");
composition.underlines.push_back(ui::CompositionUnderline(0, 3, 0, false));
// Cursor should be at the end of composition when characters are just typed.
- composition.selection = ui::Range(3, 3);
+ composition.selection = gfx::Range(3, 3);
model.SetCompositionText(composition);
EXPECT_TRUE(model.HasCompositionText());
EXPECT_FALSE(model.HasSelection());
@@ -839,24 +839,24 @@ TEST_F(TextfieldViewsModelTest, CompositionTextTest) {
composition_text_confirmed_or_cleared_ = false;
// Restart composition with targeting "67" in "678".
- composition.selection = ui::Range(0, 2);
+ composition.selection = gfx::Range(0, 2);
composition.underlines.clear();
composition.underlines.push_back(ui::CompositionUnderline(0, 2, 0, true));
composition.underlines.push_back(ui::CompositionUnderline(2, 3, 0, false));
model.SetCompositionText(composition);
EXPECT_TRUE(model.HasCompositionText());
EXPECT_TRUE(model.HasSelection());
- EXPECT_EQ(ui::Range(5, 7), model.render_text()->selection());
+ EXPECT_EQ(gfx::Range(5, 7), model.render_text()->selection());
model.GetTextRange(&range);
EXPECT_EQ(10U, range.end());
EXPECT_STR_EQ("1234567890", model.GetText());
model.GetCompositionTextRange(&range);
- EXPECT_EQ(ui::Range(5, 8), range);
+ EXPECT_EQ(gfx::Range(5, 8), range);
// composition text
- EXPECT_STR_EQ("456", model.GetTextFromRange(ui::Range(3, 6)));
- EXPECT_EQ(ui::Range(5, 7), model.render_text()->selection());
+ EXPECT_STR_EQ("456", model.GetTextFromRange(gfx::Range(3, 6)));
+ EXPECT_EQ(gfx::Range(5, 7), model.render_text()->selection());
EXPECT_FALSE(composition_text_confirmed_or_cleared_);
model.CancelCompositionText();
@@ -954,7 +954,7 @@ TEST_F(TextfieldViewsModelTest, CompositionTextTest) {
model.SetCompositionText(composition);
gfx::SelectionModel sel(
- ui::Range(model.render_text()->selection().start(), 0),
+ gfx::Range(model.render_text()->selection().start(), 0),
gfx::CURSOR_FORWARD);
model.MoveCursorTo(sel);
EXPECT_TRUE(composition_text_confirmed_or_cleared_);
@@ -962,7 +962,7 @@ TEST_F(TextfieldViewsModelTest, CompositionTextTest) {
EXPECT_STR_EQ("678678", model.GetText());
model.SetCompositionText(composition);
- model.SelectRange(ui::Range(0, 3));
+ model.SelectRange(gfx::Range(0, 3));
EXPECT_TRUE(composition_text_confirmed_or_cleared_);
composition_text_confirmed_or_cleared_ = false;
EXPECT_STR_EQ("678", model.GetText());
@@ -1095,19 +1095,19 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_SetText) {
model.SetText(ASCIIToUTF16("www.google.com"));
EXPECT_EQ(14U, model.GetCursorPosition());
EXPECT_STR_EQ("www.google.com", model.GetText());
- model.SelectRange(ui::Range(14, 1));
+ model.SelectRange(gfx::Range(14, 1));
model.InsertChar('w');
EXPECT_STR_EQ("ww", model.GetText());
model.SetText(ASCIIToUTF16("www.google.com"));
- model.SelectRange(ui::Range(14, 2));
+ model.SelectRange(gfx::Range(14, 2));
model.InsertChar('w');
EXPECT_STR_EQ("www", model.GetText());
model.SetText(ASCIIToUTF16("www.google.com"));
- model.SelectRange(ui::Range(14, 3));
+ model.SelectRange(gfx::Range(14, 3));
model.InsertChar('.');
EXPECT_STR_EQ("www.", model.GetText());
model.SetText(ASCIIToUTF16("www.google.com"));
- model.SelectRange(ui::Range(14, 4));
+ model.SelectRange(gfx::Range(14, 4));
model.InsertChar('y');
EXPECT_STR_EQ("www.y", model.GetText());
model.SetText(ASCIIToUTF16("www.youtube.com"));
@@ -1177,7 +1177,7 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_CutCopyPasteTest) {
model.SetText(ASCIIToUTF16("ABCDE"));
EXPECT_FALSE(model.Redo()); // nothing to redo
// Cut
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
model.Cut();
EXPECT_STR_EQ("ADE", model.GetText());
EXPECT_EQ(1U, model.GetCursorPosition());
@@ -1240,11 +1240,11 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_CutCopyPasteTest) {
EXPECT_FALSE(model.Redo());
// with SelectRange
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
EXPECT_TRUE(model.Cut());
EXPECT_STR_EQ("ABCBCDE", model.GetText());
EXPECT_EQ(1U, model.GetCursorPosition());
- model.SelectRange(ui::Range(1, 1));
+ model.SelectRange(gfx::Range(1, 1));
EXPECT_FALSE(model.Cut());
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_RIGHT, false);
EXPECT_TRUE(model.Paste());
@@ -1263,7 +1263,7 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_CutCopyPasteTest) {
model.SetText(ASCIIToUTF16("12345"));
EXPECT_STR_EQ("12345", model.GetText());
EXPECT_EQ(5U, model.GetCursorPosition());
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
model.Copy(); // Copy "23"
EXPECT_STR_EQ("12345", model.GetText());
EXPECT_EQ(3U, model.GetCursorPosition());
@@ -1297,7 +1297,7 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_CutCopyPasteTest) {
EXPECT_STR_EQ("1232345", model.GetText());
// Test using SelectRange
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
model.Copy();
EXPECT_STR_EQ("1232345", model.GetText());
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_RIGHT, false);
@@ -1381,28 +1381,28 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_ReplaceTest) {
SCOPED_TRACE("forward & insert by cursor");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
RunInsertReplaceTest(model);
}
{
SCOPED_TRACE("backward & insert by cursor");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(3, 1));
+ model.SelectRange(gfx::Range(3, 1));
RunInsertReplaceTest(model);
}
{
SCOPED_TRACE("forward & overwrite by cursor");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
RunOverwriteReplaceTest(model);
}
{
SCOPED_TRACE("backward & overwrite by cursor");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(3, 1));
+ model.SelectRange(gfx::Range(3, 1));
RunOverwriteReplaceTest(model);
}
// By SelectRange API
@@ -1410,28 +1410,28 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_ReplaceTest) {
SCOPED_TRACE("forward & insert by SelectRange");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
RunInsertReplaceTest(model);
}
{
SCOPED_TRACE("backward & insert by SelectRange");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(3, 1));
+ model.SelectRange(gfx::Range(3, 1));
RunInsertReplaceTest(model);
}
{
SCOPED_TRACE("forward & overwrite by SelectRange");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(1, 3));
+ model.SelectRange(gfx::Range(1, 3));
RunOverwriteReplaceTest(model);
}
{
SCOPED_TRACE("backward & overwrite by SelectRange");
TextfieldViewsModel model(NULL);
model.SetText(ASCIIToUTF16("abcd"));
- model.SelectRange(ui::Range(3, 1));
+ model.SelectRange(gfx::Range(3, 1));
RunOverwriteReplaceTest(model);
}
}
@@ -1442,7 +1442,7 @@ TEST_F(TextfieldViewsModelTest, UndoRedo_CompositionText) {
ui::CompositionText composition;
composition.text = ASCIIToUTF16("abc");
composition.underlines.push_back(ui::CompositionUnderline(0, 3, 0, false));
- composition.selection = ui::Range(2, 3);
+ composition.selection = gfx::Range(2, 3);
model.SetText(ASCIIToUTF16("ABCDE"));
model.MoveCursor(gfx::LINE_BREAK, gfx::CURSOR_RIGHT, false);
diff --git a/chromium/ui/views/controls/tree/tree_view.cc b/chromium/ui/views/controls/tree/tree_view.cc
index 0157902fad4..78d4693e4a7 100644
--- a/chromium/ui/views/controls/tree/tree_view.cc
+++ b/chromium/ui/views/controls/tree/tree_view.cc
@@ -10,9 +10,9 @@
#include "base/message_loop/message_loop.h"
#include "grit/ui_resources.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/resource/resource_bundle.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/image/image.h"
#include "ui/gfx/rect_conversions.h"
diff --git a/chromium/ui/views/controls/tree/tree_view_controller.h b/chromium/ui/views/controls/tree/tree_view_controller.h
index 38e7fcc85e4..b1ebf2b0b0c 100644
--- a/chromium/ui/views/controls/tree/tree_view_controller.h
+++ b/chromium/ui/views/controls/tree/tree_view_controller.h
@@ -5,7 +5,7 @@
#ifndef UI_VIEWS_CONTROLS_TREE_TREE_VIEW_CONTROLLER_H_
#define UI_VIEWS_CONTROLS_TREE_TREE_VIEW_CONTROLLER_H_
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/views_export.h"
namespace ui {
diff --git a/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_aurax11.cc b/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_aurax11.cc
index 41c90ff7f2f..7e09af947b5 100644
--- a/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_aurax11.cc
+++ b/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_aurax11.cc
@@ -6,7 +6,7 @@
#include "base/logging.h"
#include "content/public/browser/native_web_keyboard_event.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/focus/focus_manager.h"
using content::NativeWebKeyboardEvent;
diff --git a/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_win.cc b/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_win.cc
index fd82608bd18..b30b5576c3e 100644
--- a/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_win.cc
+++ b/chromium/ui/views/controls/webview/unhandled_keyboard_event_handler_win.cc
@@ -6,7 +6,7 @@
#include "base/logging.h"
#include "content/public/browser/native_web_keyboard_event.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/focus/focus_manager.h"
using content::NativeWebKeyboardEvent;
diff --git a/chromium/ui/views/controls/webview/web_dialog_view.cc b/chromium/ui/views/controls/webview/web_dialog_view.cc
index 15173791d03..ff9d63bb45b 100644
--- a/chromium/ui/views/controls/webview/web_dialog_view.cc
+++ b/chromium/ui/views/controls/webview/web_dialog_view.cc
@@ -14,7 +14,7 @@
#include "content/public/browser/notification_types.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/web_contents.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/controls/webview/webview.h"
#include "ui/views/layout/fill_layout.h"
#include "ui/views/widget/root_view.h"
@@ -23,7 +23,7 @@
#include "ui/web_dialogs/web_dialog_ui.h"
#if defined(USE_AURA)
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/widget/desktop_aura/desktop_native_widget_aura.h"
#include "ui/views/widget/native_widget_aura.h"
#endif
diff --git a/chromium/ui/views/controls/webview/webview.cc b/chromium/ui/views/controls/webview/webview.cc
index 89ac03758e5..9169ac0ecbf 100644
--- a/chromium/ui/views/controls/webview/webview.cc
+++ b/chromium/ui/views/controls/webview/webview.cc
@@ -4,6 +4,7 @@
#include "ui/views/controls/webview/webview.h"
+#include "content/public/browser/browser_accessibility_state.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/navigation_controller.h"
#include "content/public/browser/notification_details.h"
@@ -17,7 +18,7 @@
#include "ipc/ipc_message.h"
#include "ui/base/accessibility/accessibility_types.h"
#include "ui/base/accessibility/accessible_view_state.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/accessibility/native_view_accessibility.h"
#include "ui/views/controls/native/native_view_host.h"
#include "ui/views/focus/focus_manager.h"
@@ -34,6 +35,8 @@ const char WebView::kViewClassName[] = "WebView";
WebView::WebView(content::BrowserContext* browser_context)
: wcv_holder_(new NativeViewHost),
web_contents_(NULL),
+ embed_fullscreen_widget_mode_enabled_(false),
+ is_embedding_fullscreen_widget_(false),
browser_context_(browser_context),
allow_accelerators_(false) {
AddChildView(wcv_holder_);
@@ -63,11 +66,35 @@ void WebView::SetWebContents(content::WebContents* web_contents) {
if (web_contents == web_contents_)
return;
DetachWebContents();
- wc_owner_.reset();
+ if (wc_owner_ != web_contents)
+ wc_owner_.reset();
web_contents_ = web_contents;
+ if (embed_fullscreen_widget_mode_enabled_) {
+ WebContentsObserver::Observe(web_contents_);
+ is_embedding_fullscreen_widget_ =
+ web_contents_ && web_contents_->GetFullscreenRenderWidgetHostView();
+ } else {
+ is_embedding_fullscreen_widget_ = false;
+ }
AttachWebContents();
}
+void WebView::SetEmbedFullscreenWidgetMode(bool enable) {
+ bool should_be_embedded = enable;
+ if (!embed_fullscreen_widget_mode_enabled_ && enable) {
+ DCHECK(!is_embedding_fullscreen_widget_);
+ embed_fullscreen_widget_mode_enabled_ = true;
+ WebContentsObserver::Observe(web_contents_);
+ should_be_embedded =
+ web_contents_ && web_contents_->GetFullscreenRenderWidgetHostView();
+ } else if (embed_fullscreen_widget_mode_enabled_ && !enable) {
+ embed_fullscreen_widget_mode_enabled_ = false;
+ WebContentsObserver::Observe(NULL);
+ }
+ if (should_be_embedded != is_embedding_fullscreen_widget_)
+ ReattachForFullscreenChange(should_be_embedded);
+}
+
void WebView::LoadInitialURL(const GURL& url) {
GetWebContents()->GetController().LoadURL(
url, content::Referrer(), content::PAGE_TRANSITION_AUTO_TOPLEVEL,
@@ -125,8 +152,16 @@ bool WebView::IsFocusable() const {
}
void WebView::OnFocus() {
- if (web_contents_)
+ if (!web_contents_)
+ return;
+ if (is_embedding_fullscreen_widget_) {
+ content::RenderWidgetHostView* const current_fs_view =
+ web_contents_->GetFullscreenRenderWidgetHostView();
+ if (current_fs_view)
+ current_fs_view->Focus();
+ } else {
web_contents_->GetView()->Focus();
+ }
}
void WebView::AboutToRequestFocusFromTabTraversal(bool reverse) {
@@ -162,15 +197,13 @@ void WebView::Observe(int type,
const content::NotificationSource& source,
const content::NotificationDetails& details) {
if (type == content::NOTIFICATION_RENDER_VIEW_HOST_CHANGED) {
- std::pair<content::RenderViewHost*, content::RenderViewHost*>*
- switched_details =
- content::Details<std::pair<content::RenderViewHost*,
- content::RenderViewHost*> >(
- details).ptr();
- RenderViewHostChanged(switched_details->first,
- switched_details->second);
+ FocusManager* const focus_manager = GetFocusManager();
+ if (focus_manager && focus_manager->GetFocusedView() == this)
+ OnFocus();
} else if (type == content::NOTIFICATION_WEB_CONTENTS_DESTROYED) {
- WebContentsDestroyed(content::Source<content::WebContents>(source).ptr());
+ DCHECK(content::Source<content::WebContents>(source).ptr() ==
+ web_contents_);
+ SetWebContents(NULL);
} else {
NOTREACHED();
}
@@ -185,26 +218,22 @@ void WebView::WebContentsFocused(content::WebContents* web_contents) {
OnWebContentsFocused(web_contents_);
}
+bool WebView::EmbedsFullscreenWidget() const {
+ DCHECK(wc_owner_.get());
+ return embed_fullscreen_widget_mode_enabled_;
+}
+
////////////////////////////////////////////////////////////////////////////////
-// WebView, AccessibleWebView implementation:
+// WebView, content::WebContentsObserver implementation:
-gfx::NativeViewAccessible WebView::AccessibleObjectFromChildId(long child_id) {
-#if defined(OS_WIN) && defined(USE_AURA)
- if (!web_contents_)
- return NULL;
- content::RenderWidgetHostView* host_view =
- web_contents_->GetRenderWidgetHostView();
- if (host_view)
- return host_view->AccessibleObjectFromChildId(child_id);
- return NULL;
-#else
- NOTIMPLEMENTED();
- return NULL;
-#endif
+void WebView::DidShowFullscreenWidget(int routing_id) {
+ DCHECK(embed_fullscreen_widget_mode_enabled_);
+ ReattachForFullscreenChange(true);
}
-View* WebView::AsView() {
- return this;
+void WebView::DidDestroyFullscreenWidget(int routing_id) {
+ DCHECK(embed_fullscreen_widget_mode_enabled_);
+ ReattachForFullscreenChange(false);
}
////////////////////////////////////////////////////////////////////////////////
@@ -213,66 +242,69 @@ View* WebView::AsView() {
void WebView::AttachWebContents() {
// Prevents attachment if the WebView isn't already in a Widget, or it's
// already attached.
- if (!GetWidget() || !web_contents_ ||
- wcv_holder_->native_view() == web_contents_->GetView()->GetNativeView()) {
+ if (!GetWidget() || !web_contents_)
return;
- }
-
- if (web_contents_) {
- wcv_holder_->Attach(web_contents_->GetView()->GetNativeView());
- // The WebContentsView will not be focused automatically when it is
- // attached, so we need to pass on focus to it if the FocusManager thinks
- // the WebView is focused. Note that not every Widget has a focus manager.
- FocusManager* focus_manager = GetFocusManager();
- if (focus_manager && focus_manager->GetFocusedView() == this)
- web_contents_->GetView()->Focus();
-
- registrar_.Add(
- this,
- content::NOTIFICATION_RENDER_VIEW_HOST_CHANGED,
- content::Source<content::NavigationController>(
- &web_contents_->GetController()));
- registrar_.Add(
- this,
- content::NOTIFICATION_WEB_CONTENTS_DESTROYED,
- content::Source<content::WebContents>(web_contents_));
- }
+ const gfx::NativeView view_to_attach = is_embedding_fullscreen_widget_ ?
+ web_contents_->GetFullscreenRenderWidgetHostView()->GetNativeView() :
+ web_contents_->GetView()->GetNativeView();
+ if (wcv_holder_->native_view() == view_to_attach)
+ return;
+ wcv_holder_->Attach(view_to_attach);
+
+ // The view will not be focused automatically when it is attached, so we need
+ // to pass on focus to it if the FocusManager thinks the view is focused. Note
+ // that not every Widget has a focus manager.
+ FocusManager* const focus_manager = GetFocusManager();
+ if (focus_manager && focus_manager->GetFocusedView() == this)
+ OnFocus();
+
+ registrar_.Add(
+ this,
+ content::NOTIFICATION_RENDER_VIEW_HOST_CHANGED,
+ content::Source<content::NavigationController>(
+ &web_contents_->GetController()));
+ registrar_.Add(
+ this,
+ content::NOTIFICATION_WEB_CONTENTS_DESTROYED,
+ content::Source<content::WebContents>(web_contents_));
#if defined(OS_WIN) && defined(USE_AURA)
- web_contents_->SetParentNativeViewAccessible(
- parent()->GetNativeViewAccessible());
+ if (!is_embedding_fullscreen_widget_) {
+ web_contents_->SetParentNativeViewAccessible(
+ parent()->GetNativeViewAccessible());
+ }
#endif
}
void WebView::DetachWebContents() {
if (web_contents_) {
wcv_holder_->Detach();
-#if defined(OS_WIN) && !defined(USE_AURA)
- // TODO(beng): This should either not be necessary, or be done implicitly by
- // NativeViewHostWin on Detach(). As it stands, this is needed so that the
- // view of the detached contents knows to tell the renderer it's been
- // hidden.
- //
- // Moving this out of here would also mean we wouldn't be potentially
- // calling member functions on a half-destroyed WebContents.
- ShowWindow(web_contents_->GetView()->GetNativeView(), SW_HIDE);
-#elif defined(OS_WIN) && defined(USE_AURA)
- web_contents_->SetParentNativeViewAccessible(NULL);
+#if defined(OS_WIN)
+ if (!is_embedding_fullscreen_widget_) {
+#if !defined(USE_AURA)
+ // TODO(beng): This should either not be necessary, or be done implicitly
+ // by NativeViewHostWin on Detach(). As it stands, this is needed so that
+ // the of the detached contents knows to tell the renderer it's been
+ // hidden.
+ //
+ // Moving this out of here would also mean we wouldn't be potentially
+ // calling member functions on a half-destroyed WebContents.
+ ShowWindow(web_contents_->GetView()->GetNativeView(), SW_HIDE);
+#else
+ web_contents_->SetParentNativeViewAccessible(NULL);
+#endif
+ }
#endif
}
registrar_.RemoveAll();
}
-void WebView::RenderViewHostChanged(content::RenderViewHost* old_host,
- content::RenderViewHost* new_host) {
- if (GetFocusManager()->GetFocusedView() == this)
- web_contents_->GetView()->Focus();
-}
-
-void WebView::WebContentsDestroyed(content::WebContents* web_contents) {
- DCHECK(web_contents == web_contents_);
- SetWebContents(NULL);
+void WebView::ReattachForFullscreenChange(bool enter_fullscreen) {
+ DetachWebContents();
+ is_embedding_fullscreen_widget_ = enter_fullscreen &&
+ web_contents_ && web_contents_->GetFullscreenRenderWidgetHostView();
+ AttachWebContents();
}
content::WebContents* WebView::CreateWebContents(
diff --git a/chromium/ui/views/controls/webview/webview.h b/chromium/ui/views/controls/webview/webview.h
index cec510259e1..7e50914131c 100644
--- a/chromium/ui/views/controls/webview/webview.h
+++ b/chromium/ui/views/controls/webview/webview.h
@@ -10,6 +10,7 @@
#include "content/public/browser/notification_observer.h"
#include "content/public/browser/notification_registrar.h"
#include "content/public/browser/web_contents_delegate.h"
+#include "content/public/browser/web_contents_observer.h"
#include "ui/views/accessibility/native_view_accessibility.h"
#include "ui/views/controls/webview/webview_export.h"
#include "ui/views/view.h"
@@ -25,7 +26,7 @@ class NativeViewHost;
class WEBVIEW_EXPORT WebView : public View,
public content::NotificationObserver,
public content::WebContentsDelegate,
- public AccessibleWebView {
+ public content::WebContentsObserver {
public:
static const char kViewClassName[];
@@ -44,6 +45,12 @@ class WEBVIEW_EXPORT WebView : public View,
// those it implicitly creates via GetWebContents() above.
void SetWebContents(content::WebContents* web_contents);
+ // If |mode| is true, WebView will register itself with WebContents as a
+ // WebContentsObserver, monitor for the showing/destruction of fullscreen
+ // render widgets, and alter its child view hierarchy to embed the fullscreen
+ // widget or restore the normal WebContentsView.
+ void SetEmbedFullscreenWidgetMode(bool mode);
+
content::WebContents* web_contents() { return web_contents_; }
content::BrowserContext* browser_context() { return browser_context_; }
@@ -83,11 +90,6 @@ class WEBVIEW_EXPORT WebView : public View,
// Overridden from View:
virtual const char* GetClassName() const OVERRIDE;
- // Overridden from AccessibleWebView:
- virtual gfx::NativeViewAccessible AccessibleObjectFromChildId(
- long child_id) OVERRIDE;
- virtual View* AsView() OVERRIDE;
-
private:
// Overridden from View:
virtual void OnBoundsChanged(const gfx::Rect& previous_bounds) OVERRIDE;
@@ -109,13 +111,19 @@ class WEBVIEW_EXPORT WebView : public View,
// Overridden from content::WebContentsDelegate:
virtual void WebContentsFocused(content::WebContents* web_contents) OVERRIDE;
+ virtual bool EmbedsFullscreenWidget() const OVERRIDE;
+
+ // Overridden from content::WebContentsObserver:
+ virtual void DidShowFullscreenWidget(int routing_id) OVERRIDE;
+ virtual void DidDestroyFullscreenWidget(int routing_id) OVERRIDE;
+ // Workaround for MSVC++ linker bug/feature that requires
+ // instantiation of the inline IPC::Listener methods in all translation units.
+ virtual void OnChannelConnected(int32 peer_id) OVERRIDE {}
+ virtual void OnChannelError() OVERRIDE {}
void AttachWebContents();
void DetachWebContents();
-
- void RenderViewHostChanged(content::RenderViewHost* old_host,
- content::RenderViewHost* new_host);
- void WebContentsDestroyed(content::WebContents* web_contents);
+ void ReattachForFullscreenChange(bool enter_fullscreen);
// Create a regular or test web contents (based on whether we're running
// in a unit test or not).
@@ -126,6 +134,12 @@ class WEBVIEW_EXPORT WebView : public View,
NativeViewHost* wcv_holder_;
scoped_ptr<content::WebContents> wc_owner_;
content::WebContents* web_contents_;
+ // When true, WebView observes WebContents and auto-embeds fullscreen widgets
+ // as a child view.
+ bool embed_fullscreen_widget_mode_enabled_;
+ // Set to true while WebView is embedding a fullscreen widget view as a child
+ // view instead of the normal WebContentsView render view.
+ bool is_embedding_fullscreen_widget_;
content::BrowserContext* browser_context_;
content::NotificationRegistrar registrar_;
bool allow_accelerators_;
diff --git a/chromium/ui/views/corewm/capture_controller.cc b/chromium/ui/views/corewm/capture_controller.cc
new file mode 100644
index 00000000000..9a46988e626
--- /dev/null
+++ b/chromium/ui/views/corewm/capture_controller.cc
@@ -0,0 +1,139 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/corewm/capture_controller.h"
+
+#include "ui/aura/root_window.h"
+#include "ui/aura/window.h"
+
+namespace views {
+namespace corewm {
+
+////////////////////////////////////////////////////////////////////////////////
+// CaptureController, public:
+
+void CaptureController::Attach(aura::RootWindow* root) {
+ DCHECK_EQ(0u, root_windows_.count(root));
+ root_windows_.insert(root);
+ aura::client::SetCaptureClient(root, this);
+}
+
+void CaptureController::Detach(aura::RootWindow* root) {
+ CHECK(!root->Contains(capture_window_));
+ root_windows_.erase(root);
+ aura::client::SetCaptureClient(root, NULL);
+}
+
+////////////////////////////////////////////////////////////////////////////////
+// CaptureController, client::CaptureClient implementation:
+
+void CaptureController::SetCapture(aura::Window* new_capture_window) {
+ if (capture_window_ == new_capture_window)
+ return;
+
+ // Make sure window has a root window.
+ CHECK(!new_capture_window || new_capture_window->GetRootWindow());
+ CHECK(!capture_window_ || capture_window_->GetRootWindow());
+
+ aura::Window* old_capture_window = capture_window_;
+ aura::RootWindow* old_capture_root = old_capture_window ?
+ old_capture_window->GetRootWindow() : NULL;
+
+ // Copy the list in case it's modified out from under us.
+ RootWindows root_windows(root_windows_);
+
+ // If we're actually starting capture, then cancel any touches/gestures
+ // that aren't already locked to the new window, and transfer any on the
+ // old capture window to the new one. When capture is released we have no
+ // distinction between the touches/gestures that were in the window all
+ // along (and so shouldn't be canceled) and those that got moved, so
+ // just leave them all where they are.
+ if (new_capture_window) {
+ for (RootWindows::const_iterator i = root_windows.begin();
+ i != root_windows.end(); ++i) {
+ (*i)->gesture_recognizer()->TransferEventsTo(
+ old_capture_window, new_capture_window);
+ }
+ }
+
+ capture_window_ = new_capture_window;
+
+ for (RootWindows::const_iterator i = root_windows.begin();
+ i != root_windows.end(); ++i) {
+ (*i)->UpdateCapture(old_capture_window, new_capture_window);
+ }
+
+ aura::RootWindow* capture_root =
+ capture_window_ ? capture_window_->GetRootWindow() : NULL;
+ if (capture_root != old_capture_root) {
+ if (old_capture_root)
+ old_capture_root->ReleaseNativeCapture();
+ if (capture_root)
+ capture_root->SetNativeCapture();
+ }
+}
+
+void CaptureController::ReleaseCapture(aura::Window* window) {
+ if (capture_window_ != window)
+ return;
+ SetCapture(NULL);
+}
+
+aura::Window* CaptureController::GetCaptureWindow() {
+ return capture_window_;
+}
+
+////////////////////////////////////////////////////////////////////////////////
+// CaptureController, private:
+
+CaptureController::CaptureController()
+ : capture_window_(NULL) {
+}
+
+CaptureController::~CaptureController() {
+}
+
+////////////////////////////////////////////////////////////////////////////////
+// ScopedCaptureClient:
+
+// static
+CaptureController* ScopedCaptureClient::capture_controller_ = NULL;
+
+ScopedCaptureClient::ScopedCaptureClient(aura::RootWindow* root)
+ : root_window_(root) {
+ root->AddObserver(this);
+ if (!capture_controller_)
+ capture_controller_ = new CaptureController;
+ capture_controller_->Attach(root);
+}
+
+ScopedCaptureClient::~ScopedCaptureClient() {
+ Shutdown();
+}
+
+// static
+bool ScopedCaptureClient::IsActive() {
+ return capture_controller_ && capture_controller_->is_active();
+}
+
+void ScopedCaptureClient::OnWindowDestroyed(aura::Window* window) {
+ DCHECK_EQ(window, root_window_);
+ Shutdown();
+}
+
+void ScopedCaptureClient::Shutdown() {
+ if (!root_window_)
+ return;
+
+ root_window_->RemoveObserver(this);
+ capture_controller_->Detach(root_window_);
+ if (!capture_controller_->is_active()) {
+ delete capture_controller_;
+ capture_controller_ = NULL;
+ }
+ root_window_ = NULL;
+}
+
+} // namespace corewm
+} // namespace views
diff --git a/chromium/ui/views/corewm/capture_controller.h b/chromium/ui/views/corewm/capture_controller.h
new file mode 100644
index 00000000000..343c3c0a87b
--- /dev/null
+++ b/chromium/ui/views/corewm/capture_controller.h
@@ -0,0 +1,87 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_COREWM_CAPTURE_CONTROLLER_H_
+#define UI_VIEWS_COREWM_CAPTURE_CONTROLLER_H_
+
+#include <set>
+
+#include "base/basictypes.h"
+#include "base/compiler_specific.h"
+#include "ui/aura/client/capture_client.h"
+#include "ui/aura/window_observer.h"
+#include "ui/views/views_export.h"
+
+namespace views {
+namespace corewm {
+
+// Internal CaptureClient implementation. See ScopedCaptureClient for details.
+class VIEWS_EXPORT CaptureController : public aura::client::CaptureClient {
+ public:
+ // Adds |root| to the list of RootWindows notified when capture changes.
+ void Attach(aura::RootWindow* root);
+
+ // Removes |root| from the list of RootWindows notified when capture changes.
+ void Detach(aura::RootWindow* root);
+
+ // Returns true if this CaptureController is installed on at least one
+ // RootWindow.
+ bool is_active() const { return !root_windows_.empty(); }
+
+ // Overridden from aura::client::CaptureClient:
+ virtual void SetCapture(aura::Window* window) OVERRIDE;
+ virtual void ReleaseCapture(aura::Window* window) OVERRIDE;
+ virtual aura::Window* GetCaptureWindow() OVERRIDE;
+
+ private:
+ friend class ScopedCaptureClient;
+ typedef std::set<aura::RootWindow*> RootWindows;
+
+ CaptureController();
+ virtual ~CaptureController();
+
+ // The current capture window. NULL if there is no capture window.
+ aura::Window* capture_window_;
+
+ // Set of RootWindows notified when capture changes.
+ RootWindows root_windows_;
+
+ DISALLOW_COPY_AND_ASSIGN(CaptureController);
+};
+
+// ScopedCaptureClient is responsible for creating a CaptureClient for a
+// RootWindow. Specifically it creates a single CaptureController that is shared
+// among all ScopedCaptureClients and adds the RootWindow to it.
+class VIEWS_EXPORT ScopedCaptureClient : public aura::WindowObserver {
+ public:
+ explicit ScopedCaptureClient(aura::RootWindow* root);
+ virtual ~ScopedCaptureClient();
+
+ // Returns true if there is a CaptureController with at least one RootWindow.
+ static bool IsActive();
+
+ aura::client::CaptureClient* capture_client() {
+ return capture_controller_;
+ }
+
+ // Overridden from aura::WindowObserver:
+ virtual void OnWindowDestroyed(aura::Window* window) OVERRIDE;
+
+ private:
+ // Invoked from destructor and OnWindowDestroyed() to cleanup.
+ void Shutdown();
+
+ // The single CaptureController instance.
+ static CaptureController* capture_controller_;
+
+ // RootWindow this ScopedCaptureClient was create for.
+ aura::RootWindow* root_window_;
+
+ DISALLOW_COPY_AND_ASSIGN(ScopedCaptureClient);
+};
+
+} // namespace corewm
+} // namespace views
+
+#endif // UI_VIEWS_COREWM_CAPTURE_CONTROLLER_H_
diff --git a/chromium/ui/views/corewm/capture_controller_unittest.cc b/chromium/ui/views/corewm/capture_controller_unittest.cc
new file mode 100644
index 00000000000..46a8a2e4327
--- /dev/null
+++ b/chromium/ui/views/corewm/capture_controller_unittest.cc
@@ -0,0 +1,169 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/corewm/capture_controller.h"
+
+#include "base/logging.h"
+#include "ui/aura/env.h"
+#include "ui/aura/root_window.h"
+#include "ui/aura/test/aura_test_base.h"
+#include "ui/aura/test/event_generator.h"
+#include "ui/aura/test/test_screen.h"
+#include "ui/aura/test/test_window_delegate.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
+#include "ui/views/test/views_test_base.h"
+#include "ui/views/view.h"
+#include "ui/views/widget/root_view.h"
+#include "ui/views/widget/widget.h"
+
+#if !defined(OS_CHROMEOS)
+#include "ui/views/widget/desktop_aura/desktop_native_widget_aura.h"
+#include "ui/views/widget/desktop_aura/desktop_screen_position_client.h"
+#endif
+
+namespace views {
+
+class CaptureControllerTest : public aura::test::AuraTestBase {
+ public:
+ CaptureControllerTest() {}
+
+ virtual void SetUp() OVERRIDE {
+ AuraTestBase::SetUp();
+ capture_controller_.reset(new corewm::ScopedCaptureClient(root_window()));
+
+ second_root_.reset(new aura::RootWindow(
+ aura::RootWindow::CreateParams(gfx::Rect(0, 0, 800, 600))));
+ second_root_->Init();
+ second_root_->Show();
+ second_root_->SetHostSize(gfx::Size(800, 600));
+ second_capture_controller_.reset(
+ new corewm::ScopedCaptureClient(second_root_.get()));
+
+#if !defined(OS_CHROMEOS)
+ desktop_position_client_.reset(new DesktopScreenPositionClient());
+ aura::client::SetScreenPositionClient(root_window(),
+ desktop_position_client_.get());
+
+ second_desktop_position_client_.reset(new DesktopScreenPositionClient());
+ aura::client::SetScreenPositionClient(
+ second_root_.get(),
+ second_desktop_position_client_.get());
+#endif
+ }
+
+ virtual void TearDown() OVERRIDE {
+ RunAllPendingInMessageLoop();
+
+#if !defined(OS_CHROMEOS)
+ second_desktop_position_client_.reset();
+#endif
+ second_capture_controller_.reset();
+
+ // Kill any active compositors before we hit the compositor shutdown paths.
+ second_root_.reset();
+
+#if !defined(OS_CHROMEOS)
+ desktop_position_client_.reset();
+#endif
+ capture_controller_.reset();
+
+ AuraTestBase::TearDown();
+ }
+
+ aura::Window* GetCaptureWindow() {
+ return capture_controller_->capture_client()->GetCaptureWindow();
+ }
+
+ aura::Window* GetSecondCaptureWindow() {
+ return second_capture_controller_->capture_client()->GetCaptureWindow();
+ }
+
+ scoped_ptr<corewm::ScopedCaptureClient> capture_controller_;
+ scoped_ptr<aura::RootWindow> second_root_;
+ scoped_ptr<corewm::ScopedCaptureClient> second_capture_controller_;
+#if !defined(OS_CHROMEOS)
+ scoped_ptr<aura::client::ScreenPositionClient> desktop_position_client_;
+ scoped_ptr<aura::client::ScreenPositionClient>
+ second_desktop_position_client_;
+#endif
+
+ DISALLOW_COPY_AND_ASSIGN(CaptureControllerTest);
+};
+
+// Makes sure that internal details that are set on mouse down (such as
+// mouse_pressed_handler()) are cleared when another root window takes capture.
+TEST_F(CaptureControllerTest, ResetMouseEventHandlerOnCapture) {
+ // Create a window inside the RootWindow.
+ scoped_ptr<aura::Window> w1(CreateNormalWindow(1, root_window(), NULL));
+
+ // Make a synthesized mouse down event. Ensure that the RootWindow will
+ // dispatch further mouse events to |w1|.
+ ui::MouseEvent mouse_pressed_event(ui::ET_MOUSE_PRESSED, gfx::Point(5, 5),
+ gfx::Point(5, 5), 0);
+ root_window()->AsRootWindowHostDelegate()->OnHostMouseEvent(
+ &mouse_pressed_event);
+ EXPECT_EQ(w1.get(), root_window()->mouse_pressed_handler());
+
+ // Build a window in the second RootWindow.
+ scoped_ptr<aura::Window> w2(CreateNormalWindow(2, second_root_.get(), NULL));
+
+ // The act of having the second window take capture should clear out mouse
+ // pressed handler in the first RootWindow.
+ w2->SetCapture();
+ EXPECT_EQ(NULL, root_window()->mouse_pressed_handler());
+}
+
+// Makes sure that when one window gets capture, it forces the release on the
+// other. This is needed has to be handled explicitly on Linux, and is a sanity
+// check on Windows.
+TEST_F(CaptureControllerTest, ResetOtherWindowCaptureOnCapture) {
+ // Create a window inside the RootWindow.
+ scoped_ptr<aura::Window> w1(CreateNormalWindow(1, root_window(), NULL));
+ w1->SetCapture();
+ // Both capture clients should return the same capture window.
+ EXPECT_EQ(w1.get(), GetCaptureWindow());
+ EXPECT_EQ(w1.get(), GetSecondCaptureWindow());
+
+ // Build a window in the second RootWindow and give it capture. Both capture
+ // clients should return the same capture window.
+ scoped_ptr<aura::Window> w2(CreateNormalWindow(2, second_root_.get(), NULL));
+ w2->SetCapture();
+ EXPECT_EQ(w2.get(), GetCaptureWindow());
+ EXPECT_EQ(w2.get(), GetSecondCaptureWindow());
+}
+
+// Verifies the touch target for the RootWindow gets reset on releasing capture.
+TEST_F(CaptureControllerTest, TouchTargetResetOnCaptureChange) {
+ // Create a window inside the RootWindow.
+ scoped_ptr<aura::Window> w1(CreateNormalWindow(1, root_window(), NULL));
+ aura::test::EventGenerator event_generator1(root_window());
+ event_generator1.PressTouch();
+ w1->SetCapture();
+ // Both capture clients should return the same capture window.
+ EXPECT_EQ(w1.get(), GetCaptureWindow());
+ EXPECT_EQ(w1.get(), GetSecondCaptureWindow());
+
+ // Build a window in the second RootWindow and give it capture. Both capture
+ // clients should return the same capture window.
+ scoped_ptr<aura::Window> w2(CreateNormalWindow(2, second_root_.get(), NULL));
+ w2->SetCapture();
+ EXPECT_EQ(w2.get(), GetCaptureWindow());
+ EXPECT_EQ(w2.get(), GetSecondCaptureWindow());
+
+ // Release capture on the window. Releasing capture should reset the touch
+ // target of the first RootWindow (as it no longer contains the capture
+ // target).
+ w2->ReleaseCapture();
+ EXPECT_EQ(static_cast<aura::Window*>(NULL), GetCaptureWindow());
+ EXPECT_EQ(static_cast<aura::Window*>(NULL), GetSecondCaptureWindow());
+ ui::TouchEvent touch_event(
+ ui::ET_TOUCH_PRESSED, gfx::Point(), 0, 0, ui::EventTimeForNow(), 1.0f,
+ 1.0f, 1.0f, 1.0f);
+ EXPECT_EQ(static_cast<ui::GestureConsumer*>(NULL),
+ root_window()->gesture_recognizer()->GetTouchLockedTarget(
+ &touch_event));
+}
+
+} // namespace views
diff --git a/chromium/ui/views/corewm/compound_event_filter.cc b/chromium/ui/views/corewm/compound_event_filter.cc
index 91c15205f0d..1d4387b162e 100644
--- a/chromium/ui/views/corewm/compound_event_filter.cc
+++ b/chromium/ui/views/corewm/compound_event_filter.cc
@@ -5,6 +5,7 @@
#include "ui/views/corewm/compound_event_filter.h"
#include "base/containers/hash_tables.h"
+#include "base/logging.h"
#include "ui/aura/client/activation_client.h"
#include "ui/aura/client/cursor_client.h"
#include "ui/aura/client/drag_drop_client.h"
@@ -13,8 +14,8 @@
#include "ui/aura/root_window.h"
#include "ui/aura/window_delegate.h"
#include "ui/aura/window_tracker.h"
-#include "ui/base/events/event.h"
#include "ui/base/hit_test.h"
+#include "ui/events/event.h"
namespace views {
namespace corewm {
@@ -183,6 +184,12 @@ void CompoundEventFilter::SetCursorVisibilityOnEvent(aura::Window* target,
} else if (!show && !cursor_hidden_by_filter_) {
cursor_hidden_by_filter_ = true;
client->HideCursor();
+ } else if (show && !client->IsCursorVisible() && !client->IsCursorLocked()) {
+ // TODO(tdanderson): Remove this temporary logging once the issues related
+ // to a disappearing mouse cursor on the Pixel login screen / Pixel
+ // wakeup have been resolved. See crbug.com/275826.
+ LOG(ERROR) << "Event of type " << event->type() << " did not show cursor."
+ << " Mouse enabled state is " << client->IsMouseEventsEnabled();
}
}
diff --git a/chromium/ui/views/corewm/compound_event_filter.h b/chromium/ui/views/corewm/compound_event_filter.h
index e9c927f941a..15445cddb45 100644
--- a/chromium/ui/views/corewm/compound_event_filter.h
+++ b/chromium/ui/views/corewm/compound_event_filter.h
@@ -7,8 +7,8 @@
#include "base/compiler_specific.h"
#include "base/observer_list.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_handler.h"
+#include "ui/events/event.h"
+#include "ui/events/event_handler.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/views/views_export.h"
diff --git a/chromium/ui/views/corewm/compound_event_filter_unittest.cc b/chromium/ui/views/corewm/compound_event_filter_unittest.cc
index 07624c91ee0..a6569e2be40 100644
--- a/chromium/ui/views/corewm/compound_event_filter_unittest.cc
+++ b/chromium/ui/views/corewm/compound_event_filter_unittest.cc
@@ -13,8 +13,8 @@
#include "ui/aura/test/test_activation_client.h"
#include "ui/aura/test/test_cursor_client.h"
#include "ui/aura/test/test_windows.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
namespace {
diff --git a/chromium/ui/views/corewm/corewm_switches.cc b/chromium/ui/views/corewm/corewm_switches.cc
index 450738e6a21..8f0dd82a6a9 100644
--- a/chromium/ui/views/corewm/corewm_switches.cc
+++ b/chromium/ui/views/corewm/corewm_switches.cc
@@ -10,14 +10,6 @@ namespace views {
namespace corewm {
namespace switches {
-// When set uses the old ActivationController/FocusManager instead of the new
-// CoreWM FocusController.
-const char kDisableFocusController[] = "disable-focus-controller";
-
-// When set uses the FocusController in desktop mode.
-const char kDisableFocusControllerOnDesktop[] =
- "disable-focus-controller-on-desktop";
-
const char kNoDropShadows[] = "aura-no-shadows";
// If present animations are disabled.
@@ -25,16 +17,5 @@ const char kWindowAnimationsDisabled[] =
"views-corewm-window-animations-disabled";
} // namespace switches
-
-bool UseFocusController() {
- return !CommandLine::ForCurrentProcess()->HasSwitch(
- switches::kDisableFocusController);
-}
-
-bool UseFocusControllerOnDesktop() {
- return !CommandLine::ForCurrentProcess()->HasSwitch(
- switches::kDisableFocusControllerOnDesktop);
-}
-
} // namespace corewm
} // namespace views
diff --git a/chromium/ui/views/corewm/corewm_switches.h b/chromium/ui/views/corewm/corewm_switches.h
index a78088cd7ca..63c5251745d 100644
--- a/chromium/ui/views/corewm/corewm_switches.h
+++ b/chromium/ui/views/corewm/corewm_switches.h
@@ -21,14 +21,6 @@ VIEWS_EXPORT extern const char kNoDropShadows[];
VIEWS_EXPORT extern const char kWindowAnimationsDisabled[];
} // namespace switches
-
-// Returns true if the new FocusController should be used as the
-// Activation/FocusClient.
-VIEWS_EXPORT bool UseFocusController();
-
-// Same as above but for Desktop mode.
-VIEWS_EXPORT bool UseFocusControllerOnDesktop();
-
} // namespace corewm
} // namespace views
diff --git a/chromium/ui/views/corewm/cursor_manager.cc b/chromium/ui/views/corewm/cursor_manager.cc
index 5c4dc81fc7c..97a19ba93c3 100644
--- a/chromium/ui/views/corewm/cursor_manager.cc
+++ b/chromium/ui/views/corewm/cursor_manager.cc
@@ -23,6 +23,7 @@ class CursorState {
: cursor_(ui::kCursorNone),
visible_(true),
scale_(1.f),
+ cursor_set_(ui::CURSOR_SET_NORMAL),
mouse_events_enabled_(true),
visible_on_mouse_events_enabled_(true) {
}
@@ -42,6 +43,11 @@ class CursorState {
scale_ = scale;
}
+ ui::CursorSetType cursor_set() const { return cursor_set_; }
+ void set_cursor_set(ui::CursorSetType cursor_set) {
+ cursor_set_ = cursor_set;
+ }
+
bool mouse_events_enabled() const { return mouse_events_enabled_; }
void SetMouseEventsEnabled(bool enabled) {
if (mouse_events_enabled_ == enabled)
@@ -61,6 +67,7 @@ class CursorState {
gfx::NativeCursor cursor_;
bool visible_;
float scale_;
+ ui::CursorSetType cursor_set_;
bool mouse_events_enabled_;
// The visibility to set when mouse events are enabled.
@@ -119,10 +126,20 @@ void CursorManager::SetScale(float scale) {
delegate_->SetScale(state_on_unlock_->scale(), this);
}
+void CursorManager::SetCursorSet(ui::CursorSetType cursor_set) {
+ state_on_unlock_->set_cursor_set(cursor_set);
+ if (GetCurrentCursorSet() != state_on_unlock_->cursor_set())
+ delegate_->SetCursorSet(state_on_unlock_->cursor_set(), this);
+}
+
float CursorManager::GetCurrentScale() const {
return current_state_->scale();
}
+ui::CursorSetType CursorManager::GetCurrentCursorSet() const {
+ return current_state_->cursor_set();
+}
+
void CursorManager::EnableMouseEvents() {
state_on_unlock_->SetMouseEventsEnabled(true);
if (cursor_lock_count_ == 0 &&
@@ -172,6 +189,10 @@ void CursorManager::UnlockCursor() {
}
}
+bool CursorManager::IsCursorLocked() const {
+ return cursor_lock_count_ > 0;
+}
+
void CursorManager::AddObserver(
aura::client::CursorClientObserver* observer) {
observers_.AddObserver(observer);
@@ -208,6 +229,10 @@ void CursorManager::CommitScale(float scale) {
current_state_->set_scale(scale);
}
+void CursorManager::CommitCursorSet(ui::CursorSetType cursor_set) {
+ current_state_->set_cursor_set(cursor_set);
+}
+
void CursorManager::CommitMouseEventsEnabled(bool enabled) {
current_state_->SetMouseEventsEnabled(enabled);
}
diff --git a/chromium/ui/views/corewm/cursor_manager.h b/chromium/ui/views/corewm/cursor_manager.h
index 9e3164079df..1706ed8f7af 100644
--- a/chromium/ui/views/corewm/cursor_manager.h
+++ b/chromium/ui/views/corewm/cursor_manager.h
@@ -10,6 +10,7 @@
#include "base/memory/scoped_ptr.h"
#include "base/observer_list.h"
#include "ui/aura/client/cursor_client.h"
+#include "ui/base/cursor/cursor.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/point.h"
#include "ui/views/corewm/native_cursor_manager_delegate.h"
@@ -38,8 +39,6 @@ class VIEWS_EXPORT CursorManager : public aura::client::CursorClient,
CursorManager(scoped_ptr<NativeCursorManager> delegate);
virtual ~CursorManager();
- bool is_cursor_locked() const { return cursor_lock_count_ > 0; }
-
// Overridden from aura::client::CursorClient:
virtual void SetCursor(gfx::NativeCursor) OVERRIDE;
virtual void ShowCursor() OVERRIDE;
@@ -47,12 +46,15 @@ class VIEWS_EXPORT CursorManager : public aura::client::CursorClient,
virtual bool IsCursorVisible() const OVERRIDE;
virtual void SetScale(float scale) OVERRIDE;
virtual float GetCurrentScale() const OVERRIDE;
+ virtual void SetCursorSet(ui::CursorSetType cursor_set) OVERRIDE;
+ virtual ui::CursorSetType GetCurrentCursorSet() const OVERRIDE;
virtual void EnableMouseEvents() OVERRIDE;
virtual void DisableMouseEvents() OVERRIDE;
virtual bool IsMouseEventsEnabled() const OVERRIDE;
virtual void SetDisplay(const gfx::Display& display) OVERRIDE;
virtual void LockCursor() OVERRIDE;
virtual void UnlockCursor() OVERRIDE;
+ virtual bool IsCursorLocked() const OVERRIDE;
virtual void AddObserver(
aura::client::CursorClientObserver* observer) OVERRIDE;
virtual void RemoveObserver(
@@ -66,6 +68,7 @@ class VIEWS_EXPORT CursorManager : public aura::client::CursorClient,
virtual void CommitCursor(gfx::NativeCursor cursor) OVERRIDE;
virtual void CommitVisibility(bool visible) OVERRIDE;
virtual void CommitScale(float scale) OVERRIDE;
+ virtual void CommitCursorSet(ui::CursorSetType cursor_set) OVERRIDE;
virtual void CommitMouseEventsEnabled(bool enabled) OVERRIDE;
scoped_ptr<NativeCursorManager> delegate_;
diff --git a/chromium/ui/views/corewm/cursor_manager_unittest.cc b/chromium/ui/views/corewm/cursor_manager_unittest.cc
index 650d5b842b5..1e6a1650907 100644
--- a/chromium/ui/views/corewm/cursor_manager_unittest.cc
+++ b/chromium/ui/views/corewm/cursor_manager_unittest.cc
@@ -38,6 +38,12 @@ class TestingCursorManager : public views::corewm::NativeCursorManager {
delegate->CommitMouseEventsEnabled(enabled);
}
+ virtual void SetCursorSet(
+ ui::CursorSetType cursor_set,
+ views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE {
+ delegate->CommitCursorSet(cursor_set);
+ }
+
virtual void SetScale(
float scale,
views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE {
@@ -186,6 +192,19 @@ TEST_F(CursorManagerTest, EnableDisableMouseEvents) {
EXPECT_FALSE(cursor_manager_.IsMouseEventsEnabled());
}
+TEST_F(CursorManagerTest, SetCursorSet) {
+ EXPECT_EQ(ui::CURSOR_SET_NORMAL, cursor_manager_.GetCurrentCursorSet());
+
+ cursor_manager_.SetCursorSet(ui::CURSOR_SET_NORMAL);
+ EXPECT_EQ(ui::CURSOR_SET_NORMAL, cursor_manager_.GetCurrentCursorSet());
+
+ cursor_manager_.SetCursorSet(ui::CURSOR_SET_LARGE);
+ EXPECT_EQ(ui::CURSOR_SET_LARGE, cursor_manager_.GetCurrentCursorSet());
+
+ cursor_manager_.SetCursorSet(ui::CURSOR_SET_NORMAL);
+ EXPECT_EQ(ui::CURSOR_SET_NORMAL, cursor_manager_.GetCurrentCursorSet());
+}
+
TEST_F(CursorManagerTest, SetScale) {
EXPECT_EQ(1.f, cursor_manager_.GetCurrentScale());
cursor_manager_.SetScale(2.f);
diff --git a/chromium/ui/views/corewm/desktop_capture_controller_unittest.cc b/chromium/ui/views/corewm/desktop_capture_controller_unittest.cc
new file mode 100644
index 00000000000..4d50f68e291
--- /dev/null
+++ b/chromium/ui/views/corewm/desktop_capture_controller_unittest.cc
@@ -0,0 +1,176 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/corewm/capture_controller.h"
+
+#include "base/logging.h"
+#include "ui/aura/env.h"
+#include "ui/aura/root_window.h"
+#include "ui/aura/test/test_window_delegate.h"
+#include "ui/events/event.h"
+#include "ui/views/test/views_test_base.h"
+#include "ui/views/view.h"
+#include "ui/views/widget/desktop_aura/desktop_native_widget_aura.h"
+#include "ui/views/widget/desktop_aura/desktop_screen_position_client.h"
+#include "ui/views/widget/root_view.h"
+#include "ui/views/widget/widget.h"
+
+namespace views {
+
+typedef ViewsTestBase DesktopCaptureControllerTest;
+
+// NOTE: these tests do native capture, so they have to be in
+// interactive_ui_tests.
+
+// This class provides functionality to verify whether the View instance
+// received the gesture event.
+class DesktopViewInputTest : public View {
+ public:
+ DesktopViewInputTest()
+ : received_gesture_event_(false) {}
+
+ virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE {
+ received_gesture_event_ = true;
+ return View::OnGestureEvent(event);
+ }
+
+ // Resets state maintained by this class.
+ void Reset() {
+ received_gesture_event_ = false;
+ }
+
+ bool received_gesture_event() const { return received_gesture_event_; }
+
+ private:
+ bool received_gesture_event_;
+
+ DISALLOW_COPY_AND_ASSIGN(DesktopViewInputTest);
+};
+
+// Tests aura::Window capture and whether gesture events are sent to the window
+// which has capture.
+// The test case creates two visible widgets and sets capture to the underlying
+// aura::Windows one by one. It then sends a gesture event and validates whether
+// the window which had capture receives the gesture.
+TEST_F(DesktopCaptureControllerTest, CaptureWindowInputEventTest) {
+ scoped_ptr<aura::client::ScreenPositionClient> desktop_position_client1;
+ scoped_ptr<aura::client::ScreenPositionClient> desktop_position_client2;
+
+ scoped_ptr<Widget> widget1(new Widget());
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
+ scoped_ptr<corewm::ScopedCaptureClient> scoped_capture_client(
+ new corewm::ScopedCaptureClient(params.context->GetRootWindow()));
+ aura::client::CaptureClient* capture_client =
+ scoped_capture_client->capture_client();
+ params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ params.bounds = gfx::Rect(50, 50, 650, 650);
+ widget1->Init(params);
+ internal::RootView* root1 =
+ static_cast<internal::RootView*>(widget1->GetRootView());
+
+ desktop_position_client1.reset(new DesktopScreenPositionClient());
+ aura::client::SetScreenPositionClient(
+ widget1->GetNativeView()->GetRootWindow(),
+ desktop_position_client1.get());
+
+ DesktopViewInputTest* v1 = new DesktopViewInputTest();
+ v1->SetBoundsRect(gfx::Rect(0, 0, 300, 300));
+ root1->AddChildView(v1);
+ widget1->Show();
+
+ scoped_ptr<Widget> widget2(new Widget());
+
+ params = CreateParams(Widget::InitParams::TYPE_POPUP);
+ params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ params.bounds = gfx::Rect(50, 50, 650, 650);
+ widget2->Init(params);
+
+ internal::RootView* root2 =
+ static_cast<internal::RootView*>(widget2->GetRootView());
+ desktop_position_client2.reset(new DesktopScreenPositionClient());
+ aura::client::SetScreenPositionClient(
+ widget2->GetNativeView()->GetRootWindow(),
+ desktop_position_client2.get());
+
+ DesktopViewInputTest* v2 = new DesktopViewInputTest();
+ v2->SetBoundsRect(gfx::Rect(0, 0, 300, 300));
+ root2->AddChildView(v2);
+ widget2->Show();
+
+ EXPECT_FALSE(widget1->GetNativeView()->HasCapture());
+ EXPECT_FALSE(widget2->GetNativeView()->HasCapture());
+ EXPECT_EQ(reinterpret_cast<aura::Window*>(0),
+ capture_client->GetCaptureWindow());
+
+ widget1->GetNativeView()->SetCapture();
+ EXPECT_TRUE(widget1->GetNativeView()->HasCapture());
+ EXPECT_FALSE(widget2->GetNativeView()->HasCapture());
+ EXPECT_EQ(capture_client->GetCaptureWindow(), widget1->GetNativeView());
+
+ ui::GestureEvent g1(ui::ET_GESTURE_LONG_PRESS, 80, 80, 0,
+ base::TimeDelta(),
+ ui::GestureEventDetails(ui::ET_GESTURE_LONG_PRESS,
+ 0.0f, 0.0f), 0);
+ root1->DispatchGestureEvent(&g1);
+ EXPECT_TRUE(v1->received_gesture_event());
+ EXPECT_FALSE(v2->received_gesture_event());
+ v1->Reset();
+ v2->Reset();
+
+ widget2->GetNativeView()->SetCapture();
+
+ EXPECT_FALSE(widget1->GetNativeView()->HasCapture());
+ EXPECT_TRUE(widget2->GetNativeView()->HasCapture());
+ EXPECT_EQ(capture_client->GetCaptureWindow(), widget2->GetNativeView());
+
+ root2->DispatchGestureEvent(&g1);
+ EXPECT_TRUE(v2->received_gesture_event());
+ EXPECT_FALSE(v1->received_gesture_event());
+
+ widget1->CloseNow();
+ widget2->CloseNow();
+ RunPendingMessages();
+}
+
+// crbug.com/295342
+#if defined(OS_WIN)
+#define MAYBE_TransferOnCapture DISABLED_TransferOnCapture
+#else
+#define MAYBE_TransferOnCapture TransferOnCapture
+#endif
+// Verifies aura::RootWindow is correctly notified on capture changes.
+TEST_F(DesktopCaptureControllerTest, MAYBE_TransferOnCapture) {
+ Widget widget1;
+ Widget::InitParams params1 =
+ CreateParams(views::Widget::InitParams::TYPE_WINDOW);
+ params1.native_widget = new DesktopNativeWidgetAura(&widget1);
+ params1.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ widget1.Init(params1);
+ widget1.Show();
+
+ Widget widget2;
+ Widget::InitParams params2 =
+ CreateParams(views::Widget::InitParams::TYPE_WINDOW);
+ params2.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ params2.native_widget = new DesktopNativeWidgetAura(&widget2);
+ widget2.Init(params2);
+ widget2.Show();
+
+ // Set capture to |widget2|, then |widget1| and lastly release capture.
+ aura::Env::GetInstance()->set_mouse_button_flags(1);
+ widget2.SetCapture(widget2.GetRootView());
+ widget1.SetCapture(widget1.GetRootView());
+ widget1.ReleaseCapture();
+ // Widget1's RootWindow should still have a non-NULL |mouse_moved_handler_|
+ // (since it contains the view that had capture). OTOH Widget2 doesn't contain
+ // the Window that had capture and so its |mouse_moved_handler_| should be
+ // NULL.
+ EXPECT_NE(static_cast<aura::Window*>(NULL),
+ widget1.GetNativeView()->GetRootWindow()->mouse_moved_handler());
+ EXPECT_EQ(static_cast<aura::Window*>(NULL),
+ widget2.GetNativeView()->GetRootWindow()->mouse_moved_handler());
+ aura::Env::GetInstance()->set_mouse_button_flags(0);
+}
+
+} // namespace views
diff --git a/chromium/ui/views/corewm/focus_controller.cc b/chromium/ui/views/corewm/focus_controller.cc
index fc9c3136dfa..a5fe9c3a7a9 100644
--- a/chromium/ui/views/corewm/focus_controller.cc
+++ b/chromium/ui/views/corewm/focus_controller.cc
@@ -10,7 +10,7 @@
#include "ui/aura/client/capture_client.h"
#include "ui/aura/client/focus_change_observer.h"
#include "ui/aura/env.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/corewm/focus_rules.h"
namespace views {
@@ -130,9 +130,12 @@ void FocusController::FocusWindow(aura::Window* window) {
return;
}
- // We should not be messing with the focus if the window has capture.
- if (window && (aura::client::GetCaptureWindow(window) == window))
+ // We should not be messing with the focus if the window has capture, unless
+ // no has focus.
+ if (window && (aura::client::GetCaptureWindow(window) == window) &&
+ focused_window_) {
return;
+ }
// Focusing a window also activates its containing activatable window. Note
// that the rules could redirect activation activation and/or focus.
diff --git a/chromium/ui/views/corewm/focus_controller_unittest.cc b/chromium/ui/views/corewm/focus_controller_unittest.cc
index 62062f875c4..964fd588b48 100644
--- a/chromium/ui/views/corewm/focus_controller_unittest.cc
+++ b/chromium/ui/views/corewm/focus_controller_unittest.cc
@@ -18,7 +18,7 @@
#include "ui/aura/test/test_windows.h"
#include "ui/aura/window.h"
#include "ui/aura/window_tracker.h"
-#include "ui/base/events/event_handler.h"
+#include "ui/events/event_handler.h"
#include "ui/views/corewm/base_focus_rules.h"
namespace views {
@@ -268,7 +268,8 @@ class FocusControllerTestBase : public aura::test::AuraTestBase {
return aura::client::GetFocusClient(root_window())->GetFocusedWindow();
}
int GetFocusedWindowId() {
- return GetFocusedWindow()->id();
+ aura::Window* focused_window = GetFocusedWindow();
+ return focused_window ? focused_window->id() : -1;
}
void ActivateWindow(aura::Window* window) {
aura::client::GetActivationClient(root_window())->ActivateWindow(window);
@@ -303,6 +304,7 @@ class FocusControllerTestBase : public aura::test::AuraTestBase {
virtual void ShiftFocusOnActivationDueToHide() {}
virtual void NoShiftActiveOnActivation() {}
virtual void NoFocusChangeOnClickOnCaptureWindow() {}
+ virtual void ChangeFocusWhenNothingFocusedAndCaptured() {}
private:
scoped_ptr<FocusController> focus_controller_;
@@ -598,6 +600,24 @@ class FocusControllerDirectTestBase : public FocusControllerTestBase {
aura::client::GetCaptureClient(root_window())->ReleaseCapture(w2);
}
+ // Verifies focus change is honored while capture held.
+ virtual void ChangeFocusWhenNothingFocusedAndCaptured() OVERRIDE {
+ scoped_ptr<aura::client::DefaultCaptureClient> capture_client(
+ new aura::client::DefaultCaptureClient(root_window()));
+ aura::Window* w1 = root_window()->GetChildById(1);
+ aura::client::GetCaptureClient(root_window())->SetCapture(w1);
+
+ EXPECT_EQ(-1, GetActiveWindowId());
+ EXPECT_EQ(-1, GetFocusedWindowId());
+
+ FocusWindowById(1);
+
+ EXPECT_EQ(1, GetActiveWindowId());
+ EXPECT_EQ(1, GetFocusedWindowId());
+
+ aura::client::GetCaptureClient(root_window())->ReleaseCapture(w1);
+ }
+
private:
DISALLOW_COPY_AND_ASSIGN(FocusControllerDirectTestBase);
};
@@ -996,5 +1016,8 @@ DIRECT_FOCUS_CHANGE_TESTS(NoShiftActiveOnActivation);
// Clicking on a window which has capture should not result in a focus change.
DIRECT_FOCUS_CHANGE_TESTS(NoFocusChangeOnClickOnCaptureWindow);
+FOCUS_CONTROLLER_TEST(FocusControllerApiTest,
+ ChangeFocusWhenNothingFocusedAndCaptured);
+
} // namespace corewm
} // namespace views
diff --git a/chromium/ui/views/corewm/input_method_event_filter.cc b/chromium/ui/views/corewm/input_method_event_filter.cc
index f8e964735a9..cfdab6b7c67 100644
--- a/chromium/ui/views/corewm/input_method_event_filter.cc
+++ b/chromium/ui/views/corewm/input_method_event_filter.cc
@@ -6,9 +6,9 @@
#include "ui/aura/client/aura_constants.h"
#include "ui/aura/root_window.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/input_method.h"
#include "ui/base/ime/input_method_factory.h"
+#include "ui/events/event.h"
namespace views {
namespace corewm {
diff --git a/chromium/ui/views/corewm/input_method_event_filter.h b/chromium/ui/views/corewm/input_method_event_filter.h
index 56ef40e468c..cb1fae489c5 100644
--- a/chromium/ui/views/corewm/input_method_event_filter.h
+++ b/chromium/ui/views/corewm/input_method_event_filter.h
@@ -8,8 +8,8 @@
#include "base/basictypes.h"
#include "base/compiler_specific.h"
#include "base/memory/scoped_ptr.h"
-#include "ui/base/events/event_handler.h"
#include "ui/base/ime/input_method_delegate.h"
+#include "ui/events/event_handler.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/views/views_export.h"
diff --git a/chromium/ui/views/corewm/native_cursor_manager.h b/chromium/ui/views/corewm/native_cursor_manager.h
index c38fb344052..75e4c8580a5 100644
--- a/chromium/ui/views/corewm/native_cursor_manager.h
+++ b/chromium/ui/views/corewm/native_cursor_manager.h
@@ -48,6 +48,11 @@ class VIEWS_EXPORT NativeCursorManager {
float scale,
views::corewm::NativeCursorManagerDelegate* delegate) = 0;
+ // A request to set the scale of the cursor icon.
+ virtual void SetCursorSet(
+ ui::CursorSetType cursor_set,
+ views::corewm::NativeCursorManagerDelegate* delegate) = 0;
+
// A request to set whether mouse events are disabled. At minimum,
// implementer should call NativeCursorManagerDelegate::
// CommitMouseEventsEnabled() with whether mouse events are actually enabled.
diff --git a/chromium/ui/views/corewm/native_cursor_manager_delegate.h b/chromium/ui/views/corewm/native_cursor_manager_delegate.h
index 1e6d46a83de..ea3788f883f 100644
--- a/chromium/ui/views/corewm/native_cursor_manager_delegate.h
+++ b/chromium/ui/views/corewm/native_cursor_manager_delegate.h
@@ -5,6 +5,7 @@
#ifndef UI_VIEWS_COREWM_NATIVE_CURSOR_MANAGER_DELEGATE_H_
#define UI_VIEWS_COREWM_NATIVE_CURSOR_MANAGER_DELEGATE_H_
+#include "ui/base/cursor/cursor.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/views/views_export.h"
@@ -21,11 +22,13 @@ class VIEWS_EXPORT NativeCursorManagerDelegate {
virtual gfx::NativeCursor GetCurrentCursor() const = 0;
virtual bool GetCurrentVisibility() const = 0;
virtual float GetCurrentScale() const = 0;
+ virtual ui::CursorSetType GetCurrentCursorSet() const = 0;
virtual bool GetMouseEventsEnabled() const = 0;
virtual void CommitCursor(gfx::NativeCursor cursor) = 0;
virtual void CommitVisibility(bool visible) = 0;
virtual void CommitScale(float scale) = 0;
+ virtual void CommitCursorSet(ui::CursorSetType cursor_set) = 0;
virtual void CommitMouseEventsEnabled(bool enabled) = 0;
};
diff --git a/chromium/ui/views/corewm/tooltip_controller.cc b/chromium/ui/views/corewm/tooltip_controller.cc
index 7e3d262b4f4..54b4f7ae04a 100644
--- a/chromium/ui/views/corewm/tooltip_controller.cc
+++ b/chromium/ui/views/corewm/tooltip_controller.cc
@@ -15,13 +15,13 @@
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
#include "ui/aura/window.h"
-#include "ui/base/events/event.h"
#include "ui/base/resource/resource_bundle.h"
-#include "ui/base/text/text_elider.h"
+#include "ui/events/event.h"
#include "ui/gfx/font.h"
#include "ui/gfx/point.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/screen.h"
+#include "ui/gfx/text_elider.h"
#include "ui/views/background.h"
#include "ui/views/border.h"
#include "ui/views/controls/label.h"
@@ -102,10 +102,7 @@ class TooltipController::Tooltip : public views::WidgetObserver {
}
virtual ~Tooltip() {
- if (widget_) {
- widget_->RemoveObserver(this);
- widget_->Close();
- }
+ DestroyWidget();
}
// Updates the text on the tooltip and resizes to fit.
@@ -126,7 +123,7 @@ class TooltipController::Tooltip : public views::WidgetObserver {
width += 2 * kTooltipBorderWidth;
height += 2 * kTooltipBorderWidth;
}
- CreateWidgetIfNecessary(window);
+ GetWidgetForWindow(window);
SetTooltipBounds(location, width, height);
}
@@ -180,14 +177,30 @@ class TooltipController::Tooltip : public views::WidgetObserver {
widget_->SetBounds(tooltip_rect);
}
- void CreateWidgetIfNecessary(aura::Window* tooltip_window) {
- if (widget_)
- return;
+ void GetWidgetForWindow(aura::Window* tooltip_window) {
+ if (widget_) {
+ // If the window for which the tooltip is being displayed changes and if
+ // the tooltip window and the tooltip widget belong to different
+ // rootwindows then we need to recreate the tooltip widget under the
+ // active root window hierarchy to get it to display.
+ if (widget_->GetNativeWindow()->GetRootWindow() ==
+ tooltip_window->GetRootWindow())
+ return;
+ DestroyWidget();
+ }
widget_ = CreateTooltip(tooltip_window);
widget_->SetContentsView(&label_);
widget_->AddObserver(this);
}
+ void DestroyWidget() {
+ if (widget_) {
+ widget_->RemoveObserver(this);
+ widget_->Close();
+ widget_ = NULL;
+ }
+ }
+
views::Label label_;
TooltipController* controller_;
views::Widget* widget_;
@@ -256,13 +269,17 @@ void TooltipController::OnKeyEvent(ui::KeyEvent* event) {
void TooltipController::OnMouseEvent(ui::MouseEvent* event) {
aura::Window* target = static_cast<aura::Window*>(event->target());
switch (event->type()) {
+ case ui::ET_MOUSE_EXITED:
+ target = NULL;
+ // Fall through.
case ui::ET_MOUSE_MOVED:
case ui::ET_MOUSE_DRAGGED:
if (tooltip_window_ != target) {
if (tooltip_window_)
tooltip_window_->RemoveObserver(this);
tooltip_window_ = target;
- tooltip_window_->AddObserver(this);
+ if (tooltip_window_)
+ tooltip_window_->AddObserver(this);
}
curr_mouse_loc_ = event->location();
if (tooltip_timer_.IsRunning())
@@ -403,7 +420,7 @@ void TooltipController::TrimTooltipToFit(int max_width,
if (result_lines.size() > kMaxLines) {
result_lines.resize(kMaxLines);
// Add ellipses character to last line.
- result_lines[kMaxLines - 1] = ui::TruncateString(
+ result_lines[kMaxLines - 1] = gfx::TruncateString(
result_lines.back(), result_lines.back().length() - 1);
}
*line_count = result_lines.size();
@@ -420,7 +437,8 @@ void TooltipController::TrimTooltipToFit(int max_width,
// case, we simply truncate at available_width and add ellipses at the end.
if (line_width > available_width) {
*width = available_width;
- result.append(ui::ElideText(*l, font, available_width, ui::ELIDE_AT_END));
+ result.append(gfx::ElideText(*l, font, available_width,
+ gfx::ELIDE_AT_END));
} else {
*width = std::max(*width, line_width);
result.append(*l);
diff --git a/chromium/ui/views/corewm/tooltip_controller.h b/chromium/ui/views/corewm/tooltip_controller.h
index cc641d05ebc..9cd04d3cb8a 100644
--- a/chromium/ui/views/corewm/tooltip_controller.h
+++ b/chromium/ui/views/corewm/tooltip_controller.h
@@ -12,7 +12,7 @@
#include "base/timer/timer.h"
#include "ui/aura/client/tooltip_client.h"
#include "ui/aura/window_observer.h"
-#include "ui/base/events/event_handler.h"
+#include "ui/events/event_handler.h"
#include "ui/gfx/point.h"
#include "ui/gfx/screen_type_delegate.h"
#include "ui/views/views_export.h"
diff --git a/chromium/ui/views/corewm/tooltip_controller_unittest.cc b/chromium/ui/views/corewm/tooltip_controller_unittest.cc
index 5cb3fe6b9db..efe561d7a5b 100644
--- a/chromium/ui/views/corewm/tooltip_controller_unittest.cc
+++ b/chromium/ui/views/corewm/tooltip_controller_unittest.cc
@@ -7,15 +7,16 @@
#include "base/strings/utf_string_conversions.h"
#include "ui/aura/client/cursor_client.h"
#include "ui/aura/client/tooltip_client.h"
+#include "ui/aura/client/window_types.h"
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
#include "ui/aura/test/aura_test_base.h"
#include "ui/aura/test/event_generator.h"
#include "ui/aura/window.h"
#include "ui/base/resource/resource_bundle.h"
-#include "ui/base/text/text_elider.h"
#include "ui/gfx/font.h"
#include "ui/gfx/point.h"
+#include "ui/gfx/text_elider.h"
#include "ui/views/corewm/tooltip_controller_test_helper.h"
#include "ui/views/view.h"
#include "ui/views/widget/widget.h"
@@ -274,8 +275,8 @@ TEST_F(TooltipControllerTest, TrimTooltipToFitTests) {
max_width, &tooltip, &width, &line_count);
EXPECT_NEAR(max_pixel_width, width, 5);
EXPECT_EQ(1, line_count);
- EXPECT_EQ(ui::ElideText(UTF8ToUTF16(std::string('a', max_pixel_width)), font,
- max_pixel_width, ui::ELIDE_AT_END), tooltip);
+ EXPECT_EQ(gfx::ElideText(UTF8ToUTF16(std::string('a', max_pixel_width)), font,
+ max_pixel_width, gfx::ELIDE_AT_END), tooltip);
#endif
// Normal small tooltip should stay as is.
@@ -409,6 +410,138 @@ TEST_F(TooltipControllerTest, TooltipHidesOnTimeoutAndStaysHiddenUntilChange) {
EXPECT_EQ(window, helper_->GetTooltipWindow());
}
+// Verifies a mouse exit event hides the tooltips.
+TEST_F(TooltipControllerTest, HideOnExit) {
+ view_->set_tooltip_text(ASCIIToUTF16("Tooltip Text"));
+ generator_->MoveMouseToCenterOf(GetWindow());
+ string16 expected_tooltip = ASCIIToUTF16("Tooltip Text");
+ EXPECT_EQ(expected_tooltip, aura::client::GetTooltipText(GetWindow()));
+ EXPECT_EQ(string16(), helper_->GetTooltipText());
+ EXPECT_EQ(GetWindow(), helper_->GetTooltipWindow());
+
+ // Fire tooltip timer so tooltip becomes visible.
+ helper_->FireTooltipTimer();
+
+ EXPECT_TRUE(helper_->IsTooltipVisible());
+ generator_->SendMouseExit();
+ EXPECT_FALSE(helper_->IsTooltipVisible());
+}
+
+#if !defined(OS_CHROMEOS)
+// This test creates two top level windows and verifies that the tooltip
+// displays correctly when mouse moves are dispatched to these windows.
+// Additionally it also verifies that the tooltip is reparented to the new
+// window when mouse moves are dispatched to it.
+TEST_F(TooltipControllerTest, TooltipsInMultipleRootWindows) {
+ view_->set_tooltip_text(ASCIIToUTF16("Tooltip Text For RootWindow1"));
+ EXPECT_EQ(string16(), helper_->GetTooltipText());
+ EXPECT_EQ(NULL, helper_->GetTooltipWindow());
+
+ aura::Window* window = GetWindow();
+ aura::RootWindow* root_window = GetRootWindow();
+
+ // Fire tooltip timer so tooltip becomes visible.
+ generator_->MoveMouseRelativeTo(window, view_->bounds().CenterPoint());
+ helper_->FireTooltipTimer();
+ EXPECT_TRUE(helper_->IsTooltipVisible());
+ for (int i = 0; i < 49; ++i) {
+ generator_->MoveMouseBy(1, 0);
+ EXPECT_TRUE(helper_->IsTooltipVisible());
+ EXPECT_EQ(window, root_window->GetEventHandlerForPoint(
+ generator_->current_location()));
+ string16 expected_tooltip =
+ ASCIIToUTF16("Tooltip Text For RootWindow1");
+ EXPECT_EQ(expected_tooltip, aura::client::GetTooltipText(window));
+ EXPECT_EQ(expected_tooltip, helper_->GetTooltipText());
+ EXPECT_EQ(window, helper_->GetTooltipWindow());
+ }
+
+ views::Widget* widget2 = CreateWidget(NULL);
+ widget2->SetContentsView(new View);
+ TooltipTestView* view2 = new TooltipTestView;
+ widget2->GetContentsView()->AddChildView(view2);
+ view2->SetBoundsRect(widget2->GetContentsView()->GetLocalBounds());
+ helper_.reset(new TooltipControllerTestHelper(
+ GetController(widget2)));
+ generator_.reset(new aura::test::EventGenerator(
+ widget2->GetNativeWindow()->GetRootWindow()));
+ view2->set_tooltip_text(ASCIIToUTF16("Tooltip Text For RootWindow2"));
+
+ aura::Window* window2 = widget2->GetNativeWindow();
+ aura::RootWindow* root_window2 =
+ widget2->GetNativeWindow()->GetRootWindow();
+ // Fire tooltip timer so tooltip becomes visible.
+ generator_->MoveMouseRelativeTo(window2, view2->bounds().CenterPoint());
+ helper_->FireTooltipTimer();
+
+ EXPECT_NE(root_window, root_window2);
+ EXPECT_NE(window, window2);
+
+ for (int i = 0; i < 49; ++i) {
+ generator_->MoveMouseBy(1, 0);
+ EXPECT_TRUE(helper_->IsTooltipVisible());
+ EXPECT_EQ(window2, root_window2->GetEventHandlerForPoint(
+ generator_->current_location()));
+ string16 expected_tooltip = ASCIIToUTF16("Tooltip Text For RootWindow2");
+ EXPECT_EQ(expected_tooltip, aura::client::GetTooltipText(window2));
+ EXPECT_EQ(expected_tooltip, helper_->GetTooltipText());
+ EXPECT_EQ(window2, helper_->GetTooltipWindow());
+ }
+
+ bool tooltip_reparented = false;
+ for (size_t i = 0; i < root_window2->children().size(); ++i) {
+ if (root_window2->children()[i]->type() ==
+ aura::client::WINDOW_TYPE_TOOLTIP) {
+ tooltip_reparented = true;
+ break;
+ }
+ }
+ EXPECT_TRUE(tooltip_reparented);
+ widget2->Close();
+}
+
+// This test validates whether the tooltip after becoming visible stays at the
+// top of the ZOrder in its root window after activation changes.
+TEST_F(TooltipControllerTest, TooltipAtTopOfZOrderAfterActivation) {
+ view_->set_tooltip_text(ASCIIToUTF16("Tooltip Text"));
+ EXPECT_EQ(string16(), helper_->GetTooltipText());
+ EXPECT_EQ(NULL, helper_->GetTooltipWindow());
+ generator_->MoveMouseToCenterOf(GetWindow());
+
+ EXPECT_EQ(GetWindow(), GetRootWindow()->GetEventHandlerForPoint(
+ generator_->current_location()));
+ string16 expected_tooltip = ASCIIToUTF16("Tooltip Text");
+ EXPECT_EQ(expected_tooltip, aura::client::GetTooltipText(GetWindow()));
+ EXPECT_EQ(string16(), helper_->GetTooltipText());
+ EXPECT_EQ(GetWindow(), helper_->GetTooltipWindow());
+
+ // Fire tooltip timer so tooltip becomes visible.
+ helper_->FireTooltipTimer();
+
+ EXPECT_TRUE(helper_->IsTooltipVisible());
+ generator_->MoveMouseBy(1, 0);
+
+ EXPECT_TRUE(helper_->IsTooltipVisible());
+ EXPECT_EQ(expected_tooltip, aura::client::GetTooltipText(GetWindow()));
+ EXPECT_EQ(expected_tooltip, helper_->GetTooltipText());
+ EXPECT_EQ(GetWindow(), helper_->GetTooltipWindow());
+
+ // Fake activation loss and gain in the native widget. This should cause a
+ // ZOrder change which should not affect the position of the tooltip.
+ DesktopNativeWidgetAura* native_widget =
+ static_cast<DesktopNativeWidgetAura*>(widget_->native_widget());
+ EXPECT_TRUE(native_widget != NULL);
+
+ native_widget->HandleActivationChanged(false);
+ native_widget->HandleActivationChanged(true);
+
+ EXPECT_EQ(
+ widget_->GetNativeWindow()->GetRootWindow()->children().back()->type(),
+ aura::client::WINDOW_TYPE_TOOLTIP);
+}
+
+#endif
+
} // namespace test
} // namespace corewm
} // namespace views
diff --git a/chromium/ui/views/corewm/window_animations.cc b/chromium/ui/views/corewm/window_animations.cc
index f346e22a5b5..84759fe6f6b 100644
--- a/chromium/ui/views/corewm/window_animations.cc
+++ b/chromium/ui/views/corewm/window_animations.cc
@@ -336,7 +336,7 @@ ui::LayerAnimationElement* CreateGrowShrinkElement(
base::TimeDelta::FromMilliseconds(
kWindowAnimation_Bounce_DurationMS *
kWindowAnimation_Bounce_GrowShrinkDurationPercent / 100)));
- transition->set_tween_type(grow ? ui::Tween::EASE_OUT : ui::Tween::EASE_IN);
+ transition->set_tween_type(grow ? gfx::Tween::EASE_OUT : gfx::Tween::EASE_IN);
return transition.release();
}
@@ -380,7 +380,7 @@ void AddLayerAnimationsForRotate(aura::Window* window, bool show) {
ui::LayerAnimationElement::CreateOpacityElement(
show ? kWindowAnimation_ShowOpacity : kWindowAnimation_HideOpacity,
duration * kWindowAnimation_Rotate_OpacityDurationPercent / 100));
- opacity->set_tween_type(ui::Tween::EASE_IN_OUT);
+ opacity->set_tween_type(gfx::Tween::EASE_IN_OUT);
window->layer()->GetAnimator()->ScheduleAnimation(
new ui::LayerAnimationSequence(opacity.release()));
diff --git a/chromium/ui/views/corewm/window_animations_unittest.cc b/chromium/ui/views/corewm/window_animations_unittest.cc
index 26fda675af7..5332c7d7d50 100644
--- a/chromium/ui/views/corewm/window_animations_unittest.cc
+++ b/chromium/ui/views/corewm/window_animations_unittest.cc
@@ -9,10 +9,10 @@
#include "ui/aura/test/aura_test_base.h"
#include "ui/aura/test/test_windows.h"
#include "ui/aura/window.h"
-#include "ui/base/animation/animation_container_element.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animator.h"
#include "ui/compositor/scoped_animation_duration_scale_mode.h"
+#include "ui/gfx/animation/animation_container_element.h"
using aura::Window;
using ui::Layer;
diff --git a/chromium/ui/views/corewm/window_modality_controller.cc b/chromium/ui/views/corewm/window_modality_controller.cc
index 6afc7d2c20e..8a3a7ff2040 100644
--- a/chromium/ui/views/corewm/window_modality_controller.cc
+++ b/chromium/ui/views/corewm/window_modality_controller.cc
@@ -12,8 +12,8 @@
#include "ui/aura/root_window.h"
#include "ui/aura/window.h"
#include "ui/aura/window_property.h"
-#include "ui/base/events/event.h"
#include "ui/base/ui_base_types.h"
+#include "ui/events/event.h"
#include "ui/views/corewm/window_animations.h"
#include "ui/views/corewm/window_util.h"
diff --git a/chromium/ui/views/corewm/window_modality_controller.h b/chromium/ui/views/corewm/window_modality_controller.h
index 4787a97a71f..07fe308e0df 100644
--- a/chromium/ui/views/corewm/window_modality_controller.h
+++ b/chromium/ui/views/corewm/window_modality_controller.h
@@ -10,7 +10,7 @@
#include "base/compiler_specific.h"
#include "ui/aura/env_observer.h"
#include "ui/aura/window_observer.h"
-#include "ui/base/events/event_handler.h"
+#include "ui/events/event_handler.h"
#include "ui/views/views_export.h"
namespace ui {
diff --git a/chromium/ui/views/event_utils.h b/chromium/ui/views/event_utils.h
new file mode 100644
index 00000000000..3527c507d4e
--- /dev/null
+++ b/chromium/ui/views/event_utils.h
@@ -0,0 +1,25 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_EVENT_UTILS_H_
+#define UI_VIEWS_EVENT_UTILS_H_
+
+#include "ui/gfx/native_widget_types.h"
+#include "ui/views/views_export.h"
+
+namespace ui {
+class LocatedEvent;
+}
+
+namespace views {
+
+// Reposts a located event natively. Returns false when |event| could not be
+// reposted. |event| should be in screen coordinates. |window| is the target
+// window that the event will be forwarded to. Only some events are supported.
+VIEWS_EXPORT bool RepostLocatedEvent(gfx::NativeWindow window,
+ const ui::LocatedEvent& event);
+
+} // namespace views
+
+#endif // UI_VIEWS_EVENT_UTILS_H_
diff --git a/chromium/ui/views/event_utils_aura.cc b/chromium/ui/views/event_utils_aura.cc
new file mode 100644
index 00000000000..54e81246264
--- /dev/null
+++ b/chromium/ui/views/event_utils_aura.cc
@@ -0,0 +1,51 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/event_utils.h"
+
+#include "base/logging.h"
+#include "base/memory/scoped_ptr.h"
+#include "ui/aura/client/screen_position_client.h"
+#include "ui/aura/root_window.h"
+#include "ui/events/event.h"
+#include "ui/gfx/point.h"
+
+using aura::client::ScreenPositionClient;
+
+namespace views {
+
+bool RepostLocatedEvent(gfx::NativeWindow window,
+ const ui::LocatedEvent& event) {
+ if (!window)
+ return false;
+
+ aura::RootWindow* root_window = window->GetRootWindow();
+
+ gfx::Point root_loc(event.location());
+ ScreenPositionClient* spc = GetScreenPositionClient(root_window);
+ if (!spc)
+ return false;
+
+ spc->ConvertPointFromScreen(root_window, &root_loc);
+
+ scoped_ptr<ui::LocatedEvent> relocated;
+ if (event.IsMouseEvent()) {
+ const ui::MouseEvent& orig = static_cast<const ui::MouseEvent&>(event);
+ relocated.reset(new ui::MouseEvent(orig));
+ } else if (event.IsGestureEvent()) {
+ // TODO(rbyers): Gesture event repost is tricky to get right
+ // crbug.com/170987.
+ return false;
+ } else {
+ NOTREACHED();
+ return false;
+ }
+ relocated->set_location(root_loc);
+ relocated->set_root_location(root_loc);
+
+ root_window->RepostEvent(*relocated);
+ return true;
+}
+
+} // namespace views
diff --git a/chromium/ui/views/event_utils_win.cc b/chromium/ui/views/event_utils_win.cc
new file mode 100644
index 00000000000..38c05c988fa
--- /dev/null
+++ b/chromium/ui/views/event_utils_win.cc
@@ -0,0 +1,59 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/event_utils.h"
+
+#include <windowsx.h>
+
+#include "base/logging.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
+#include "ui/gfx/point.h"
+
+namespace views {
+
+bool RepostLocatedEvent(gfx::NativeWindow window,
+ const ui::LocatedEvent& event) {
+ if (!window)
+ return false;
+
+ // Determine whether the click was in the client area or not.
+ // NOTE: WM_NCHITTEST coordinates are relative to the screen.
+ const gfx::Point screen_loc = event.location();
+ LRESULT nc_hit_result = SendMessage(window, WM_NCHITTEST, 0,
+ MAKELPARAM(screen_loc.x(),
+ screen_loc.y()));
+ const bool in_client_area = nc_hit_result == HTCLIENT;
+
+ // TODO(sky): this isn't right. The event to generate should correspond with
+ // the event we just got. MouseEvent only tells us what is down, which may
+ // differ. Need to add ability to get changed button from MouseEvent.
+ int event_type;
+ int flags = event.flags();
+ if (flags & ui::EF_LEFT_MOUSE_BUTTON) {
+ event_type = in_client_area ? WM_LBUTTONDOWN : WM_NCLBUTTONDOWN;
+ } else if (flags & ui::EF_MIDDLE_MOUSE_BUTTON) {
+ event_type = in_client_area ? WM_MBUTTONDOWN : WM_NCMBUTTONDOWN;
+ } else if (flags & ui::EF_RIGHT_MOUSE_BUTTON) {
+ event_type = in_client_area ? WM_RBUTTONDOWN : WM_NCRBUTTONDOWN;
+ } else {
+ NOTREACHED();
+ return false;
+ }
+
+ int window_x = screen_loc.x();
+ int window_y = screen_loc.y();
+ if (in_client_area) {
+ RECT window_bounds;
+ GetWindowRect(window, &window_bounds);
+ window_x -= window_bounds.left;
+ window_y -= window_bounds.top;
+ }
+
+ WPARAM target = in_client_area ? event.native_event().wParam : nc_hit_result;
+ PostMessage(window, event_type, target, MAKELPARAM(window_x, window_y));
+ return true;
+}
+
+} // namespace views
diff --git a/chromium/ui/views/examples/content_client/examples_browser_main_parts.cc b/chromium/ui/views/examples/content_client/examples_browser_main_parts.cc
index d357e7699ac..2cea5ef3b31 100644
--- a/chromium/ui/views/examples/content_client/examples_browser_main_parts.cc
+++ b/chromium/ui/views/examples/content_client/examples_browser_main_parts.cc
@@ -12,7 +12,7 @@
#include "base/threading/thread.h"
#include "base/threading/thread_restrictions.h"
#include "content/public/common/content_switches.h"
-#include "content/shell/shell_browser_context.h"
+#include "content/shell/browser/shell_browser_context.h"
#include "ui/views/examples/examples_window_with_content.h"
#include "ui/views/focus/accelerator_handler.h"
#include "ui/views/test/desktop_test_views_delegate.h"
diff --git a/chromium/ui/views/examples/example_base.h b/chromium/ui/views/examples/example_base.h
index f28fdefba1e..a17cc0d0f91 100644
--- a/chromium/ui/views/examples/example_base.h
+++ b/chromium/ui/views/examples/example_base.h
@@ -27,6 +27,8 @@ class ExampleBase {
protected:
explicit ExampleBase(const char* title);
+ View* container() { return container_; }
+
// Prints a message in the status area, at the bottom of the window.
void PrintStatus(const char* format, ...);
diff --git a/chromium/ui/views/examples/multiline_example.cc b/chromium/ui/views/examples/multiline_example.cc
index 8d13bf510c6..dd8a633c9ae 100644
--- a/chromium/ui/views/examples/multiline_example.cc
+++ b/chromium/ui/views/examples/multiline_example.cc
@@ -5,7 +5,7 @@
#include "ui/views/examples/multiline_example.h"
#include "base/strings/utf_string_conversions.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/gfx/render_text.h"
#include "ui/views/controls/label.h"
#include "ui/views/controls/textfield/textfield.h"
@@ -18,9 +18,10 @@ namespace examples {
// A simple View that hosts a RenderText object.
class MultilineExample::RenderTextView : public View {
public:
- explicit RenderTextView(gfx::RenderText* render_text)
- : render_text_(render_text) {
+ RenderTextView() : render_text_(gfx::RenderText::CreateInstance()) {
+ render_text_->SetHorizontalAlignment(gfx::ALIGN_CENTER);
render_text_->SetColor(SK_ColorBLACK);
+ render_text_->SetMultiline(true);
set_border(Border::CreateSolidBorder(2, SK_ColorGRAY));
}
@@ -30,13 +31,40 @@ class MultilineExample::RenderTextView : public View {
}
virtual gfx::Size GetPreferredSize() OVERRIDE {
- return gfx::Size(0,
- render_text_->font_list().GetHeight() + GetInsets().height());
+ // Turn off multiline mode to get the single-line text size, which is the
+ // preferred size for this view.
+ render_text_->SetMultiline(false);
+ gfx::Size size(render_text_->GetContentWidth(),
+ render_text_->GetStringSize().height());
+ size.Enlarge(GetInsets().width(), GetInsets().height());
+ render_text_->SetMultiline(true);
+ return size;
+ }
+
+ virtual int GetHeightForWidth(int w) OVERRIDE {
+ // TODO(ckocagil): Why does this happen?
+ if (w == 0)
+ return View::GetHeightForWidth(w);
+ gfx::Rect rect = render_text_->display_rect();
+ rect.set_width(w - GetInsets().width());
+ render_text_->SetDisplayRect(rect);
+ return render_text_->GetStringSize().height() + GetInsets().height();
}
void SetText(const string16& new_contents) {
+ // Color and style the text inside |test_range| to test colors and styles.
+ gfx::Range test_range(1, 21);
+ test_range.set_start(std::min(test_range.start(), new_contents.length()));
+ test_range.set_end(std::min(test_range.end(), new_contents.length()));
+
render_text_->SetText(new_contents);
- SchedulePaint();
+ render_text_->SetColor(SK_ColorBLACK);
+ render_text_->ApplyColor(0xFFFF0000, test_range);
+ render_text_->SetStyle(gfx::DIAGONAL_STRIKE, false);
+ render_text_->ApplyStyle(gfx::DIAGONAL_STRIKE, true, test_range);
+ render_text_->SetStyle(gfx::UNDERLINE, false);
+ render_text_->ApplyStyle(gfx::UNDERLINE, true, test_range);
+ InvalidateLayout();
}
private:
@@ -55,7 +83,8 @@ MultilineExample::MultilineExample()
: ExampleBase("Multiline RenderText"),
render_text_view_(NULL),
label_(NULL),
- textfield_(NULL) {
+ textfield_(NULL),
+ label_checkbox_(NULL) {
}
MultilineExample::~MultilineExample() {
@@ -65,17 +94,19 @@ void MultilineExample::CreateExampleView(View* container) {
const char kTestString[] = "test string asdf 1234 test string asdf 1234 "
"test string asdf 1234 test string asdf 1234";
- gfx::RenderText* render_text = gfx::RenderText::CreateInstance();
- render_text->SetText(ASCIIToUTF16(kTestString));
- render_text->SetHorizontalAlignment(gfx::ALIGN_CENTER);
-
- render_text_view_ = new RenderTextView(render_text);
+ render_text_view_ = new RenderTextView();
+ render_text_view_->SetText(ASCIIToUTF16(kTestString));
label_ = new Label();
label_->SetText(ASCIIToUTF16(kTestString));
label_->SetMultiLine(true);
label_->set_border(Border::CreateSolidBorder(2, SK_ColorCYAN));
+ label_checkbox_ = new Checkbox(ASCIIToUTF16("views::Label:"));
+ label_checkbox_->SetChecked(true);
+ label_checkbox_->set_listener(this);
+ label_checkbox_->set_request_focus_on_press(false);
+
textfield_ = new Textfield();
textfield_->SetController(this);
textfield_->SetText(ASCIIToUTF16(kTestString));
@@ -84,7 +115,7 @@ void MultilineExample::CreateExampleView(View* container) {
container->SetLayoutManager(layout);
ColumnSet* column_set = layout->AddColumnSet(0);
- column_set->AddColumn(GridLayout::LEADING, GridLayout::FILL,
+ column_set->AddColumn(GridLayout::LEADING, GridLayout::CENTER,
0.0f, GridLayout::USE_PREF, 0, 0);
column_set->AddColumn(GridLayout::FILL, GridLayout::FILL,
1.0f, GridLayout::FIXED, 0, 0);
@@ -94,7 +125,7 @@ void MultilineExample::CreateExampleView(View* container) {
layout->AddView(render_text_view_);
layout->StartRow(0, 0);
- layout->AddView(new Label(ASCIIToUTF16("views::Label:")));
+ layout->AddView(label_checkbox_);
layout->AddView(label_);
layout->StartRow(0, 0);
@@ -105,7 +136,10 @@ void MultilineExample::CreateExampleView(View* container) {
void MultilineExample::ContentsChanged(Textfield* sender,
const string16& new_contents) {
render_text_view_->SetText(new_contents);
- label_->SetText(new_contents);
+ if (label_checkbox_->checked())
+ label_->SetText(new_contents);
+ container()->Layout();
+ container()->SchedulePaint();
}
bool MultilineExample::HandleKeyEvent(Textfield* sender,
@@ -113,5 +147,12 @@ bool MultilineExample::HandleKeyEvent(Textfield* sender,
return false;
}
+void MultilineExample::ButtonPressed(Button* sender, const ui::Event& event) {
+ DCHECK_EQ(sender, label_checkbox_);
+ label_->SetText(label_checkbox_->checked() ? textfield_->text() : string16());
+ container()->Layout();
+ container()->SchedulePaint();
+}
+
} // namespace examples
} // namespace views
diff --git a/chromium/ui/views/examples/multiline_example.h b/chromium/ui/views/examples/multiline_example.h
index bc5d8c8f548..2757c4ac933 100644
--- a/chromium/ui/views/examples/multiline_example.h
+++ b/chromium/ui/views/examples/multiline_example.h
@@ -7,6 +7,7 @@
#include "base/compiler_specific.h"
#include "base/strings/string16.h"
+#include "ui/views/controls/button/checkbox.h"
#include "ui/views/controls/textfield/textfield_controller.h"
#include "ui/views/examples/example_base.h"
@@ -16,9 +17,10 @@ class Label;
namespace examples {
-// An example that compares the multi-line rendering of different controls.
+// An example that compares the multiline rendering of different controls.
class MultilineExample : public ExampleBase,
- public TextfieldController {
+ public TextfieldController,
+ public ButtonListener {
public:
MultilineExample();
virtual ~MultilineExample();
@@ -26,6 +28,9 @@ class MultilineExample : public ExampleBase,
// ExampleBase:
virtual void CreateExampleView(View* container) OVERRIDE;
+ // ButtonListener:
+ virtual void ButtonPressed(Button* sender, const ui::Event& event) OVERRIDE;
+
private:
class RenderTextView;
@@ -39,6 +44,9 @@ class MultilineExample : public ExampleBase,
Label* label_;
Textfield* textfield_;
+ // Checkbox to enable and disable text rendering in |label_|.
+ Checkbox* label_checkbox_;
+
DISALLOW_COPY_AND_ASSIGN(MultilineExample);
};
diff --git a/chromium/ui/views/examples/textfield_example.cc b/chromium/ui/views/examples/textfield_example.cc
index 55f1c44c7ea..ec18cf74a5b 100644
--- a/chromium/ui/views/examples/textfield_example.cc
+++ b/chromium/ui/views/examples/textfield_example.cc
@@ -5,8 +5,8 @@
#include "ui/views/examples/textfield_example.h"
#include "base/strings/utf_string_conversions.h"
-#include "ui/base/events/event.h"
-#include "ui/base/range/range.h"
+#include "ui/events/event.h"
+#include "ui/gfx/range/range.h"
#include "ui/gfx/render_text.h"
#include "ui/views/controls/button/label_button.h"
#include "ui/views/controls/label.h"
@@ -121,12 +121,12 @@ void TextfieldExample::ButtonPressed(Button* sender, const ui::Event& event) {
if (name_->text().length() >= 5) {
size_t fifth = name_->text().length() / 5;
- const ui::Range big_range(1 * fifth, 4 * fifth);
+ const gfx::Range big_range(1 * fifth, 4 * fifth);
name_->ApplyStyle(gfx::BOLD, false, big_range);
name_->ApplyStyle(gfx::UNDERLINE, true, big_range);
name_->ApplyColor(SK_ColorBLUE, big_range);
- const ui::Range small_range(2 * fifth, 3 * fifth);
+ const gfx::Range small_range(2 * fifth, 3 * fifth);
name_->ApplyStyle(gfx::ITALIC, true, small_range);
name_->ApplyStyle(gfx::UNDERLINE, false, small_range);
name_->ApplyStyle(gfx::DIAGONAL_STRIKE, true, small_range);
diff --git a/chromium/ui/views/focus/accelerator_handler.h b/chromium/ui/views/focus/accelerator_handler.h
index 31ec0b5aff6..29f353e697c 100644
--- a/chromium/ui/views/focus/accelerator_handler.h
+++ b/chromium/ui/views/focus/accelerator_handler.h
@@ -24,21 +24,13 @@ bool VIEWS_EXPORT DispatchXEvent(XEvent* xevent);
// This class delegates the key messages to the associated FocusManager class
// for the window that is receiving these messages for accelerator processing.
-#if defined(OS_MACOSX)
-class VIEWS_EXPORT AcceleratorHandler {
-#else
class VIEWS_EXPORT AcceleratorHandler : public base::MessageLoop::Dispatcher {
-#endif // defined(OS_MACOSX)
public:
AcceleratorHandler();
// Dispatcher method. This returns true if an accelerator was processed by the
// focus manager
-#if defined(OS_WIN) || defined(USE_AURA)
virtual bool Dispatch(const base::NativeEvent& event) OVERRIDE;
-#elif defined(OS_MACOSX)
- // TODO(dhollowa): Implement on Mac. http://crbug.com/109946
-#endif
private:
#if defined(OS_WIN)
diff --git a/chromium/ui/views/focus/accelerator_handler_win.cc b/chromium/ui/views/focus/accelerator_handler_win.cc
index 7d11c97d28f..ea82daed717 100644
--- a/chromium/ui/views/focus/accelerator_handler_win.cc
+++ b/chromium/ui/views/focus/accelerator_handler_win.cc
@@ -4,9 +4,9 @@
#include "ui/views/focus/accelerator_handler.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/widget/widget.h"
diff --git a/chromium/ui/views/focus/focus_manager.cc b/chromium/ui/views/focus/focus_manager.cc
index 0a60ee17e8a..429b9ada1b0 100644
--- a/chromium/ui/views/focus/focus_manager.cc
+++ b/chromium/ui/views/focus/focus_manager.cc
@@ -11,8 +11,8 @@
#include "base/logging.h"
#include "build/build_config.h"
#include "ui/base/accelerators/accelerator.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/focus/focus_manager_delegate.h"
#include "ui/views/focus/focus_search.h"
#include "ui/views/focus/view_storage.h"
@@ -139,7 +139,7 @@ bool FocusManager::ContainsView(View* view) {
}
void FocusManager::AdvanceFocus(bool reverse) {
- View* v = GetNextFocusableView(focused_view_, reverse, false);
+ View* v = GetNextFocusableView(focused_view_, NULL, reverse, false);
// Note: Do not skip this next block when v == focused_view_. If the user
// tabs past the last focusable element in a webpage, we'll get here, and if
// the TabContentsContainerView is the only focusable view (possible in
@@ -219,6 +219,7 @@ bool FocusManager::RotatePaneFocus(Direction direction,
}
View* FocusManager::GetNextFocusableView(View* original_starting_view,
+ Widget* starting_widget,
bool reverse,
bool dont_loop) {
FocusTraversable* focus_traversable = NULL;
@@ -262,7 +263,8 @@ View* FocusManager::GetNextFocusableView(View* original_starting_view,
}
}
} else {
- focus_traversable = widget_->GetFocusTraversable();
+ Widget* widget = starting_widget ? starting_widget : widget_;
+ focus_traversable = widget->GetFocusTraversable();
}
// Traverse the FocusTraversable tree down to find the focusable view.
@@ -303,9 +305,12 @@ View* FocusManager::GetNextFocusableView(View* original_starting_view,
// infinitely looping in empty windows.
if (!dont_loop && original_starting_view) {
// Easy, just clear the selection and press tab again.
- // By calling with NULL as the starting view, we'll start from the
- // top_root_view.
- return GetNextFocusableView(NULL, reverse, true);
+ // By calling with NULL as the starting view, we'll start from either
+ // the starting views widget or |widget_|.
+ Widget* widget = original_starting_view->GetWidget();
+ if (widget->widget_delegate()->ShouldAdvanceFocusToTopLevelWidget())
+ widget = widget_;
+ return GetNextFocusableView(NULL, widget, reverse, true);
}
}
return NULL;
@@ -451,7 +456,6 @@ View* FocusManager::FindFocusableView(FocusTraversable* focus_traversable,
while (new_focus_traversable) {
DCHECK(!v);
focus_traversable = new_focus_traversable;
- starting_view = new_starting_view;
new_focus_traversable = NULL;
starting_view = NULL;
v = focus_traversable->GetFocusSearch()->FindNextFocusableView(
diff --git a/chromium/ui/views/focus/focus_manager.h b/chromium/ui/views/focus/focus_manager.h
index 6a17fc2bc1a..be254133826 100644
--- a/chromium/ui/views/focus/focus_manager.h
+++ b/chromium/ui/views/focus/focus_manager.h
@@ -308,8 +308,16 @@ class VIEWS_EXPORT FocusManager {
}
private:
- // Returns the next focusable view.
- View* GetNextFocusableView(View* starting_view, bool reverse, bool dont_loop);
+ // Returns the next focusable view. Traversal starts at |starting_view|. If
+ // |starting_view| is NULL |starting_widget| is consuled to determine which
+ // Widget to start from. See
+ // WidgetDelegate::ShouldAdvanceFocusToTopLevelWidget() for details. If both
+ // |starting_view| and |starting_widget| are NULL, traversal starts at
+ // |widget_|.
+ View* GetNextFocusableView(View* starting_view,
+ Widget* starting_widget,
+ bool reverse,
+ bool dont_loop);
// Returns the focusable view found in the FocusTraversable specified starting
// at the specified view. This traverses down along the FocusTraversable
diff --git a/chromium/ui/views/focus/focus_manager_unittest.cc b/chromium/ui/views/focus/focus_manager_unittest.cc
index 51341f56500..a2c9d48f6fa 100644
--- a/chromium/ui/views/focus/focus_manager_unittest.cc
+++ b/chromium/ui/views/focus/focus_manager_unittest.cc
@@ -7,7 +7,7 @@
#include "base/strings/utf_string_conversions.h"
#include "ui/base/accelerators/accelerator.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/accessible_pane_view.h"
#include "ui/views/controls/button/label_button.h"
#include "ui/views/controls/textfield/textfield.h"
@@ -829,4 +829,85 @@ TEST_F(FocusManagerTest, StoreFocusedView) {
EXPECT_EQ(&view, GetFocusManager()->GetStoredFocusView());
}
+namespace {
+
+// Trivial WidgetDelegate implementation that allows setting return value of
+// ShouldAdvanceFocusToTopLevelWidget().
+class AdvanceFocusWidgetDelegate : public WidgetDelegate {
+ public:
+ explicit AdvanceFocusWidgetDelegate(Widget* widget)
+ : widget_(widget),
+ should_advance_focus_to_parent_(false) {}
+ virtual ~AdvanceFocusWidgetDelegate() {}
+
+ void set_should_advance_focus_to_parent(bool value) {
+ should_advance_focus_to_parent_ = value;
+ }
+
+ // WidgetDelegate overrides:
+ virtual bool ShouldAdvanceFocusToTopLevelWidget() const OVERRIDE {
+ return should_advance_focus_to_parent_;
+ }
+ virtual Widget* GetWidget() OVERRIDE { return widget_; }
+ virtual const Widget* GetWidget() const OVERRIDE { return widget_; }
+
+ private:
+ Widget* widget_;
+ bool should_advance_focus_to_parent_;
+
+ DISALLOW_COPY_AND_ASSIGN(AdvanceFocusWidgetDelegate);
+};
+
+} // namespace
+
+// Verifies focus wrapping happens in the same widget.
+TEST_F(FocusManagerTest, AdvanceFocusStaysInWidget) {
+ // Add |widget_view| as a child of the Widget.
+ View* widget_view = new View;
+ widget_view->set_focusable(true);
+ widget_view->SetBounds(20, 0, 20, 20);
+ GetContentsView()->AddChildView(widget_view);
+
+ // Create a widget with two views, focus the second.
+ scoped_ptr<AdvanceFocusWidgetDelegate> delegate;
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_WINDOW);
+ params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ params.child = true;
+ params.bounds = gfx::Rect(10, 10, 100, 100);
+ params.parent = GetWidget()->GetNativeView();
+ Widget child_widget;
+ delegate.reset(new AdvanceFocusWidgetDelegate(&child_widget));
+ params.delegate = delegate.get();
+ child_widget.Init(params);
+ View* view1 = new View;
+ view1->set_focusable(true);
+ view1->SetBounds(0, 0, 20, 20);
+ View* view2 = new View;
+ view2->set_focusable(true);
+ view2->SetBounds(20, 0, 20, 20);
+ child_widget.client_view()->AddChildView(view1);
+ child_widget.client_view()->AddChildView(view2);
+ child_widget.Show();
+ view2->RequestFocus();
+ EXPECT_EQ(view2, GetFocusManager()->GetFocusedView());
+
+ // Advance focus backwards, which should focus the first.
+ GetFocusManager()->AdvanceFocus(false);
+ EXPECT_EQ(view1, GetFocusManager()->GetFocusedView());
+
+ // Focus forward to |view2|.
+ GetFocusManager()->AdvanceFocus(true);
+ EXPECT_EQ(view2, GetFocusManager()->GetFocusedView());
+
+ // And forward again, wrapping back to |view1|.
+ GetFocusManager()->AdvanceFocus(true);
+ EXPECT_EQ(view1, GetFocusManager()->GetFocusedView());
+
+ // Allow focus to go to the parent, and focus backwards which should now move
+ // up |widget_view| (in the parent).
+ delegate->set_should_advance_focus_to_parent(true);
+ GetFocusManager()->AdvanceFocus(true);
+ EXPECT_EQ(widget_view, GetFocusManager()->GetFocusedView());
+}
+
} // namespace views
diff --git a/chromium/ui/views/focus/focus_manager_unittest_win.cc b/chromium/ui/views/focus/focus_manager_unittest_win.cc
index 2e7ddc0e3b2..1309ed2d5b9 100644
--- a/chromium/ui/views/focus/focus_manager_unittest_win.cc
+++ b/chromium/ui/views/focus/focus_manager_unittest_win.cc
@@ -7,7 +7,7 @@
#include "base/memory/scoped_ptr.h"
#include "base/run_loop.h"
#include "base/strings/utf_string_conversions.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/views/controls/button/label_button.h"
#include "ui/views/focus/accelerator_handler.h"
#include "ui/views/focus/focus_manager_test.h"
diff --git a/chromium/ui/views/ime/input_method_base.cc b/chromium/ui/views/ime/input_method_base.cc
index 4c4298b7694..784746b7e37 100644
--- a/chromium/ui/views/ime/input_method_base.cc
+++ b/chromium/ui/views/ime/input_method_base.cc
@@ -5,8 +5,8 @@
#include "ui/views/ime/input_method_base.h"
#include "base/logging.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/text_input_client.h"
+#include "ui/events/event.h"
#include "ui/views/view.h"
#include "ui/views/widget/widget.h"
diff --git a/chromium/ui/views/ime/input_method_bridge.cc b/chromium/ui/views/ime/input_method_bridge.cc
index 550764757c1..f0ce73b00d9 100644
--- a/chromium/ui/views/ime/input_method_bridge.cc
+++ b/chromium/ui/views/ime/input_method_bridge.cc
@@ -4,8 +4,8 @@
#include "ui/views/ime/input_method_bridge.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/input_method.h"
+#include "ui/events/event.h"
#include "ui/gfx/rect.h"
#include "ui/views/view.h"
#include "ui/views/widget/widget.h"
@@ -16,8 +16,7 @@ InputMethodBridge::InputMethodBridge(internal::InputMethodDelegate* delegate,
ui::InputMethod* host,
bool shared_input_method)
: host_(host),
- shared_input_method_(shared_input_method),
- context_focused_(false) {
+ shared_input_method_(shared_input_method) {
DCHECK(host_);
SetDelegate(delegate);
}
@@ -29,8 +28,7 @@ InputMethodBridge::~InputMethodBridge() {
// this and go into |widget_|. NULL out |widget_| so we don't attempt to use
// it.
DetachFromWidget();
- if (host_->GetTextInputClient() == this)
- host_->SetFocusedTextInputClient(NULL);
+ host_->DetachTextInputClient(this);
}
void InputMethodBridge::OnFocus() {
@@ -180,33 +178,33 @@ bool InputMethodBridge::HasCompositionText() {
return client ? client->HasCompositionText() : false;
}
-bool InputMethodBridge::GetTextRange(ui::Range* range) {
+bool InputMethodBridge::GetTextRange(gfx::Range* range) {
TextInputClient* client = GetTextInputClient();
return client ? client->GetTextRange(range) : false;
}
-bool InputMethodBridge::GetCompositionTextRange(ui::Range* range) {
+bool InputMethodBridge::GetCompositionTextRange(gfx::Range* range) {
TextInputClient* client = GetTextInputClient();
return client ? client->GetCompositionTextRange(range) : false;
}
-bool InputMethodBridge::GetSelectionRange(ui::Range* range) {
+bool InputMethodBridge::GetSelectionRange(gfx::Range* range) {
TextInputClient* client = GetTextInputClient();
return client ? client->GetSelectionRange(range) : false;
}
-bool InputMethodBridge::SetSelectionRange(const ui::Range& range) {
+bool InputMethodBridge::SetSelectionRange(const gfx::Range& range) {
TextInputClient* client = GetTextInputClient();
return client ? client->SetSelectionRange(range) : false;
}
-bool InputMethodBridge::DeleteRange(const ui::Range& range) {
+bool InputMethodBridge::DeleteRange(const gfx::Range& range) {
TextInputClient* client = GetTextInputClient();
return client ? client->DeleteRange(range) : false;
}
bool InputMethodBridge::GetTextFromRange(
- const ui::Range& range, string16* text) {
+ const gfx::Range& range, string16* text) {
TextInputClient* client = GetTextInputClient();
return client ? client->GetTextFromRange(range, text) : false;
}
diff --git a/chromium/ui/views/ime/input_method_bridge.h b/chromium/ui/views/ime/input_method_bridge.h
index 03ea567aa6d..1a50880154a 100644
--- a/chromium/ui/views/ime/input_method_bridge.h
+++ b/chromium/ui/views/ime/input_method_bridge.h
@@ -64,13 +64,13 @@ class InputMethodBridge : public InputMethodBase,
virtual bool GetCompositionCharacterBounds(uint32 index,
gfx::Rect* rect) OVERRIDE;
virtual bool HasCompositionText() OVERRIDE;
- virtual bool GetTextRange(ui::Range* range) OVERRIDE;
- virtual bool GetCompositionTextRange(ui::Range* range) OVERRIDE;
- virtual bool GetSelectionRange(ui::Range* range) OVERRIDE;
- virtual bool SetSelectionRange(const ui::Range& range) OVERRIDE;
- virtual bool DeleteRange(const ui::Range& range) OVERRIDE;
+ virtual bool GetTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetCompositionTextRange(gfx::Range* range) OVERRIDE;
+ virtual bool GetSelectionRange(gfx::Range* range) OVERRIDE;
+ virtual bool SetSelectionRange(const gfx::Range& range) OVERRIDE;
+ virtual bool DeleteRange(const gfx::Range& range) OVERRIDE;
virtual bool GetTextFromRange(
- const ui::Range& range, string16* text) OVERRIDE;
+ const gfx::Range& range, string16* text) OVERRIDE;
virtual void OnInputMethodChanged() OVERRIDE;
virtual bool ChangeTextDirectionAndLayoutAlignment(
base::i18n::TextDirection direction) OVERRIDE;
@@ -90,8 +90,6 @@ class InputMethodBridge : public InputMethodBase,
const bool shared_input_method_;
- bool context_focused_;
-
DISALLOW_COPY_AND_ASSIGN(InputMethodBridge);
};
diff --git a/chromium/ui/views/ime/input_method_bridge_unittest.cc b/chromium/ui/views/ime/input_method_bridge_unittest.cc
index f04615291f0..64a12470731 100644
--- a/chromium/ui/views/ime/input_method_bridge_unittest.cc
+++ b/chromium/ui/views/ime/input_method_bridge_unittest.cc
@@ -4,7 +4,8 @@
#include "ui/aura/client/aura_constants.h"
#include "ui/aura/window.h"
-#include "ui/base/ime/dummy_input_method.h"
+#include "ui/base/ime/dummy_input_method_delegate.h"
+#include "ui/base/ime/fake_input_method.h"
#include "ui/base/ime/text_input_client.h"
#include "ui/views/ime/input_method.h"
#include "ui/views/test/views_test_base.h"
@@ -16,41 +17,10 @@ namespace views {
typedef ViewsTestBase InputMethodBridgeTest;
-namespace {
-
-class TestInputMethod : public ui::DummyInputMethod {
- public:
- TestInputMethod();
- virtual ~TestInputMethod();
-
- virtual void SetFocusedTextInputClient(ui::TextInputClient* client) OVERRIDE;
- virtual ui::TextInputClient* GetTextInputClient() const OVERRIDE;
-
- private:
- ui::TextInputClient* text_input_client_;
-
- DISALLOW_COPY_AND_ASSIGN(TestInputMethod);
-};
-
-TestInputMethod::TestInputMethod() : text_input_client_(NULL) {}
-
-TestInputMethod::~TestInputMethod() {}
-
-void TestInputMethod::SetFocusedTextInputClient(ui::TextInputClient* client) {
- // This simulates what the real InputMethod implementation does.
- if (text_input_client_)
- text_input_client_->GetTextInputType();
- text_input_client_ = client;
-}
-
-ui::TextInputClient* TestInputMethod::GetTextInputClient() const {
- return text_input_client_;
-}
-
-} // namespace
-
TEST_F(InputMethodBridgeTest, DestructTest) {
- TestInputMethod input_method;
+ ui::internal::DummyInputMethodDelegate input_method_delegate;
+ ui::FakeInputMethod input_method(&input_method_delegate);
+
GetContext()->SetProperty(aura::client::kRootWindowInputMethodKey,
static_cast<ui::InputMethod*>(&input_method));
diff --git a/chromium/ui/views/ime/mock_input_method.cc b/chromium/ui/views/ime/mock_input_method.cc
index e48af72b76c..b04dafbfa63 100644
--- a/chromium/ui/views/ime/mock_input_method.cc
+++ b/chromium/ui/views/ime/mock_input_method.cc
@@ -6,9 +6,9 @@
#include "base/basictypes.h"
#include "base/logging.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/text_input_client.h"
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/widget/widget.h"
namespace views {
diff --git a/chromium/ui/views/layout/grid_layout.cc b/chromium/ui/views/layout/grid_layout.cc
index 2927b88da9d..0e4d4150020 100644
--- a/chromium/ui/views/layout/grid_layout.cc
+++ b/chromium/ui/views/layout/grid_layout.cc
@@ -995,6 +995,9 @@ void GridLayout::AddViewState(ViewState* view_state) {
void GridLayout::AddRow(Row* row) {
current_row_++;
remaining_row_span_--;
+ // GridLayout requires that if you add a View with a row span you use the same
+ // column set for each of the rows the view lands it. This DCHECK verifies
+ // that.
DCHECK(remaining_row_span_ <= 0 ||
row->column_set() == NULL ||
row->column_set() == GetLastValidColumnSet());
diff --git a/chromium/ui/linux_ui/OWNERS b/chromium/ui/views/linux_ui/OWNERS
index 4733a4f06bf..4733a4f06bf 100644
--- a/chromium/ui/linux_ui/OWNERS
+++ b/chromium/ui/views/linux_ui/OWNERS
diff --git a/chromium/ui/linux_ui/linux_ui.cc b/chromium/ui/views/linux_ui/linux_ui.cc
index 40ead2fc9fa..79f0a4082c9 100644
--- a/chromium/ui/linux_ui/linux_ui.cc
+++ b/chromium/ui/views/linux_ui/linux_ui.cc
@@ -1,18 +1,18 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/linux_ui/linux_ui.h"
+#include "ui/views/linux_ui/linux_ui.h"
#include "ui/shell_dialogs/linux_shell_dialog.h"
namespace {
-ui::LinuxUI* g_linux_ui = NULL;
+views::LinuxUI* g_linux_ui = NULL;
} // namespace
-namespace ui {
+namespace views {
void LinuxUI::SetInstance(LinuxUI* instance) {
delete g_linux_ui;
@@ -21,8 +21,8 @@ void LinuxUI::SetInstance(LinuxUI* instance) {
LinuxShellDialog::SetInstance(instance);
}
-const LinuxUI* LinuxUI::instance() {
+LinuxUI* LinuxUI::instance() {
return g_linux_ui;
}
-} // namespace ui
+} // namespace views
diff --git a/chromium/ui/linux_ui/linux_ui.gyp b/chromium/ui/views/linux_ui/linux_ui.gyp
index c2140760c65..7feb238f240 100644
--- a/chromium/ui/linux_ui/linux_ui.gyp
+++ b/chromium/ui/views/linux_ui/linux_ui.gyp
@@ -1,4 +1,4 @@
-# Copyright (c) 2012 The Chromium Authors. All rights reserved.
+# Copyright 2013 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
diff --git a/chromium/ui/linux_ui/linux_ui.h b/chromium/ui/views/linux_ui/linux_ui.h
index f609e9a78a0..443677c812b 100644
--- a/chromium/ui/linux_ui/linux_ui.h
+++ b/chromium/ui/views/linux_ui/linux_ui.h
@@ -1,14 +1,14 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_LINUX_UI_LINUX_UI_H_
-#define UI_LINUX_UI_LINUX_UI_H_
+#ifndef UI_VIEWS_LINUX_UI_LINUX_UI_H_
+#define UI_VIEWS_LINUX_UI_LINUX_UI_H_
#include "third_party/skia/include/core/SkColor.h"
-#include "ui/linux_ui/linux_ui_export.h"
-#include "ui/linux_ui/status_icon_linux.h"
#include "ui/shell_dialogs/linux_shell_dialog.h"
+#include "ui/views/linux_ui/status_icon_linux.h"
+#include "ui/views/views_export.h"
// The main entrypoint into Linux toolkit specific code. GTK code should only
// be executed behind this interface.
@@ -19,6 +19,10 @@ class Image;
namespace ui {
class NativeTheme;
+}
+
+namespace views {
+class WindowButtonOrderObserver;
// Adapter class with targets to render like different toolkits. Set by any
// project that wants to do linux desktop native rendering.
@@ -27,10 +31,7 @@ class NativeTheme;
// minimum) GTK2 and GTK3. LinuxUI::instance() should actually be a very
// complex method that pokes around with dlopen against a libuigtk2.so, a
// liuigtk3.so, etc.
-//
-// TODO(erg): This class should be folded into ui/views/ instead of living in
-// its own component once we've deleted out the GTK+ port.
-class LINUX_UI_EXPORT LinuxUI : public LinuxShellDialog {
+class VIEWS_EXPORT LinuxUI : public ui::LinuxShellDialog {
public:
virtual ~LinuxUI() {}
@@ -42,7 +43,7 @@ class LINUX_UI_EXPORT LinuxUI : public LinuxShellDialog {
//
// Can return NULL, in case no toolkit has been set. (For example, if we're
// running with the "--ash" flag.)
- static const LinuxUI* instance();
+ static LinuxUI* instance();
// Returns an themed image per theme_provider.h
virtual bool UseNativeTheme() const = 0;
@@ -52,7 +53,7 @@ class LINUX_UI_EXPORT LinuxUI : public LinuxShellDialog {
// Returns a NativeTheme that will provide system colors and draw system
// style widgets.
- virtual NativeTheme* GetNativeTheme() const = 0;
+ virtual ui::NativeTheme* GetNativeTheme() const = 0;
// Returns whether we should be using the native theme provided by this
// object by default.
@@ -70,8 +71,18 @@ class LINUX_UI_EXPORT LinuxUI : public LinuxShellDialog {
virtual scoped_ptr<StatusIconLinux> CreateLinuxStatusIcon(
const gfx::ImageSkia& image,
const string16& tool_tip) const = 0;
+
+ // Notifies the observer about changes about how window buttons should be
+ // laid out. If the order is anything other than the default min,max,close on
+ // the right, will immediately send a button change event to the observer.
+ virtual void AddWindowButtonOrderObserver(
+ WindowButtonOrderObserver* observer) = 0;
+
+ // Removes the observer from the LinuxUI's list.
+ virtual void RemoveWindowButtonOrderObserver(
+ WindowButtonOrderObserver* observer) = 0;
};
-} // namespace ui
+} // namespace views
-#endif // UI_LINUX_UI_LINUX_UI_H_
+#endif // UI_VIEWS_LINUX_UI_LINUX_UI_H_
diff --git a/chromium/ui/linux_ui/status_icon_linux.cc b/chromium/ui/views/linux_ui/status_icon_linux.cc
index 1e273d3589f..bf2ec05a9f1 100644
--- a/chromium/ui/linux_ui/status_icon_linux.cc
+++ b/chromium/ui/views/linux_ui/status_icon_linux.cc
@@ -2,7 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "ui/linux_ui/status_icon_linux.h"
+#include "ui/views/linux_ui/status_icon_linux.h"
+
+namespace views {
StatusIconLinux::Delegate::~Delegate() {
}
@@ -12,3 +14,8 @@ StatusIconLinux::StatusIconLinux() : delegate_(NULL) {
StatusIconLinux::~StatusIconLinux() {
}
+
+void StatusIconLinux::RefreshPlatformContextMenu() {
+}
+
+} // namespace views
diff --git a/chromium/ui/linux_ui/status_icon_linux.h b/chromium/ui/views/linux_ui/status_icon_linux.h
index fbbf28f304e..5ed8be21a7e 100644
--- a/chromium/ui/linux_ui/status_icon_linux.h
+++ b/chromium/ui/views/linux_ui/status_icon_linux.h
@@ -2,11 +2,11 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#ifndef UI_LINUX_UI_STATUS_ICON_LINUX_H_
-#define UI_LINUX_UI_STATUS_ICON_LINUX_H_
+#ifndef UI_VIEWS_LINUX_UI_STATUS_ICON_LINUX_H_
+#define UI_VIEWS_LINUX_UI_STATUS_ICON_LINUX_H_
#include "base/strings/string16.h"
-#include "ui/linux_ui/linux_ui_export.h"
+#include "ui/views/views_export.h"
namespace gfx {
class ImageSkia;
@@ -16,11 +16,13 @@ namespace ui {
class MenuModel;
} // namespace ui
+namespace views {
+
// Since liblinux_ui cannot have dependencies on any chrome browser components
// we cannot inherit from StatusIcon. So we implement the necessary methods
// and let a wrapper class implement the StatusIcon interface and defer the
-// callbacks to a delegate.
-class LINUX_UI_EXPORT StatusIconLinux {
+// callbacks to a delegate. For the same reason, do not use StatusIconMenuModel.
+class VIEWS_EXPORT StatusIconLinux {
public:
class Delegate {
public:
@@ -43,6 +45,11 @@ class LINUX_UI_EXPORT StatusIconLinux {
// subclass should destroy the existing native context menu on this call.
virtual void UpdatePlatformContextMenu(ui::MenuModel* model) = 0;
+ // Update all the enabled/checked states and the dynamic labels. Some status
+ // icon implementations do not refresh the native menu before showing so we
+ // need to manually refresh it when the menu model changes.
+ virtual void RefreshPlatformContextMenu();
+
Delegate* delegate() { return delegate_; }
void set_delegate(Delegate* delegate) { delegate_ = delegate; }
@@ -50,4 +57,6 @@ class LINUX_UI_EXPORT StatusIconLinux {
Delegate* delegate_;
};
+} // namespace views
+
#endif // UI_LINUX_UI_STATUS_ICON_LINUX_H_
diff --git a/chromium/ui/views/linux_ui/window_button_order_observer.h b/chromium/ui/views/linux_ui/window_button_order_observer.h
new file mode 100644
index 00000000000..96b7cb8290f
--- /dev/null
+++ b/chromium/ui/views/linux_ui/window_button_order_observer.h
@@ -0,0 +1,29 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_LINUX_UI_WINDOW_BUTTON_ORDER_OBSERVER_H_
+#define UI_VIEWS_LINUX_UI_WINDOW_BUTTON_ORDER_OBSERVER_H_
+
+#include <vector>
+
+#include "ui/views/window/frame_buttons.h"
+
+namespace views {
+
+// Observer interface to receive the ordering of the min,max,close buttons.
+class WindowButtonOrderObserver {
+ public:
+ // Called when first added to the LinuxUI class, or on a system-wide
+ // configuration event.
+ virtual void OnWindowButtonOrderingChange(
+ const std::vector<views::FrameButton>& leading_buttons,
+ const std::vector<views::FrameButton>& trailing_buttons) = 0;
+
+ protected:
+ virtual ~WindowButtonOrderObserver() {}
+};
+
+} // namespace views
+
+#endif // UI_VIEWS_LINUX_UI_WINDOW_BUTTON_ORDER_OBSERVER_H_
diff --git a/chromium/ui/views/mouse_constants.cc b/chromium/ui/views/mouse_constants.cc
new file mode 100644
index 00000000000..b2f3b964af3
--- /dev/null
+++ b/chromium/ui/views/mouse_constants.cc
@@ -0,0 +1,12 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/mouse_constants.h"
+
+namespace views {
+
+const int kMinimumMsPressedToActivate = 200;
+const int kMinimumMsBetweenButtonClicks = 100;
+
+} // namespace views
diff --git a/chromium/ui/views/mouse_constants.h b/chromium/ui/views/mouse_constants.h
new file mode 100644
index 00000000000..e22c75cdd65
--- /dev/null
+++ b/chromium/ui/views/mouse_constants.h
@@ -0,0 +1,25 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_MOUSE_CONSTANTS_H_
+#define UI_VIEWS_MOUSE_CONSTANTS_H_
+
+#include "base/basictypes.h"
+#include "ui/views/views_export.h"
+
+namespace views {
+
+// The amount of time the mouse should be down before a mouse release is
+// considered intentional. This is to prevent spurious mouse releases from
+// activating controls, especially when some UI element is revealed under the
+// source of the activation (ex. menus showing underneath menu buttons).
+VIEWS_EXPORT extern const int kMinimumMsPressedToActivate;
+
+// The amount of time, in milliseconds, between clicks until they're considered
+// intentionally different.
+VIEWS_EXPORT extern const int kMinimumMsBetweenButtonClicks;
+
+} // namespace views
+
+#endif // UI_VIEWS_MOUSE_CONSTANTS_H_
diff --git a/chromium/ui/views/mouse_watcher.cc b/chromium/ui/views/mouse_watcher.cc
index e4f156f0ea5..5a2b4bd0ae8 100644
--- a/chromium/ui/views/mouse_watcher.cc
+++ b/chromium/ui/views/mouse_watcher.cc
@@ -9,8 +9,8 @@
#include "base/event_types.h"
#include "base/memory/weak_ptr.h"
#include "base/message_loop/message_loop.h"
-#include "ui/base/events/event_constants.h"
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event_constants.h"
+#include "ui/events/event_utils.h"
#include "ui/gfx/screen.h"
namespace views {
diff --git a/chromium/ui/views/mouse_watcher_view_host.cc b/chromium/ui/views/mouse_watcher_view_host.cc
index 1d420fa1cbc..54412cf10d5 100644
--- a/chromium/ui/views/mouse_watcher_view_host.cc
+++ b/chromium/ui/views/mouse_watcher_view_host.cc
@@ -50,7 +50,7 @@ bool MouseWatcherViewHost::IsMouseOverWindow() {
return false;
return gfx::Screen::GetScreenFor(widget->GetNativeView())->
- GetWindowAtCursorScreenPoint() == widget->GetNativeWindow();
+ GetWindowUnderCursor() == widget->GetNativeWindow();
}
} // namespace views
diff --git a/chromium/ui/views/native_theme_delegate.h b/chromium/ui/views/native_theme_delegate.h
index d4bc880fd8d..f17f164462e 100644
--- a/chromium/ui/views/native_theme_delegate.h
+++ b/chromium/ui/views/native_theme_delegate.h
@@ -34,7 +34,7 @@ class VIEWS_EXPORT NativeThemeDelegate {
// If the native theme drawign should be animated, return the Animation object
// that controlls it. If no animation is ongoing, NULL may be returned.
- virtual const ui::Animation* GetThemeAnimation() const = 0;
+ virtual const gfx::Animation* GetThemeAnimation() const = 0;
// If animation is onging, this returns the background native theme state.
virtual ui::NativeTheme::State GetBackgroundThemeState(
diff --git a/chromium/ui/views/run_all_unittests.cc b/chromium/ui/views/run_all_unittests.cc
index 6c425d7a31e..fb99c447d71 100644
--- a/chromium/ui/views/run_all_unittests.cc
+++ b/chromium/ui/views/run_all_unittests.cc
@@ -3,8 +3,10 @@
// found in the LICENSE file.
#include "base/basictypes.h"
+#include "base/bind.h"
#include "base/compiler_specific.h"
#include "base/test/test_suite.h"
+#include "base/test/unit_test_launcher.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/base/ui_base_paths.h"
#include "ui/views/view.h"
@@ -25,5 +27,9 @@ class ViewTestSuite : public base::TestSuite {
};
int main(int argc, char** argv) {
- return ViewTestSuite(argc, argv).Run();
+ ViewTestSuite test_suite(argc, argv);
+
+ return base::LaunchUnitTests(
+ argc, argv, base::Bind(&ViewTestSuite::Run,
+ base::Unretained(&test_suite)));
}
diff --git a/chromium/ui/views/touchui/touch_selection_controller_impl.cc b/chromium/ui/views/touchui/touch_selection_controller_impl.cc
index 8b6b35116c8..89f6bdcafa8 100644
--- a/chromium/ui/views/touchui/touch_selection_controller_impl.cc
+++ b/chromium/ui/views/touchui/touch_selection_controller_impl.cc
@@ -193,7 +193,7 @@ class TouchSelectionControllerImpl::EditingHandleView
case ui::ET_GESTURE_SCROLL_BEGIN:
widget_->SetCapture(this);
controller_->SetDraggingHandle(this);
- drag_offset_ = event->y() - cursor_height() -
+ drag_offset_ = event->y() - cursor_height() +
kSelectionHandleVerticalDragOffset;
break;
case ui::ET_GESTURE_SCROLL_UPDATE: {
@@ -259,6 +259,10 @@ class TouchSelectionControllerImpl::EditingHandleView
scoped_ptr<Widget> widget_;
TouchSelectionControllerImpl* controller_;
gfx::Rect selection_rect_;
+
+ // Vertical offset between the scroll event position and the drag position
+ // reported to the client view (see the ASCII figure at the top of the file
+ // and its description for more details).
int drag_offset_;
// If set to true, the handle will not draw anything, hence providing an empty
diff --git a/chromium/ui/views/touchui/touch_selection_controller_impl_unittest.cc b/chromium/ui/views/touchui/touch_selection_controller_impl_unittest.cc
index 2925046fb6a..54c997223c2 100644
--- a/chromium/ui/views/touchui/touch_selection_controller_impl_unittest.cc
+++ b/chromium/ui/views/touchui/touch_selection_controller_impl_unittest.cc
@@ -200,7 +200,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectionInTextfieldTest) {
textfield_view_->OnGestureEvent(&tap);
// Test selecting a range.
- textfield_->SelectRange(ui::Range(3, 7));
+ textfield_->SelectRange(gfx::Range(3, 7));
VERIFY_HANDLE_POSITIONS(false);
// Test selecting everything.
@@ -237,35 +237,35 @@ TEST_F(TouchSelectionControllerImplTest, SelectionInBidiTextfieldTest) {
VERIFY_HANDLE_POSITIONS(false);
// Test selection range inside one run and starts or ends at run boundary.
- textfield_->SelectRange(ui::Range(2, 3));
+ textfield_->SelectRange(gfx::Range(2, 3));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(3, 2));
+ textfield_->SelectRange(gfx::Range(3, 2));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(3, 4));
+ textfield_->SelectRange(gfx::Range(3, 4));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(4, 3));
+ textfield_->SelectRange(gfx::Range(4, 3));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(3, 6));
+ textfield_->SelectRange(gfx::Range(3, 6));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(6, 3));
+ textfield_->SelectRange(gfx::Range(6, 3));
VERIFY_HANDLE_POSITIONS(false);
// Test selection range accross runs.
- textfield_->SelectRange(ui::Range(0, 6));
+ textfield_->SelectRange(gfx::Range(0, 6));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(6, 0));
+ textfield_->SelectRange(gfx::Range(6, 0));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(1, 4));
+ textfield_->SelectRange(gfx::Range(1, 4));
VERIFY_HANDLE_POSITIONS(false);
- textfield_->SelectRange(ui::Range(4, 1));
+ textfield_->SelectRange(gfx::Range(4, 1));
VERIFY_HANDLE_POSITIONS(false);
}
@@ -278,7 +278,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectCallbackTest) {
ui::GestureEvent tap(ui::ET_GESTURE_TAP, 0, 0, 0, base::TimeDelta(),
ui::GestureEventDetails(ui::ET_GESTURE_TAP, 1.0f, 0.0f), 0);
textfield_view_->OnGestureEvent(&tap);
- textfield_->SelectRange(ui::Range(3, 7));
+ textfield_->SelectRange(gfx::Range(3, 7));
EXPECT_EQ(UTF16ToUTF8(textfield_->GetSelectedText()), "tfie");
VERIFY_HANDLE_POSITIONS(false);
@@ -318,7 +318,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectInBidiCallbackTest) {
textfield_view_->OnGestureEvent(&tap);
// Select [c] from left to right.
- textfield_->SelectRange(ui::Range(2, 3));
+ textfield_->SelectRange(gfx::Range(2, 3));
EXPECT_EQ(WideToUTF16(L"c"), textfield_->GetSelectedText());
VERIFY_HANDLE_POSITIONS(false);
@@ -336,7 +336,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectInBidiCallbackTest) {
VERIFY_HANDLE_POSITIONS(true);
// Select [c] from right to left.
- textfield_->SelectRange(ui::Range(3, 2));
+ textfield_->SelectRange(gfx::Range(3, 2));
EXPECT_EQ(WideToUTF16(L"c"), textfield_->GetSelectedText());
VERIFY_HANDLE_POSITIONS(false);
@@ -353,7 +353,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectInBidiCallbackTest) {
VERIFY_HANDLE_POSITIONS(false);
// Select [\x5e1] from right to left.
- textfield_->SelectRange(ui::Range(3, 4));
+ textfield_->SelectRange(gfx::Range(3, 4));
EXPECT_EQ(WideToUTF16(L"\x05e1"), textfield_->GetSelectedText());
VERIFY_HANDLE_POSITIONS(false);
@@ -379,7 +379,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectInBidiCallbackTest) {
VERIFY_HANDLE_POSITIONS(true);
// Select [\x5e1] from left to right.
- textfield_->SelectRange(ui::Range(4, 3));
+ textfield_->SelectRange(gfx::Range(4, 3));
EXPECT_EQ(WideToUTF16(L"\x05e1"), textfield_->GetSelectedText());
VERIFY_HANDLE_POSITIONS(false);
@@ -398,7 +398,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectInBidiCallbackTest) {
VERIFY_HANDLE_POSITIONS(false);
// Select [\x05r3] from right to left.
- textfield_->SelectRange(ui::Range(5, 6));
+ textfield_->SelectRange(gfx::Range(5, 6));
EXPECT_EQ(WideToUTF16(L"\x05e3"), textfield_->GetSelectedText());
VERIFY_HANDLE_POSITIONS(false);
@@ -415,7 +415,7 @@ TEST_F(TouchSelectionControllerImplTest, SelectRectInBidiCallbackTest) {
VERIFY_HANDLE_POSITIONS(true);
// Select [\x05r3] from left to right.
- textfield_->SelectRange(ui::Range(6, 5));
+ textfield_->SelectRange(gfx::Range(6, 5));
EXPECT_EQ(WideToUTF16(L"\x05e3"), textfield_->GetSelectedText());
VERIFY_HANDLE_POSITIONS(false);
@@ -447,12 +447,12 @@ TEST_F(TouchSelectionControllerImplTest,
textfield_view_->OnGestureEvent(&tap);
// Select some text such that one handle is hidden.
- textfield_->SelectRange(ui::Range(10, textfield_text.length()));
+ textfield_->SelectRange(gfx::Range(10, textfield_text.length()));
// Check that one selection handle is hidden.
EXPECT_FALSE(IsSelectionHandle1Visible());
EXPECT_TRUE(IsSelectionHandle2Visible());
- EXPECT_EQ(ui::Range(10, textfield_text.length()),
+ EXPECT_EQ(gfx::Range(10, textfield_text.length()),
textfield_->GetSelectedRange());
// Drag the visible handle around and make sure the selection end point of the
diff --git a/chromium/ui/views/view.cc b/chromium/ui/views/view.cc
index 080df12881d..d816a0a16d0 100644
--- a/chromium/ui/views/view.cc
+++ b/chromium/ui/views/view.cc
@@ -43,6 +43,10 @@
#include "ui/views/widget/tooltip_manager.h"
#include "ui/views/widget/widget.h"
+#if defined(USE_AURA)
+#include "ui/base/cursor/cursor.h"
+#endif
+
#if defined(OS_WIN)
#include "base/win/scoped_gdi_object.h"
#endif
@@ -176,7 +180,6 @@ View::View()
focus_border_(FocusBorder::CreateDashedFocusBorder()),
flip_canvas_on_paint_for_rtl_ui_(false),
paint_to_layer_(false),
- accelerator_registration_delayed_(false),
accelerator_focus_manager_(NULL),
registered_accelerator_count_(0),
next_focusable_view_(NULL),
@@ -1299,21 +1302,13 @@ void View::ViewHierarchyChanged(const ViewHierarchyChangedDetails& details) {
void View::VisibilityChanged(View* starting_from, bool is_visible) {
}
-void View::NativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view,
- internal::RootView* root_view) {
+void View::NativeViewHierarchyChanged() {
FocusManager* focus_manager = GetFocusManager();
- if (!accelerator_registration_delayed_ &&
- accelerator_focus_manager_ &&
- accelerator_focus_manager_ != focus_manager) {
+ if (accelerator_focus_manager_ != focus_manager) {
UnregisterAccelerators(true);
- accelerator_registration_delayed_ = true;
- }
- if (accelerator_registration_delayed_ && attached) {
- if (focus_manager) {
+
+ if (focus_manager)
RegisterPendingAccelerators();
- accelerator_registration_delayed_ = false;
- }
}
}
@@ -1815,14 +1810,10 @@ void View::PropagateAddNotifications(
ViewHierarchyChangedImpl(true, details);
}
-void View::PropagateNativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view,
- internal::RootView* root_view) {
+void View::PropagateNativeViewHierarchyChanged() {
for (int i = 0, count = child_count(); i < count; ++i)
- child_at(i)->PropagateNativeViewHierarchyChanged(attached,
- native_view,
- root_view);
- NativeViewHierarchyChanged(attached, native_view, root_view);
+ child_at(i)->PropagateNativeViewHierarchyChanged();
+ NativeViewHierarchyChanged();
}
void View::ViewHierarchyChangedImpl(
@@ -1832,13 +1823,8 @@ void View::ViewHierarchyChangedImpl(
if (details.is_add) {
// If you get this registration, you are part of a subtree that has been
// added to the view hierarchy.
- if (GetFocusManager()) {
+ if (GetFocusManager())
RegisterPendingAccelerators();
- } else {
- // Delay accelerator registration until visible as we do not have
- // focus manager until then.
- accelerator_registration_delayed_ = true;
- }
} else {
if (details.child == this)
UnregisterAccelerators(true);
@@ -1851,7 +1837,7 @@ void View::ViewHierarchyChangedImpl(
if (widget)
widget->UpdateRootLayers();
} else if (!details.is_add && details.child == this) {
- // Make sure the layers beloning to the subtree rooted at |child| get
+ // Make sure the layers belonging to the subtree rooted at |child| get
// removed from layers that do not belong in the same subtree.
OrphanLayers();
if (use_acceleration_when_possible) {
@@ -2017,7 +2003,7 @@ bool View::ConvertPointForAncestor(const View* ancestor,
// TODO(sad): Have some way of caching the transformation results.
bool result = GetTransformRelativeTo(ancestor, &trans);
gfx::Point3F p(*point);
- trans.TransformPoint(p);
+ trans.TransformPoint(&p);
*point = gfx::ToFlooredPoint(p.AsPointF());
return result;
}
@@ -2027,7 +2013,7 @@ bool View::ConvertPointFromAncestor(const View* ancestor,
gfx::Transform trans;
bool result = GetTransformRelativeTo(ancestor, &trans);
gfx::Point3F p(*point);
- trans.TransformPointReverse(p);
+ trans.TransformPointReverse(&p);
*point = gfx::ToFlooredPoint(p.AsPointF());
return result;
}
@@ -2229,9 +2215,6 @@ void View::UnregisterAccelerators(bool leave_data_intact) {
if (GetWidget()) {
if (accelerator_focus_manager_) {
- // We may not have a FocusManager if the window containing us is being
- // closed, in which case the FocusManager is being deleted so there is
- // nothing to unregister.
accelerator_focus_manager_->UnregisterAccelerators(this);
accelerator_focus_manager_ = NULL;
}
@@ -2317,11 +2300,20 @@ void View::UpdateTooltip() {
bool View::DoDrag(const ui::LocatedEvent& event,
const gfx::Point& press_pt,
ui::DragDropTypes::DragEventSource source) {
-#if !defined(OS_MACOSX)
int drag_operations = GetDragOperations(press_pt);
if (drag_operations == ui::DragDropTypes::DRAG_NONE)
return false;
+ Widget* widget = GetWidget();
+ // We should only start a drag from an event, implying we have a widget.
+ DCHECK(widget);
+
+ // Don't attempt to start a drag while in the process of dragging. This is
+ // especially important on X where we can get multiple mouse move events when
+ // we start the drag.
+ if (widget->dragged_view())
+ return false;
+
OSExchangeData data;
WriteDragData(press_pt, &data);
@@ -2329,12 +2321,9 @@ bool View::DoDrag(const ui::LocatedEvent& event,
// the RootView can detect it and avoid calling us back.
gfx::Point widget_location(event.location());
ConvertPointToWidget(this, &widget_location);
- GetWidget()->RunShellDrag(this, data, widget_location, drag_operations,
- source);
+ widget->RunShellDrag(this, data, widget_location, drag_operations, source);
+ // WARNING: we may have been deleted.
return true;
-#else
- return false;
-#endif // !defined(OS_MACOSX)
}
} // namespace views
diff --git a/chromium/ui/views/view.h b/chromium/ui/views/view.h
index 2ffc6204be7..b0ed0c0a314 100644
--- a/chromium/ui/views/view.h
+++ b/chromium/ui/views/view.h
@@ -20,11 +20,11 @@
#include "ui/base/accessibility/accessibility_types.h"
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/base/dragdrop/os_exchange_data.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_target.h"
#include "ui/base/ui_base_types.h"
#include "ui/compositor/layer_delegate.h"
#include "ui/compositor/layer_owner.h"
+#include "ui/events/event.h"
+#include "ui/events/event_target.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/vector2d.h"
@@ -1032,17 +1032,13 @@ class VIEWS_EXPORT View : public ui::LayerDelegate,
// invoked for that view as well as all the children recursively.
virtual void VisibilityChanged(View* starting_from, bool is_visible);
- // Called when the native view hierarchy changed.
- // |attached| is true if that view has been attached to a new NativeView
- // hierarchy, false if it has been detached.
- // |native_view| is the NativeView this view was attached/detached from, and
- // |root_view| is the root view associated with the NativeView.
- // Views created without a native view parent don't have a focus manager.
- // When this function is called they could do the processing that requires
- // it - like registering accelerators, for example.
- virtual void NativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view,
- internal::RootView* root_view);
+ // This method is invoked when the parent NativeView of the widget that the
+ // view is attached to has changed and the view hierarchy has not changed.
+ // ViewHierarchyChanged() is called when the parent NativeView of the widget
+ // that the view is attached to is changed as a result of changing the view
+ // hierarchy. Overriding this method is useful for tracking which
+ // FocusManager manages this view.
+ virtual void NativeViewHierarchyChanged();
// Painting ------------------------------------------------------------------
@@ -1260,9 +1256,7 @@ class VIEWS_EXPORT View : public ui::LayerDelegate,
// Propagates NativeViewHierarchyChanged() notification through all the
// children.
- void PropagateNativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view,
- internal::RootView* root_view);
+ void PropagateNativeViewHierarchyChanged();
// Takes care of registering/unregistering accelerators if
// |register_accelerators| true and calls ViewHierarchyChanged().
@@ -1503,10 +1497,6 @@ class VIEWS_EXPORT View : public ui::LayerDelegate,
// Accelerators --------------------------------------------------------------
- // true if when we were added to hierarchy we were without focus manager
- // attempt addition when ancestor chain changed.
- bool accelerator_registration_delayed_;
-
// Focus manager accelerators registered on.
FocusManager* accelerator_focus_manager_;
diff --git a/chromium/ui/views/view_unittest.cc b/chromium/ui/views/view_unittest.cc
index 53b28f3cb93..e0fa07e46b1 100644
--- a/chromium/ui/views/view_unittest.cc
+++ b/chromium/ui/views/view_unittest.cc
@@ -12,12 +12,12 @@
#include "testing/gmock/include/gmock/gmock.h"
#include "ui/base/accelerators/accelerator.h"
#include "ui/base/clipboard/clipboard.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/compositor/compositor.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animator.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/path.h"
#include "ui/gfx/transform.h"
@@ -1545,131 +1545,71 @@ TEST_F(ViewTest, DISABLED_RerouteMouseWheelTest) {
////////////////////////////////////////////////////////////////////////////////
// Native view hierachy
////////////////////////////////////////////////////////////////////////////////
-class TestNativeViewHierarchy : public View {
+class ToplevelWidgetObserverView : public View {
public:
- TestNativeViewHierarchy() {
+ ToplevelWidgetObserverView() : toplevel_(NULL) {
}
-
- virtual void NativeViewHierarchyChanged(
- bool attached,
- gfx::NativeView native_view,
- internal::RootView* root_view) OVERRIDE {
- NotificationInfo info;
- info.attached = attached;
- info.native_view = native_view;
- info.root_view = root_view;
- notifications_.push_back(info);
- };
- struct NotificationInfo {
- bool attached;
- gfx::NativeView native_view;
- internal::RootView* root_view;
- };
- static const size_t kTotalViews = 2;
- std::vector<NotificationInfo> notifications_;
-};
-
-class TestChangeNativeViewHierarchy {
- public:
- explicit TestChangeNativeViewHierarchy(ViewTest *view_test) {
- view_test_ = view_test;
- native_host_ = new NativeViewHost();
- host_ = new Widget;
- Widget::InitParams params =
- view_test->CreateParams(Widget::InitParams::TYPE_POPUP);
- params.bounds = gfx::Rect(0, 0, 500, 300);
- host_->Init(params);
- host_->GetRootView()->AddChildView(native_host_);
- for (size_t i = 0; i < TestNativeViewHierarchy::kTotalViews; ++i) {
- windows_[i] = new Widget;
- Widget::InitParams params(Widget::InitParams::TYPE_CONTROL);
- params.parent = host_->GetNativeView();
- params.bounds = gfx::Rect(0, 0, 500, 300);
- windows_[i]->Init(params);
- root_views_[i] = windows_[i]->GetRootView();
- test_views_[i] = new TestNativeViewHierarchy;
- root_views_[i]->AddChildView(test_views_[i]);
- }
+ virtual ~ToplevelWidgetObserverView() {
}
- ~TestChangeNativeViewHierarchy() {
- for (size_t i = 0; i < TestNativeViewHierarchy::kTotalViews; ++i) {
- windows_[i]->Close();
+ // View overrides:
+ virtual void ViewHierarchyChanged(
+ const ViewHierarchyChangedDetails& details) OVERRIDE {
+ if (details.is_add) {
+ toplevel_ = GetWidget() ? GetWidget()->GetTopLevelWidget() : NULL;
+ } else {
+ toplevel_ = NULL;
}
- host_->Close();
- // Will close and self-delete widgets - no need to manually delete them.
- view_test_->RunPendingMessages();
}
-
- void CheckEnumeratingNativeWidgets() {
- if (!host_->GetTopLevelWidget())
- return;
- Widget::Widgets widgets;
- Widget::GetAllChildWidgets(host_->GetNativeView(), &widgets);
- EXPECT_EQ(TestNativeViewHierarchy::kTotalViews + 1, widgets.size());
- // Unfortunately there is no guarantee the sequence of views here so always
- // go through all of them.
- for (Widget::Widgets::iterator i = widgets.begin();
- i != widgets.end(); ++i) {
- View* root_view = (*i)->GetRootView();
- if (host_->GetRootView() == root_view)
- continue;
- size_t j;
- for (j = 0; j < TestNativeViewHierarchy::kTotalViews; ++j)
- if (root_views_[j] == root_view)
- break;
- // EXPECT_LT/GT/GE() fails to compile with class-defined constants
- // with gcc, with error
- // "error: undefined reference to 'TestNativeViewHierarchy::kTotalViews'"
- // so I forced to use EXPECT_TRUE() instead.
- EXPECT_TRUE(TestNativeViewHierarchy::kTotalViews > j);
- }
+ virtual void NativeViewHierarchyChanged() OVERRIDE {
+ toplevel_ = GetWidget() ? GetWidget()->GetTopLevelWidget() : NULL;
}
- void CheckChangingHierarhy() {
- size_t i;
- for (i = 0; i < TestNativeViewHierarchy::kTotalViews; ++i) {
- // TODO(georgey): use actual hierarchy changes to send notifications.
- static_cast<internal::RootView*>(root_views_[i])->
- NotifyNativeViewHierarchyChanged(false, host_->GetNativeView());
- static_cast<internal::RootView*>(root_views_[i])->
- NotifyNativeViewHierarchyChanged(true, host_->GetNativeView());
- }
- for (i = 0; i < TestNativeViewHierarchy::kTotalViews; ++i) {
- ASSERT_EQ(static_cast<size_t>(2), test_views_[i]->notifications_.size());
- EXPECT_FALSE(test_views_[i]->notifications_[0].attached);
- EXPECT_EQ(host_->GetNativeView(),
- test_views_[i]->notifications_[0].native_view);
- EXPECT_EQ(root_views_[i], test_views_[i]->notifications_[0].root_view);
- EXPECT_TRUE(test_views_[i]->notifications_[1].attached);
- EXPECT_EQ(host_->GetNativeView(),
- test_views_[i]->notifications_[1].native_view);
- EXPECT_EQ(root_views_[i], test_views_[i]->notifications_[1].root_view);
- }
- }
+ Widget* toplevel() { return toplevel_; }
- NativeViewHost* native_host_;
- Widget* host_;
- Widget* windows_[TestNativeViewHierarchy::kTotalViews];
- View* root_views_[TestNativeViewHierarchy::kTotalViews];
- TestNativeViewHierarchy* test_views_[TestNativeViewHierarchy::kTotalViews];
- ViewTest* view_test_;
-};
+ private:
+ Widget* toplevel_;
-TEST_F(ViewTest, ChangeNativeViewHierarchyFindRoots) {
- // TODO(georgey): Fix the test for Linux
-#if defined(OS_WIN)
- TestChangeNativeViewHierarchy test(this);
- test.CheckEnumeratingNativeWidgets();
-#endif
-}
+ DISALLOW_COPY_AND_ASSIGN(ToplevelWidgetObserverView);
+};
-TEST_F(ViewTest, ChangeNativeViewHierarchyChangeHierarchy) {
- // TODO(georgey): Fix the test for Linux
-#if defined(OS_WIN)
- TestChangeNativeViewHierarchy test(this);
- test.CheckChangingHierarhy();
-#endif
+// Test that a view can track the current top level widget by overriding
+// View::ViewHierarchyChanged() and View::NativeViewHierarchyChanged().
+TEST_F(ViewTest, NativeViewHierarchyChanged) {
+ scoped_ptr<Widget> toplevel1(new Widget);
+ Widget::InitParams toplevel1_params =
+ CreateParams(Widget::InitParams::TYPE_POPUP);
+ toplevel1_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ toplevel1->Init(toplevel1_params);
+
+ scoped_ptr<Widget> toplevel2(new Widget);
+ Widget::InitParams toplevel2_params =
+ CreateParams(Widget::InitParams::TYPE_POPUP);
+ toplevel2_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ toplevel2->Init(toplevel2_params);
+
+ Widget* child = new Widget;
+ Widget::InitParams child_params(Widget::InitParams::TYPE_CONTROL);
+ child_params.parent = toplevel1->GetNativeView();
+ child->Init(child_params);
+
+ ToplevelWidgetObserverView* observer_view =
+ new ToplevelWidgetObserverView();
+ EXPECT_EQ(NULL, observer_view->toplevel());
+
+ child->SetContentsView(observer_view);
+ EXPECT_EQ(toplevel1, observer_view->toplevel());
+
+ Widget::ReparentNativeView(child->GetNativeView(),
+ toplevel2->GetNativeView());
+ EXPECT_EQ(toplevel2, observer_view->toplevel());
+
+ observer_view->parent()->RemoveChildView(observer_view);
+ EXPECT_EQ(NULL, observer_view->toplevel());
+
+ // Make |observer_view| |child|'s contents view again so that it gets deleted
+ // with the widget.
+ child->SetContentsView(observer_view);
}
////////////////////////////////////////////////////////////////////////////////
diff --git a/chromium/ui/views/views.gyp b/chromium/ui/views/views.gyp
index de8cdef4e19..8ba7958a728 100644
--- a/chromium/ui/views/views.gyp
+++ b/chromium/ui/views/views.gyp
@@ -95,11 +95,6 @@
'controls/combobox/combobox.cc',
'controls/combobox/combobox.h',
'controls/combobox/combobox_listener.h',
- 'controls/combobox/native_combobox_views.cc',
- 'controls/combobox/native_combobox_views.h',
- 'controls/combobox/native_combobox_win.cc',
- 'controls/combobox/native_combobox_win.h',
- 'controls/combobox/native_combobox_wrapper.h',
'controls/focusable_border.cc',
'controls/focusable_border.h',
'controls/glow_hover_controller.cc',
@@ -237,6 +232,8 @@
'controls/tree/tree_view_controller.h',
'corewm/base_focus_rules.cc',
'corewm/base_focus_rules.h',
+ 'corewm/capture_controller.cc',
+ 'corewm/capture_controller.h',
'corewm/compound_event_filter.cc',
'corewm/compound_event_filter.h',
'corewm/corewm_switches.cc',
@@ -273,6 +270,9 @@
'drag_controller.h',
'drag_utils.cc',
'drag_utils.h',
+ 'event_utils.h',
+ 'event_utils_aura.cc',
+ 'event_utils_win.cc',
'focus/accelerator_handler.h',
'focus/accelerator_handler_aura.cc',
'focus/accelerator_handler_win.cc',
@@ -308,10 +308,17 @@
'layout/layout_constants.h',
'layout/layout_manager.cc',
'layout/layout_manager.h',
+ 'linux_ui/linux_ui.h',
+ 'linux_ui/linux_ui.cc',
+ 'linux_ui/status_icon_linux.h',
+ 'linux_ui/status_icon_linux.cc',
+ 'linux_ui/window_button_order_observer.h',
'metrics.cc',
'metrics.h',
'metrics_aura.cc',
'metrics_win.cc',
+ 'mouse_constants.cc',
+ 'mouse_constants.h',
'mouse_watcher.cc',
'mouse_watcher.h',
'mouse_watcher_view_host.cc',
@@ -347,10 +354,6 @@
'widget/aero_tooltip_manager.h',
'widget/child_window_message_processor.cc',
'widget/child_window_message_processor.h',
- 'widget/desktop_aura/desktop_activation_client.cc',
- 'widget/desktop_aura/desktop_activation_client.h',
- 'widget/desktop_aura/desktop_capture_client.cc',
- 'widget/desktop_aura/desktop_capture_client.h',
'widget/desktop_aura/desktop_cursor_loader_updater.h',
'widget/desktop_aura/desktop_cursor_loader_updater_aurax11.cc',
'widget/desktop_aura/desktop_cursor_loader_updater_aurax11.h',
@@ -362,6 +365,8 @@
'widget/desktop_aura/desktop_drag_drop_client_win.h',
'widget/desktop_aura/desktop_drop_target_win.cc',
'widget/desktop_aura/desktop_drop_target_win.h',
+ 'widget/desktop_aura/desktop_factory_ozone.cc',
+ 'widget/desktop_aura/desktop_factory_ozone.h',
'widget/desktop_aura/desktop_focus_rules.cc',
'widget/desktop_aura/desktop_focus_rules.h',
'widget/desktop_aura/desktop_layout_manager.cc',
@@ -371,16 +376,20 @@
'widget/desktop_aura/desktop_native_widget_aura.cc',
'widget/desktop_aura/desktop_native_widget_aura.h',
'widget/desktop_aura/desktop_root_window_host.h',
+ 'widget/desktop_aura/desktop_root_window_host_ozone.cc',
'widget/desktop_aura/desktop_root_window_host_win.cc',
'widget/desktop_aura/desktop_root_window_host_win.h',
'widget/desktop_aura/desktop_root_window_host_x11.cc',
'widget/desktop_aura/desktop_root_window_host_x11.h',
'widget/desktop_aura/desktop_screen.h',
+ 'widget/desktop_aura/desktop_screen_ozone.cc',
'widget/desktop_aura/desktop_screen_position_client.cc',
'widget/desktop_aura/desktop_screen_position_client.h',
'widget/desktop_aura/desktop_screen_win.cc',
'widget/desktop_aura/desktop_screen_win.h',
'widget/desktop_aura/desktop_screen_x11.cc',
+ 'widget/desktop_aura/scoped_tooltip_client.cc',
+ 'widget/desktop_aura/scoped_tooltip_client.h',
'widget/desktop_aura/x11_desktop_handler.cc',
'widget/desktop_aura/x11_desktop_handler.h',
'widget/desktop_aura/x11_desktop_window_move_client.cc',
@@ -448,6 +457,7 @@
'window/dialog_delegate.h',
'window/frame_background.cc',
'window/frame_background.h',
+ 'window/frame_buttons.h',
'window/native_frame_view.cc',
'window/native_frame_view.h',
'window/non_client_view.cc',
@@ -475,14 +485,6 @@
'widget/tooltip_manager_win.h',
],
'conditions': [
- ['OS=="mac"', {
- 'sources/': [
- ['exclude', 'mouse_watcher.cc'],
- ['exclude', 'controls/menu/'],
- ['exclude', 'controls/scrollbar/'],
- ['exclude', 'focus/accelerator_handler_aura.cc'],
- ],
- }],
['OS=="win"', {
'sources/': [
['include', 'controls/menu/menu_insertion_delegate_win.h'],
@@ -539,10 +541,13 @@
['include', 'accessibility/native_view_accessibility_win.h'],
],
}],
- ['use_aura==1 and OS=="linux" and chromeos==0', {
+ ['OS=="linux" and chromeos==0', {
'dependencies': [
'../ui.gyp:shell_dialogs',
- '../linux_ui/linux_ui.gyp:linux_ui',
+ ],
+ }, { # OS=="linux" and chromeos==0
+ 'sources/': [
+ ['exclude', 'linux_ui'],
],
}],
['OS=="win"', {
@@ -554,6 +559,10 @@
'../../third_party/wtl/include',
],
'link_settings': {
+ 'libraries': [
+ '-limm32.lib',
+ '-loleacc.lib',
+ ],
'msvs_settings': {
'VCLinkerTool': {
'DelayLoadDLLs': [
@@ -614,6 +623,9 @@
'test/test_widget_observer.h',
'test/views_test_base.cc',
'test/views_test_base.h',
+ 'test/widget_test.cc',
+ 'test/widget_test.h',
+ 'widget/root_view_test_helper.h',
],
'conditions': [
['use_aura==1', {
@@ -693,7 +705,7 @@
'controls/button/custom_button_unittest.cc',
'controls/button/image_button_unittest.cc',
'controls/button/label_button_unittest.cc',
- 'controls/combobox/native_combobox_views_unittest.cc',
+ 'controls/combobox/combobox_unittest.cc',
'controls/label_unittest.cc',
'controls/menu/menu_model_adapter_unittest.cc',
'controls/native/native_view_host_aura_unittest.cc',
@@ -713,6 +725,7 @@
'controls/textfield/native_textfield_views_unittest.cc',
'controls/textfield/textfield_views_model_unittest.cc',
'controls/tree/tree_view_unittest.cc',
+ 'corewm/capture_controller_unittest.cc',
'corewm/compound_event_filter_unittest.cc',
'corewm/cursor_manager_unittest.cc',
'corewm/focus_controller_unittest.cc',
@@ -731,20 +744,21 @@
'ime/input_method_bridge_unittest.cc',
'layout/box_layout_unittest.cc',
'layout/grid_layout_unittest.cc',
+ 'run_all_unittests.cc',
'touchui/touch_selection_controller_impl_unittest.cc',
'view_model_unittest.cc',
'view_model_utils_unittest.cc',
'view_unittest.cc',
- 'window/dialog_client_view_unittest.cc',
- 'window/dialog_delegate_unittest.cc',
- 'widget/desktop_aura/desktop_capture_client_unittest.cc',
+ 'widget/desktop_aura/desktop_native_widget_aura_unittest.cc',
'widget/desktop_aura/desktop_screen_position_client_unittest.cc',
'widget/native_widget_aura_unittest.cc',
'widget/native_widget_unittest.cc',
'widget/native_widget_win_unittest.cc',
+ 'widget/root_view_unittest.cc',
'widget/widget_unittest.cc',
'widget/window_reorderer_unittest.cc',
- 'run_all_unittests.cc',
+ 'window/dialog_client_view_unittest.cc',
+ 'window/dialog_delegate_unittest.cc',
],
'conditions': [
['chromeos==0', {
@@ -798,6 +812,11 @@
['exclude', 'widget/window_reorderer_unittest.cc']
],
}],
+ ['use_ozone==1', {
+ 'sources!': [
+ 'corewm/capture_controller_unittest.cc',
+ ],
+ }],
],
}, # target_name: views_unittests
{
diff --git a/chromium/ui/views/widget/aero_tooltip_manager.cc b/chromium/ui/views/widget/aero_tooltip_manager.cc
index b1719def27f..c54124c90bf 100644
--- a/chromium/ui/views/widget/aero_tooltip_manager.cc
+++ b/chromium/ui/views/widget/aero_tooltip_manager.cc
@@ -11,9 +11,9 @@
#include "base/bind.h"
#include "base/message_loop/message_loop.h"
#include "ui/base/l10n/l10n_util_win.h"
-#include "ui/base/win/dpi.h"
-#include "ui/base/win/hwnd_util.h"
#include "ui/gfx/point.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/hwnd_util.h"
namespace views {
@@ -42,13 +42,13 @@ void AeroTooltipManager::OnMouse(UINT u_msg, WPARAM w_param, LPARAM l_param) {
if (u_msg == WM_MOUSEMOVE || u_msg == WM_NCMOUSEMOVE) {
gfx::Point mouse_pos_in_pixels(l_param);
- gfx::Point mouse_pos = ui::win::ScreenToDIPPoint(mouse_pos_in_pixels);
+ gfx::Point mouse_pos = gfx::win::ScreenToDIPPoint(mouse_pos_in_pixels);
if (u_msg == WM_NCMOUSEMOVE) {
// NC message coordinates are in screen coordinates.
POINT temp = mouse_pos_in_pixels.ToPOINT();
::MapWindowPoints(HWND_DESKTOP, GetParent(), &temp, 1);
mouse_pos_in_pixels.SetPoint(temp.x, temp.y);
- mouse_pos = ui::win::ScreenToDIPPoint(mouse_pos_in_pixels);
+ mouse_pos = gfx::win::ScreenToDIPPoint(mouse_pos_in_pixels);
}
if (last_mouse_pos_ != mouse_pos) {
last_mouse_pos_ = mouse_pos;
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_activation_client.cc b/chromium/ui/views/widget/desktop_aura/desktop_activation_client.cc
deleted file mode 100644
index dc8f062cc32..00000000000
--- a/chromium/ui/views/widget/desktop_aura/desktop_activation_client.cc
+++ /dev/null
@@ -1,190 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/views/widget/desktop_aura/desktop_activation_client.h"
-
-#include "base/auto_reset.h"
-#include "base/compiler_specific.h"
-#include "ui/aura/client/activation_delegate.h"
-#include "ui/aura/client/activation_change_observer.h"
-#include "ui/aura/client/focus_client.h"
-#include "ui/aura/root_window.h"
-#include "ui/aura/window.h"
-
-namespace views {
-
-namespace {
-
-aura::Window* FindFocusableWindowFor(aura::Window* window) {
- while (window && !window->CanFocus())
- window = window->parent();
- return window;
-}
-
-} // namespace
-
-DesktopActivationClient::DesktopActivationClient(aura::RootWindow* root_window)
- : root_window_(root_window),
- current_active_(NULL),
- updating_activation_(false),
- observer_manager_(this) {
- aura::client::GetFocusClient(root_window_)->AddObserver(this);
- aura::client::SetActivationClient(root_window_, this);
- root_window->AddPreTargetHandler(this);
-}
-
-DesktopActivationClient::~DesktopActivationClient() {
- root_window_->RemovePreTargetHandler(this);
- aura::client::GetFocusClient(root_window_)->RemoveObserver(this);
- aura::client::SetActivationClient(root_window_, NULL);
-}
-
-void DesktopActivationClient::AddObserver(
- aura::client::ActivationChangeObserver* observer) {
- observers_.AddObserver(observer);
-}
-
-void DesktopActivationClient::RemoveObserver(
- aura::client::ActivationChangeObserver* observer) {
- observers_.RemoveObserver(observer);
-}
-
-void DesktopActivationClient::ActivateWindow(aura::Window* window) {
- // Prevent recursion when called from focus.
- if (updating_activation_)
- return;
-
- base::AutoReset<bool> in_activate_window(&updating_activation_, true);
- // Nothing may actually have changed.
- if (current_active_ == window)
- return;
- // The stacking client may impose rules on what window configurations can be
- // activated or deactivated.
- if (window && !CanActivateWindow(window))
- return;
- // Switch internal focus before we change the activation. Will probably cause
- // recursion.
- if (window &&
- !window->Contains(aura::client::GetFocusClient(window)->
- GetFocusedWindow())) {
- aura::client::GetFocusClient(window)->FocusWindow(window);
- }
-
- aura::Window* old_active = current_active_;
- current_active_ = window;
- if (window && !observer_manager_.IsObserving(window))
- observer_manager_.Add(window);
-
- FOR_EACH_OBSERVER(aura::client::ActivationChangeObserver,
- observers_,
- OnWindowActivated(window, old_active));
- aura::client::ActivationChangeObserver* observer =
- aura::client::GetActivationChangeObserver(old_active);
- if (observer)
- observer->OnWindowActivated(window, old_active);
- observer = aura::client::GetActivationChangeObserver(window);
- if (observer)
- observer->OnWindowActivated(window, old_active);
-}
-
-void DesktopActivationClient::DeactivateWindow(aura::Window* window) {
- if (window == current_active_)
- current_active_ = NULL;
-}
-
-aura::Window* DesktopActivationClient::GetActiveWindow() {
- return current_active_;
-}
-
-aura::Window* DesktopActivationClient::GetActivatableWindow(
- aura::Window* window) {
- aura::Window* parent = window->parent();
- aura::Window* child = window;
- while (parent) {
- if (CanActivateWindow(child))
- return child;
- // If |child| isn't activatable, but has transient parent, trace
- // that path instead.
- if (child->transient_parent())
- return GetActivatableWindow(child->transient_parent());
- parent = parent->parent();
- child = child->parent();
- }
- return NULL;
-}
-
-aura::Window* DesktopActivationClient::GetToplevelWindow(aura::Window* window) {
- aura::Window* parent = window->parent();
- aura::Window* child = window;
- aura::Window* root = child->GetRootWindow();
- while (parent) {
- if (parent == root)
- return child;
- parent = parent->parent();
- child = child->parent();
- }
- return NULL;
-}
-
-bool DesktopActivationClient::OnWillFocusWindow(aura::Window* window,
- const ui::Event* event) {
- return CanActivateWindow(GetActivatableWindow(window));
-}
-
-void DesktopActivationClient::OnWindowDestroying(aura::Window* window) {
- if (current_active_ == window) {
- current_active_ = NULL;
- FOR_EACH_OBSERVER(aura::client::ActivationChangeObserver,
- observers_,
- OnWindowActivated(NULL, window));
-
- // ash::ActivationController will also activate the next window here; we
- // don't do this because that's the desktop environment's job.
- }
- observer_manager_.Remove(window);
-}
-
-void DesktopActivationClient::OnWindowFocused(aura::Window* gained_focus,
- aura::Window* lost_focus) {
- if (gained_focus)
- ActivateWindow(GetActivatableWindow(gained_focus));
-}
-
-bool DesktopActivationClient::CanActivateWindow(aura::Window* window) const {
- return window &&
- window->IsVisible() &&
- (!aura::client::GetActivationDelegate(window) ||
- aura::client::GetActivationDelegate(window)->ShouldActivate());
-}
-
-void DesktopActivationClient::OnKeyEvent(ui::KeyEvent* event) {
-}
-
-void DesktopActivationClient::OnMouseEvent(ui::MouseEvent* event) {
- if (event->type() == ui::ET_MOUSE_PRESSED)
- FocusWindowWithEvent(event);
-}
-
-void DesktopActivationClient::OnScrollEvent(ui::ScrollEvent* event) {
-}
-
-void DesktopActivationClient::OnTouchEvent(ui::TouchEvent* event) {
-}
-
-void DesktopActivationClient::OnGestureEvent(ui::GestureEvent* event) {
- if (event->type() == ui::ET_GESTURE_BEGIN &&
- event->details().touch_points() == 1) {
- FocusWindowWithEvent(event);
- }
-}
-
-void DesktopActivationClient::FocusWindowWithEvent(const ui::Event* event) {
- aura::Window* window = static_cast<aura::Window*>(event->target());
- if (GetActiveWindow() != window) {
- aura::client::GetFocusClient(window)->FocusWindow(
- FindFocusableWindowFor(window));
- }
-}
-
-} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_activation_client.h b/chromium/ui/views/widget/desktop_aura/desktop_activation_client.h
deleted file mode 100644
index b34181792ff..00000000000
--- a/chromium/ui/views/widget/desktop_aura/desktop_activation_client.h
+++ /dev/null
@@ -1,90 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_VIEWS_WIDGET_DESKTOP_AURA_DESTKOP_ACTIVATION_CLIENT_H_
-#define UI_VIEWS_WIDGET_DESKTOP_AURA_DESTKOP_ACTIVATION_CLIENT_H_
-
-#include "base/basictypes.h"
-#include "base/observer_list.h"
-#include "base/scoped_observer.h"
-#include "ui/aura/client/activation_client.h"
-#include "ui/aura/client/focus_change_observer.h"
-#include "ui/aura/env_observer.h"
-#include "ui/aura/root_window_observer.h"
-#include "ui/aura/window_observer.h"
-#include "ui/views/views_export.h"
-
-namespace aura {
-class FocusManager;
-class RootWindow;
-
-namespace client {
-class ActivationChangeObserver;
-}
-}
-
-namespace views {
-
-// An activation client that handles activation events in a single
-// RootWindow. Used only on the Desktop where there can be multiple RootWindow
-// objects.
-class VIEWS_EXPORT DesktopActivationClient
- : public aura::client::ActivationClient,
- public aura::WindowObserver,
- public ui::EventHandler,
- public aura::client::FocusChangeObserver {
- public:
- explicit DesktopActivationClient(aura::RootWindow* root_window);
- virtual ~DesktopActivationClient();
-
- // ActivationClient:
- virtual void AddObserver(
- aura::client::ActivationChangeObserver* observer) OVERRIDE;
- virtual void RemoveObserver(
- aura::client::ActivationChangeObserver* observer) OVERRIDE;
- virtual void ActivateWindow(aura::Window* window) OVERRIDE;
- virtual void DeactivateWindow(aura::Window* window) OVERRIDE;
- virtual aura::Window* GetActiveWindow() OVERRIDE;
- virtual aura::Window* GetActivatableWindow(aura::Window* window) OVERRIDE;
- virtual aura::Window* GetToplevelWindow(aura::Window* window) OVERRIDE;
- virtual bool OnWillFocusWindow(aura::Window* window,
- const ui::Event* event) OVERRIDE;
- virtual bool CanActivateWindow(aura::Window* window) const OVERRIDE;
-
- // Overridden from aura::WindowObserver:
- virtual void OnWindowDestroying(aura::Window* window) OVERRIDE;
-
- // Overridden from aura::client::FocusChangeObserver:
- virtual void OnWindowFocused(aura::Window* gained_focus,
- aura::Window* lost_focus) OVERRIDE;
-
- // Overridden from ui::EventHandler:
- virtual void OnKeyEvent(ui::KeyEvent* event) OVERRIDE;
- virtual void OnMouseEvent(ui::MouseEvent* event) OVERRIDE;
- virtual void OnScrollEvent(ui::ScrollEvent* event) OVERRIDE;
- virtual void OnTouchEvent(ui::TouchEvent* event) OVERRIDE;
- virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE;
-
- private:
- void FocusWindowWithEvent(const ui::Event* event);
-
- aura::RootWindow* root_window_;
-
- // The current active window.
- aura::Window* current_active_;
-
- // True inside ActivateWindow(). Used to prevent recursion of focus
- // change notifications causing activation.
- bool updating_activation_;
-
- ObserverList<aura::client::ActivationChangeObserver> observers_;
-
- ScopedObserver<aura::Window, aura::WindowObserver> observer_manager_;
-
- DISALLOW_COPY_AND_ASSIGN(DesktopActivationClient);
-};
-
-} // namespace views
-
-#endif // UI_VIEWS_WIDGET_DESKTOP_AURA_DESTKOP_ACTIVATION_CLIENT_H_
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_capture_client.cc b/chromium/ui/views/widget/desktop_aura/desktop_capture_client.cc
deleted file mode 100644
index bf89a4eb916..00000000000
--- a/chromium/ui/views/widget/desktop_aura/desktop_capture_client.cc
+++ /dev/null
@@ -1,88 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/views/widget/desktop_aura/desktop_capture_client.h"
-
-#include "ui/aura/root_window.h"
-
-namespace views {
-
-std::set<DesktopCaptureClient*> DesktopCaptureClient::live_capture_clients_;
-
-DesktopCaptureClient::DesktopCaptureClient(aura::RootWindow* root_window)
- : root_window_(root_window),
- capture_window_(NULL) {
- aura::client::SetCaptureClient(root_window_, this);
- live_capture_clients_.insert(this);
-}
-
-DesktopCaptureClient::~DesktopCaptureClient() {
- live_capture_clients_.erase(this);
- aura::client::SetCaptureClient(root_window_, NULL);
-}
-
-void DesktopCaptureClient::SetCapture(aura::Window* window) {
- if (capture_window_ == window)
- return;
- if (window) {
- // If we're actually starting capture, then cancel any touches/gestures
- // that aren't already locked to the new window, and transfer any on the
- // old capture window to the new one. When capture is released we have no
- // distinction between the touches/gestures that were in the window all
- // along (and so shouldn't be canceled) and those that got moved, so
- // just leave them all where they are.
- for (std::set<DesktopCaptureClient*>::iterator it =
- live_capture_clients_.begin(); it != live_capture_clients_.end();
- ++it) {
- (*it)->root_window_->gesture_recognizer()->TransferEventsTo(
- capture_window_, window);
- }
- }
- aura::Window* old_capture_window = GetCaptureWindow();
- capture_window_ = window;
-
- if (capture_window_) {
- root_window_->SetNativeCapture();
-
- for (std::set<DesktopCaptureClient*>::iterator it =
- live_capture_clients_.begin(); it != live_capture_clients_.end();
- ++it) {
- if (*it != this)
- (*it)->OnOtherCaptureClientTookCapture();
- }
- } else {
- root_window_->ReleaseNativeCapture();
- }
-
- root_window_->UpdateCapture(old_capture_window, capture_window_);
-}
-
-void DesktopCaptureClient::ReleaseCapture(aura::Window* window) {
- if (capture_window_ != window)
- return;
- SetCapture(NULL);
-}
-
-aura::Window* DesktopCaptureClient::GetCaptureWindow() {
- for (std::set<DesktopCaptureClient*>::iterator it =
- live_capture_clients_.begin(); it != live_capture_clients_.end();
- ++it) {
- if ((*it)->capture_window_)
- return (*it)->capture_window_;
- }
- return NULL;
-}
-
-void DesktopCaptureClient::OnOtherCaptureClientTookCapture() {
- if (capture_window_ == NULL) {
- // While RootWindow may not technically have capture, it will store state
- // that needs to be cleared on capture changed regarding mouse up/down.
- root_window_->ClearMouseHandlers();
- }
- else {
- SetCapture(NULL);
- }
-}
-
-} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_capture_client.h b/chromium/ui/views/widget/desktop_aura/desktop_capture_client.h
deleted file mode 100644
index ba126826196..00000000000
--- a/chromium/ui/views/widget/desktop_aura/desktop_capture_client.h
+++ /dev/null
@@ -1,44 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef UI_VIEWS_WIDGET_DESKTOP_AURA_DESKTOP_CAPTURE_CLIENT_H_
-#define UI_VIEWS_WIDGET_DESKTOP_AURA_DESKTOP_CAPTURE_CLIENT_H_
-
-#include <set>
-
-#include "base/basictypes.h"
-#include "base/compiler_specific.h"
-#include "ui/aura/client/capture_client.h"
-#include "ui/views/views_export.h"
-
-namespace views {
-
-// A capture client which will collaborate with all other capture clients of
-// its class. When capture is changed in an instance of this capture client,
-// capture is released in all other windows.
-class VIEWS_EXPORT DesktopCaptureClient : public aura::client::CaptureClient {
- public:
- explicit DesktopCaptureClient(aura::RootWindow* root_window);
- virtual ~DesktopCaptureClient();
-
- // Overridden from client::CaptureClient:
- virtual void SetCapture(aura::Window* window) OVERRIDE;
- virtual void ReleaseCapture(aura::Window* window) OVERRIDE;
- virtual aura::Window* GetCaptureWindow() OVERRIDE;
-
- private:
- // Called when another instance of the capture client takes capture.
- void OnOtherCaptureClientTookCapture();
-
- aura::RootWindow* root_window_;
- aura::Window* capture_window_;
-
- static std::set<DesktopCaptureClient*> live_capture_clients_;
-
- DISALLOW_COPY_AND_ASSIGN(DesktopCaptureClient);
-};
-
-} // namespace views
-
-#endif // UI_VIEWS_WIDGET_DESKTOP_AURA_DESKTOP_CAPTURE_CLIENT_H_
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_capture_client_unittest.cc b/chromium/ui/views/widget/desktop_aura/desktop_capture_client_unittest.cc
deleted file mode 100644
index d96c4456724..00000000000
--- a/chromium/ui/views/widget/desktop_aura/desktop_capture_client_unittest.cc
+++ /dev/null
@@ -1,231 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "ui/views/widget/desktop_aura/desktop_capture_client.h"
-
-#include "ui/aura/root_window.h"
-#include "ui/aura/test/aura_test_base.h"
-#include "ui/aura/test/test_screen.h"
-#include "ui/aura/test/test_window_delegate.h"
-#include "ui/base/events/event.h"
-#include "ui/views/test/views_test_base.h"
-#include "ui/views/view.h"
-#include "ui/views/widget/desktop_aura/desktop_screen_position_client.h"
-#include "ui/views/widget/root_view.h"
-#include "ui/views/widget/widget.h"
-
-namespace views {
-
-typedef ViewsTestBase ViewTest;
-
-class DesktopCaptureClientTest : public aura::test::AuraTestBase {
- public:
- virtual void SetUp() OVERRIDE {
- AuraTestBase::SetUp();
- desktop_capture_client_.reset(new DesktopCaptureClient(root_window()));
-
- second_root_.reset(new aura::RootWindow(
- aura::RootWindow::CreateParams(gfx::Rect(0, 0, 800, 600))));
- second_root_->Init();
- second_root_->Show();
- second_root_->SetHostSize(gfx::Size(800, 600));
- second_desktop_capture_client_.reset(
- new DesktopCaptureClient(second_root_.get()));
-
- desktop_position_client_.reset(new DesktopScreenPositionClient());
- aura::client::SetScreenPositionClient(root_window(),
- desktop_position_client_.get());
-
- second_desktop_position_client_.reset(new DesktopScreenPositionClient());
- aura::client::SetScreenPositionClient(
- second_root_.get(),
- second_desktop_position_client_.get());
- }
-
- virtual void TearDown() OVERRIDE {
- RunAllPendingInMessageLoop();
-
- second_desktop_position_client_.reset();
- second_desktop_capture_client_.reset();
-
- // Kill any active compositors before we hit the compositor shutdown paths.
- second_root_.reset();
-
- desktop_position_client_.reset();
- desktop_capture_client_.reset();
-
- AuraTestBase::TearDown();
- }
-
- scoped_ptr<DesktopCaptureClient> desktop_capture_client_;
- scoped_ptr<aura::RootWindow> second_root_;
- scoped_ptr<DesktopCaptureClient> second_desktop_capture_client_;
- scoped_ptr<aura::client::ScreenPositionClient> desktop_position_client_;
- scoped_ptr<aura::client::ScreenPositionClient>
- second_desktop_position_client_;
-};
-
-// Makes sure that internal details that are set on mouse down (such as
-// mouse_pressed_handler()) are cleared when another root window takes capture.
-TEST_F(DesktopCaptureClientTest, ResetMouseEventHandlerOnCapture) {
- // Create a window inside the RootWindow.
- scoped_ptr<aura::Window> w1(CreateNormalWindow(1, root_window(), NULL));
-
- // Make a synthesized mouse down event. Ensure that the RootWindow will
- // dispatch further mouse events to |w1|.
- ui::MouseEvent mouse_pressed_event(ui::ET_MOUSE_PRESSED, gfx::Point(5, 5),
- gfx::Point(5, 5), 0);
- root_window()->AsRootWindowHostDelegate()->OnHostMouseEvent(
- &mouse_pressed_event);
- EXPECT_EQ(w1.get(), root_window()->mouse_pressed_handler());
-
- // Build a window in the second RootWindow.
- scoped_ptr<aura::Window> w2(CreateNormalWindow(2, second_root_.get(), NULL));
-
- // The act of having the second window take capture should clear out mouse
- // pressed handler in the first RootWindow.
- w2->SetCapture();
- EXPECT_EQ(NULL, root_window()->mouse_pressed_handler());
-}
-
-// Makes sure that when one window gets capture, it forces the release on the
-// other. This is needed has to be handled explicitly on Linux, and is a sanity
-// check on Windows.
-TEST_F(DesktopCaptureClientTest, ResetOtherWindowCaptureOnCapture) {
- // Create a window inside the RootWindow.
- scoped_ptr<aura::Window> w1(CreateNormalWindow(1, root_window(), NULL));
- w1->SetCapture();
- // Both capture clients should return the same capture window.
- EXPECT_EQ(w1.get(), desktop_capture_client_->GetCaptureWindow());
- EXPECT_EQ(w1.get(), second_desktop_capture_client_->GetCaptureWindow());
-
- // Build a window in the second RootWindow and give it capture. Both capture
- // clients should return the same capture window.
- scoped_ptr<aura::Window> w2(CreateNormalWindow(2, second_root_.get(), NULL));
- w2->SetCapture();
- EXPECT_EQ(w2.get(), desktop_capture_client_->GetCaptureWindow());
- EXPECT_EQ(w2.get(), second_desktop_capture_client_->GetCaptureWindow());
-}
-
-// This class provides functionality to verify whether the View instance
-// received the gesture event.
-class DesktopViewInputTest : public View {
- public:
- DesktopViewInputTest()
- : received_gesture_event_(false) {}
-
- virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE {
- received_gesture_event_ = true;
- return View::OnGestureEvent(event);
- }
-
- // Resets state maintained by this class.
- void Reset() {
- received_gesture_event_ = false;
- }
-
- bool received_gesture_event() const { return received_gesture_event_; }
-
- private:
- bool received_gesture_event_;
-
- DISALLOW_COPY_AND_ASSIGN(DesktopViewInputTest);
-};
-
-// Tests aura::Window capture and whether gesture events are sent to the window
-// which has capture.
-// The test case creates two visible widgets and sets capture to the underlying
-// aura::Windows one by one. It then sends a gesture event and validates whether
-// the window which had capture receives the gesture.
-TEST_F(ViewTest, CaptureWindowInputEventTest) {
- scoped_ptr<DesktopCaptureClient> desktop_capture_client1;
- scoped_ptr<DesktopCaptureClient> desktop_capture_client2;
- scoped_ptr<aura::client::ScreenPositionClient> desktop_position_client1;
- scoped_ptr<aura::client::ScreenPositionClient> desktop_position_client2;
-
- scoped_ptr<Widget> widget1(new Widget());
- Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
- params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
- params.bounds = gfx::Rect(50, 50, 650, 650);
- widget1->Init(params);
- internal::RootView* root1 =
- static_cast<internal::RootView*>(widget1->GetRootView());
-
- desktop_capture_client1.reset(new DesktopCaptureClient(
- widget1->GetNativeView()->GetRootWindow()));
- desktop_position_client1.reset(new DesktopScreenPositionClient());
- aura::client::SetScreenPositionClient(
- widget1->GetNativeView()->GetRootWindow(),
- desktop_position_client1.get());
-
- DesktopViewInputTest* v1 = new DesktopViewInputTest();
- v1->SetBoundsRect(gfx::Rect(0, 0, 300, 300));
- root1->AddChildView(v1);
- widget1->Show();
-
- scoped_ptr<Widget> widget2(new Widget());
-
- params = CreateParams(Widget::InitParams::TYPE_POPUP);
- params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
- params.bounds = gfx::Rect(50, 50, 650, 650);
- widget2->Init(params);
-
- internal::RootView* root2 =
- static_cast<internal::RootView*>(widget2->GetRootView());
- desktop_capture_client2.reset(new DesktopCaptureClient(
- widget2->GetNativeView()->GetRootWindow()));
- desktop_position_client2.reset(new DesktopScreenPositionClient());
- aura::client::SetScreenPositionClient(
- widget2->GetNativeView()->GetRootWindow(),
- desktop_position_client2.get());
-
- DesktopViewInputTest* v2 = new DesktopViewInputTest();
- v2->SetBoundsRect(gfx::Rect(0, 0, 300, 300));
- root2->AddChildView(v2);
- widget2->Show();
-
- EXPECT_FALSE(widget1->GetNativeView()->HasCapture());
- EXPECT_FALSE(widget2->GetNativeView()->HasCapture());
- EXPECT_EQ(desktop_capture_client1->GetCaptureWindow(),
- reinterpret_cast<aura::Window*>(0));
- EXPECT_EQ(desktop_capture_client2->GetCaptureWindow(),
- reinterpret_cast<aura::Window*>(0));
-
- widget1->GetNativeView()->SetCapture();
- EXPECT_TRUE(widget1->GetNativeView()->HasCapture());
- EXPECT_FALSE(widget2->GetNativeView()->HasCapture());
- EXPECT_EQ(desktop_capture_client1->GetCaptureWindow(),
- widget1->GetNativeView());
- EXPECT_EQ(desktop_capture_client2->GetCaptureWindow(),
- widget1->GetNativeView());
-
- ui::GestureEvent g1(ui::ET_GESTURE_LONG_PRESS, 80, 80, 0,
- base::TimeDelta(),
- ui::GestureEventDetails(ui::ET_GESTURE_LONG_PRESS,
- 0.0f, 0.0f), 0);
- root1->DispatchGestureEvent(&g1);
- EXPECT_TRUE(v1->received_gesture_event());
- EXPECT_FALSE(v2->received_gesture_event());
- v1->Reset();
- v2->Reset();
-
- widget2->GetNativeView()->SetCapture();
-
- EXPECT_FALSE(widget1->GetNativeView()->HasCapture());
- EXPECT_TRUE(widget2->GetNativeView()->HasCapture());
- EXPECT_EQ(desktop_capture_client1->GetCaptureWindow(),
- widget2->GetNativeView());
- EXPECT_EQ(desktop_capture_client2->GetCaptureWindow(),
- widget2->GetNativeView());
-
- root2->DispatchGestureEvent(&g1);
- EXPECT_TRUE(v2->received_gesture_event());
- EXPECT_FALSE(v1->received_gesture_event());
-
- widget1->CloseNow();
- widget2->CloseNow();
- RunPendingMessages();
-}
-
-} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_cursor_loader_updater_aurax11.cc b/chromium/ui/views/widget/desktop_aura/desktop_cursor_loader_updater_aurax11.cc
index e771f69be29..88f219300e0 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_cursor_loader_updater_aurax11.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_cursor_loader_updater_aurax11.cc
@@ -35,8 +35,12 @@ void LoadImageCursors(float device_scale_factor, ui::CursorLoader* loader) {
int resource_id;
gfx::Point point;
for (size_t i = 0; i < arraysize(kImageCursorIds); ++i) {
- bool success = ui::GetCursorDataFor(kImageCursorIds[i], device_scale_factor,
- &resource_id, &point);
+ bool success = ui::GetCursorDataFor(
+ ui::CURSOR_SET_NORMAL, // Not support custom cursor set.
+ kImageCursorIds[i],
+ device_scale_factor,
+ &resource_id,
+ &point);
DCHECK(success);
loader->LoadImageCursor(kImageCursorIds[i], resource_id, point);
}
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.cc b/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.cc
index 1870e11f5b8..bc0e6e9157c 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.cc
@@ -15,9 +15,9 @@
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/base/dragdrop/os_exchange_data.h"
#include "ui/base/dragdrop/os_exchange_data_provider_aurax11.h"
-#include "ui/base/events/event.h"
#include "ui/base/x/selection_utils.h"
#include "ui/base/x/x11_util.h"
+#include "ui/events/event.h"
#include "ui/views/widget/desktop_aura/desktop_native_cursor_manager.h"
using aura::client::DragDropDelegate;
@@ -236,14 +236,13 @@ DesktopDragDropClientAuraX11::X11DragContext::X11DragContext(
if (!client) {
// The window doesn't have a DesktopDragDropClientAuraX11, that means it's
// created by some other process. Listen for messages on it.
- base::MessagePumpAuraX11::Current()->AddDispatcherForWindow(
+ base::MessagePumpX11::Current()->AddDispatcherForWindow(
this, source_window_);
- XSelectInput(base::MessagePumpAuraX11::GetDefaultXDisplay(),
- source_window_, PropertyChangeMask);
+ XSelectInput(gfx::GetXDisplay(), source_window_, PropertyChangeMask);
// We must perform a full sync here because we could be racing
// |source_window_|.
- XSync(base::MessagePumpAuraX11::GetDefaultXDisplay(), False);
+ XSync(gfx::GetXDisplay(), False);
} else {
// This drag originates from an aura window within our process. This means
// that we can shortcut the X11 server and ask the owning SelectionOwner
@@ -260,7 +259,7 @@ DesktopDragDropClientAuraX11::X11DragContext::~X11DragContext() {
DesktopDragDropClientAuraX11::GetForWindow(source_window_);
if (!client) {
// Unsubscribe from message events.
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(
source_window_);
}
}
@@ -289,7 +288,7 @@ void DesktopDragDropClientAuraX11::X11DragContext::RequestNextTarget() {
::Atom target = unfetched_targets_.back();
unfetched_targets_.pop_back();
- XConvertSelection(base::MessagePumpAuraX11::GetDefaultXDisplay(),
+ XConvertSelection(gfx::GetXDisplay(),
atom_cache_->GetAtom(kXdndSelection),
target,
atom_cache_->GetAtom(kChromiumDragReciever),
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.h b/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.h
index 2dee7305f2f..0ebbb9511eb 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.h
@@ -17,6 +17,7 @@
#include "base/memory/scoped_ptr.h"
#include "ui/aura/client/drag_drop_client.h"
#include "ui/aura/window_observer.h"
+#include "ui/base/cursor/cursor.h"
#include "ui/base/x/x11_atom_cache.h"
#include "ui/gfx/point.h"
#include "ui/views/views_export.h"
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_drop_target_win.cc b/chromium/ui/views/widget/desktop_aura/desktop_drop_target_win.cc
index d3a01f3c208..c9c7540b5cb 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_drop_target_win.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_drop_target_win.cc
@@ -4,13 +4,15 @@
#include "ui/views/widget/desktop_aura/desktop_drop_target_win.h"
+#include "base/win/win_util.h"
#include "ui/aura/client/drag_drop_client.h"
#include "ui/aura/client/drag_drop_delegate.h"
#include "ui/aura/window.h"
#include "ui/aura/root_window.h"
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/base/dragdrop/os_exchange_data_provider_win.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
+#include "ui/events/event_constants.h"
using aura::client::DragDropDelegate;
using ui::OSExchangeData;
@@ -121,6 +123,11 @@ void DesktopDropTargetWin::Translate(
location,
root_location,
ui::DragDropTypes::DropEffectToDragOperation(effect)));
+ int flags = 0;
+ flags |= base::win::IsAltPressed() ? ui::EF_ALT_DOWN : ui::EF_NONE;
+ flags |= base::win::IsShiftPressed() ? ui::EF_SHIFT_DOWN : ui::EF_NONE;
+ flags |= base::win::IsCtrlPressed() ? ui::EF_CONTROL_DOWN : ui::EF_NONE;
+ (*event)->set_flags(flags);
if (target_window_changed)
(*delegate)->OnDragEntered(*event->get());
}
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.cc b/chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.cc
new file mode 100644
index 00000000000..e0a44890bc2
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.cc
@@ -0,0 +1,29 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/widget/desktop_aura/desktop_factory_ozone.h"
+
+#include "base/logging.h"
+
+namespace views {
+
+// static
+DesktopFactoryOzone* DesktopFactoryOzone::impl_ = NULL;
+
+DesktopFactoryOzone::DesktopFactoryOzone() {
+}
+
+DesktopFactoryOzone::~DesktopFactoryOzone() {
+}
+
+DesktopFactoryOzone* DesktopFactoryOzone::GetInstance() {
+ CHECK(impl_) << "DesktopFactoryOzone accessed before constructed";
+ return impl_;
+}
+
+void DesktopFactoryOzone::SetInstance(DesktopFactoryOzone* impl) {
+ impl_ = impl;
+}
+
+} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.h b/chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.h
new file mode 100644
index 00000000000..18cf36e8698
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/desktop_factory_ozone.h
@@ -0,0 +1,46 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_WIDGET_DESKTOP_AURA_DESKTOP_FACTORY_OZONE_H_
+#define UI_VIEWS_WIDGET_DESKTOP_AURA_DESKTOP_FACTORY_OZONE_H_
+
+#include "ui/views/views_export.h"
+
+namespace gfx {
+class Rect;
+}
+
+namespace views {
+class DesktopNativeWidgetAura;
+class DesktopRootWindowHost;
+
+namespace internal {
+class NativeWidgetDelegate;
+}
+
+class VIEWS_EXPORT DesktopFactoryOzone {
+ public:
+ DesktopFactoryOzone();
+ virtual ~DesktopFactoryOzone();
+
+ // Returns the instance.
+ static DesktopFactoryOzone* GetInstance();
+
+ // Sets the implementation delegate. Ownership is retained by the caller.
+ static void SetInstance(DesktopFactoryOzone* impl);
+
+ // Delegates implementation of DesktopRootWindowHost::Create externally to
+ // Ozone implementation.
+ virtual DesktopRootWindowHost* CreateRootWindowHost(
+ internal::NativeWidgetDelegate* native_widget_delegate,
+ DesktopNativeWidgetAura* desktop_native_widget_aura,
+ const gfx::Rect& initial_bounds) = 0;
+
+ private:
+ static DesktopFactoryOzone* impl_; // not owned
+};
+
+} // namespace views
+
+#endif // UI_VIEWS_WIDGET_DESKTOP_AURA_DESKTOP_FACTORY_OZONE_H_
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.cc b/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.cc
index 54894f8dc9f..96634f06d57 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.cc
@@ -9,12 +9,16 @@
namespace views {
-DesktopFocusRules::DesktopFocusRules() {}
+DesktopFocusRules::DesktopFocusRules(aura::Window* content_window)
+ : content_window_(content_window) {}
+
DesktopFocusRules::~DesktopFocusRules() {}
bool DesktopFocusRules::SupportsChildActivation(aura::Window* window) const {
- // In Desktop-Aura, only children of the RootWindow are activatable.
- return window->GetRootWindow() == window;
+ // In Desktop-Aura, only the content_window or children of the RootWindow are
+ // activatable.
+ return window == content_window_->parent() ||
+ window->GetRootWindow() == window;
}
} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.h b/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.h
index a7db8c2504f..bb12b1ecf31 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_focus_rules.h
@@ -11,13 +11,17 @@ namespace views {
class DesktopFocusRules : public corewm::BaseFocusRules {
public:
- DesktopFocusRules();
+ explicit DesktopFocusRules(aura::Window* content_window);
virtual ~DesktopFocusRules();
private:
// Overridden from corewm::BaseFocusRules:
virtual bool SupportsChildActivation(aura::Window* window) const OVERRIDE;
+ // The content window. This is an activatable window even though it is a
+ // child.
+ aura::Window* content_window_;
+
DISALLOW_COPY_AND_ASSIGN(DesktopFocusRules);
};
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.cc b/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.cc
index a9b902dee46..eed97f32af5 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.cc
@@ -68,6 +68,11 @@ void DesktopNativeCursorManager::SetVisibility(
root_window_->OnCursorVisibilityChanged(visible);
}
+void DesktopNativeCursorManager::SetCursorSet(
+ ui::CursorSetType cursor_set,
+ views::corewm::NativeCursorManagerDelegate* delegate) {
+ NOTIMPLEMENTED();
+}
void DesktopNativeCursorManager::SetScale(
float scale,
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.h b/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.h
index f6a800bfb9f..563131d92cc 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_native_cursor_manager.h
@@ -49,6 +49,9 @@ class VIEWS_EXPORT DesktopNativeCursorManager
virtual void SetVisibility(
bool visible,
views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE;
+ virtual void SetCursorSet(
+ ui::CursorSetType cursor_set,
+ views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE;
virtual void SetScale(
float scale,
views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE;
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc b/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc
index 207e655e0e6..d5ed686ec1b 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc
@@ -23,19 +23,21 @@
#include "ui/gfx/screen.h"
#include "ui/gfx/size_conversions.h"
#include "ui/native_theme/native_theme.h"
+#include "ui/views/corewm/capture_controller.h"
#include "ui/views/corewm/compound_event_filter.h"
#include "ui/views/corewm/corewm_switches.h"
#include "ui/views/corewm/input_method_event_filter.h"
#include "ui/views/corewm/shadow_controller.h"
#include "ui/views/corewm/shadow_types.h"
-#include "ui/views/corewm/tooltip_controller.h"
#include "ui/views/corewm/visibility_controller.h"
#include "ui/views/corewm/window_modality_controller.h"
#include "ui/views/drag_utils.h"
#include "ui/views/ime/input_method.h"
#include "ui/views/ime/input_method_bridge.h"
#include "ui/views/widget/desktop_aura/desktop_root_window_host.h"
+#include "ui/views/widget/desktop_aura/scoped_tooltip_client.h"
#include "ui/views/widget/drop_helper.h"
+#include "ui/views/widget/native_widget_aura.h"
#include "ui/views/widget/native_widget_aura_window_observer.h"
#include "ui/views/widget/root_view.h"
#include "ui/views/widget/tooltip_manager_aura.h"
@@ -54,38 +56,40 @@ DEFINE_WINDOW_PROPERTY_KEY(DesktopNativeWidgetAura*,
namespace {
-// This class provides functionality to create a top level fullscreen widget to
-// host a child window.
-class DesktopNativeWidgetFullscreenHandler : public aura::WindowObserver {
+// This class provides functionality to create a top level widget to host a
+// child window.
+class DesktopNativeWidgetTopLevelHandler : public aura::WindowObserver {
public:
- // This function creates a full screen widget with the bounds passed in
- // which eventually becomes the parent of the child window passed in.
+ // This function creates a widget with the bounds passed in which eventually
+ // becomes the parent of the child window passed in.
static aura::Window* CreateParentWindow(aura::Window* child_window,
- const gfx::Rect& bounds) {
- // This instance will get deleted when the fullscreen widget is destroyed.
- DesktopNativeWidgetFullscreenHandler* full_screen_handler =
- new DesktopNativeWidgetFullscreenHandler;
+ const gfx::Rect& bounds,
+ bool full_screen) {
+ // This instance will get deleted when the widget is destroyed.
+ DesktopNativeWidgetTopLevelHandler* top_level_handler =
+ new DesktopNativeWidgetTopLevelHandler;
child_window->SetBounds(gfx::Rect(bounds.size()));
Widget::InitParams init_params;
- init_params.type = Widget::InitParams::TYPE_WINDOW;
+ init_params.type = full_screen ? Widget::InitParams::TYPE_WINDOW :
+ Widget::InitParams::TYPE_POPUP;
init_params.bounds = bounds;
init_params.ownership = Widget::InitParams::NATIVE_WIDGET_OWNS_WIDGET;
init_params.layer_type = ui::LAYER_NOT_DRAWN;
-
- // This widget instance will get deleted when the fullscreen window is
+ init_params.can_activate = full_screen;
+ // This widget instance will get deleted when the window is
// destroyed.
- full_screen_handler->full_screen_widget_ = new Widget();
- full_screen_handler->full_screen_widget_->Init(init_params);
+ top_level_handler->top_level_widget_ = new Widget();
+ top_level_handler->top_level_widget_->Init(init_params);
- full_screen_handler->full_screen_widget_->SetFullscreen(true);
- full_screen_handler->full_screen_widget_->Show();
+ top_level_handler->top_level_widget_->SetFullscreen(full_screen);
+ top_level_handler->top_level_widget_->Show();
aura::Window* native_window =
- full_screen_handler->full_screen_widget_->GetNativeView();
- child_window->AddObserver(full_screen_handler);
- native_window->AddObserver(full_screen_handler);
+ top_level_handler->top_level_widget_->GetNativeView();
+ child_window->AddObserver(top_level_handler);
+ native_window->AddObserver(top_level_handler);
return native_window;
}
@@ -95,33 +99,33 @@ class DesktopNativeWidgetFullscreenHandler : public aura::WindowObserver {
// If the widget is being destroyed by the OS then we should not try and
// destroy it again.
- if (full_screen_widget_ &&
- window == full_screen_widget_->GetNativeView()) {
- full_screen_widget_ = NULL;
+ if (top_level_widget_ &&
+ window == top_level_widget_->GetNativeView()) {
+ top_level_widget_ = NULL;
return;
}
- if (full_screen_widget_) {
- DCHECK(full_screen_widget_->GetNativeView());
- full_screen_widget_->GetNativeView()->RemoveObserver(this);
- // When we receive a notification that the child of the fullscreen window
- // created above is being destroyed we go ahead and initiate the
- // destruction of the corresponding widget.
- full_screen_widget_->Close();
- full_screen_widget_ = NULL;
+ if (top_level_widget_) {
+ DCHECK(top_level_widget_->GetNativeView());
+ top_level_widget_->GetNativeView()->RemoveObserver(this);
+ // When we receive a notification that the child of the window created
+ // above is being destroyed we go ahead and initiate the destruction of
+ // the corresponding widget.
+ top_level_widget_->Close();
+ top_level_widget_ = NULL;
}
delete this;
}
private:
- DesktopNativeWidgetFullscreenHandler()
- : full_screen_widget_(NULL) {}
+ DesktopNativeWidgetTopLevelHandler()
+ : top_level_widget_(NULL) {}
- virtual ~DesktopNativeWidgetFullscreenHandler() {}
+ virtual ~DesktopNativeWidgetTopLevelHandler() {}
- Widget* full_screen_widget_;
+ Widget* top_level_widget_;
- DISALLOW_COPY_AND_ASSIGN(DesktopNativeWidgetFullscreenHandler);
+ DISALLOW_COPY_AND_ASSIGN(DesktopNativeWidgetTopLevelHandler);
};
class DesktopNativeWidgetAuraStackingClient :
@@ -139,10 +143,18 @@ class DesktopNativeWidgetAuraStackingClient :
virtual aura::Window* GetDefaultParent(aura::Window* context,
aura::Window* window,
const gfx::Rect& bounds) OVERRIDE {
- if (window->GetProperty(aura::client::kShowStateKey) ==
- ui::SHOW_STATE_FULLSCREEN) {
- return DesktopNativeWidgetFullscreenHandler::CreateParentWindow(window,
- bounds);
+ bool full_screen = window->GetProperty(aura::client::kShowStateKey) ==
+ ui::SHOW_STATE_FULLSCREEN;
+ bool is_menu = false;
+ // TODO(erg): We need to be able to spawn and deal with toplevel windows if
+ // we want the popups to extend past our window
+ // bounds. http://crbug.com/288988
+#if !defined(OS_LINUX)
+ is_menu = window->type() == aura::client::WINDOW_TYPE_MENU;
+#endif
+ if (full_screen || is_menu) {
+ return DesktopNativeWidgetTopLevelHandler::CreateParentWindow(
+ window, bounds, full_screen);
}
return root_window_;
}
@@ -165,6 +177,7 @@ DesktopNativeWidgetAura::DesktopNativeWidgetAura(
can_activate_(true),
desktop_root_window_host_(NULL),
window_(new aura::Window(this)),
+ content_window_container_(NULL),
native_widget_delegate_(delegate),
last_drop_operation_(ui::DragDropTypes::DRAG_NONE),
restore_focus_on_activate_(false),
@@ -218,6 +231,42 @@ void DesktopNativeWidgetAura::InstallInputMethodEventFilter(
root_window_event_filter_->AddHandler(input_method_event_filter_.get());
}
+void DesktopNativeWidgetAura::CreateCaptureClient(aura::RootWindow* root) {
+ DCHECK(!capture_client_.get());
+ capture_client_.reset(new corewm::ScopedCaptureClient(root));
+}
+
+void DesktopNativeWidgetAura::HandleActivationChanged(bool active) {
+ native_widget_delegate_->OnNativeWidgetActivationChanged(active);
+ aura::client::ActivationClient* activation_client =
+ aura::client::GetActivationClient(root_window_.get());
+ if (!activation_client)
+ return;
+ if (active) {
+ if (GetWidget()->HasFocusManager()) {
+ // This function can be called before the focus manager has had a
+ // chance to set the focused view. In which case we should get the
+ // last focused view.
+ View* view_for_activation =
+ GetWidget()->GetFocusManager()->GetFocusedView() ?
+ GetWidget()->GetFocusManager()->GetFocusedView() :
+ GetWidget()->GetFocusManager()->GetStoredFocusView();
+ if (!view_for_activation)
+ view_for_activation = GetWidget()->GetRootView();
+ activation_client->ActivateWindow(
+ view_for_activation->GetWidget()->GetNativeView());
+ }
+ } else {
+ // If we're not active we need to deactivate the corresponding
+ // aura::Window. This way if a child widget is active it gets correctly
+ // deactivated (child widgets don't get native desktop activation changes,
+ // only aura activation changes).
+ aura::Window* active_window = activation_client->GetActiveWindow();
+ if (active_window)
+ activation_client->DeactivateWindow(active_window);
+ }
+}
+
////////////////////////////////////////////////////////////////////////////////
// DesktopNativeWidgetAura, internal::NativeWidgetPrivate implementation:
@@ -225,7 +274,14 @@ void DesktopNativeWidgetAura::InitNativeWidget(
const Widget::InitParams& params) {
ownership_ = params.ownership;
- window_->set_user_data(this);
+ NativeWidgetAura::RegisterNativeWidgetForWindow(this, window_);
+ // Animations on TYPE_WINDOW are handled by the OS. Additionally if we animate
+ // these windows the size of the window gets augmented, effecting restore
+ // bounds and maximized windows in bad ways.
+ if (params.type == Widget::InitParams::TYPE_WINDOW &&
+ !params.remove_standard_frame) {
+ window_->SetProperty(aura::client::kAnimationsDisabledKey, true);
+ }
window_->SetType(GetAuraWindowTypeForWidgetType(params.type));
window_->SetTransparent(true);
window_->Init(params.layer_type);
@@ -240,6 +296,14 @@ void DesktopNativeWidgetAura::InitNativeWidget(
this, params.bounds);
root_window_.reset(
desktop_root_window_host_->Init(window_, params));
+
+ content_window_container_ = new aura::Window(NULL);
+ content_window_container_->Init(ui::LAYER_NOT_DRAWN);
+ content_window_container_->Show();
+ content_window_container_->AddChild(window_);
+ content_window_container_->SetBounds(root_window_->bounds());
+ root_window_->AddChild(content_window_container_);
+
root_window_->AddRootWindowObserver(this);
stacking_client_.reset(
@@ -249,11 +313,8 @@ void DesktopNativeWidgetAura::InitNativeWidget(
aura::client::SetDragDropDelegate(window_, this);
tooltip_manager_.reset(new views::TooltipManagerAura(window_, GetWidget()));
- tooltip_controller_.reset(
- new corewm::TooltipController(gfx::SCREEN_TYPE_NATIVE));
- aura::client::SetTooltipClient(root_window_.get(),
- tooltip_controller_.get());
- root_window_->AddPreTargetHandler(tooltip_controller_.get());
+
+ scoped_tooltip_client_.reset(new ScopedTooltipClient(root_window_.get()));
if (params.opacity == Widget::InitParams::TRANSLUCENT_WINDOW) {
visibility_controller_.reset(new views::corewm::VisibilityController);
@@ -315,15 +376,16 @@ Widget* DesktopNativeWidgetAura::GetTopLevelWidget() {
}
const ui::Compositor* DesktopNativeWidgetAura::GetCompositor() const {
- return window_->layer()->GetCompositor();
+ return window_ ? window_->layer()->GetCompositor() : NULL;
}
ui::Compositor* DesktopNativeWidgetAura::GetCompositor() {
- return window_->layer()->GetCompositor();
+ return const_cast<ui::Compositor*>(
+ const_cast<const DesktopNativeWidgetAura*>(this)->GetCompositor());
}
ui::Layer* DesktopNativeWidgetAura::GetLayer() {
- return window_->layer();
+ return window_ ? window_->layer() : NULL;
}
void DesktopNativeWidgetAura::ReorderNativeViews() {
@@ -335,11 +397,12 @@ void DesktopNativeWidgetAura::ViewRemoved(View* view) {
void DesktopNativeWidgetAura::SetNativeWindowProperty(const char* name,
void* value) {
- window_->SetNativeWindowProperty(name, value);
+ if (window_)
+ window_->SetNativeWindowProperty(name, value);
}
void* DesktopNativeWidgetAura::GetNativeWindowProperty(const char* name) const {
- return window_->GetNativeWindowProperty(name);
+ return window_ ? window_->GetNativeWindowProperty(name) : NULL;
}
TooltipManager* DesktopNativeWidgetAura::GetTooltipManager() const {
@@ -347,6 +410,9 @@ TooltipManager* DesktopNativeWidgetAura::GetTooltipManager() const {
}
void DesktopNativeWidgetAura::SetCapture() {
+ if (!window_)
+ return;
+
window_->SetCapture();
// aura::Window doesn't implicitly update capture on the RootWindowHost, so
// we have to do that manually.
@@ -355,6 +421,9 @@ void DesktopNativeWidgetAura::SetCapture() {
}
void DesktopNativeWidgetAura::ReleaseCapture() {
+ if (!window_)
+ return;
+
window_->ReleaseCapture();
// aura::Window doesn't implicitly update capture on the RootWindowHost, so
// we have to do that manually.
@@ -363,7 +432,8 @@ void DesktopNativeWidgetAura::ReleaseCapture() {
}
bool DesktopNativeWidgetAura::HasCapture() const {
- return window_->HasCapture() && desktop_root_window_host_->HasCapture();
+ return window_ && window_->HasCapture() &&
+ desktop_root_window_host_->HasCapture();
}
InputMethod* DesktopNativeWidgetAura::CreateInputMethod() {
@@ -377,46 +447,53 @@ internal::InputMethodDelegate*
}
void DesktopNativeWidgetAura::CenterWindow(const gfx::Size& size) {
- desktop_root_window_host_->CenterWindow(size);
+ if (window_)
+ desktop_root_window_host_->CenterWindow(size);
}
void DesktopNativeWidgetAura::GetWindowPlacement(
gfx::Rect* bounds,
ui::WindowShowState* maximized) const {
- desktop_root_window_host_->GetWindowPlacement(bounds, maximized);
+ if (window_)
+ desktop_root_window_host_->GetWindowPlacement(bounds, maximized);
}
void DesktopNativeWidgetAura::SetWindowTitle(const string16& title) {
- desktop_root_window_host_->SetWindowTitle(title);
+ if (window_)
+ desktop_root_window_host_->SetWindowTitle(title);
}
void DesktopNativeWidgetAura::SetWindowIcons(const gfx::ImageSkia& window_icon,
const gfx::ImageSkia& app_icon) {
- desktop_root_window_host_->SetWindowIcons(window_icon, app_icon);
+ if (window_)
+ desktop_root_window_host_->SetWindowIcons(window_icon, app_icon);
}
void DesktopNativeWidgetAura::InitModalType(ui::ModalType modal_type) {
// 99% of the time, we should not be asked to create a
- // DesktopNativeWidgetAura that is modal. The case where this breaks down is
- // when there are no browser windows and a background extension tries to
- // display a simple alert dialog. (This case was masked because we used to
- // have a hidden RootWindow which was the parent of these modal dialogs; they
- // weren't displayed to the user.)
+ // DesktopNativeWidgetAura that is modal. We only support window modal
+ // dialogs on the same lines as non AURA.
+ desktop_root_window_host_->InitModalType(modal_type);
}
gfx::Rect DesktopNativeWidgetAura::GetWindowBoundsInScreen() const {
- return desktop_root_window_host_->GetWindowBoundsInScreen();
+ return window_ ? desktop_root_window_host_->GetWindowBoundsInScreen() :
+ gfx::Rect();
}
gfx::Rect DesktopNativeWidgetAura::GetClientAreaBoundsInScreen() const {
- return desktop_root_window_host_->GetClientAreaBoundsInScreen();
+ return window_ ? desktop_root_window_host_->GetClientAreaBoundsInScreen() :
+ gfx::Rect();
}
gfx::Rect DesktopNativeWidgetAura::GetRestoredBounds() const {
- return desktop_root_window_host_->GetRestoredBounds();
+ return window_ ? desktop_root_window_host_->GetRestoredBounds() : gfx::Rect();
}
void DesktopNativeWidgetAura::SetBounds(const gfx::Rect& bounds) {
+ if (!window_)
+ return;
+
float scale = 1;
aura::RootWindow* root = root_window_.get();
if (root) {
@@ -427,10 +504,15 @@ void DesktopNativeWidgetAura::SetBounds(const gfx::Rect& bounds) {
gfx::ToCeiledPoint(gfx::ScalePoint(bounds.origin(), scale)),
gfx::ToFlooredSize(gfx::ScaleSize(bounds.size(), scale)));
desktop_root_window_host_->AsRootWindowHost()->SetBounds(bounds_in_pixels);
+ if (content_window_container_) {
+ content_window_container_->SetBounds(
+ content_window_container_->GetRootWindow()->bounds());
+ }
}
void DesktopNativeWidgetAura::SetSize(const gfx::Size& size) {
- desktop_root_window_host_->SetSize(size);
+ if (window_)
+ desktop_root_window_host_->SetSize(size);
}
void DesktopNativeWidgetAura::StackAbove(gfx::NativeView native_view) {
@@ -443,98 +525,117 @@ void DesktopNativeWidgetAura::StackBelow(gfx::NativeView native_view) {
}
void DesktopNativeWidgetAura::SetShape(gfx::NativeRegion shape) {
- desktop_root_window_host_->SetShape(shape);
+ if (window_)
+ desktop_root_window_host_->SetShape(shape);
}
void DesktopNativeWidgetAura::Close() {
+ if (!window_)
+ return;
desktop_root_window_host_->Close();
- if (window_)
- window_->SuppressPaint();
+ window_->SuppressPaint();
}
void DesktopNativeWidgetAura::CloseNow() {
- desktop_root_window_host_->CloseNow();
+ if (window_)
+ desktop_root_window_host_->CloseNow();
}
void DesktopNativeWidgetAura::Show() {
+ if (!window_)
+ return;
desktop_root_window_host_->AsRootWindowHost()->Show();
window_->Show();
}
void DesktopNativeWidgetAura::Hide() {
+ if (!window_)
+ return;
desktop_root_window_host_->AsRootWindowHost()->Hide();
- if (window_)
- window_->Hide();
+ window_->Hide();
}
void DesktopNativeWidgetAura::ShowMaximizedWithBounds(
const gfx::Rect& restored_bounds) {
+ if (!window_)
+ return;
desktop_root_window_host_->ShowMaximizedWithBounds(restored_bounds);
window_->Show();
}
void DesktopNativeWidgetAura::ShowWithWindowState(ui::WindowShowState state) {
+ if (!window_)
+ return;
desktop_root_window_host_->ShowWindowWithState(state);
window_->Show();
}
bool DesktopNativeWidgetAura::IsVisible() const {
- return desktop_root_window_host_->IsVisible();
+ return window_ && desktop_root_window_host_->IsVisible();
}
void DesktopNativeWidgetAura::Activate() {
- desktop_root_window_host_->Activate();
+ if (window_)
+ desktop_root_window_host_->Activate();
}
void DesktopNativeWidgetAura::Deactivate() {
- desktop_root_window_host_->Deactivate();
+ if (window_)
+ desktop_root_window_host_->Deactivate();
}
bool DesktopNativeWidgetAura::IsActive() const {
- return desktop_root_window_host_->IsActive();
+ return window_ && desktop_root_window_host_->IsActive();
}
void DesktopNativeWidgetAura::SetAlwaysOnTop(bool always_on_top) {
- desktop_root_window_host_->SetAlwaysOnTop(always_on_top);
+ if (window_)
+ desktop_root_window_host_->SetAlwaysOnTop(always_on_top);
}
void DesktopNativeWidgetAura::Maximize() {
- desktop_root_window_host_->Maximize();
+ if (window_)
+ desktop_root_window_host_->Maximize();
}
void DesktopNativeWidgetAura::Minimize() {
- desktop_root_window_host_->Minimize();
+ if (window_)
+ desktop_root_window_host_->Minimize();
}
bool DesktopNativeWidgetAura::IsMaximized() const {
- return desktop_root_window_host_->IsMaximized();
+ return window_ && desktop_root_window_host_->IsMaximized();
}
bool DesktopNativeWidgetAura::IsMinimized() const {
- return desktop_root_window_host_->IsMinimized();
+ return window_ && desktop_root_window_host_->IsMinimized();
}
void DesktopNativeWidgetAura::Restore() {
- desktop_root_window_host_->Restore();
+ if (window_)
+ desktop_root_window_host_->Restore();
}
void DesktopNativeWidgetAura::SetFullscreen(bool fullscreen) {
- desktop_root_window_host_->SetFullscreen(fullscreen);
+ if (window_)
+ desktop_root_window_host_->SetFullscreen(fullscreen);
}
bool DesktopNativeWidgetAura::IsFullscreen() const {
- return desktop_root_window_host_->IsFullscreen();
+ return window_ && desktop_root_window_host_->IsFullscreen();
}
void DesktopNativeWidgetAura::SetOpacity(unsigned char opacity) {
- desktop_root_window_host_->SetOpacity(opacity);
+ if (window_)
+ desktop_root_window_host_->SetOpacity(opacity);
}
void DesktopNativeWidgetAura::SetUseDragFrame(bool use_drag_frame) {
}
void DesktopNativeWidgetAura::FlashFrame(bool flash_frame) {
- desktop_root_window_host_->FlashFrame(flash_frame);
+ if (window_)
+ desktop_root_window_host_->FlashFrame(flash_frame);
}
void DesktopNativeWidgetAura::RunShellDrag(
@@ -560,6 +661,8 @@ void DesktopNativeWidgetAura::SetCursor(gfx::NativeCursor cursor) {
}
bool DesktopNativeWidgetAura::IsMouseEventsEnabled() const {
+ if (!window_)
+ return false;
aura::client::CursorClient* cursor_client =
aura::client::GetCursorClient(window_->GetRootWindow());
return cursor_client ? cursor_client->IsMouseEventsEnabled() : true;
@@ -579,34 +682,45 @@ gfx::Rect DesktopNativeWidgetAura::GetWorkAreaBoundsInScreen() const {
}
void DesktopNativeWidgetAura::SetInactiveRenderingDisabled(bool value) {
+ if (!window_)
+ return;
+
if (!value) {
active_window_observer_.reset();
} else {
active_window_observer_.reset(
new NativeWidgetAuraWindowObserver(window_, native_widget_delegate_));
}
- desktop_root_window_host_->SetInactiveRenderingDisabled(value);
}
Widget::MoveLoopResult DesktopNativeWidgetAura::RunMoveLoop(
const gfx::Vector2d& drag_offset,
Widget::MoveLoopSource source) {
+ if (!window_)
+ return Widget::MOVE_LOOP_CANCELED;
return desktop_root_window_host_->RunMoveLoop(drag_offset, source);
}
void DesktopNativeWidgetAura::EndMoveLoop() {
- desktop_root_window_host_->EndMoveLoop();
+ if (window_)
+ desktop_root_window_host_->EndMoveLoop();
}
void DesktopNativeWidgetAura::SetVisibilityChangedAnimationsEnabled(
bool value) {
- desktop_root_window_host_->SetVisibilityChangedAnimationsEnabled(value);
+ if (window_)
+ desktop_root_window_host_->SetVisibilityChangedAnimationsEnabled(value);
}
ui::NativeTheme* DesktopNativeWidgetAura::GetNativeTheme() const {
return DesktopRootWindowHost::GetNativeTheme(window_);
}
+void DesktopNativeWidgetAura::OnRootViewLayout() const {
+ if (window_)
+ desktop_root_window_host_->OnRootViewLayout();
+}
+
////////////////////////////////////////////////////////////////////////////////
// DesktopNativeWidgetAura, aura::WindowDelegate implementation:
@@ -624,6 +738,10 @@ void DesktopNativeWidgetAura::OnBoundsChanged(const gfx::Rect& old_bounds,
native_widget_delegate_->OnNativeWidgetMove();
if (old_bounds.size() != new_bounds.size())
native_widget_delegate_->OnNativeWidgetSizeChanged(new_bounds.size());
+ if (content_window_container_) {
+ content_window_container_->SetBounds(
+ content_window_container_->GetRootWindow()->bounds());
+ }
}
gfx::NativeCursor DesktopNativeWidgetAura::GetCursor(const gfx::Point& point) {
@@ -665,11 +783,7 @@ void DesktopNativeWidgetAura::OnWindowDestroying() {
shadow_controller_.reset();
// The DesktopRootWindowHost implementation sends OnNativeWidgetDestroying().
tooltip_manager_.reset();
- if (tooltip_controller_.get()) {
- root_window_->RemovePreTargetHandler(tooltip_controller_.get());
- tooltip_controller_.reset();
- aura::client::SetTooltipClient(root_window_.get(), NULL);
- }
+ scoped_tooltip_client_.reset();
if (window_modality_controller_) {
root_window_->RemovePreTargetHandler(window_modality_controller_.get());
window_modality_controller_.reset();
@@ -694,12 +808,8 @@ void DesktopNativeWidgetAura::GetHitTestMask(gfx::Path* mask) const {
native_widget_delegate_->GetHitTestMask(mask);
}
-scoped_refptr<ui::Texture> DesktopNativeWidgetAura::CopyTexture() {
- // The layer we create doesn't have an external texture, so this should never
- // get invoked.
- NOTREACHED();
- return scoped_refptr<ui::Texture>();
-}
+void DesktopNativeWidgetAura::DidRecreateLayer(ui::Layer* old_layer,
+ ui::Layer* new_layer) {}
////////////////////////////////////////////////////////////////////////////////
// DesktopNativeWidgetAura, ui::EventHandler implementation:
@@ -780,28 +890,10 @@ void DesktopNativeWidgetAura::OnWindowActivated(aura::Window* gained_active,
restore_focus_on_activate_ = false;
GetWidget()->GetFocusManager()->RestoreFocusedView();
} else if (lost_active == window_ && GetWidget()->HasFocusManager()) {
- bool store_focused_view = corewm::UseFocusControllerOnDesktop();
- if (!store_focused_view) {
- // If we're losing focus to a window that is a top level (such as a
- // bubble) store the focus. Such a window shares the same
- // RootWindowHost, so that such a change won't trigger an activation
- // change (which calls StoreFocusedView()). Without this the focused
- // view is never told it lost focus.
- aura::Window* focused_window =
- aura::client::GetFocusClient(window_)->GetFocusedWindow();
- if (focused_window && focused_window != window_) {
- Widget* focused_widget =
- Widget::GetWidgetForNativeWindow(focused_window);
- store_focused_view = focused_widget && focused_widget != GetWidget() &&
- focused_widget->is_top_level();
- }
- }
- if (store_focused_view) {
- DCHECK(!restore_focus_on_activate_);
- restore_focus_on_activate_ = true;
- // Pass in false so that ClearNativeFocus() isn't invoked.
- GetWidget()->GetFocusManager()->StoreFocusedView(false);
- }
+ DCHECK(!restore_focus_on_activate_);
+ restore_focus_on_activate_ = true;
+ // Pass in false so that ClearNativeFocus() isn't invoked.
+ GetWidget()->GetFocusManager()->StoreFocusedView(false);
}
}
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.h b/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.h
index b98e1ccc7f9..a70e767ebde 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura.h
@@ -12,6 +12,7 @@
#include "ui/aura/client/focus_change_observer.h"
#include "ui/aura/root_window_observer.h"
#include "ui/aura/window_delegate.h"
+#include "ui/base/cursor/cursor.h"
#include "ui/views/ime/input_method_delegate.h"
#include "ui/views/widget/native_widget_private.h"
@@ -27,8 +28,8 @@ namespace views {
namespace corewm {
class CompoundEventFilter;
class InputMethodEventFilter;
+class ScopedCaptureClient;
class ShadowController;
-class TooltipController;
class VisibilityController;
class WindowModalityController;
}
@@ -36,6 +37,7 @@ class WindowModalityController;
class DesktopRootWindowHost;
class DropHelper;
class NativeWidgetAuraWindowObserver;
+class ScopedTooltipClient;
class TooltipManagerAura;
class WindowReorderer;
@@ -69,9 +71,16 @@ class VIEWS_EXPORT DesktopNativeWidgetAura
return root_window_event_filter_;
}
+ // Invoked from DesktopRootWindowHost creation to create the CaptureClient.
+ void CreateCaptureClient(aura::RootWindow* root);
+
// Overridden from NativeWidget:
virtual ui::EventHandler* GetEventHandler() OVERRIDE;
+ // Ensures that the correct window is activated/deactivated based on whether
+ // we are being activated/deactivated.
+ void HandleActivationChanged(bool active);
+
protected:
// Overridden from internal::NativeWidgetPrivate:
virtual void InitNativeWidget(const Widget::InitParams& params) OVERRIDE;
@@ -152,6 +161,7 @@ class VIEWS_EXPORT DesktopNativeWidgetAura
virtual void EndMoveLoop() OVERRIDE;
virtual void SetVisibilityChangedAnimationsEnabled(bool value) OVERRIDE;
virtual ui::NativeTheme* GetNativeTheme() const OVERRIDE;
+ virtual void OnRootViewLayout() const OVERRIDE;
// Overridden from aura::WindowDelegate:
virtual gfx::Size GetMinimumSize() const OVERRIDE;
@@ -172,7 +182,8 @@ class VIEWS_EXPORT DesktopNativeWidgetAura
virtual void OnWindowTargetVisibilityChanged(bool visible) OVERRIDE;
virtual bool HasHitTestMask() const OVERRIDE;
virtual void GetHitTestMask(gfx::Path* mask) const OVERRIDE;
- virtual scoped_refptr<ui::Texture> CopyTexture() OVERRIDE;
+ virtual void DidRecreateLayer(ui::Layer* old_layer,
+ ui::Layer* new_layer) OVERRIDE;
// Overridden from ui::EventHandler:
virtual void OnKeyEvent(ui::KeyEvent* event) OVERRIDE;
@@ -209,6 +220,8 @@ class VIEWS_EXPORT DesktopNativeWidgetAura
// See class documentation for Widget in widget.h for a note about ownership.
Widget::InitParams::Ownership ownership_;
+ scoped_ptr<corewm::ScopedCaptureClient> capture_client_;
+
// The NativeWidget owns the RootWindow. Required because the RootWindow owns
// its RootWindowHost, so DesktopRootWindowHost can't own it.
scoped_ptr<aura::RootWindow> root_window_;
@@ -224,7 +237,16 @@ class VIEWS_EXPORT DesktopNativeWidgetAura
// Ownership passed to RootWindow on Init.
DesktopRootWindowHost* desktop_root_window_host_;
+
+ // The content of |root_window_|. WARNING: this may be NULL if deleted out
+ // from under us.
aura::Window* window_;
+
+ // Contains the content window defined above. Ensures that ZOrder changes
+ // occurring in the content window hierarchy don't affect the other children
+ // of the root window.
+ aura::Window* content_window_container_;
+
internal::NativeWidgetDelegate* native_widget_delegate_;
scoped_ptr<aura::client::StackingClient> stacking_client_;
@@ -237,7 +259,7 @@ class VIEWS_EXPORT DesktopNativeWidgetAura
scoped_ptr<DropHelper> drop_helper_;
int last_drop_operation_;
- scoped_ptr<corewm::TooltipController> tooltip_controller_;
+ scoped_ptr<ScopedTooltipClient> scoped_tooltip_client_;
scoped_ptr<TooltipManagerAura> tooltip_manager_;
scoped_ptr<views::corewm::VisibilityController> visibility_controller_;
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura_unittest.cc b/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura_unittest.cc
new file mode 100644
index 00000000000..1342abaa310
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/desktop_native_widget_aura_unittest.cc
@@ -0,0 +1,27 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/aura/window.h"
+#include "ui/views/test/views_test_base.h"
+#include "ui/views/widget/desktop_aura/desktop_native_widget_aura.h"
+#include "ui/views/widget/widget.h"
+
+namespace views {
+
+typedef ViewsTestBase DesktopNativeWidgetAuraTest;
+
+// Verifies creating a Widget with a parent that is not in a RootWindow doesn't
+// crash.
+TEST_F(DesktopNativeWidgetAuraTest, CreateWithParentNotInRootWindow) {
+ scoped_ptr<aura::Window> window(new aura::Window(NULL));
+ Widget widget;
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_WINDOW);
+ params.bounds = gfx::Rect(0, 0, 200, 200);
+ params.parent = window.get();
+ params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ params.native_widget = new DesktopNativeWidgetAura(&widget);
+ widget.Init(params);
+}
+
+} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host.h b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host.h
index afc412aad65..583b0ac5773 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host.h
@@ -109,13 +109,12 @@ class VIEWS_EXPORT DesktopRootWindowHost {
virtual void FlashFrame(bool flash_frame) = 0;
+ virtual void OnRootViewLayout() const = 0;
+
// Called when the DesktopNativeWidgetAura's aura::Window is focused and
// blurred.
virtual void OnNativeWidgetFocus() = 0;
virtual void OnNativeWidgetBlur() = 0;
-
- // Paints the host window as activated depending on the bool passed in.
- virtual void SetInactiveRenderingDisabled(bool disable_inactive) = 0;
};
} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_ozone.cc b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_ozone.cc
new file mode 100644
index 00000000000..ff905a3e583
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_ozone.cc
@@ -0,0 +1,22 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/aura/root_window_host.h"
+#include "ui/views/widget/desktop_aura/desktop_root_window_host.h"
+#include "ui/views/widget/desktop_aura/desktop_factory_ozone.h"
+
+namespace views {
+
+DesktopRootWindowHost* DesktopRootWindowHost::Create(
+ internal::NativeWidgetDelegate* native_widget_delegate,
+ DesktopNativeWidgetAura* desktop_native_widget_aura,
+ const gfx::Rect& initial_bounds) {
+ DesktopFactoryOzone* d_factory = DesktopFactoryOzone::GetInstance();
+
+ return d_factory->CreateRootWindowHost(native_widget_delegate,
+ desktop_native_widget_aura,
+ initial_bounds);
+}
+
+} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.cc b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.cc
index 159ffc1080e..ae4a982b19e 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.cc
@@ -15,11 +15,11 @@
#include "ui/base/cursor/cursor_loader_win.h"
#include "ui/base/ime/input_method.h"
#include "ui/base/ime/win/tsf_bridge.h"
-#include "ui/base/win/dpi.h"
#include "ui/base/win/shell.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/path_win.h"
+#include "ui/gfx/win/dpi.h"
#include "ui/native_theme/native_theme_aura.h"
#include "ui/native_theme/native_theme_win.h"
#include "ui/views/corewm/compound_event_filter.h"
@@ -29,8 +29,6 @@
#include "ui/views/corewm/input_method_event_filter.h"
#include "ui/views/corewm/window_animations.h"
#include "ui/views/ime/input_method_bridge.h"
-#include "ui/views/widget/desktop_aura/desktop_activation_client.h"
-#include "ui/views/widget/desktop_aura/desktop_capture_client.h"
#include "ui/views/widget/desktop_aura/desktop_cursor_loader_updater.h"
#include "ui/views/widget/desktop_aura/desktop_dispatcher_client.h"
#include "ui/views/widget/desktop_aura/desktop_drag_drop_client_win.h"
@@ -68,10 +66,8 @@ DesktopRootWindowHostWin::DesktopRootWindowHostWin(
}
DesktopRootWindowHostWin::~DesktopRootWindowHostWin() {
- if (corewm::UseFocusControllerOnDesktop()) {
- aura::client::SetFocusClient(root_window_, NULL);
- aura::client::SetActivationClient(root_window_, NULL);
- }
+ aura::client::SetFocusClient(root_window_, NULL);
+ aura::client::SetActivationClient(root_window_, NULL);
}
// static
@@ -109,46 +105,32 @@ aura::RootWindow* DesktopRootWindowHostWin::Init(
native_widget_delegate_);
HWND parent_hwnd = NULL;
- aura::Window* parent_window = params.parent;
- if (parent_window)
- parent_hwnd = parent_window->GetRootWindow()->GetAcceleratedWidget();
+ if (params.parent && params.parent->GetRootWindow())
+ parent_hwnd = params.parent->GetRootWindow()->GetAcceleratedWidget();
message_handler_->set_remove_standard_frame(params.remove_standard_frame);
has_non_client_view_ = Widget::RequiresNonClientView(params.type);
- gfx::Rect pixel_bounds = ui::win::DIPToScreenRect(params.bounds);
+ gfx::Rect pixel_bounds = gfx::win::DIPToScreenRect(params.bounds);
message_handler_->Init(parent_hwnd, pixel_bounds);
aura::RootWindow::CreateParams rw_params(params.bounds);
rw_params.host = this;
root_window_ = new aura::RootWindow(rw_params);
- // TODO(beng): We probably need to move these two calls to some function that
- // can change depending on the native-ness of the frame. For right
- // now in the hack-n-slash days of win-aura, we can just
- // unilaterally turn this on.
- root_window_->compositor()->SetHostHasTransparentBackground(true);
- root_window_->SetTransparent(true);
-
+ SetWindowTransparency();
root_window_->Init();
root_window_->AddChild(content_window_);
- capture_client_.reset(new views::DesktopCaptureClient(root_window_));
- aura::client::SetCaptureClient(root_window_, capture_client_.get());
+ desktop_native_widget_aura_->CreateCaptureClient(root_window_);
- if (corewm::UseFocusControllerOnDesktop()) {
- corewm::FocusController* focus_controller =
- new corewm::FocusController(new DesktopFocusRules);
- focus_client_.reset(focus_controller);
- aura::client::SetFocusClient(root_window_, focus_controller);
- aura::client::SetActivationClient(root_window_, focus_controller);
- root_window_->AddPreTargetHandler(focus_controller);
- } else {
- focus_client_.reset(new aura::FocusManager);
- aura::client::SetFocusClient(root_window_, focus_client_.get());
- activation_client_.reset(new DesktopActivationClient(root_window_));
- }
+ corewm::FocusController* focus_controller =
+ new corewm::FocusController(new DesktopFocusRules(content_window));
+ focus_client_.reset(focus_controller);
+ aura::client::SetFocusClient(root_window_, focus_controller);
+ aura::client::SetActivationClient(root_window_, focus_controller);
+ root_window_->AddPreTargetHandler(focus_controller);
dispatcher_client_.reset(new DesktopDispatcherClient);
aura::client::SetDispatcherClient(root_window_,
@@ -220,7 +202,7 @@ void DesktopRootWindowHostWin::ShowWindowWithState(
void DesktopRootWindowHostWin::ShowMaximizedWithBounds(
const gfx::Rect& restored_bounds) {
- gfx::Rect pixel_bounds = ui::win::DIPToScreenRect(restored_bounds);
+ gfx::Rect pixel_bounds = gfx::win::DIPToScreenRect(restored_bounds);
message_handler_->ShowMaximizedWithBounds(pixel_bounds);
}
@@ -229,12 +211,12 @@ bool DesktopRootWindowHostWin::IsVisible() const {
}
void DesktopRootWindowHostWin::SetSize(const gfx::Size& size) {
- gfx::Size size_in_pixels = ui::win::DIPToScreenSize(size);
+ gfx::Size size_in_pixels = gfx::win::DIPToScreenSize(size);
message_handler_->SetSize(size_in_pixels);
}
void DesktopRootWindowHostWin::CenterWindow(const gfx::Size& size) {
- gfx::Size size_in_pixels = ui::win::DIPToScreenSize(size);
+ gfx::Size size_in_pixels = gfx::win::DIPToScreenSize(size);
message_handler_->CenterWindow(size_in_pixels);
}
@@ -242,22 +224,22 @@ void DesktopRootWindowHostWin::GetWindowPlacement(
gfx::Rect* bounds,
ui::WindowShowState* show_state) const {
message_handler_->GetWindowPlacement(bounds, show_state);
- *bounds = ui::win::ScreenToDIPRect(*bounds);
+ *bounds = gfx::win::ScreenToDIPRect(*bounds);
}
gfx::Rect DesktopRootWindowHostWin::GetWindowBoundsInScreen() const {
gfx::Rect pixel_bounds = message_handler_->GetWindowBoundsInScreen();
- return ui::win::ScreenToDIPRect(pixel_bounds);
+ return gfx::win::ScreenToDIPRect(pixel_bounds);
}
gfx::Rect DesktopRootWindowHostWin::GetClientAreaBoundsInScreen() const {
gfx::Rect pixel_bounds = message_handler_->GetClientAreaBoundsInScreen();
- return ui::win::ScreenToDIPRect(pixel_bounds);
+ return gfx::win::ScreenToDIPRect(pixel_bounds);
}
gfx::Rect DesktopRootWindowHostWin::GetRestoredBounds() const {
gfx::Rect pixel_bounds = message_handler_->GetRestoredBounds();
- return ui::win::ScreenToDIPRect(pixel_bounds);
+ return gfx::win::ScreenToDIPRect(pixel_bounds);
}
gfx::Rect DesktopRootWindowHostWin::GetWorkAreaBoundsInScreen() const {
@@ -267,7 +249,7 @@ gfx::Rect DesktopRootWindowHostWin::GetWorkAreaBoundsInScreen() const {
MONITOR_DEFAULTTONEAREST),
&monitor_info);
gfx::Rect pixel_bounds = gfx::Rect(monitor_info.rcWork);
- return ui::win::ScreenToDIPRect(pixel_bounds);
+ return gfx::win::ScreenToDIPRect(pixel_bounds);
}
void DesktopRootWindowHostWin::SetShape(gfx::NativeRegion native_region) {
@@ -347,6 +329,7 @@ bool DesktopRootWindowHostWin::ShouldUseNativeFrame() {
void DesktopRootWindowHostWin::FrameTypeChanged() {
message_handler_->FrameTypeChanged();
+ SetWindowTransparency();
}
NonClientFrameView* DesktopRootWindowHostWin::CreateNonClientFrameView() {
@@ -356,6 +339,7 @@ NonClientFrameView* DesktopRootWindowHostWin::CreateNonClientFrameView() {
void DesktopRootWindowHostWin::SetFullscreen(bool fullscreen) {
message_handler_->fullscreen_handler()->SetFullscreen(fullscreen);
+ SetWindowTransparency();
}
bool DesktopRootWindowHostWin::IsFullscreen() const {
@@ -381,6 +365,9 @@ void DesktopRootWindowHostWin::FlashFrame(bool flash_frame) {
message_handler_->FlashFrame(flash_frame);
}
+void DesktopRootWindowHostWin::OnRootViewLayout() const {
+}
+
void DesktopRootWindowHostWin::OnNativeWidgetFocus() {
// HWNDMessageHandler will perform the proper updating on its own.
}
@@ -388,13 +375,6 @@ void DesktopRootWindowHostWin::OnNativeWidgetFocus() {
void DesktopRootWindowHostWin::OnNativeWidgetBlur() {
}
-void DesktopRootWindowHostWin::SetInactiveRenderingDisabled(
- bool disable_inactive) {
- // Force the non-client area (most notably the title bar) to paint as either
- // active or inactive, depending on the input.
- SendMessage(message_handler_->hwnd(), WM_NCACTIVATE, !!disable_inactive, 0);
-}
-
////////////////////////////////////////////////////////////////////////////////
// DesktopRootWindowHostWin, RootWindowHost implementation:
@@ -422,6 +402,7 @@ void DesktopRootWindowHostWin::Hide() {
}
void DesktopRootWindowHostWin::ToggleFullScreen() {
+ SetWindowTransparency();
}
// GetBounds and SetBounds work in pixel coordinates, whereas other get/set
@@ -506,14 +487,6 @@ void DesktopRootWindowHostWin::MoveCursorTo(const gfx::Point& location) {
void DesktopRootWindowHostWin::SetFocusWhenShown(bool focus_when_shown) {
}
-bool DesktopRootWindowHostWin::CopyAreaToSkCanvas(
- const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- NOTIMPLEMENTED();
- return false;
-}
-
void DesktopRootWindowHostWin::PostNativeEvent(
const base::NativeEvent& native_event) {
}
@@ -610,7 +583,7 @@ bool DesktopRootWindowHostWin::WillProcessWorkAreaChange() const {
int DesktopRootWindowHostWin::GetNonClientComponent(
const gfx::Point& point) const {
- gfx::Point dip_position = ui::win::ScreenToDIPPoint(point);
+ gfx::Point dip_position = gfx::win::ScreenToDIPPoint(point);
return native_widget_delegate_->GetNonClientComponent(dip_position);
}
@@ -661,20 +634,7 @@ void DesktopRootWindowHostWin::HandleAppDeactivated() {
void DesktopRootWindowHostWin::HandleActivationChanged(bool active) {
if (active)
root_window_host_delegate_->OnHostActivated();
- native_widget_delegate_->OnNativeWidgetActivationChanged(active);
- // If we're not active we need to deactivate the corresponding aura::Window.
- // This way if a child widget is active it gets correctly deactivated (child
- // widgets don't get native desktop activation changes, only aura activation
- // changes).
- if (!active) {
- aura::client::ActivationClient* activation_client =
- aura::client::GetActivationClient(root_window_);
- if (activation_client) {
- aura::Window* active_window = activation_client->GetActiveWindow();
- if (active_window)
- activation_client->DeactivateWindow(active_window);
- }
- }
+ desktop_native_widget_aura_->HandleActivationChanged(active);
}
bool DesktopRootWindowHostWin::HandleAppCommand(short command) {
@@ -751,6 +711,10 @@ void DesktopRootWindowHostWin::HandleWorkAreaChanged() {
GetWidget()->widget_delegate()->OnWorkAreaChanged();
}
+void DesktopRootWindowHostWin::HandleVisibilityChanging(bool visible) {
+ native_widget_delegate_->OnNativeWidgetVisibilityChanging(visible);
+}
+
void DesktopRootWindowHostWin::HandleVisibilityChanged(bool visible) {
native_widget_delegate_->OnNativeWidgetVisibilityChanged(visible);
}
@@ -762,7 +726,7 @@ void DesktopRootWindowHostWin::HandleClientSizeChanged(
if (root_window_host_delegate_)
root_window_host_delegate_->OnHostResized(new_size);
// TODO(beng): replace with a layout manager??
- gfx::Size dip_size = ui::win::ScreenToDIPSize(without_expansion);
+ gfx::Size dip_size = gfx::win::ScreenToDIPSize(without_expansion);
content_window_->SetBounds(gfx::Rect(dip_size));
native_widget_delegate_->OnNativeWidgetSizeChanged(dip_size);
}
@@ -804,9 +768,14 @@ bool DesktopRootWindowHostWin::HandleUntranslatedKeyEvent(
OnHostKeyEvent(duplicate_event.get());
}
-bool DesktopRootWindowHostWin::HandleTouchEvent(
+void DesktopRootWindowHostWin::HandleTouchEvent(
const ui::TouchEvent& event) {
- return root_window_host_delegate_->OnHostTouchEvent(
+ // HWNDMessageHandler asynchronously processes touch events. Because of this
+ // it's possible for the aura::RootWindow to have been destroyed by the time
+ // we attempt to process them.
+ if (!GetWidget()->GetNativeView())
+ return;
+ root_window_host_delegate_->OnHostTouchEvent(
const_cast<ui::TouchEvent*>(&event));
}
@@ -877,6 +846,12 @@ HWND DesktopRootWindowHostWin::GetHWND() const {
return message_handler_->hwnd();
}
+void DesktopRootWindowHostWin::SetWindowTransparency() {
+ bool transparent = ShouldUseNativeFrame() && !IsFullscreen();
+ root_window_->compositor()->SetHostHasTransparentBackground(transparent);
+ root_window_->SetTransparent(transparent);
+}
+
////////////////////////////////////////////////////////////////////////////////
// DesktopRootWindowHost, public:
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.h b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.h
index 9ad6b6998c9..3e112087f00 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_win.h
@@ -19,8 +19,6 @@ class ScreenPositionClient;
}
namespace views {
-class DesktopActivationClient;
-class DesktopCaptureClient;
class DesktopCursorClient;
class DesktopDispatcherClient;
class DesktopDragDropClientWin;
@@ -94,9 +92,9 @@ class VIEWS_EXPORT DesktopRootWindowHostWin
const gfx::ImageSkia& app_icon) OVERRIDE;
virtual void InitModalType(ui::ModalType modal_type) OVERRIDE;
virtual void FlashFrame(bool flash_frame) OVERRIDE;
+ virtual void OnRootViewLayout() const OVERRIDE;
virtual void OnNativeWidgetFocus() OVERRIDE;
virtual void OnNativeWidgetBlur() OVERRIDE;
- virtual void SetInactiveRenderingDisabled(bool disable_inactive) OVERRIDE;
// Overridden from aura::RootWindowHost:
virtual void SetDelegate(aura::RootWindowHostDelegate* delegate) OVERRIDE;
@@ -119,9 +117,6 @@ class VIEWS_EXPORT DesktopRootWindowHostWin
virtual void OnCursorVisibilityChanged(bool show) OVERRIDE;
virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
virtual void SetFocusWhenShown(bool focus_when_shown) OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
virtual void PostNativeEvent(const base::NativeEvent& native_event) OVERRIDE;
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
virtual void PrepareForShutdown() OVERRIDE;
@@ -175,6 +170,7 @@ class VIEWS_EXPORT DesktopRootWindowHostWin
virtual void HandleEndWMSizeMove() OVERRIDE;
virtual void HandleMove() OVERRIDE;
virtual void HandleWorkAreaChanged() OVERRIDE;
+ virtual void HandleVisibilityChanging(bool visible) OVERRIDE;
virtual void HandleVisibilityChanged(bool visible) OVERRIDE;
virtual void HandleClientSizeChanged(const gfx::Size& new_size) OVERRIDE;
virtual void HandleFrameChanged() OVERRIDE;
@@ -183,7 +179,7 @@ class VIEWS_EXPORT DesktopRootWindowHostWin
virtual bool HandleMouseEvent(const ui::MouseEvent& event) OVERRIDE;
virtual bool HandleKeyEvent(const ui::KeyEvent& event) OVERRIDE;
virtual bool HandleUntranslatedKeyEvent(const ui::KeyEvent& event) OVERRIDE;
- virtual bool HandleTouchEvent(const ui::TouchEvent& event) OVERRIDE;
+ virtual void HandleTouchEvent(const ui::TouchEvent& event) OVERRIDE;
virtual bool HandleIMEMessage(UINT message,
WPARAM w_param,
LPARAM l_param,
@@ -211,15 +207,14 @@ class VIEWS_EXPORT DesktopRootWindowHostWin
HWND GetHWND() const;
private:
+ void SetWindowTransparency();
+
// We are owned by the RootWindow, but we have to have a back pointer to it.
aura::RootWindow* root_window_;
scoped_ptr<HWNDMessageHandler> message_handler_;
- scoped_ptr<DesktopCaptureClient> capture_client_;
scoped_ptr<DesktopDispatcherClient> dispatcher_client_;
scoped_ptr<aura::client::FocusClient> focus_client_;
- // Depends on focus_manager_.
- scoped_ptr<DesktopActivationClient> activation_client_;
// TODO(beng): Consider providing an interface to DesktopNativeWidgetAura
// instead of providing this route back to Widget.
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.cc b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.cc
index 8c4ba7c8da5..1610558b3cb 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.cc
@@ -10,7 +10,7 @@
#include <X11/Xregion.h>
#include <X11/Xutil.h>
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/strings/stringprintf.h"
#include "base/strings/utf_string_conversions.h"
#include "third_party/skia/include/core/SkPath.h"
@@ -20,20 +20,18 @@
#include "ui/aura/root_window.h"
#include "ui/aura/window_property.h"
#include "ui/base/dragdrop/os_exchange_data_provider_aurax11.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/touch/touch_factory_x11.h"
#include "ui/base/x/x11_util.h"
+#include "ui/events/event_utils.h"
#include "ui/gfx/insets.h"
#include "ui/gfx/path_x11.h"
-#include "ui/linux_ui/linux_ui.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/corewm/compound_event_filter.h"
#include "ui/views/corewm/corewm_switches.h"
#include "ui/views/corewm/cursor_manager.h"
#include "ui/views/corewm/focus_controller.h"
#include "ui/views/ime/input_method.h"
-#include "ui/views/widget/desktop_aura/desktop_activation_client.h"
-#include "ui/views/widget/desktop_aura/desktop_capture_client.h"
+#include "ui/views/linux_ui/linux_ui.h"
#include "ui/views/widget/desktop_aura/desktop_cursor_loader_updater_aurax11.h"
#include "ui/views/widget/desktop_aura/desktop_dispatcher_client.h"
#include "ui/views/widget/desktop_aura/desktop_drag_drop_client_aurax11.h"
@@ -116,12 +114,13 @@ DesktopRootWindowHostX11::DesktopRootWindowHostX11(
DesktopNativeWidgetAura* desktop_native_widget_aura,
const gfx::Rect& initial_bounds)
: close_widget_factory_(this),
- xdisplay_(base::MessagePumpAuraX11::GetDefaultXDisplay()),
+ xdisplay_(gfx::GetXDisplay()),
xwindow_(0),
x_root_window_(DefaultRootWindow(xdisplay_)),
atom_cache_(xdisplay_, kAtomsToCache),
window_mapped_(false),
focus_when_shown_(false),
+ is_fullscreen_(false),
current_cursor_(ui::kCursorNull),
native_widget_delegate_(native_widget_delegate),
desktop_native_widget_aura_(desktop_native_widget_aura) {
@@ -129,10 +128,8 @@ DesktopRootWindowHostX11::DesktopRootWindowHostX11(
DesktopRootWindowHostX11::~DesktopRootWindowHostX11() {
root_window_->ClearProperty(kHostForRootWindow);
- if (corewm::UseFocusControllerOnDesktop()) {
- aura::client::SetFocusClient(root_window_, NULL);
- aura::client::SetActivationClient(root_window_, NULL);
- }
+ aura::client::SetFocusClient(root_window_, NULL);
+ aura::client::SetActivationClient(root_window_, NULL);
}
// static
@@ -161,20 +158,8 @@ void DesktopRootWindowHostX11::HandleNativeWidgetActivationChanged(
bool active) {
if (active)
root_window_host_delegate_->OnHostActivated();
- native_widget_delegate_->OnNativeWidgetActivationChanged(active);
- // If we're not active we need to deactivate the corresponding aura::Window.
- // This way if a child widget is active it gets correctly deactivated (child
- // widgets don't get native desktop activation changes, only aura activation
- // changes).
- if (!active) {
- aura::client::ActivationClient* activation_client =
- aura::client::GetActivationClient(root_window_);
- if (activation_client) {
- aura::Window* active_window = activation_client->GetActiveWindow();
- if (active_window)
- activation_client->DeactivateWindow(active_window);
- }
- }
+
+ desktop_native_widget_aura_->HandleActivationChanged(active);
native_widget_delegate_->AsWidget()->GetRootView()->SchedulePaint();
}
@@ -248,7 +233,7 @@ void DesktopRootWindowHostX11::CloseNow() {
open_windows().remove(xwindow_);
// Actually free our native resources.
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(xwindow_);
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(xwindow_);
XDestroyWindow(xdisplay_, xwindow_);
xwindow_ = None;
@@ -317,9 +302,17 @@ void DesktopRootWindowHostX11::GetWindowPlacement(
ui::WindowShowState* show_state) const {
*bounds = bounds_;
- // TODO(erg): This needs a better implementation. For now, we're just pass
- // back the normal state until we keep track of this.
- *show_state = ui::SHOW_STATE_NORMAL;
+ if (IsFullscreen()) {
+ *show_state = ui::SHOW_STATE_FULLSCREEN;
+ } else if (IsMinimized()) {
+ *show_state = ui::SHOW_STATE_MINIMIZED;
+ } else if (IsMaximized()) {
+ *show_state = ui::SHOW_STATE_MAXIMIZED;
+ } else if (!IsActive()) {
+ *show_state = ui::SHOW_STATE_INACTIVE;
+ } else {
+ *show_state = ui::SHOW_STATE_NORMAL;
+ }
}
gfx::Rect DesktopRootWindowHostX11::GetWindowBoundsInScreen() const {
@@ -488,13 +481,14 @@ NonClientFrameView* DesktopRootWindowHostX11::CreateNonClientFrameView() {
}
void DesktopRootWindowHostX11::SetFullscreen(bool fullscreen) {
+ is_fullscreen_ = fullscreen;
SetWMSpecState(fullscreen,
atom_cache_.GetAtom("_NET_WM_STATE_FULLSCREEN"),
None);
}
bool DesktopRootWindowHostX11::IsFullscreen() const {
- return HasWMSpecProperty("_NET_WM_STATE_FULLSCREEN");
+ return is_fullscreen_;
}
void DesktopRootWindowHostX11::SetOpacity(unsigned char opacity) {
@@ -521,8 +515,15 @@ void DesktopRootWindowHostX11::SetWindowIcons(
}
void DesktopRootWindowHostX11::InitModalType(ui::ModalType modal_type) {
- // TODO(erg):
- NOTIMPLEMENTED();
+ switch (modal_type) {
+ case ui::MODAL_TYPE_NONE:
+ break;
+ default:
+ // TODO(erg): Figure out under what situations |modal_type| isn't
+ // none. The comment in desktop_native_widget_aura.cc suggests that this
+ // is rare.
+ NOTIMPLEMENTED();
+ }
}
void DesktopRootWindowHostX11::FlashFrame(bool flash_frame) {
@@ -530,6 +531,35 @@ void DesktopRootWindowHostX11::FlashFrame(bool flash_frame) {
NOTIMPLEMENTED();
}
+void DesktopRootWindowHostX11::OnRootViewLayout() const {
+ if (!window_mapped_)
+ return;
+
+ XSizeHints hints;
+ long supplied_return;
+ XGetWMNormalHints(xdisplay_, xwindow_, &hints, &supplied_return);
+
+ gfx::Size minimum = native_widget_delegate_->GetMinimumSize();
+ if (minimum.IsEmpty()) {
+ hints.flags &= ~PMinSize;
+ } else {
+ hints.flags |= PMinSize;
+ hints.min_width = minimum.width();
+ hints.min_height = minimum.height();
+ }
+
+ gfx::Size maximum = native_widget_delegate_->GetMaximumSize();
+ if (maximum.IsEmpty()) {
+ hints.flags &= ~PMaxSize;
+ } else {
+ hints.flags |= PMaxSize;
+ hints.max_width = maximum.width();
+ hints.max_height = maximum.height();
+ }
+
+ XSetWMNormalHints(xdisplay_, xwindow_, &hints);
+}
+
void DesktopRootWindowHostX11::OnNativeWidgetFocus() {
native_widget_delegate_->AsWidget()->GetInputMethod()->OnFocus();
}
@@ -539,10 +569,6 @@ void DesktopRootWindowHostX11::OnNativeWidgetBlur() {
native_widget_delegate_->AsWidget()->GetInputMethod()->OnBlur();
}
-void DesktopRootWindowHostX11::SetInactiveRenderingDisabled(
- bool disable_inactive) {
-}
-
////////////////////////////////////////////////////////////////////////////////
// DesktopRootWindowHostX11, aura::RootWindowHost implementation:
@@ -574,7 +600,7 @@ void DesktopRootWindowHostX11::Show() {
// We now block until our window is mapped. Some X11 APIs will crash and
// burn if passed |xwindow_| before the window is mapped, and XMapWindow is
// asynchronous.
- base::MessagePumpAuraX11::Current()->BlockUntilWindowMapped(xwindow_);
+ base::MessagePumpX11::Current()->BlockUntilWindowMapped(xwindow_);
window_mapped_ = true;
}
}
@@ -731,14 +757,6 @@ void DesktopRootWindowHostX11::SetFocusWhenShown(bool focus_when_shown) {
}
}
-bool DesktopRootWindowHostX11::CopyAreaToSkCanvas(
- const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) {
- NOTIMPLEMENTED();
- return false;
-}
-
void DesktopRootWindowHostX11::PostNativeEvent(
const base::NativeEvent& native_event) {
DCHECK(xwindow_);
@@ -814,7 +832,7 @@ void DesktopRootWindowHostX11::InitX11Window(
CopyFromParent, // visual
attribute_mask,
&swa);
- base::MessagePumpAuraX11::Current()->AddDispatcherForWindow(this, xwindow_);
+ base::MessagePumpX11::Current()->AddDispatcherForWindow(this, xwindow_);
// TODO(erg): Maybe need to set a ViewProp here like in RWHL::RWHL().
@@ -877,6 +895,11 @@ void DesktopRootWindowHostX11::InitX11Window(
PropModeAppend,
reinterpret_cast<unsigned char*>(&atom), 1);
}
+
+ if (!params.wm_class_name.empty() || !params.wm_class_class.empty()) {
+ ui::SetWindowClassHint(
+ xdisplay_, xwindow_, params.wm_class_name, params.wm_class_class);
+ }
}
// TODO(erg): This method should basically be everything I need form
@@ -903,25 +926,18 @@ aura::RootWindow* DesktopRootWindowHostX11::InitRootWindow(
native_widget_delegate_->OnNativeWidgetCreated(true);
- capture_client_.reset(new views::DesktopCaptureClient(root_window_));
- aura::client::SetCaptureClient(root_window_, capture_client_.get());
+ desktop_native_widget_aura_->CreateCaptureClient(root_window_);
// Ensure that the X11DesktopHandler exists so that it dispatches activation
// messages to us.
X11DesktopHandler::get();
- if (corewm::UseFocusControllerOnDesktop()) {
- corewm::FocusController* focus_controller =
- new corewm::FocusController(new DesktopFocusRules);
- focus_client_.reset(focus_controller);
- aura::client::SetFocusClient(root_window_, focus_controller);
- aura::client::SetActivationClient(root_window_, focus_controller);
- root_window_->AddPreTargetHandler(focus_controller);
- } else {
- focus_client_.reset(new aura::FocusManager);
- aura::client::SetFocusClient(root_window_, focus_client_.get());
- activation_client_.reset(new DesktopActivationClient(root_window_));
- }
+ corewm::FocusController* focus_controller =
+ new corewm::FocusController(new DesktopFocusRules(content_window_));
+ focus_client_.reset(focus_controller);
+ aura::client::SetFocusClient(root_window_, focus_controller);
+ aura::client::SetActivationClient(root_window_, focus_controller);
+ root_window_->AddPreTargetHandler(focus_controller);
dispatcher_client_.reset(new DesktopDispatcherClient);
aura::client::SetDispatcherClient(root_window_,
@@ -950,8 +966,7 @@ aura::RootWindow* DesktopRootWindowHostX11::InitRootWindow(
aura::client::SetDragDropClient(root_window_, drag_drop_client_.get());
// TODO(erg): Unify this code once the other consumer goes away.
- x11_window_event_filter_.reset(
- new X11WindowEventFilter(root_window_, activation_client_.get()));
+ x11_window_event_filter_.reset(new X11WindowEventFilter(root_window_));
x11_window_event_filter_->SetUseHostWindowBorders(false);
desktop_native_widget_aura_->root_window_event_filter()->AddHandler(
x11_window_event_filter_.get());
@@ -1303,6 +1318,8 @@ bool DesktopRootWindowHostX11::Dispatch(const base::NativeEvent& event) {
restored_bounds_ = previous_bounds_;
}
+ is_fullscreen_ = HasWMSpecProperty("_NET_WM_STATE_FULLSCREEN");
+
// Now that we have different window properties, we may need to
// relayout the window. (The windows code doesn't need this because
// their window change is synchronous.)
@@ -1340,13 +1357,13 @@ DesktopRootWindowHost* DesktopRootWindowHost::Create(
DesktopNativeWidgetAura* desktop_native_widget_aura,
const gfx::Rect& initial_bounds) {
return new DesktopRootWindowHostX11(native_widget_delegate,
- desktop_native_widget_aura,
- initial_bounds);
+ desktop_native_widget_aura,
+ initial_bounds);
}
// static
ui::NativeTheme* DesktopRootWindowHost::GetNativeTheme(aura::Window* window) {
- const ui::LinuxUI* linux_ui = ui::LinuxUI::instance();
+ const views::LinuxUI* linux_ui = views::LinuxUI::instance();
if (linux_ui) {
ui::NativeTheme* native_theme = linux_ui->GetNativeTheme();
if (native_theme)
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.h b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.h
index e1dcc766930..ded7e98ca68 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.h
+++ b/chromium/ui/views/widget/desktop_aura/desktop_root_window_host_x11.h
@@ -29,8 +29,6 @@ class ScreenPositionClient;
}
namespace views {
-class DesktopActivationClient;
-class DesktopCaptureClient;
class DesktopDragDropClientAuraX11;
class DesktopDispatcherClient;
class DesktopRootWindowHostObserverX11;
@@ -121,9 +119,9 @@ class VIEWS_EXPORT DesktopRootWindowHostX11 :
const gfx::ImageSkia& app_icon) OVERRIDE;
virtual void InitModalType(ui::ModalType modal_type) OVERRIDE;
virtual void FlashFrame(bool flash_frame) OVERRIDE;
+ virtual void OnRootViewLayout() const OVERRIDE;
virtual void OnNativeWidgetFocus() OVERRIDE;
virtual void OnNativeWidgetBlur() OVERRIDE;
- virtual void SetInactiveRenderingDisabled(bool disable_inactive) OVERRIDE;
// Overridden from aura::RootWindowHost:
virtual void SetDelegate(aura::RootWindowHostDelegate* delegate) OVERRIDE;
@@ -146,9 +144,6 @@ class VIEWS_EXPORT DesktopRootWindowHostX11 :
virtual void OnCursorVisibilityChanged(bool show) OVERRIDE;
virtual void MoveCursorTo(const gfx::Point& location) OVERRIDE;
virtual void SetFocusWhenShown(bool focus_when_shown) OVERRIDE;
- virtual bool CopyAreaToSkCanvas(const gfx::Rect& source_bounds,
- const gfx::Point& dest_offset,
- SkCanvas* canvas) OVERRIDE;
virtual void PostNativeEvent(const base::NativeEvent& native_event) OVERRIDE;
virtual void OnDeviceScaleFactorChanged(float device_scale_factor) OVERRIDE;
virtual void PrepareForShutdown() OVERRIDE;
@@ -193,7 +188,7 @@ private:
// X11 things
// The display and the native X window hosting the root window.
- Display* xdisplay_;
+ XDisplay* xdisplay_;
::Window xwindow_;
// The native root window.
@@ -224,13 +219,15 @@ private:
// The window manager state bits.
std::set< ::Atom> window_properties_;
+ // Local flag for fullscreen state to avoid a state mismatch between
+ // server and local window_properties_ during app-initiated fullscreen.
+ bool is_fullscreen_;
+
// We are owned by the RootWindow, but we have to have a back pointer to it.
aura::RootWindow* root_window_;
// aura:: objects that we own.
- scoped_ptr<DesktopCaptureClient> capture_client_;
scoped_ptr<aura::client::FocusClient> focus_client_;
- scoped_ptr<DesktopActivationClient> activation_client_;
scoped_ptr<views::corewm::CursorManager> cursor_client_;
scoped_ptr<DesktopDispatcherClient> dispatcher_client_;
scoped_ptr<aura::client::ScreenPositionClient> position_client_;
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_screen_ozone.cc b/chromium/ui/views/widget/desktop_aura/desktop_screen_ozone.cc
new file mode 100644
index 00000000000..5542178baaa
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/desktop_screen_ozone.cc
@@ -0,0 +1,15 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/widget/desktop_aura/desktop_screen.h"
+
+#include "ui/gfx/ozone/surface_factory_ozone.h"
+
+namespace views {
+
+gfx::Screen* CreateDesktopScreen() {
+ return gfx::SurfaceFactoryOzone::GetInstance()->CreateDesktopScreen();
+}
+
+} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/desktop_screen_x11.cc b/chromium/ui/views/widget/desktop_aura/desktop_screen_x11.cc
index 77dbaa497a7..880b3d05a98 100644
--- a/chromium/ui/views/widget/desktop_aura/desktop_screen_x11.cc
+++ b/chromium/ui/views/widget/desktop_aura/desktop_screen_x11.cc
@@ -12,17 +12,17 @@
#include "base/logging.h"
#include "ui/aura/root_window.h"
#include "ui/aura/root_window_host.h"
-#include "ui/base/x/x11_util.h"
#include "ui/gfx/display.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/screen.h"
+#include "ui/gfx/x/x11_types.h"
namespace {
// TODO(erg): This method is a temporary hack, until we can reliably extract
// location data out of XRandR.
gfx::Size GetPrimaryDisplaySize() {
- ::Display* display = ui::GetXDisplay();
+ ::XDisplay* display = gfx::GetXDisplay();
::Screen* screen = DefaultScreenOfDisplay(display);
int width = WidthOfScreen(screen);
int height = HeightOfScreen(screen);
@@ -38,8 +38,11 @@ class DesktopScreenX11 : public gfx::Screen {
// Overridden from gfx::Screen:
virtual bool IsDIPEnabled() OVERRIDE;
virtual gfx::Point GetCursorScreenPoint() OVERRIDE;
- virtual gfx::NativeWindow GetWindowAtCursorScreenPoint() OVERRIDE;
- virtual int GetNumDisplays() OVERRIDE;
+ virtual gfx::NativeWindow GetWindowUnderCursor() OVERRIDE;
+ virtual gfx::NativeWindow GetWindowAtScreenPoint(const gfx::Point& point)
+ OVERRIDE;
+ virtual int GetNumDisplays() const OVERRIDE;
+ virtual std::vector<gfx::Display> GetAllDisplays() const OVERRIDE;
virtual gfx::Display GetDisplayNearestWindow(
gfx::NativeView window) const OVERRIDE;
virtual gfx::Display GetDisplayNearestPoint(
@@ -71,7 +74,7 @@ bool DesktopScreenX11::IsDIPEnabled() {
}
gfx::Point DesktopScreenX11::GetCursorScreenPoint() {
- Display* display = ui::GetXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
::Window root, child;
int root_x, root_y, win_x, win_y;
@@ -89,18 +92,29 @@ gfx::Point DesktopScreenX11::GetCursorScreenPoint() {
return gfx::Point(root_x, root_y);
}
-gfx::NativeWindow DesktopScreenX11::GetWindowAtCursorScreenPoint() {
+gfx::NativeWindow DesktopScreenX11::GetWindowUnderCursor() {
// TODO(erg): Implement using the discussion at
// http://codereview.chromium.org/10279005/
return NULL;
}
-int DesktopScreenX11::GetNumDisplays() {
+gfx::NativeWindow DesktopScreenX11::GetWindowAtScreenPoint(
+ const gfx::Point& point) {
+ NOTIMPLEMENTED();
+ return NULL;
+}
+
+int DesktopScreenX11::GetNumDisplays() const {
// TODO(erg): Figure this out with oshima or piman because I have no clue
// about the XRandR implications here.
return 1;
}
+std::vector<gfx::Display> DesktopScreenX11::GetAllDisplays() const {
+ // TODO(erg): Do the right thing once we know what that is.
+ return std::vector<gfx::Display>(1, GetPrimaryDisplay());
+}
+
gfx::Display DesktopScreenX11::GetDisplayNearestWindow(
gfx::NativeView window) const {
// TODO(erg): Do the right thing once we know what that is.
diff --git a/chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.cc b/chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.cc
new file mode 100644
index 00000000000..cf131022d89
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.cc
@@ -0,0 +1,37 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/widget/desktop_aura/scoped_tooltip_client.h"
+
+#include "ui/aura/root_window.h"
+#include "ui/views/corewm/tooltip_controller.h"
+
+namespace views {
+
+// static
+corewm::TooltipController* ScopedTooltipClient::tooltip_controller_ = NULL;
+
+// static
+int ScopedTooltipClient::scoped_tooltip_client_count_ = 0;
+
+ScopedTooltipClient::ScopedTooltipClient(aura::RootWindow* root_window)
+ : root_window_(root_window) {
+ if (scoped_tooltip_client_count_++ == 0) {
+ tooltip_controller_ =
+ new corewm::TooltipController(gfx::SCREEN_TYPE_NATIVE);
+ }
+ aura::client::SetTooltipClient(root_window_, tooltip_controller_);
+ root_window_->AddPreTargetHandler(tooltip_controller_);
+}
+
+ScopedTooltipClient::~ScopedTooltipClient() {
+ root_window_->RemovePreTargetHandler(tooltip_controller_);
+ aura::client::SetTooltipClient(root_window_, NULL);
+ if (--scoped_tooltip_client_count_ == 0) {
+ delete tooltip_controller_;
+ tooltip_controller_ = NULL;
+ }
+}
+
+} // namespace views
diff --git a/chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.h b/chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.h
new file mode 100644
index 00000000000..bb3e57b9d2c
--- /dev/null
+++ b/chromium/ui/views/widget/desktop_aura/scoped_tooltip_client.h
@@ -0,0 +1,43 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_WIDGET_DESKTOP_AURA_SCOPED_TOOLTIP_CLIENT_H_
+#define UI_VIEWS_WIDGET_DESKTOP_AURA_SCOPED_TOOLTIP_CLIENT_H_
+
+#include "base/basictypes.h"
+
+namespace aura {
+class RootWindow;
+}
+
+namespace views {
+
+namespace corewm {
+class TooltipController;
+}
+
+// ScopedTooltipClient is responsible for installing a TooltipClient
+// implementation on a RootWindow. Additionally it ensures only one
+// TooltipController is only ever created. In this way all
+// DesktopNativeWidgetAuras share the same TooltipClient.
+class ScopedTooltipClient {
+ public:
+ explicit ScopedTooltipClient(aura::RootWindow* root_window);
+ ~ScopedTooltipClient();
+
+ private:
+ // Single TooltipController.
+ static corewm::TooltipController* tooltip_controller_;
+
+ // Number of ScopedTooltipClients created.
+ static int scoped_tooltip_client_count_;
+
+ aura::RootWindow* root_window_;
+
+ DISALLOW_COPY_AND_ASSIGN(ScopedTooltipClient);
+};
+
+} // namespace views
+
+#endif // UI_VIEWS_WIDGET_DESKTOP_AURA_SCOPED_TOOLTIP_CLIENT_H_
diff --git a/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.cc b/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.cc
index 46906992fce..0c965653f57 100644
--- a/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.cc
+++ b/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.cc
@@ -9,7 +9,6 @@
#include "ui/aura/focus_manager.h"
#include "ui/aura/root_window.h"
#include "ui/base/x/x11_util.h"
-#include "ui/views/widget/desktop_aura/desktop_activation_client.h"
#if !defined(OS_CHROMEOS)
#include "ui/views/ime/input_method.h"
@@ -39,11 +38,11 @@ X11DesktopHandler* X11DesktopHandler::get() {
}
X11DesktopHandler::X11DesktopHandler()
- : xdisplay_(base::MessagePumpAuraX11::GetDefaultXDisplay()),
+ : xdisplay_(gfx::GetXDisplay()),
x_root_window_(DefaultRootWindow(xdisplay_)),
current_window_(None),
atom_cache_(xdisplay_, kAtomsToCache) {
- base::MessagePumpAuraX11::Current()->AddDispatcherForRootWindow(this);
+ base::MessagePumpX11::Current()->AddDispatcherForRootWindow(this);
aura::Env::GetInstance()->AddObserver(this);
XWindowAttributes attr;
@@ -55,11 +54,11 @@ X11DesktopHandler::X11DesktopHandler()
X11DesktopHandler::~X11DesktopHandler() {
aura::Env::GetInstance()->RemoveObserver(this);
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForRootWindow(this);
+ base::MessagePumpX11::Current()->RemoveDispatcherForRootWindow(this);
}
void X11DesktopHandler::ActivateWindow(::Window window) {
- DCHECK_EQ(base::MessagePumpAuraX11::GetDefaultXDisplay(), xdisplay_);
+ DCHECK_EQ(gfx::GetXDisplay(), xdisplay_);
XEvent xclient;
memset(&xclient, 0, sizeof(xclient));
diff --git a/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.h b/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.h
index 8cda9eeaaab..e84b6d44a93 100644
--- a/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.h
+++ b/chromium/ui/views/widget/desktop_aura/x11_desktop_handler.h
@@ -12,6 +12,7 @@
#include "base/message_loop/message_loop.h"
#include "ui/aura/env_observer.h"
#include "ui/base/x/x11_atom_cache.h"
+#include "ui/gfx/x/x11_types.h"
#include "ui/views/views_export.h"
template <typename T> struct DefaultSingletonTraits;
@@ -48,7 +49,7 @@ class VIEWS_EXPORT X11DesktopHandler : public base::MessageLoop::Dispatcher,
void OnActiveWindowChanged(::Window window);
// The display and the native X window hosting the root window.
- Display* xdisplay_;
+ XDisplay* xdisplay_;
// The native root window.
::Window x_root_window_;
diff --git a/chromium/ui/views/widget/desktop_aura/x11_desktop_window_move_client.cc b/chromium/ui/views/widget/desktop_aura/x11_desktop_window_move_client.cc
index d28de216dce..273372f0340 100644
--- a/chromium/ui/views/widget/desktop_aura/x11_desktop_window_move_client.cc
+++ b/chromium/ui/views/widget/desktop_aura/x11_desktop_window_move_client.cc
@@ -10,12 +10,12 @@
#include "base/debug/stack_trace.h"
#include "base/message_loop/message_loop.h"
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/run_loop.h"
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
-#include "ui/base/events/event.h"
#include "ui/base/x/x11_util.h"
+#include "ui/events/event.h"
#include "ui/gfx/screen.h"
namespace views {
diff --git a/chromium/ui/views/widget/desktop_aura/x11_whole_screen_move_loop.cc b/chromium/ui/views/widget/desktop_aura/x11_whole_screen_move_loop.cc
index d04dd88cb2f..177d137a2da 100644
--- a/chromium/ui/views/widget/desktop_aura/x11_whole_screen_move_loop.cc
+++ b/chromium/ui/views/widget/desktop_aura/x11_whole_screen_move_loop.cc
@@ -10,12 +10,12 @@
#include "base/debug/stack_trace.h"
#include "base/message_loop/message_loop.h"
-#include "base/message_loop/message_pump_aurax11.h"
+#include "base/message_loop/message_pump_x11.h"
#include "base/run_loop.h"
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
-#include "ui/base/events/event.h"
#include "ui/base/x/x11_util.h"
+#include "ui/events/event.h"
#include "ui/gfx/screen.h"
namespace views {
@@ -64,7 +64,7 @@ bool X11WholeScreenMoveLoop::RunMoveLoop(aura::Window* source,
DCHECK(!in_move_loop_); // Can only handle one nested loop at a time.
in_move_loop_ = true;
- Display* display = base::MessagePumpAuraX11::GetDefaultXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
// Creates an invisible, InputOnly toplevel window. This window will receive
// all mouse movement for drags. It turns out that normal windows doing a
@@ -83,12 +83,12 @@ bool X11WholeScreenMoveLoop::RunMoveLoop(aura::Window* source,
-100, -100, 10, 10,
0, 0, InputOnly, CopyFromParent,
attribute_mask, &swa);
- base::MessagePumpAuraX11::Current()->AddDispatcherForWindow(
+ base::MessagePumpX11::Current()->AddDispatcherForWindow(
this, grab_input_window_);
// Wait for the window to be mapped. If we don't, XGrabPointer fails.
XMapRaised(display, grab_input_window_);
- base::MessagePumpAuraX11::Current()->BlockUntilWindowMapped(
+ base::MessagePumpX11::Current()->BlockUntilWindowMapped(
grab_input_window_);
if (!GrabPointerWithCursor(cursor))
@@ -116,10 +116,10 @@ void X11WholeScreenMoveLoop::EndMoveLoop() {
// the chrome process.
// Ungrab before we let go of the window.
- Display* display = base::MessagePumpAuraX11::GetDefaultXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
XUngrabPointer(display, CurrentTime);
- base::MessagePumpAuraX11::Current()->RemoveDispatcherForWindow(
+ base::MessagePumpX11::Current()->RemoveDispatcherForWindow(
grab_input_window_);
delegate_->OnMoveLoopEnded();
XDestroyWindow(display, grab_input_window_);
@@ -129,7 +129,7 @@ void X11WholeScreenMoveLoop::EndMoveLoop() {
}
bool X11WholeScreenMoveLoop::GrabPointerWithCursor(gfx::NativeCursor cursor) {
- Display* display = base::MessagePumpAuraX11::GetDefaultXDisplay();
+ XDisplay* display = gfx::GetXDisplay();
XGrabServer(display);
XUngrabPointer(display, CurrentTime);
int ret = XGrabPointer(
diff --git a/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.cc b/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.cc
index 3495b04bc58..740e1204df0 100644
--- a/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.cc
+++ b/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.cc
@@ -9,13 +9,12 @@
#include <X11/Xatom.h>
#include <X11/Xlib.h>
-#include "base/message_loop/message_pump_aurax11.h"
#include "ui/aura/root_window.h"
#include "ui/aura/window_delegate.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/hit_test.h"
-#include "ui/views/widget/desktop_aura/desktop_activation_client.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
+#include "ui/gfx/x/x11_types.h"
#include "ui/views/widget/native_widget_aura.h"
namespace {
@@ -59,10 +58,8 @@ const char* kAtomsToCache[] = {
namespace views {
X11WindowEventFilter::X11WindowEventFilter(
- aura::RootWindow* root_window,
- DesktopActivationClient* activation_client)
- : activation_client_(activation_client),
- xdisplay_(base::MessagePumpAuraX11::GetDefaultXDisplay()),
+ aura::RootWindow* root_window)
+ : xdisplay_(gfx::GetXDisplay()),
xwindow_(root_window->GetAcceleratedWidget()),
x_root_window_(DefaultRootWindow(xdisplay_)),
atom_cache_(xdisplay_, kAtomsToCache),
@@ -79,7 +76,7 @@ void X11WindowEventFilter::SetUseHostWindowBorders(bool use_os_border) {
motif_hints.decorations = use_os_border ? 1 : 0;
::Atom hint_atom = atom_cache_.GetAtom("_MOTIF_WM_HINTS");
- XChangeProperty(base::MessagePumpAuraX11::GetDefaultXDisplay(),
+ XChangeProperty(gfx::GetXDisplay(),
xwindow_,
hint_atom,
hint_atom,
diff --git a/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.h b/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.h
index a6bdce8d3c8..9fab5a6fca0 100644
--- a/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.h
+++ b/chromium/ui/views/widget/desktop_aura/x11_window_event_filter.h
@@ -11,8 +11,9 @@
#include "base/compiler_specific.h"
#include "base/message_loop/message_loop.h"
-#include "ui/base/events/event_handler.h"
#include "ui/base/x/x11_atom_cache.h"
+#include "ui/events/event_handler.h"
+#include "ui/gfx/x/x11_types.h"
#include "ui/views/views_export.h"
namespace aura {
@@ -25,14 +26,12 @@ class Point;
}
namespace views {
-class DesktopActivationClient;
class NativeWidgetAura;
// An EventFilter that sets properties on X11 windows.
class VIEWS_EXPORT X11WindowEventFilter : public ui::EventHandler {
public:
- explicit X11WindowEventFilter(aura::RootWindow* root_window,
- DesktopActivationClient* activation_client);
+ explicit X11WindowEventFilter(aura::RootWindow* root_window);
virtual ~X11WindowEventFilter();
// Changes whether borders are shown on this |root_window|.
@@ -47,10 +46,8 @@ class VIEWS_EXPORT X11WindowEventFilter : public ui::EventHandler {
bool DispatchHostWindowDragMovement(int hittest,
const gfx::Point& screen_location);
- DesktopActivationClient* activation_client_;
-
// The display and the native X window hosting the root window.
- Display* xdisplay_;
+ XDisplay* xdisplay_;
::Window xwindow_;
// The native root window.
diff --git a/chromium/ui/views/widget/drop_helper.cc b/chromium/ui/views/widget/drop_helper.cc
index e4493a30b48..ace1f900a70 100644
--- a/chromium/ui/views/widget/drop_helper.cc
+++ b/chromium/ui/views/widget/drop_helper.cc
@@ -99,7 +99,7 @@ View* DropHelper::CalculateTargetViewImpl(
(!view->enabled() || !view->CanDrop(data))) {
view = view->parent();
}
-#elif !defined(OS_MACOSX)
+#else
int formats = 0;
std::set<OSExchangeData::CustomFormat> custom_formats;
while (view && view != target_view_) {
diff --git a/chromium/ui/views/widget/monitor_win.cc b/chromium/ui/views/widget/monitor_win.cc
index c183cb0f6db..1292692d9f3 100644
--- a/chromium/ui/views/widget/monitor_win.cc
+++ b/chromium/ui/views/widget/monitor_win.cc
@@ -7,6 +7,7 @@
#include <shellapi.h>
#include "base/logging.h"
+#include "base/win/win_util.h"
#include "ui/gfx/rect.h"
namespace views {
@@ -17,7 +18,7 @@ gfx::Rect GetMonitorBoundsForRect(const gfx::Rect& rect) {
if (monitor) {
MONITORINFO mi = {0};
mi.cbSize = sizeof(mi);
- GetMonitorInfo(monitor, &mi);
+ base::win::GetMonitorInfoWrapper(monitor, &mi);
return gfx::Rect(mi.rcWork);
}
NOTREACHED();
diff --git a/chromium/ui/views/widget/native_widget_aura.cc b/chromium/ui/views/widget/native_widget_aura.cc
index 8c9ad02b899..5c5136bf604 100644
--- a/chromium/ui/views/widget/native_widget_aura.cc
+++ b/chromium/ui/views/widget/native_widget_aura.cc
@@ -21,9 +21,9 @@
#include "ui/aura/window.h"
#include "ui/aura/window_observer.h"
#include "ui/base/dragdrop/os_exchange_data.h"
-#include "ui/base/events/event.h"
#include "ui/base/ui_base_types.h"
#include "ui/compositor/layer.h"
+#include "ui/events/event.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/font.h"
#include "ui/gfx/screen.h"
@@ -95,6 +95,13 @@ gfx::Font NativeWidgetAura::GetWindowTitleFont() {
#endif
}
+// static
+void NativeWidgetAura::RegisterNativeWidgetForWindow(
+ internal::NativeWidgetPrivate* native_widget,
+ aura::Window* window) {
+ window->set_user_data(native_widget);
+}
+
////////////////////////////////////////////////////////////////////////////////
// NativeWidgetAura, internal::NativeWidgetPrivate implementation:
@@ -105,7 +112,7 @@ void NativeWidgetAura::InitNativeWidget(const Widget::InitParams& params) {
ownership_ = params.ownership;
- window_->set_user_data(this);
+ RegisterNativeWidgetForWindow(this, window_);
window_->SetType(GetAuraWindowTypeForWidgetType(params.type));
window_->SetProperty(aura::client::kShowStateKey, params.show_state);
if (params.type == Widget::InitParams::TYPE_BUBBLE)
@@ -162,10 +169,8 @@ void NativeWidgetAura::InitNativeWidget(const Widget::InitParams& params) {
params.type != Widget::InitParams::TYPE_CONTROL &&
params.type != Widget::InitParams::TYPE_TOOLTIP;
DCHECK(GetWidget()->GetRootView());
-#if !defined(OS_MACOSX)
if (params.type != Widget::InitParams::TYPE_TOOLTIP)
tooltip_manager_.reset(new views::TooltipManagerAura(window_, GetWidget()));
-#endif // !defined(OS_MACOSX)
drop_helper_.reset(new DropHelper(GetWidget()->GetRootView()));
if (params.type != Widget::InitParams::TYPE_TOOLTIP &&
@@ -222,15 +227,15 @@ Widget* NativeWidgetAura::GetTopLevelWidget() {
}
const ui::Compositor* NativeWidgetAura::GetCompositor() const {
- return window_->layer()->GetCompositor();
+ return window_ ? window_->layer()->GetCompositor() : NULL;
}
ui::Compositor* NativeWidgetAura::GetCompositor() {
- return window_->layer()->GetCompositor();
+ return window_ ? window_->layer()->GetCompositor() : NULL;
}
ui::Layer* NativeWidgetAura::GetLayer() {
- return window_->layer();
+ return window_ ? window_->layer() : NULL;
}
void NativeWidgetAura::ReorderNativeViews() {
@@ -256,18 +261,22 @@ TooltipManager* NativeWidgetAura::GetTooltipManager() const {
}
void NativeWidgetAura::SetCapture() {
- window_->SetCapture();
+ if (window_)
+ window_->SetCapture();
}
void NativeWidgetAura::ReleaseCapture() {
- window_->ReleaseCapture();
+ if (window_)
+ window_->ReleaseCapture();
}
bool NativeWidgetAura::HasCapture() const {
- return window_->HasCapture();
+ return window_ && window_->HasCapture();
}
InputMethod* NativeWidgetAura::CreateInputMethod() {
+ if (!window_)
+ return NULL;
aura::RootWindow* root_window = window_->GetRootWindow();
ui::InputMethod* host =
root_window->GetProperty(aura::client::kRootWindowInputMethodKey);
@@ -279,6 +288,9 @@ internal::InputMethodDelegate* NativeWidgetAura::GetInputMethodDelegate() {
}
void NativeWidgetAura::CenterWindow(const gfx::Size& size) {
+ if (!window_)
+ return;
+
gfx::Rect parent_bounds(window_->parent()->GetBoundsInRootWindow());
// When centering window, we take the intersection of the host and
// the parent. We assume the root window represents the visible
@@ -330,11 +342,13 @@ void NativeWidgetAura::GetWindowPlacement(
ui::WindowShowState* show_state) const {
// The interface specifies returning restored bounds, not current bounds.
*bounds = GetRestoredBounds();
- *show_state = window_->GetProperty(aura::client::kShowStateKey);
+ *show_state = window_ ? window_->GetProperty(aura::client::kShowStateKey) :
+ ui::SHOW_STATE_DEFAULT;
}
void NativeWidgetAura::SetWindowTitle(const string16& title) {
- window_->set_title(title);
+ if (window_)
+ window_->set_title(title);
}
void NativeWidgetAura::SetWindowIcons(const gfx::ImageSkia& window_icon,
@@ -348,16 +362,19 @@ void NativeWidgetAura::InitModalType(ui::ModalType modal_type) {
}
gfx::Rect NativeWidgetAura::GetWindowBoundsInScreen() const {
- return window_->GetBoundsInScreen();
+ return window_ ? window_->GetBoundsInScreen() : gfx::Rect();
}
gfx::Rect NativeWidgetAura::GetClientAreaBoundsInScreen() const {
// View-to-screen coordinate system transformations depend on this returning
// the full window bounds, for example View::ConvertPointToScreen().
- return window_->GetBoundsInScreen();
+ return window_ ? window_->GetBoundsInScreen() : gfx::Rect();
}
gfx::Rect NativeWidgetAura::GetRestoredBounds() const {
+ if (!window_)
+ return gfx::Rect();
+
// Restored bounds should only be relevant if the window is minimized or
// maximized. However, in some places the code expects GetRestoredBounds()
// to return the current window bounds if the window is not in either state.
@@ -372,6 +389,9 @@ gfx::Rect NativeWidgetAura::GetRestoredBounds() const {
}
void NativeWidgetAura::SetBounds(const gfx::Rect& bounds) {
+ if (!window_)
+ return;
+
aura::RootWindow* root = window_->GetRootWindow();
if (root) {
aura::client::ScreenPositionClient* screen_position_client =
@@ -387,20 +407,24 @@ void NativeWidgetAura::SetBounds(const gfx::Rect& bounds) {
}
void NativeWidgetAura::SetSize(const gfx::Size& size) {
- window_->SetBounds(gfx::Rect(window_->bounds().origin(), size));
+ if (window_)
+ window_->SetBounds(gfx::Rect(window_->bounds().origin(), size));
}
void NativeWidgetAura::StackAbove(gfx::NativeView native_view) {
- if (window_->parent() && window_->parent() == native_view->parent())
+ if (window_ && window_->parent() &&
+ window_->parent() == native_view->parent())
window_->parent()->StackChildAbove(window_, native_view);
}
void NativeWidgetAura::StackAtTop() {
- window_->parent()->StackChildAtTop(window_);
+ if (window_)
+ window_->parent()->StackChildAtTop(window_);
}
void NativeWidgetAura::StackBelow(gfx::NativeView native_view) {
- if (window_->parent() && window_->parent() == native_view->parent())
+ if (window_ && window_->parent() &&
+ window_->parent() == native_view->parent())
window_->parent()->StackChildBelow(window_, native_view);
}
@@ -438,7 +462,8 @@ void NativeWidgetAura::Show() {
}
void NativeWidgetAura::Hide() {
- window_->Hide();
+ if (window_)
+ window_->Hide();
}
void NativeWidgetAura::ShowMaximizedWithBounds(
@@ -448,6 +473,9 @@ void NativeWidgetAura::ShowMaximizedWithBounds(
}
void NativeWidgetAura::ShowWithWindowState(ui::WindowShowState state) {
+ if (!window_)
+ return;
+
if (state == ui::SHOW_STATE_MAXIMIZED || state == ui::SHOW_STATE_FULLSCREEN)
window_->SetProperty(aura::client::kShowStateKey, state);
window_->Show();
@@ -466,10 +494,13 @@ void NativeWidgetAura::ShowWithWindowState(ui::WindowShowState state) {
}
bool NativeWidgetAura::IsVisible() const {
- return window_->IsVisible();
+ return window_ && window_->IsVisible();
}
void NativeWidgetAura::Activate() {
+ if (!window_)
+ return;
+
// We don't necessarily have a root window yet. This can happen with
// constrained windows.
if (window_->GetRootWindow()) {
@@ -481,43 +512,55 @@ void NativeWidgetAura::Activate() {
}
void NativeWidgetAura::Deactivate() {
+ if (!window_)
+ return;
aura::client::GetActivationClient(window_->GetRootWindow())->DeactivateWindow(
window_);
}
bool NativeWidgetAura::IsActive() const {
- return aura::client::GetActivationClient(window_->GetRootWindow())->
- GetActiveWindow() == window_;
+ if (!window_)
+ return false;
+
+ // We may up here during destruction of the root, in which case
+ // GetRootWindow() returns NULL (~RootWindow() has run and we're in ~Window).
+ aura::RootWindow* root = window_->GetRootWindow();
+ return root &&
+ aura::client::GetActivationClient(root)->GetActiveWindow() == window_;
}
void NativeWidgetAura::SetAlwaysOnTop(bool on_top) {
- window_->SetProperty(aura::client::kAlwaysOnTopKey, on_top);
+ if (window_)
+ window_->SetProperty(aura::client::kAlwaysOnTopKey, on_top);
}
void NativeWidgetAura::Maximize() {
- window_->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_MAXIMIZED);
+ if (window_)
+ window_->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_MAXIMIZED);
}
void NativeWidgetAura::Minimize() {
- window_->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_MINIMIZED);
+ if (window_)
+ window_->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_MINIMIZED);
}
bool NativeWidgetAura::IsMaximized() const {
- return window_->GetProperty(aura::client::kShowStateKey) ==
+ return window_ && window_->GetProperty(aura::client::kShowStateKey) ==
ui::SHOW_STATE_MAXIMIZED;
}
bool NativeWidgetAura::IsMinimized() const {
- return window_->GetProperty(aura::client::kShowStateKey) ==
+ return window_ && window_->GetProperty(aura::client::kShowStateKey) ==
ui::SHOW_STATE_MINIMIZED;
}
void NativeWidgetAura::Restore() {
- window_->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_NORMAL);
+ if (window_)
+ window_->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_NORMAL);
}
void NativeWidgetAura::SetFullscreen(bool fullscreen) {
- if (IsFullscreen() == fullscreen)
+ if (!window_ || IsFullscreen() == fullscreen)
return; // Nothing to do.
// Save window state before entering full screen so that it could restored
@@ -531,12 +574,13 @@ void NativeWidgetAura::SetFullscreen(bool fullscreen) {
}
bool NativeWidgetAura::IsFullscreen() const {
- return window_->GetProperty(aura::client::kShowStateKey) ==
+ return window_ && window_->GetProperty(aura::client::kShowStateKey) ==
ui::SHOW_STATE_FULLSCREEN;
}
void NativeWidgetAura::SetOpacity(unsigned char opacity) {
- window_->layer()->SetOpacity(opacity / 255.0);
+ if (window_)
+ window_->layer()->SetOpacity(opacity / 255.0);
}
void NativeWidgetAura::SetUseDragFrame(bool use_drag_frame) {
@@ -544,7 +588,8 @@ void NativeWidgetAura::SetUseDragFrame(bool use_drag_frame) {
}
void NativeWidgetAura::FlashFrame(bool flash) {
- window_->SetProperty(aura::client::kDrawAttentionKey, flash);
+ if (window_)
+ window_->SetProperty(aura::client::kDrawAttentionKey, flash);
}
void NativeWidgetAura::RunShellDrag(View* view,
@@ -552,7 +597,8 @@ void NativeWidgetAura::RunShellDrag(View* view,
const gfx::Point& location,
int operation,
ui::DragDropTypes::DragEventSource source) {
- views::RunShellDrag(window_, data, location, operation, source);
+ if (window_)
+ views::RunShellDrag(window_, data, location, operation, source);
}
void NativeWidgetAura::SchedulePaintInRect(const gfx::Rect& rect) {
@@ -569,6 +615,8 @@ void NativeWidgetAura::SetCursor(gfx::NativeCursor cursor) {
}
bool NativeWidgetAura::IsMouseEventsEnabled() const {
+ if (!window_)
+ return false;
aura::client::CursorClient* cursor_client =
aura::client::GetCursorClient(window_->GetRootWindow());
return cursor_client ? cursor_client->IsMouseEventsEnabled() : true;
@@ -581,11 +629,16 @@ void NativeWidgetAura::ClearNativeFocus() {
}
gfx::Rect NativeWidgetAura::GetWorkAreaBoundsInScreen() const {
- return gfx::Screen::GetScreenFor(GetNativeView())->
- GetDisplayNearestWindow(GetNativeView()).work_area();
+ if (!window_)
+ return gfx::Rect();
+ return gfx::Screen::GetScreenFor(window_)->
+ GetDisplayNearestWindow(window_).work_area();
}
void NativeWidgetAura::SetInactiveRenderingDisabled(bool value) {
+ if (!window_)
+ return;
+
if (!value) {
active_window_observer_.reset();
} else {
@@ -597,7 +650,7 @@ void NativeWidgetAura::SetInactiveRenderingDisabled(bool value) {
Widget::MoveLoopResult NativeWidgetAura::RunMoveLoop(
const gfx::Vector2d& drag_offset,
Widget::MoveLoopSource source) {
- if (window_->parent() &&
+ if (window_ && window_->parent() &&
aura::client::GetWindowMoveClient(window_->parent())) {
SetCapture();
aura::client::WindowMoveSource window_move_source =
@@ -614,14 +667,15 @@ Widget::MoveLoopResult NativeWidgetAura::RunMoveLoop(
}
void NativeWidgetAura::EndMoveLoop() {
- if (window_->parent() &&
+ if (window_ && window_->parent() &&
aura::client::GetWindowMoveClient(window_->parent())) {
aura::client::GetWindowMoveClient(window_->parent())->EndMoveLoop();
}
}
void NativeWidgetAura::SetVisibilityChangedAnimationsEnabled(bool value) {
- window_->SetProperty(aura::client::kAnimationsDisabledKey, !value);
+ if (window_)
+ window_->SetProperty(aura::client::kAnimationsDisabledKey, !value);
}
ui::NativeTheme* NativeWidgetAura::GetNativeTheme() const {
@@ -632,6 +686,9 @@ ui::NativeTheme* NativeWidgetAura::GetNativeTheme() const {
#endif
}
+void NativeWidgetAura::OnRootViewLayout() const {
+}
+
////////////////////////////////////////////////////////////////////////////////
// NativeWidgetAura, views::InputMethodDelegate implementation:
@@ -748,17 +805,15 @@ void NativeWidgetAura::GetHitTestMask(gfx::Path* mask) const {
delegate_->GetHitTestMask(mask);
}
-scoped_refptr<ui::Texture> NativeWidgetAura::CopyTexture() {
- // The layer we create doesn't have an external texture, so this should never
- // get invoked.
- NOTREACHED();
- return scoped_refptr<ui::Texture>();
+void NativeWidgetAura::DidRecreateLayer(ui::Layer *old_layer,
+ ui::Layer *new_layer) {
}
////////////////////////////////////////////////////////////////////////////////
// NativeWidgetAura, ui::EventHandler implementation:
void NativeWidgetAura::OnKeyEvent(ui::KeyEvent* event) {
+ DCHECK(window_);
if (event->is_char()) {
// If a ui::InputMethod object is attached to the root window, character
// events are handled inside the object and are not passed to this function.
@@ -775,6 +830,7 @@ void NativeWidgetAura::OnKeyEvent(ui::KeyEvent* event) {
}
void NativeWidgetAura::OnMouseEvent(ui::MouseEvent* event) {
+ DCHECK(window_);
DCHECK(window_->IsVisible());
if (event->type() == ui::ET_MOUSEWHEEL) {
delegate_->OnMouseEvent(event);
@@ -792,11 +848,13 @@ void NativeWidgetAura::OnScrollEvent(ui::ScrollEvent* event) {
}
void NativeWidgetAura::OnTouchEvent(ui::TouchEvent* event) {
+ DCHECK(window_);
DCHECK(window_->IsVisible());
delegate_->OnTouchEvent(event);
}
void NativeWidgetAura::OnGestureEvent(ui::GestureEvent* event) {
+ DCHECK(window_);
DCHECK(window_->IsVisible());
delegate_->OnGestureEvent(event);
}
@@ -975,12 +1033,14 @@ NativeWidgetPrivate* NativeWidgetPrivate::CreateNativeWidget(
// static
NativeWidgetPrivate* NativeWidgetPrivate::GetNativeWidgetForNativeView(
gfx::NativeView native_view) {
+ // Cast must match type supplied to RegisterNativeWidgetForWindow().
return reinterpret_cast<NativeWidgetPrivate*>(native_view->user_data());
}
// static
NativeWidgetPrivate* NativeWidgetPrivate::GetNativeWidgetForNativeWindow(
gfx::NativeWindow native_window) {
+ // Cast must match type supplied to RegisterNativeWidgetForWindow().
return reinterpret_cast<NativeWidgetPrivate*>(native_window->user_data());
}
@@ -1012,10 +1072,22 @@ void NativeWidgetPrivate::GetAllChildWidgets(gfx::NativeView native_view,
const aura::Window::Windows& child_windows = native_view->children();
for (aura::Window::Windows::const_iterator i = child_windows.begin();
i != child_windows.end(); ++i) {
- NativeWidgetAura* native_widget =
- static_cast<NativeWidgetAura*>(GetNativeWidgetForNativeView(*i));
- if (native_widget)
- children->insert(native_widget->GetWidget());
+ GetAllChildWidgets((*i), children);
+ }
+}
+
+// static
+void NativeWidgetPrivate::GetAllOwnedWidgets(gfx::NativeView native_view,
+ Widget::Widgets* owned) {
+ const aura::Window::Windows& transient_children =
+ native_view->transient_children();
+ for (aura::Window::Windows::const_iterator i = transient_children.begin();
+ i != transient_children.end(); ++i) {
+ NativeWidgetPrivate* native_widget = static_cast<NativeWidgetPrivate*>(
+ GetNativeWidgetForNativeView(*i));
+ if (native_widget && native_widget->GetWidget())
+ owned->insert(native_widget->GetWidget());
+ GetAllOwnedWidgets((*i), owned);
}
}
@@ -1035,7 +1107,7 @@ void NativeWidgetPrivate::ReparentNativeView(gfx::NativeView native_view,
// from their previous parent.
for (Widget::Widgets::iterator it = widgets.begin();
it != widgets.end(); ++it) {
- (*it)->NotifyNativeViewHierarchyChanged(false, previous_parent);
+ (*it)->NotifyNativeViewHierarchyWillChange();
}
if (new_parent) {
@@ -1060,7 +1132,7 @@ void NativeWidgetPrivate::ReparentNativeView(gfx::NativeView native_view,
// And now, notify them that they have a brand new parent.
for (Widget::Widgets::iterator it = widgets.begin();
it != widgets.end(); ++it) {
- (*it)->NotifyNativeViewHierarchyChanged(true, new_parent);
+ (*it)->NotifyNativeViewHierarchyChanged();
}
}
diff --git a/chromium/ui/views/widget/native_widget_aura.h b/chromium/ui/views/widget/native_widget_aura.h
index 57271e81a98..dfd3aaf44e6 100644
--- a/chromium/ui/views/widget/native_widget_aura.h
+++ b/chromium/ui/views/widget/native_widget_aura.h
@@ -12,7 +12,8 @@
#include "ui/aura/client/drag_drop_delegate.h"
#include "ui/aura/client/focus_change_observer.h"
#include "ui/aura/window_delegate.h"
-#include "ui/base/events/event_constants.h"
+#include "ui/base/cursor/cursor.h"
+#include "ui/events/event_constants.h"
#include "ui/views/ime/input_method_delegate.h"
#include "ui/views/views_export.h"
#include "ui/views/widget/native_widget_private.h"
@@ -46,6 +47,12 @@ class VIEWS_EXPORT NativeWidgetAura
// NativeWidgetWin.
static gfx::Font GetWindowTitleFont();
+ // Called internally by NativeWidgetAura and DesktopNativeWidgetAura to
+ // associate |native_widget| with |window|.
+ static void RegisterNativeWidgetForWindow(
+ internal::NativeWidgetPrivate* native_widget,
+ aura::Window* window);
+
// Overridden from internal::NativeWidgetPrivate:
virtual void InitNativeWidget(const Widget::InitParams& params) OVERRIDE;
virtual NonClientFrameView* CreateNonClientFrameView() OVERRIDE;
@@ -125,6 +132,7 @@ class VIEWS_EXPORT NativeWidgetAura
virtual void EndMoveLoop() OVERRIDE;
virtual void SetVisibilityChangedAnimationsEnabled(bool value) OVERRIDE;
virtual ui::NativeTheme* GetNativeTheme() const OVERRIDE;
+ virtual void OnRootViewLayout() const OVERRIDE;
// Overridden from views::InputMethodDelegate:
virtual void DispatchKeyEventPostIME(const ui::KeyEvent& key) OVERRIDE;
@@ -148,7 +156,8 @@ class VIEWS_EXPORT NativeWidgetAura
virtual void OnWindowTargetVisibilityChanged(bool visible) OVERRIDE;
virtual bool HasHitTestMask() const OVERRIDE;
virtual void GetHitTestMask(gfx::Path* mask) const OVERRIDE;
- virtual scoped_refptr<ui::Texture> CopyTexture() OVERRIDE;
+ virtual void DidRecreateLayer(ui::Layer* old_layer,
+ ui::Layer* new_layer) OVERRIDE;
// Overridden from ui::EventHandler:
virtual void OnKeyEvent(ui::KeyEvent* event) OVERRIDE;
@@ -189,6 +198,9 @@ class VIEWS_EXPORT NativeWidgetAura
internal::NativeWidgetDelegate* delegate_;
+ // WARNING: set to NULL when destroyed. As the Widget is not necessarily
+ // destroyed along with |window_| all usage of |window_| should first verify
+ // non-NULL.
aura::Window* window_;
// See class documentation for Widget in widget.h for a note about ownership.
diff --git a/chromium/ui/views/widget/native_widget_aura_unittest.cc b/chromium/ui/views/widget/native_widget_aura_unittest.cc
index 612616bc2c0..de63a0b8a90 100644
--- a/chromium/ui/views/widget/native_widget_aura_unittest.cc
+++ b/chromium/ui/views/widget/native_widget_aura_unittest.cc
@@ -15,7 +15,7 @@
#include "ui/aura/root_window.h"
#include "ui/aura/test/aura_test_helper.h"
#include "ui/aura/window.h"
-#include "ui/base/events/event.h"
+#include "ui/events/event.h"
#include "ui/gfx/screen.h"
#include "ui/views/layout/fill_layout.h"
#include "ui/views/widget/root_view.h"
diff --git a/chromium/ui/views/widget/native_widget_delegate.h b/chromium/ui/views/widget/native_widget_delegate.h
index c1fd073370e..914b575f30d 100644
--- a/chromium/ui/views/widget/native_widget_delegate.h
+++ b/chromium/ui/views/widget/native_widget_delegate.h
@@ -7,7 +7,7 @@
#include <vector>
-#include "ui/base/events/event_constants.h"
+#include "ui/events/event_constants.h"
#include "ui/views/views_export.h"
namespace gfx {
@@ -61,6 +61,9 @@ class VIEWS_EXPORT NativeWidgetDelegate {
virtual void OnNativeFocus(gfx::NativeView focused_view) = 0;
virtual void OnNativeBlur(gfx::NativeView focused_view) = 0;
+ // Called when the window is about to be shown/hidden.
+ virtual void OnNativeWidgetVisibilityChanging(bool visible) = 0;
+
// Called when the window is shown/hidden.
virtual void OnNativeWidgetVisibilityChanged(bool visible) = 0;
diff --git a/chromium/ui/views/widget/native_widget_private.h b/chromium/ui/views/widget/native_widget_private.h
index 3bdd6810cfc..4654b20e3f0 100644
--- a/chromium/ui/views/widget/native_widget_private.h
+++ b/chromium/ui/views/widget/native_widget_private.h
@@ -61,6 +61,8 @@ class VIEWS_EXPORT NativeWidgetPrivate : public NativeWidget {
static void GetAllChildWidgets(gfx::NativeView native_view,
Widget::Widgets* children);
+ static void GetAllOwnedWidgets(gfx::NativeView native_view,
+ Widget::Widgets* owned);
static void ReparentNativeView(gfx::NativeView native_view,
gfx::NativeView new_parent);
@@ -213,6 +215,7 @@ class VIEWS_EXPORT NativeWidgetPrivate : public NativeWidget {
virtual void EndMoveLoop() = 0;
virtual void SetVisibilityChangedAnimationsEnabled(bool value) = 0;
virtual ui::NativeTheme* GetNativeTheme() const = 0;
+ virtual void OnRootViewLayout() const = 0;
// Overridden from NativeWidget:
virtual internal::NativeWidgetPrivate* AsNativeWidgetPrivate() OVERRIDE;
diff --git a/chromium/ui/views/widget/native_widget_win.cc b/chromium/ui/views/widget/native_widget_win.cc
index d6ebdd6d664..53aed93a29a 100644
--- a/chromium/ui/views/widget/native_widget_win.cc
+++ b/chromium/ui/views/widget/native_widget_win.cc
@@ -18,22 +18,22 @@
#include "ui/base/dragdrop/drag_source_win.h"
#include "ui/base/dragdrop/os_exchange_data.h"
#include "ui/base/dragdrop/os_exchange_data_provider_win.h"
-#include "ui/base/events/event.h"
#include "ui/base/ime/input_method_factory.h"
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
#include "ui/base/l10n/l10n_util_win.h"
#include "ui/base/theme_provider.h"
#include "ui/base/view_prop.h"
-#include "ui/base/win/dpi.h"
-#include "ui/base/win/hwnd_util.h"
#include "ui/base/win/mouse_wheel_util.h"
#include "ui/base/win/shell.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/canvas_skia_paint.h"
#include "ui/gfx/path.h"
#include "ui/gfx/point_conversions.h"
#include "ui/gfx/screen.h"
#include "ui/gfx/size_conversions.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/native_theme/native_theme.h"
#include "ui/views/controls/native_control_win.h"
#include "ui/views/controls/textfield/textfield.h"
@@ -61,9 +61,10 @@ namespace views {
namespace {
-// Enumeration callback for NativeWidget::GetAllChildWidgets(). Called for each
-// child HWND beneath the original HWND.
-BOOL CALLBACK EnumerateChildWindowsForNativeWidgets(HWND hwnd, LPARAM l_param) {
+// Enumeration callback for NativeWidget::GetAllChildWidgets() and
+// NativeWidget::GetAllOwnedWidgets. Adds any HWNDs that correspond to
+// Widgets to a set.
+BOOL CALLBACK EnumerateNativeWidgets(HWND hwnd, LPARAM l_param) {
Widget* widget = Widget::GetWidgetForNativeView(hwnd);
if (widget) {
Widget::Widgets* widgets = reinterpret_cast<Widget::Widgets*>(l_param);
@@ -116,7 +117,7 @@ void NativeWidgetWin::Show(int show_state) {
// NativeWidgetWin, NativeWidget implementation:
void NativeWidgetWin::InitNativeWidget(const Widget::InitParams& params) {
- gfx::Rect pixel_bounds = ui::win::DIPToScreenRect(params.bounds);
+ gfx::Rect pixel_bounds = gfx::win::DIPToScreenRect(params.bounds);
Widget::InitParams params_in_pixel(params);
params_in_pixel.bounds = pixel_bounds;
SetInitParams(params_in_pixel);
@@ -220,7 +221,7 @@ internal::InputMethodDelegate* NativeWidgetWin::GetInputMethodDelegate() {
}
void NativeWidgetWin::CenterWindow(const gfx::Size& size) {
- gfx::Size size_in_pixels = ui::win::DIPToScreenSize(size);
+ gfx::Size size_in_pixels = gfx::win::DIPToScreenSize(size);
message_handler_->CenterWindow(size_in_pixels);
}
@@ -228,7 +229,7 @@ void NativeWidgetWin::GetWindowPlacement(
gfx::Rect* bounds,
ui::WindowShowState* show_state) const {
message_handler_->GetWindowPlacement(bounds, show_state);
- *bounds = ui::win::ScreenToDIPRect(*bounds);
+ *bounds = gfx::win::ScreenToDIPRect(*bounds);
}
void NativeWidgetWin::SetWindowTitle(const string16& title) {
@@ -246,21 +247,21 @@ void NativeWidgetWin::InitModalType(ui::ModalType modal_type) {
gfx::Rect NativeWidgetWin::GetWindowBoundsInScreen() const {
gfx::Rect bounds_in_pixels = message_handler_->GetWindowBoundsInScreen();
- return ui::win::ScreenToDIPRect(bounds_in_pixels);
+ return gfx::win::ScreenToDIPRect(bounds_in_pixels);
}
gfx::Rect NativeWidgetWin::GetClientAreaBoundsInScreen() const {
gfx::Rect bounds_in_pixels = message_handler_->GetClientAreaBoundsInScreen();
- return ui::win::ScreenToDIPRect(bounds_in_pixels);
+ return gfx::win::ScreenToDIPRect(bounds_in_pixels);
}
gfx::Rect NativeWidgetWin::GetRestoredBounds() const {
gfx::Rect bounds_in_pixels = message_handler_->GetRestoredBounds();
- return ui::win::ScreenToDIPRect(bounds_in_pixels);
+ return gfx::win::ScreenToDIPRect(bounds_in_pixels);
}
void NativeWidgetWin::SetBounds(const gfx::Rect& bounds) {
- float scale = ui::win::GetDeviceScaleFactor();
+ float scale = gfx::win::GetDeviceScaleFactor();
gfx::Rect bounds_in_pixels(
gfx::ToCeiledPoint(gfx::ScalePoint(bounds.origin(), scale)),
gfx::ToFlooredSize(gfx::ScaleSize(bounds.size(), scale)));
@@ -305,7 +306,7 @@ void NativeWidgetWin::Hide() {
void NativeWidgetWin::ShowMaximizedWithBounds(
const gfx::Rect& restored_bounds) {
- gfx::Rect pixel_bounds = ui::win::DIPToScreenRect(restored_bounds);
+ gfx::Rect pixel_bounds = gfx::win::DIPToScreenRect(restored_bounds);
message_handler_->ShowMaximizedWithBounds(pixel_bounds);
}
@@ -412,7 +413,7 @@ void NativeWidgetWin::RunShellDrag(View* view,
}
void NativeWidgetWin::SchedulePaintInRect(const gfx::Rect& rect) {
- gfx::Rect pixel_rect = ui::win::DIPToScreenRect(rect);
+ gfx::Rect pixel_rect = gfx::win::DIPToScreenRect(rect);
message_handler_->SchedulePaintInRect(pixel_rect);
}
@@ -429,7 +430,7 @@ void NativeWidgetWin::ClearNativeFocus() {
}
gfx::Rect NativeWidgetWin::GetWorkAreaBoundsInScreen() const {
- return ui::win::ScreenToDIPRect(
+ return gfx::win::ScreenToDIPRect(
gfx::Screen::GetNativeScreen()->GetDisplayNearestWindow(
GetNativeView()).work_area());
}
@@ -456,6 +457,9 @@ ui::NativeTheme* NativeWidgetWin::GetNativeTheme() const {
return ui::NativeTheme::instance();
}
+void NativeWidgetWin::OnRootViewLayout() const {
+}
+
////////////////////////////////////////////////////////////////////////////////
// NativeWidgetWin, NativeWidget implementation:
@@ -566,7 +570,7 @@ bool NativeWidgetWin::WillProcessWorkAreaChange() const {
}
int NativeWidgetWin::GetNonClientComponent(const gfx::Point& point) const {
- gfx::Point point_in_dip = ui::win::ScreenToDIPPoint(point);
+ gfx::Point point_in_dip = gfx::win::ScreenToDIPPoint(point);
return delegate_->GetNonClientComponent(point_in_dip);
}
@@ -581,13 +585,13 @@ bool NativeWidgetWin::GetClientAreaInsets(gfx::Insets* insets) const {
void NativeWidgetWin::GetMinMaxSize(gfx::Size* min_size,
gfx::Size* max_size) const {
- *min_size = ui::win::ScreenToDIPSize(delegate_->GetMinimumSize());
- *max_size = ui::win::ScreenToDIPSize(delegate_->GetMaximumSize());
+ *min_size = gfx::win::ScreenToDIPSize(delegate_->GetMinimumSize());
+ *max_size = gfx::win::ScreenToDIPSize(delegate_->GetMaximumSize());
}
gfx::Size NativeWidgetWin::GetRootViewSize() const {
gfx::Size pixel_size = GetWidget()->GetRootView()->size();
- return ui::win::ScreenToDIPSize(pixel_size);
+ return gfx::win::ScreenToDIPSize(pixel_size);
}
void NativeWidgetWin::ResetWindowControls() {
@@ -717,12 +721,16 @@ void NativeWidgetWin::HandleWorkAreaChanged() {
GetWidget()->widget_delegate()->OnWorkAreaChanged();
}
+void NativeWidgetWin::HandleVisibilityChanging(bool visible) {
+ delegate_->OnNativeWidgetVisibilityChanging(visible);
+}
+
void NativeWidgetWin::HandleVisibilityChanged(bool visible) {
delegate_->OnNativeWidgetVisibilityChanged(visible);
}
void NativeWidgetWin::HandleClientSizeChanged(const gfx::Size& new_size) {
- gfx::Size size_in_dip = ui::win::ScreenToDIPSize(new_size);
+ gfx::Size size_in_dip = gfx::win::ScreenToDIPSize(new_size);
delegate_->OnNativeWidgetSizeChanged(size_in_dip);
}
@@ -747,8 +755,8 @@ void NativeWidgetWin::HandleNativeBlur(HWND focused_window) {
bool NativeWidgetWin::HandleMouseEvent(const ui::MouseEvent& event) {
static gfx::Transform scale_transform(
- 1/ui::win::GetDeviceScaleFactor(), 0.0,
- 0.0, 1/ui::win::GetDeviceScaleFactor(),
+ 1/gfx::win::GetDeviceScaleFactor(), 0.0,
+ 0.0, 1/gfx::win::GetDeviceScaleFactor(),
0.0, 0.0);
if (event.IsMouseWheelEvent()) {
ui::MouseWheelEvent dpi_event(
@@ -780,9 +788,8 @@ bool NativeWidgetWin::HandleUntranslatedKeyEvent(const ui::KeyEvent& event) {
return !!input_method;
}
-bool NativeWidgetWin::HandleTouchEvent(const ui::TouchEvent& event) {
+void NativeWidgetWin::HandleTouchEvent(const ui::TouchEvent& event) {
NOTREACHED() << "Touch events are not supported";
- return false;
}
bool NativeWidgetWin::HandleIMEMessage(UINT message,
@@ -812,7 +819,7 @@ void NativeWidgetWin::HandleInputLanguageChange(DWORD character_set,
}
bool NativeWidgetWin::HandlePaintAccelerated(const gfx::Rect& invalid_rect) {
- gfx::Rect dpi_rect = ui::win::ScreenToDIPRect(invalid_rect);
+ gfx::Rect dpi_rect = gfx::win::ScreenToDIPRect(invalid_rect);
return delegate_->OnNativeWidgetPaintAccelerated(dpi_rect);
}
@@ -902,11 +909,11 @@ bool Widget::ConvertRect(const Widget* source,
if (source_hwnd == target_hwnd)
return true;
- RECT win_rect = ui::win::DIPToScreenRect(*rect).ToRECT();
+ RECT win_rect = gfx::win::DIPToScreenRect(*rect).ToRECT();
if (::MapWindowPoints(source_hwnd, target_hwnd,
reinterpret_cast<LPPOINT>(&win_rect),
sizeof(RECT)/sizeof(POINT))) {
- *rect = ui::win::ScreenToDIPRect(gfx::Rect(win_rect));
+ *rect = gfx::win::ScreenToDIPRect(gfx::Rect(win_rect));
return true;
}
return false;
@@ -984,11 +991,26 @@ void NativeWidgetPrivate::GetAllChildWidgets(gfx::NativeView native_view,
Widget* widget = Widget::GetWidgetForNativeView(native_view);
if (widget)
children->insert(widget);
- EnumChildWindows(native_view, EnumerateChildWindowsForNativeWidgets,
+ EnumChildWindows(native_view, EnumerateNativeWidgets,
reinterpret_cast<LPARAM>(children));
}
// static
+void NativeWidgetPrivate::GetAllOwnedWidgets(gfx::NativeView native_view,
+ Widget::Widgets* owned) {
+ if (!native_view)
+ return;
+
+ Widget::Widgets all;
+ EnumWindows(EnumerateNativeWidgets, reinterpret_cast<LPARAM>(&all));
+ for (Widget::Widgets::const_iterator iter = all.begin();
+ iter != all.end(); ++iter) {
+ if (native_view == GetWindow((*iter)->GetNativeView(), GW_OWNER))
+ owned->insert(*iter);
+ }
+}
+
+// static
void NativeWidgetPrivate::ReparentNativeView(gfx::NativeView native_view,
gfx::NativeView new_parent) {
if (!native_view)
@@ -1005,9 +1027,7 @@ void NativeWidgetPrivate::ReparentNativeView(gfx::NativeView native_view,
// from their previous parent.
for (Widget::Widgets::iterator it = widgets.begin();
it != widgets.end(); ++it) {
- // TODO(beng): Rename this notification to NotifyNativeViewChanging()
- // and eliminate the bool parameter.
- (*it)->NotifyNativeViewHierarchyChanged(false, previous_parent);
+ (*it)->NotifyNativeViewHierarchyWillChange();
}
::SetParent(native_view, new_parent);
@@ -1015,7 +1035,7 @@ void NativeWidgetPrivate::ReparentNativeView(gfx::NativeView native_view,
// And now, notify them that they have a brand new parent.
for (Widget::Widgets::iterator it = widgets.begin();
it != widgets.end(); ++it) {
- (*it)->NotifyNativeViewHierarchyChanged(true, new_parent);
+ (*it)->NotifyNativeViewHierarchyChanged();
}
}
diff --git a/chromium/ui/views/widget/native_widget_win.h b/chromium/ui/views/widget/native_widget_win.h
index 81fa718ef41..cadc6fdb7a3 100644
--- a/chromium/ui/views/widget/native_widget_win.h
+++ b/chromium/ui/views/widget/native_widget_win.h
@@ -11,7 +11,7 @@
#include "base/memory/scoped_vector.h"
#include "base/win/scoped_comptr.h"
#include "base/win/win_util.h"
-#include "ui/base/win/window_impl.h"
+#include "ui/gfx/win/window_impl.h"
#include "ui/views/widget/native_widget_private.h"
#include "ui/views/win/hwnd_message_handler_delegate.h"
@@ -146,6 +146,7 @@ class VIEWS_EXPORT NativeWidgetWin : public internal::NativeWidgetPrivate,
virtual void EndMoveLoop() OVERRIDE;
virtual void SetVisibilityChangedAnimationsEnabled(bool value) OVERRIDE;
virtual ui::NativeTheme* GetNativeTheme() const OVERRIDE;
+ virtual void OnRootViewLayout() const OVERRIDE;
// Overridden from NativeWidget:
virtual ui::EventHandler* GetEventHandler() OVERRIDE;
@@ -202,6 +203,7 @@ class VIEWS_EXPORT NativeWidgetWin : public internal::NativeWidgetPrivate,
virtual void HandleEndWMSizeMove() OVERRIDE;
virtual void HandleMove() OVERRIDE;
virtual void HandleWorkAreaChanged() OVERRIDE;
+ virtual void HandleVisibilityChanging(bool visible) OVERRIDE;
virtual void HandleVisibilityChanged(bool visible) OVERRIDE;
virtual void HandleClientSizeChanged(const gfx::Size& new_size) OVERRIDE;
virtual void HandleFrameChanged() OVERRIDE;
@@ -210,7 +212,7 @@ class VIEWS_EXPORT NativeWidgetWin : public internal::NativeWidgetPrivate,
virtual bool HandleMouseEvent(const ui::MouseEvent& event) OVERRIDE;
virtual bool HandleKeyEvent(const ui::KeyEvent& event) OVERRIDE;
virtual bool HandleUntranslatedKeyEvent(const ui::KeyEvent& event) OVERRIDE;
- virtual bool HandleTouchEvent(const ui::TouchEvent& event) OVERRIDE;
+ virtual void HandleTouchEvent(const ui::TouchEvent& event) OVERRIDE;
virtual bool HandleIMEMessage(UINT message,
WPARAM w_param,
LPARAM l_param,
diff --git a/chromium/ui/views/widget/root_view.cc b/chromium/ui/views/widget/root_view.cc
index b304c520b97..1185c755153 100644
--- a/chromium/ui/views/widget/root_view.cc
+++ b/chromium/ui/views/widget/root_view.cc
@@ -10,9 +10,9 @@
#include "base/message_loop/message_loop.h"
#include "ui/base/accessibility/accessible_view_state.h"
#include "ui/base/dragdrop/drag_drop_types.h"
-#include "ui/base/events/event.h"
-#include "ui/base/keycodes/keyboard_codes.h"
#include "ui/compositor/layer.h"
+#include "ui/events/event.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/gfx/canvas.h"
#include "ui/views/focus/view_storage.h"
#include "ui/views/layout/fill_layout.h"
@@ -20,6 +20,10 @@
#include "ui/views/widget/widget_delegate.h"
#include "ui/views/widget/widget_deletion_observer.h"
+#if defined(USE_AURA)
+#include "ui/base/cursor/cursor.h"
+#endif
+
namespace views {
namespace internal {
@@ -102,9 +106,8 @@ View* RootView::GetContentsView() {
return child_count() > 0 ? child_at(0) : NULL;
}
-void RootView::NotifyNativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view) {
- PropagateNativeViewHierarchyChanged(attached, native_view, this);
+void RootView::NotifyNativeViewHierarchyChanged() {
+ PropagateNativeViewHierarchyChanged();
}
// Input -----------------------------------------------------------------------
@@ -123,8 +126,7 @@ void RootView::DispatchKeyEvent(ui::KeyEvent* event) {
return;
}
- for (; v && v != this && !event->handled(); v = v->parent())
- DispatchEventToTarget(v, event);
+ DispatchKeyEventStartAt(v, event);
}
void RootView::DispatchScrollEvent(ui::ScrollEvent* event) {
@@ -364,6 +366,11 @@ bool RootView::IsDrawn() const {
return visible();
}
+void RootView::Layout() {
+ View::Layout();
+ widget_->OnRootViewLayout();
+}
+
const char* RootView::GetClassName() const {
return kViewClassName;
}
@@ -637,10 +644,6 @@ void RootView::OnPaint(gfx::Canvas* canvas) {
if (!layer() || !layer()->fills_bounds_opaquely())
canvas->DrawColor(SK_ColorBLACK, SkXfermode::kClear_Mode);
- // TODO (pkotwicz): Remove this once we switch over to Aura desktop.
- // This is needed so that we can set the background behind the RWHV when the
- // RWHV is not visible. Not needed once there is a view between the RootView
- // and RWHV.
View::OnPaint(canvas);
}
@@ -699,6 +702,19 @@ void RootView::NotifyEnterExitOfDescendant(const ui::MouseEvent& event,
}
}
+
+void RootView::DispatchKeyEventStartAt(View* view, ui::KeyEvent* event) {
+ if (event->handled() || !view)
+ return;
+
+ for (; view && view != this; view = view->parent()) {
+ DispatchEventToTarget(view, event);
+ // Do this check here rather than in the if as |view| may have been deleted.
+ if (event->handled())
+ return;
+ }
+}
+
bool RootView::CanDispatchToTarget(ui::EventTarget* target) {
return event_dispatch_target_ == target;
}
diff --git a/chromium/ui/views/widget/root_view.h b/chromium/ui/views/widget/root_view.h
index b89ab8fe8eb..6ab367bd992 100644
--- a/chromium/ui/views/widget/root_view.h
+++ b/chromium/ui/views/widget/root_view.h
@@ -8,7 +8,7 @@
#include <string>
#include "base/memory/ref_counted.h"
-#include "ui/base/events/event_dispatcher.h"
+#include "ui/events/event_dispatcher.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/focus/focus_search.h"
#include "ui/views/view.h"
@@ -16,6 +16,7 @@
namespace views {
namespace test {
+class RootViewTestHelper;
class WidgetTest;
}
@@ -60,8 +61,7 @@ class VIEWS_EXPORT RootView : public View,
View* GetContentsView();
// Called when parent of the host changed.
- void NotifyNativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view);
+ void NotifyNativeViewHierarchyChanged();
// Input ---------------------------------------------------------------------
@@ -101,6 +101,7 @@ class VIEWS_EXPORT RootView : public View,
virtual const Widget* GetWidget() const OVERRIDE;
virtual Widget* GetWidget() OVERRIDE;
virtual bool IsDrawn() const OVERRIDE;
+ virtual void Layout() OVERRIDE;
virtual const char* GetClassName() const OVERRIDE;
virtual void SchedulePaintInRect(const gfx::Rect& rect) OVERRIDE;
virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE;
@@ -127,6 +128,7 @@ class VIEWS_EXPORT RootView : public View,
private:
friend class ::views::View;
friend class ::views::Widget;
+ friend class ::views::test::RootViewTestHelper;
friend class ::views::test::WidgetTest;
// Input ---------------------------------------------------------------------
@@ -153,6 +155,10 @@ class VIEWS_EXPORT RootView : public View,
View* view,
View* sibling);
+ // Dispatches the KeyEvent to |view| and ancestors until the event is
+ // handled.
+ void DispatchKeyEventStartAt(View* view, ui::KeyEvent* event);
+
// Overridden from ui::EventDispatcherDelegate:
virtual bool CanDispatchToTarget(ui::EventTarget* target) OVERRIDE;
diff --git a/chromium/ui/views/widget/root_view_test_helper.h b/chromium/ui/views/widget/root_view_test_helper.h
new file mode 100644
index 00000000000..a26396730b2
--- /dev/null
+++ b/chromium/ui/views/widget/root_view_test_helper.h
@@ -0,0 +1,33 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_WIDGET_ROOT_VIEW_TEST_HELPER_H_
+#define UI_VIEWS_WIDGET_ROOT_VIEW_TEST_HELPER_H_
+
+#include "ui/views/widget/root_view.h"
+
+namespace views {
+namespace test {
+
+class RootViewTestHelper {
+ public:
+ explicit RootViewTestHelper(internal::RootView* root_view)
+ : root_view_(root_view) {
+ }
+ ~RootViewTestHelper() {}
+
+ void DispatchKeyEventStartAt(View* view, ui::KeyEvent* event) {
+ root_view_->DispatchKeyEventStartAt(view, event);
+ }
+
+ private:
+ internal::RootView* root_view_;
+
+ DISALLOW_COPY_AND_ASSIGN(RootViewTestHelper);
+};
+
+} // namespace test
+} // namespace views
+
+#endif // UI_VIEWS_WIDGET_ROOT_VIEW_TEST_HELPER_H_
diff --git a/chromium/ui/views/widget/root_view_unittest.cc b/chromium/ui/views/widget/root_view_unittest.cc
new file mode 100644
index 00000000000..ebe20d65346
--- /dev/null
+++ b/chromium/ui/views/widget/root_view_unittest.cc
@@ -0,0 +1,55 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ui/views/test/views_test_base.h"
+#include "ui/views/widget/root_view_test_helper.h"
+
+namespace views {
+namespace test {
+
+typedef ViewsTestBase RootViewTest;
+
+class DeleteOnKeyEventView : public View {
+ public:
+ explicit DeleteOnKeyEventView(bool* set_on_key) : set_on_key_(set_on_key) {}
+ virtual ~DeleteOnKeyEventView() {}
+
+ virtual bool OnKeyPressed(const ui::KeyEvent& event) OVERRIDE {
+ *set_on_key_ = true;
+ delete this;
+ return true;
+ }
+
+ private:
+ // Set to true in OnKeyPressed().
+ bool* set_on_key_;
+
+ DISALLOW_COPY_AND_ASSIGN(DeleteOnKeyEventView);
+};
+
+// Verifies deleting a View in OnKeyPressed() doesn't crash.
+TEST_F(RootViewTest, DeleteViewDuringKeyEventDispatch) {
+ Widget widget;
+ Widget::InitParams init_params =
+ CreateParams(Widget::InitParams::TYPE_POPUP);
+ init_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ widget.Init(init_params);
+
+ bool got_key_event = false;
+
+ View* content = new View;
+ widget.SetContentsView(content);
+
+ View* child = new DeleteOnKeyEventView(&got_key_event);
+ content->AddChildView(child);
+
+ ui::KeyEvent key_event(ui::ET_KEY_PRESSED, ui::VKEY_ESCAPE, 0, false);
+ RootViewTestHelper test_helper(
+ static_cast<internal::RootView*>(widget.GetRootView()));
+ test_helper.DispatchKeyEventStartAt(child, &key_event);
+ EXPECT_TRUE(got_key_event);
+}
+
+} // namespace test
+} // namespace views
diff --git a/chromium/ui/views/widget/tooltip_manager.cc b/chromium/ui/views/widget/tooltip_manager.cc
index bfcbf02b47d..7eb49787641 100644
--- a/chromium/ui/views/widget/tooltip_manager.cc
+++ b/chromium/ui/views/widget/tooltip_manager.cc
@@ -4,13 +4,13 @@
#include "ui/views/widget/tooltip_manager.h"
+#include <algorithm>
#include <vector>
#include "base/strings/string_split.h"
#include "base/strings/utf_string_conversions.h"
-#include "ui/base/text/text_elider.h"
-
-namespace {
+#include "ui/gfx/text_elider.h"
+#include "ui/gfx/text_utils.h"
// Maximum number of characters we allow in a tooltip.
const size_t kMaxTooltipLength = 1024;
@@ -18,8 +18,6 @@ const size_t kMaxTooltipLength = 1024;
// Maximum number of lines we allow in the tooltip.
const size_t kMaxLines = 6;
-} // namespace
-
namespace views {
// static
@@ -48,13 +46,14 @@ void TooltipManager::TrimTooltipToFit(string16* text,
*line_count = static_cast<int>(lines.size());
// Format each line to fit.
- gfx::Font font = GetDefaultFont();
+ const gfx::FontList& font_list = GetDefaultFontList();
string16 result;
for (std::vector<string16>::iterator i = lines.begin(); i != lines.end();
++i) {
string16 elided_text =
- ui::ElideText(*i, font, available_width, ui::ELIDE_AT_END);
- *max_width = std::max(*max_width, font.GetStringWidth(elided_text));
+ gfx::ElideText(*i, font_list, available_width, gfx::ELIDE_AT_END);
+ *max_width = std::max(*max_width,
+ gfx::GetStringWidth(elided_text, font_list));
if (!result.empty())
result.push_back('\n');
result.append(elided_text);
diff --git a/chromium/ui/views/widget/tooltip_manager.h b/chromium/ui/views/widget/tooltip_manager.h
index f8601dd6ae3..1228f5a509a 100644
--- a/chromium/ui/views/widget/tooltip_manager.h
+++ b/chromium/ui/views/widget/tooltip_manager.h
@@ -13,7 +13,7 @@
#include "ui/views/views_export.h"
namespace gfx {
-class Font;
+class FontList;
} // namespace gfx
namespace views {
@@ -30,7 +30,7 @@ class VIEWS_EXPORT TooltipManager {
static int GetTooltipHeight();
// Returns the default font used by tooltips.
- static gfx::Font GetDefaultFont();
+ static const gfx::FontList& GetDefaultFontList();
// Returns the maximum width of the tooltip. |x| and |y| give the location
// the tooltip is to be displayed on in screen coordinates. |context| is
diff --git a/chromium/ui/views/widget/tooltip_manager_aura.cc b/chromium/ui/views/widget/tooltip_manager_aura.cc
index f7a47613fc3..632946339a0 100644
--- a/chromium/ui/views/widget/tooltip_manager_aura.cc
+++ b/chromium/ui/views/widget/tooltip_manager_aura.cc
@@ -8,7 +8,6 @@
#include "ui/aura/client/tooltip_client.h"
#include "ui/aura/root_window.h"
#include "ui/base/resource/resource_bundle.h"
-#include "ui/gfx/font.h"
#include "ui/gfx/rect.h"
#include "ui/gfx/screen.h"
#include "ui/views/widget/widget.h"
@@ -23,8 +22,8 @@ int TooltipManager::GetTooltipHeight() {
}
// static
-gfx::Font TooltipManager::GetDefaultFont() {
- return ui::ResourceBundle::GetSharedInstance().GetFont(
+const gfx::FontList& TooltipManager::GetDefaultFontList() {
+ return ui::ResourceBundle::GetSharedInstance().GetFontList(
ui::ResourceBundle::BaseFont);
}
diff --git a/chromium/ui/views/widget/tooltip_manager_win.cc b/chromium/ui/views/widget/tooltip_manager_win.cc
index fa0ad45d711..362ff33e886 100644
--- a/chromium/ui/views/widget/tooltip_manager_win.cc
+++ b/chromium/ui/views/widget/tooltip_manager_win.cc
@@ -16,11 +16,11 @@
#include "base/win/scoped_hdc.h"
#include "base/win/scoped_select_object.h"
#include "ui/base/l10n/l10n_util_win.h"
-#include "ui/base/win/dpi.h"
-#include "ui/base/win/hwnd_util.h"
-#include "ui/base/win/scoped_set_map_mode.h"
-#include "ui/gfx/font.h"
+#include "ui/gfx/font_list.h"
#include "ui/gfx/screen.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/hwnd_util.h"
+#include "ui/gfx/win/scoped_set_map_mode.h"
#include "ui/views/view.h"
#include "ui/views/widget/monitor_win.h"
#include "ui/views/widget/widget.h"
@@ -52,11 +52,11 @@ static gfx::Font DetermineDefaultFont() {
}
// static
-gfx::Font TooltipManager::GetDefaultFont() {
- static gfx::Font* font = NULL;
- if (!font)
- font = new gfx::Font(DetermineDefaultFont());
- return *font;
+const gfx::FontList& TooltipManager::GetDefaultFontList() {
+ static gfx::FontList* font_list = NULL;
+ if (!font_list)
+ font_list = new gfx::FontList(DetermineDefaultFont());
+ return *font_list;
}
// static
@@ -227,7 +227,7 @@ bool TooltipManagerWin::SetTooltipPosition(int text_x, int text_y) {
// Calculate the bounds the tooltip will get.
gfx::Point view_loc;
View::ConvertPointToScreen(last_tooltip_view_, &view_loc);
- view_loc = ui::win::DIPToScreenPoint(view_loc);
+ view_loc = gfx::win::DIPToScreenPoint(view_loc);
RECT bounds = { view_loc.x() + text_x,
view_loc.y() + text_y,
view_loc.x() + text_x + tooltip_width_,
@@ -257,7 +257,7 @@ int TooltipManagerWin::CalcTooltipHeight() {
if (hfont != NULL) {
base::win::ScopedGetDC dc(tooltip_hwnd_);
base::win::ScopedSelectObject font(dc, hfont);
- ui::ScopedSetMapMode mode(dc, MM_TEXT);
+ gfx::ScopedSetMapMode mode(dc, MM_TEXT);
TEXTMETRIC font_metrics;
GetTextMetrics(dc, &font_metrics);
height = font_metrics.tmHeight;
@@ -301,14 +301,14 @@ void TooltipManagerWin::UpdateTooltip(const gfx::Point& mouse_pos) {
void TooltipManagerWin::OnMouse(UINT u_msg, WPARAM w_param, LPARAM l_param) {
gfx::Point mouse_pos_in_pixels(l_param);
- gfx::Point mouse_pos = ui::win::ScreenToDIPPoint(mouse_pos_in_pixels);
+ gfx::Point mouse_pos = gfx::win::ScreenToDIPPoint(mouse_pos_in_pixels);
if (u_msg >= WM_NCMOUSEMOVE && u_msg <= WM_NCXBUTTONDBLCLK) {
// NC message coordinates are in screen coordinates.
POINT temp = mouse_pos_in_pixels.ToPOINT();
::MapWindowPoints(HWND_DESKTOP, GetParent(), &temp, 1);
mouse_pos_in_pixels.SetPoint(temp.x, temp.y);
- mouse_pos = ui::win::ScreenToDIPPoint(mouse_pos_in_pixels);
+ mouse_pos = gfx::win::ScreenToDIPPoint(mouse_pos_in_pixels);
}
if (u_msg != WM_MOUSEMOVE || last_mouse_pos_ != mouse_pos) {
diff --git a/chromium/ui/views/widget/widget.cc b/chromium/ui/views/widget/widget.cc
index e97c950261b..168cfdfa163 100644
--- a/chromium/ui/views/widget/widget.cc
+++ b/chromium/ui/views/widget/widget.cc
@@ -9,13 +9,14 @@
#include "base/message_loop/message_loop.h"
#include "base/strings/utf_string_conversions.h"
#include "ui/base/default_theme_provider.h"
-#include "ui/base/events/event.h"
#include "ui/base/hit_test.h"
#include "ui/base/l10n/l10n_font_util.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/compositor/compositor.h"
#include "ui/compositor/layer.h"
+#include "ui/events/event.h"
#include "ui/gfx/screen.h"
+#include "ui/views/controls/menu/menu_controller.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/focus/focus_manager_factory.h"
#include "ui/views/focus/view_storage.h"
@@ -29,9 +30,10 @@
#include "ui/views/widget/widget_deletion_observer.h"
#include "ui/views/widget/widget_observer.h"
#include "ui/views/window/custom_frame_view.h"
+#include "ui/views/window/dialog_delegate.h"
-#if !defined(OS_MACOSX)
-#include "ui/views/controls/menu/menu_controller.h"
+#if defined(USE_AURA)
+#include "ui/base/cursor/cursor.h"
#endif
namespace views {
@@ -85,10 +87,15 @@ class DefaultWidgetDelegate : public WidgetDelegate {
virtual const Widget* GetWidget() const OVERRIDE {
return widget_;
}
-
virtual bool CanActivate() const OVERRIDE {
return can_activate_;
}
+ virtual bool ShouldAdvanceFocusToTopLevelWidget() const OVERRIDE {
+ // In most situations where a Widget is used without a delegate the Widget
+ // is used as a container, so that we want focus to advance to the top-level
+ // widget. A good example of this is the find bar.
+ return true;
+ }
private:
Widget* widget_;
@@ -172,6 +179,7 @@ Widget::Widget()
is_mouse_button_pressed_(false),
is_touch_down_(false),
last_mouse_event_was_move_(false),
+ auto_release_capture_(true),
root_layers_dirty_(false),
movement_disabled_(false) {
}
@@ -243,6 +251,30 @@ Widget* Widget::CreateWindowWithContextAndBounds(WidgetDelegate* delegate,
}
// static
+Widget* Widget::CreateWindowAsFramelessChild(WidgetDelegate* widget_delegate,
+ gfx::NativeView parent,
+ gfx::NativeView new_style_parent) {
+ views::Widget* widget = new views::Widget;
+
+ views::Widget::InitParams params;
+ params.delegate = widget_delegate;
+ params.child = true;
+ if (views::DialogDelegate::UseNewStyle()) {
+ params.parent = new_style_parent;
+ params.remove_standard_frame = true;
+#if defined(USE_AURA)
+ params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW;
+#endif
+ } else {
+ params.parent = parent;
+ }
+
+ widget->Init(params);
+
+ return widget;
+}
+
+// static
Widget* Widget::GetWidgetForNativeView(gfx::NativeView native_view) {
internal::NativeWidgetPrivate* native_widget =
internal::NativeWidgetPrivate::GetNativeWidgetForNativeView(native_view);
@@ -272,6 +304,12 @@ void Widget::GetAllChildWidgets(gfx::NativeView native_view,
}
// static
+void Widget::GetAllOwnedWidgets(gfx::NativeView native_view,
+ Widgets* owned) {
+ internal::NativeWidgetPrivate::GetAllOwnedWidgets(native_view, owned);
+}
+
+// static
void Widget::ReparentNativeView(gfx::NativeView native_view,
gfx::NativeView new_parent) {
internal::NativeWidgetPrivate::ReparentNativeView(native_view, new_parent);
@@ -402,16 +440,16 @@ void Widget::ViewHierarchyChanged(
}
}
-void Widget::NotifyNativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view) {
- if (!attached) {
- FocusManager* focus_manager = GetFocusManager();
- // We are being removed from a window hierarchy. Treat this as
- // the root_view_ being removed.
- if (focus_manager)
- focus_manager->ViewRemoved(root_view_.get());
- }
- root_view_->NotifyNativeViewHierarchyChanged(attached, native_view);
+void Widget::NotifyNativeViewHierarchyWillChange() {
+ FocusManager* focus_manager = GetFocusManager();
+ // We are being removed from a window hierarchy. Treat this as
+ // the root_view_ being removed.
+ if (focus_manager)
+ focus_manager->ViewRemoved(root_view_.get());
+}
+
+void Widget::NotifyNativeViewHierarchyChanged() {
+ root_view_->NotifyNativeViewHierarchyChanged();
}
// Converted methods (see header) ----------------------------------------------
@@ -561,17 +599,6 @@ bool Widget::IsClosed() const {
void Widget::Show() {
TRACE_EVENT0("views", "Widget::Show");
if (non_client_view_) {
-#if defined(OS_MACOSX)
- // On the Mac the FullScreenBookmarkBar test is different then for any other
- // OS. Since the new maximize logic from ash does not apply to the mac, we
- // continue to ignore the fullscreen mode here.
- if (saved_show_state_ == ui::SHOW_STATE_MAXIMIZED &&
- !initial_restored_bounds_.IsEmpty()) {
- native_widget_->ShowMaximizedWithBounds(initial_restored_bounds_);
- } else {
- native_widget_->ShowWithWindowState(saved_show_state_);
- }
-#else
// While initializing, the kiosk mode will go to full screen before the
// widget gets shown. In that case we stay in full screen mode, regardless
// of the |saved_show_state_| member.
@@ -583,7 +610,6 @@ void Widget::Show() {
native_widget_->ShowWithWindowState(
IsFullscreen() ? ui::SHOW_STATE_FULLSCREEN : saved_show_state_);
}
-#endif
// |saved_show_state_| only applies the first time the window is shown.
// If we don't reset the value the window may be shown maximized every time
// it is subsequently shown after being hidden.
@@ -923,10 +949,6 @@ bool Widget::SetInitialFocus() {
return !!v;
}
-View* Widget::GetChildViewParent() {
- return GetContentsView() ? GetContentsView() : GetRootView();
-}
-
gfx::Rect Widget::GetWorkAreaBoundsInScreen() const {
return native_widget_->GetWorkAreaBoundsInScreen();
}
@@ -940,6 +962,10 @@ void Widget::SynthesizeMouseMoveEvent() {
root_view_->OnMouseMoved(mouse_event);
}
+void Widget::OnRootViewLayout() {
+ native_widget_->OnRootViewLayout();
+}
+
void Widget::OnOwnerClosing() {
}
@@ -987,6 +1013,11 @@ void Widget::OnNativeBlur(gfx::NativeView new_focused_view) {
new_focused_view);
}
+void Widget::OnNativeWidgetVisibilityChanging(bool visible) {
+ FOR_EACH_OBSERVER(WidgetObserver, observers_,
+ OnWidgetVisibilityChanging(this, visible));
+}
+
void Widget::OnNativeWidgetVisibilityChanged(bool visible) {
View* root = GetRootView();
if (root)
@@ -1098,9 +1129,6 @@ void Widget::OnKeyEvent(ui::KeyEvent* event) {
}
void Widget::OnMouseEvent(ui::MouseEvent* event) {
- if (!IsMouseEventsEnabled())
- return;
-
View* root_view = GetRootView();
switch (event->type()) {
case ui::ET_MOUSE_PRESSED: {
@@ -1134,10 +1162,8 @@ void Widget::OnMouseEvent(ui::MouseEvent* event) {
last_mouse_event_was_move_ = false;
is_mouse_button_pressed_ = false;
// Release capture first, to avoid confusion if OnMouseReleased blocks.
- if (native_widget_->HasCapture() &&
- ShouldReleaseCaptureOnMouseReleased()) {
+ if (auto_release_capture_ && native_widget_->HasCapture())
native_widget_->ReleaseCapture();
- }
if (root_view)
root_view->OnMouseReleased(*event);
if ((event->flags() & ui::EF_IS_NON_CLIENT) == 0)
@@ -1205,7 +1231,7 @@ void Widget::OnGestureEvent(ui::GestureEvent* event) {
case ui::ET_GESTURE_END:
if (event->details().touch_points() == 1) {
is_touch_down_ = false;
- if (ShouldReleaseCaptureOnMouseReleased())
+ if (auto_release_capture_)
ReleaseCapture();
}
break;
@@ -1288,10 +1314,6 @@ void Widget::DestroyRootView() {
////////////////////////////////////////////////////////////////////////////////
// Widget, private:
-bool Widget::ShouldReleaseCaptureOnMouseReleased() const {
- return true;
-}
-
void Widget::SetInactiveRenderingDisabled(bool value) {
if (value == disable_inactive_rendering_)
return;
diff --git a/chromium/ui/views/widget/widget.h b/chromium/ui/views/widget/widget.h
index f020a0c7de1..1600f946921 100644
--- a/chromium/ui/views/widget/widget.h
+++ b/chromium/ui/views/widget/widget.h
@@ -156,7 +156,6 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
InitParams();
explicit InitParams(Type type);
-
// Will return the first of the following that isn't NULL: the native view,
// |parent|, |context|.
gfx::NativeView GetContext() const;
@@ -177,9 +176,9 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
Ownership ownership;
bool mirror_origin_in_rtl;
bool has_dropshadow;
- // Only used by NativeWidgetWin. Specifies that the system default caption
- // and icon should not be rendered, and that the client area should be
- // equivalent to the window area.
+ // Only used by Windows. Specifies that the system default caption and icon
+ // should not be rendered, and that the client area should be equivalent to
+ // the window area.
bool remove_standard_frame;
// Only used by ShellWindow on Windows. Specifies that the default icon of
// packaged app should be the system default icon.
@@ -217,6 +216,11 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
// where it wants your window placed.) NULL is not allowed if you are using
// aura.
gfx::NativeView context;
+ // Only used by X11, for root level windows. Specifies the res_name and
+ // res_class fields, respectively, of the WM_CLASS window property. Controls
+ // window grouping and desktop file matching in Linux window managers.
+ std::string wm_class_name;
+ std::string wm_class_class;
};
Widget();
@@ -248,6 +252,14 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
gfx::NativeView context,
const gfx::Rect& bounds);
+ // Creates an undecorated child window Widget. |new_style_parent| is the
+ // parent to use for new style dialogs, |parent| for currently-styled dialogs.
+ //
+ // TODO(wittman): use a single parent parameter once we move fully to
+ // new-style dialogs.
+ static Widget* CreateWindowAsFramelessChild(WidgetDelegate* widget_delegate,
+ gfx::NativeView parent,
+ gfx::NativeView new_style_parent);
// Enumerates all windows pertaining to us and notifies their
// view hierarchies that the locale has changed.
@@ -284,6 +296,10 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
static void GetAllChildWidgets(gfx::NativeView native_view,
Widgets* children);
+ // Returns all non-child Widgets owned by |native_view|.
+ static void GetAllOwnedWidgets(gfx::NativeView native_view,
+ Widgets* owned);
+
// Re-parent a NativeView and notify all Widgets in |native_view|'s hierarchy
// of the change.
static void ReparentNativeView(gfx::NativeView native_view,
@@ -324,9 +340,13 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
// Forwarded from the RootView so that the widget can do any cleanup.
void ViewHierarchyChanged(const View::ViewHierarchyChangedDetails& details);
- // Performs any necessary cleanup and forwards to RootView.
- void NotifyNativeViewHierarchyChanged(bool attached,
- gfx::NativeView native_view);
+ // Called right before changing the widget's parent NativeView to do any
+ // cleanup.
+ void NotifyNativeViewHierarchyWillChange();
+
+ // Called after changing the widget's parent NativeView. Notifies the RootView
+ // about the change.
+ void NotifyNativeViewHierarchyChanged();
// Returns the top level widget in a hierarchy (see is_top_level() for
// the definition of top level widget.) Will return NULL if called
@@ -615,7 +635,9 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
}
// Sets capture to the specified view. This makes it so that all mouse, touch
- // and gesture events go to |view|.
+ // and gesture events go to |view|. If |view| is NULL, the widget still
+ // obtains event capture, but the events will go to the view they'd normally
+ // go to.
void SetCapture(View* view);
// Releases capture.
@@ -624,6 +646,10 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
// Returns true if the widget has capture.
bool HasCapture();
+ void set_auto_release_capture(bool auto_release_capture) {
+ auto_release_capture_ = auto_release_capture;
+ }
+
// Invoked when the tooltip text changes for the specified views.
void TooltipTextChanged(View* view);
@@ -637,11 +663,6 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
focus_on_creation_ = focus_on_creation;
}
- // Returns a View* that any child Widgets backed by NativeWidgetViews
- // are added to. The default implementation returns the contents view
- // if it exists and the root view otherwise.
- virtual View* GetChildViewParent();
-
// True if the widget is considered top level widget. Top level widget
// is a widget of TYPE_WINDOW, TYPE_PANEL, TYPE_WINDOW_FRAMELESS, BUBBLE,
// POPUP or MENU, and has a focus manager and input method object associated
@@ -659,6 +680,10 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
// mouse location to refresh hovering status in the widget.
void SynthesizeMouseMoveEvent();
+ // Called by our RootView after it has performed a Layout. Used to forward
+ // window sizing information to the window server on some platforms.
+ void OnRootViewLayout();
+
// Notification that our owner is closing.
// NOTE: this is not invoked for aura as it's currently not needed there.
// Under aura menus close by way of activation getting reset when the owner
@@ -674,6 +699,7 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
virtual void OnNativeWidgetActivationChanged(bool active) OVERRIDE;
virtual void OnNativeFocus(gfx::NativeView old_focused_view) OVERRIDE;
virtual void OnNativeBlur(gfx::NativeView new_focused_view) OVERRIDE;
+ virtual void OnNativeWidgetVisibilityChanging(bool visible) OVERRIDE;
virtual void OnNativeWidgetVisibilityChanged(bool visible) OVERRIDE;
virtual void OnNativeWidgetCreated(bool desktop_widget) OVERRIDE;
virtual void OnNativeWidgetDestroying() OVERRIDE;
@@ -720,11 +746,8 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
void DestroyRootView();
private:
+ friend class ComboboxTest;
friend class NativeTextfieldViewsTest;
- friend class NativeComboboxViewsTest;
-
- // Returns whether capture should be released on mouse release.
- virtual bool ShouldReleaseCaptureOnMouseReleased() const;
// Sets the value of |disable_inactive_rendering_|. If the value changes,
// both the NonClientView and WidgetDelegate are notified.
@@ -757,8 +780,8 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
ObserverList<WidgetObserver> observers_;
- // Non-owned pointer to the Widget's delegate. May be NULL if no delegate is
- // being used.
+ // Non-owned pointer to the Widget's delegate. If a NULL delegate is supplied
+ // to Init() a default WidgetDelegate is created.
WidgetDelegate* widget_delegate_;
// The root of the View hierarchy attached to this window.
@@ -840,6 +863,10 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate,
bool last_mouse_event_was_move_;
gfx::Point last_mouse_event_position_;
+ // True if event capture should be released on a mouse up event. Default is
+ // true.
+ bool auto_release_capture_;
+
// See description in GetRootLayers().
std::vector<ui::Layer*> root_layers_;
diff --git a/chromium/ui/views/widget/widget_delegate.cc b/chromium/ui/views/widget/widget_delegate.cc
index dcb7c361030..37816da4eef 100644
--- a/chromium/ui/views/widget/widget_delegate.cc
+++ b/chromium/ui/views/widget/widget_delegate.cc
@@ -162,6 +162,10 @@ void WidgetDelegate::GetWidgetHitTestMask(gfx::Path* mask) const {
DCHECK(mask);
}
+bool WidgetDelegate::ShouldAdvanceFocusToTopLevelWidget() const {
+ return false;
+}
+
bool WidgetDelegate::ShouldDescendIntoChildForEventHandling(
gfx::NativeView child,
const gfx::Point& location) {
diff --git a/chromium/ui/views/widget/widget_delegate.h b/chromium/ui/views/widget/widget_delegate.h
index f465ffb3bc1..4466e52cfa2 100644
--- a/chromium/ui/views/widget/widget_delegate.h
+++ b/chromium/ui/views/widget/widget_delegate.h
@@ -159,6 +159,11 @@ class VIEWS_EXPORT WidgetDelegate {
// Provides the hit-test mask if HasHitTestMask above returns true.
virtual void GetWidgetHitTestMask(gfx::Path* mask) const;
+ // Returns true if focus should advance to the top level widget when
+ // tab/shift-tab is hit and on the last/first focusable view. Default returns
+ // false, which means tab/shift-tab never advance to the top level Widget.
+ virtual bool ShouldAdvanceFocusToTopLevelWidget() const;
+
// Returns true if event handling should descend into |child|.
// |location| is in terms of the Window.
virtual bool ShouldDescendIntoChildForEventHandling(
diff --git a/chromium/ui/views/widget/widget_interactive_uitest.cc b/chromium/ui/views/widget/widget_interactive_uitest.cc
new file mode 100644
index 00000000000..b05a0bc8be6
--- /dev/null
+++ b/chromium/ui/views/widget/widget_interactive_uitest.cc
@@ -0,0 +1,445 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "base/basictypes.h"
+#include "base/bind.h"
+#include "base/run_loop.h"
+#include "ui/gfx/native_widget_types.h"
+#include "ui/views/test/widget_test.h"
+#include "ui/views/widget/widget.h"
+
+#if defined(USE_AURA)
+#include "ui/aura/client/activation_client.h"
+#include "ui/aura/env.h"
+#include "ui/aura/root_window.h"
+#if !defined(OS_CHROMEOS)
+#include "ui/views/widget/desktop_aura/desktop_native_widget_aura.h"
+#endif
+#endif
+
+namespace views {
+namespace test {
+
+namespace {
+
+// A View that closes the Widget and exits the current message-loop when it
+// receives a mouse-release event.
+class ExitLoopOnRelease : public View {
+ public:
+ ExitLoopOnRelease() {}
+ virtual ~ExitLoopOnRelease() {}
+
+ private:
+ // Overridden from View:
+ virtual void OnMouseReleased(const ui::MouseEvent& event) OVERRIDE {
+ GetWidget()->Close();
+ base::MessageLoop::current()->QuitNow();
+ }
+
+ DISALLOW_COPY_AND_ASSIGN(ExitLoopOnRelease);
+};
+
+// A view that does a capture on gesture-begin events.
+class GestureCaptureView : public View {
+ public:
+ GestureCaptureView() {}
+ virtual ~GestureCaptureView() {}
+
+ private:
+ // Overridden from View:
+ virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE {
+ if (event->type() == ui::ET_GESTURE_BEGIN) {
+ GetWidget()->SetCapture(this);
+ event->StopPropagation();
+ }
+ }
+
+ DISALLOW_COPY_AND_ASSIGN(GestureCaptureView);
+};
+
+// A view that always processes all mouse events.
+class MouseView : public View {
+ public:
+ MouseView()
+ : View(),
+ entered_(0),
+ exited_(0),
+ pressed_(0) {
+ }
+ virtual ~MouseView() {}
+
+ virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE {
+ pressed_++;
+ return true;
+ }
+
+ virtual void OnMouseEntered(const ui::MouseEvent& event) OVERRIDE {
+ entered_++;
+ }
+
+ virtual void OnMouseExited(const ui::MouseEvent& event) OVERRIDE {
+ exited_++;
+ }
+
+ // Return the number of OnMouseEntered calls and reset the counter.
+ int EnteredCalls() {
+ int i = entered_;
+ entered_ = 0;
+ return i;
+ }
+
+ // Return the number of OnMouseExited calls and reset the counter.
+ int ExitedCalls() {
+ int i = exited_;
+ exited_ = 0;
+ return i;
+ }
+
+ int pressed() const { return pressed_; }
+
+ private:
+ int entered_;
+ int exited_;
+
+ int pressed_;
+
+ DISALLOW_COPY_AND_ASSIGN(MouseView);
+};
+
+// A View that shows a different widget, sets capture on that widget, and
+// initiates a nested message-loop when it receives a mouse-press event.
+class NestedLoopCaptureView : public View {
+ public:
+ explicit NestedLoopCaptureView(Widget* widget) : widget_(widget) {}
+ virtual ~NestedLoopCaptureView() {}
+
+ private:
+ // Overridden from View:
+ virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE {
+ // Start a nested loop.
+ widget_->Show();
+ widget_->SetCapture(widget_->GetContentsView());
+ EXPECT_TRUE(widget_->HasCapture());
+
+ base::MessageLoopForUI* loop = base::MessageLoopForUI::current();
+ base::MessageLoop::ScopedNestableTaskAllower allow(loop);
+
+ base::RunLoop run_loop;
+#if defined(USE_AURA)
+ run_loop.set_dispatcher(aura::Env::GetInstance()->GetDispatcher());
+#endif
+ run_loop.Run();
+ return true;
+ }
+
+ Widget* widget_;
+
+ DISALLOW_COPY_AND_ASSIGN(NestedLoopCaptureView);
+};
+
+} // namespace
+
+#if defined(OS_WIN) && defined(USE_AURA)
+// Tests whether activation and focus change works correctly in Windows AURA.
+// We test the following:-
+// 1. If the active aura window is correctly set when a top level widget is
+// created.
+// 2. If the active aura window in widget 1 created above, is set to NULL when
+// another top level widget is created and focused.
+// 3. On focusing the native platform window for widget 1, the active aura
+// window for widget 1 should be set and that for widget 2 should reset.
+// TODO(ananta)
+// Discuss with erg on how to write this test for linux x11 aura.
+TEST_F(WidgetTest, DesktopNativeWidgetAuraActivationAndFocusTest) {
+ // Create widget 1 and expect the active window to be its window.
+ View* contents_view1 = new View;
+ contents_view1->set_focusable(true);
+ Widget widget1;
+ Widget::InitParams init_params =
+ CreateParams(Widget::InitParams::TYPE_WINDOW_FRAMELESS);
+ init_params.bounds = gfx::Rect(0, 0, 200, 200);
+ init_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ init_params.native_widget = new DesktopNativeWidgetAura(&widget1);
+ widget1.Init(init_params);
+ widget1.SetContentsView(contents_view1);
+ widget1.Show();
+ aura::RootWindow* root_window1= widget1.GetNativeView()->GetRootWindow();
+ contents_view1->RequestFocus();
+
+ EXPECT_TRUE(root_window1 != NULL);
+ aura::client::ActivationClient* activation_client1 =
+ aura::client::GetActivationClient(root_window1);
+ EXPECT_TRUE(activation_client1 != NULL);
+ EXPECT_EQ(activation_client1->GetActiveWindow(), widget1.GetNativeView());
+
+ // Create widget 2 and expect the active window to be its window.
+ View* contents_view2 = new View;
+ Widget widget2;
+ Widget::InitParams init_params2 =
+ CreateParams(Widget::InitParams::TYPE_WINDOW_FRAMELESS);
+ init_params2.bounds = gfx::Rect(0, 0, 200, 200);
+ init_params2.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ init_params2.native_widget = new DesktopNativeWidgetAura(&widget2);
+ widget2.Init(init_params2);
+ widget2.SetContentsView(contents_view2);
+ widget2.Show();
+ aura::RootWindow* root_window2 = widget2.GetNativeView()->GetRootWindow();
+ contents_view2->RequestFocus();
+ ::SetActiveWindow(root_window2->GetAcceleratedWidget());
+
+ aura::client::ActivationClient* activation_client2 =
+ aura::client::GetActivationClient(root_window2);
+ EXPECT_TRUE(activation_client2 != NULL);
+ EXPECT_EQ(activation_client2->GetActiveWindow(), widget2.GetNativeView());
+ EXPECT_EQ(activation_client1->GetActiveWindow(),
+ reinterpret_cast<aura::Window*>(NULL));
+
+ // Now set focus back to widget 1 and expect the active window to be its
+ // window.
+ contents_view1->RequestFocus();
+ ::SetActiveWindow(root_window1->GetAcceleratedWidget());
+ EXPECT_EQ(activation_client2->GetActiveWindow(),
+ reinterpret_cast<aura::Window*>(NULL));
+ EXPECT_EQ(activation_client1->GetActiveWindow(), widget1.GetNativeView());
+}
+#endif
+
+TEST_F(WidgetTest, CaptureAutoReset) {
+ Widget* toplevel = CreateTopLevelFramelessPlatformWidget();
+ View* container = new View;
+ toplevel->SetContentsView(container);
+
+ EXPECT_FALSE(toplevel->HasCapture());
+ toplevel->SetCapture(NULL);
+ EXPECT_TRUE(toplevel->HasCapture());
+
+ // By default, mouse release removes capture.
+ gfx::Point click_location(45, 15);
+ ui::MouseEvent release(ui::ET_MOUSE_RELEASED, click_location, click_location,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ toplevel->OnMouseEvent(&release);
+ EXPECT_FALSE(toplevel->HasCapture());
+
+ // Now a mouse release shouldn't remove capture.
+ toplevel->set_auto_release_capture(false);
+ toplevel->SetCapture(NULL);
+ EXPECT_TRUE(toplevel->HasCapture());
+ toplevel->OnMouseEvent(&release);
+ EXPECT_TRUE(toplevel->HasCapture());
+ toplevel->ReleaseCapture();
+ EXPECT_FALSE(toplevel->HasCapture());
+
+ toplevel->Close();
+ RunPendingMessages();
+}
+
+TEST_F(WidgetTest, ResetCaptureOnGestureEnd) {
+ Widget* toplevel = CreateTopLevelFramelessPlatformWidget();
+ View* container = new View;
+ toplevel->SetContentsView(container);
+
+ View* gesture = new GestureCaptureView;
+ gesture->SetBounds(0, 0, 30, 30);
+ container->AddChildView(gesture);
+
+ MouseView* mouse = new MouseView;
+ mouse->SetBounds(30, 0, 30, 30);
+ container->AddChildView(mouse);
+
+ toplevel->SetSize(gfx::Size(100, 100));
+ toplevel->Show();
+
+ // Start a gesture on |gesture|.
+ ui::GestureEvent begin(ui::ET_GESTURE_BEGIN,
+ 15, 15, 0, base::TimeDelta(),
+ ui::GestureEventDetails(ui::ET_GESTURE_BEGIN, 0, 0), 1);
+ ui::GestureEvent end(ui::ET_GESTURE_END,
+ 15, 15, 0, base::TimeDelta(),
+ ui::GestureEventDetails(ui::ET_GESTURE_END, 0, 0), 1);
+ toplevel->OnGestureEvent(&begin);
+
+ // Now try to click on |mouse|. Since |gesture| will have capture, |mouse|
+ // will not receive the event.
+ gfx::Point click_location(45, 15);
+
+ ui::MouseEvent press(ui::ET_MOUSE_PRESSED, click_location, click_location,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ ui::MouseEvent release(ui::ET_MOUSE_RELEASED, click_location, click_location,
+ ui::EF_LEFT_MOUSE_BUTTON);
+
+ EXPECT_TRUE(toplevel->HasCapture());
+
+ toplevel->OnMouseEvent(&press);
+ toplevel->OnMouseEvent(&release);
+ EXPECT_EQ(0, mouse->pressed());
+
+ EXPECT_FALSE(toplevel->HasCapture());
+
+ // The end of the gesture should release the capture, and pressing on |mouse|
+ // should now reach |mouse|.
+ toplevel->OnGestureEvent(&end);
+ toplevel->OnMouseEvent(&press);
+ toplevel->OnMouseEvent(&release);
+ EXPECT_EQ(1, mouse->pressed());
+
+ toplevel->Close();
+ RunPendingMessages();
+}
+
+// Checks that if a mouse-press triggers a capture on a different widget (which
+// consumes the mouse-release event), then the target of the press does not have
+// capture.
+// Fails on chromium.webkit Windows bot, see crbug.com/264872.
+#if defined(OS_WIN)
+#define MAYBE_DisableCaptureWidgetFromMousePress\
+ DISABLED_CaptureWidgetFromMousePress
+#else
+#define MAYBE_DisableCaptureWidgetFromMousePress\
+ CaptureWidgetFromMousePress
+#endif
+TEST_F(WidgetTest, MAYBE_DisableCaptureWidgetFromMousePress) {
+ // The test creates two widgets: |first| and |second|.
+ // The View in |first| makes |second| visible, sets capture on it, and starts
+ // a nested loop (like a menu does). The View in |second| terminates the
+ // nested loop and closes the widget.
+ // The test sends a mouse-press event to |first|, and posts a task to send a
+ // release event to |second|, to make sure that the release event is
+ // dispatched after the nested loop starts.
+
+ Widget* first = CreateTopLevelFramelessPlatformWidget();
+ Widget* second = CreateTopLevelFramelessPlatformWidget();
+
+ View* container = new NestedLoopCaptureView(second);
+ first->SetContentsView(container);
+
+ second->SetContentsView(new ExitLoopOnRelease());
+
+ first->SetSize(gfx::Size(100, 100));
+ first->Show();
+
+ gfx::Point location(20, 20);
+ base::MessageLoop::current()->PostTask(FROM_HERE,
+ base::Bind(&Widget::OnMouseEvent,
+ base::Unretained(second),
+ base::Owned(new ui::MouseEvent(ui::ET_MOUSE_RELEASED,
+ location,
+ location,
+ ui::EF_LEFT_MOUSE_BUTTON))));
+ ui::MouseEvent press(ui::ET_MOUSE_PRESSED, location, location,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ first->OnMouseEvent(&press);
+ EXPECT_FALSE(first->HasCapture());
+ first->Close();
+ RunPendingMessages();
+}
+
+// Tests some grab/ungrab events.
+// TODO(estade): can this be enabled now that this is an interactive ui test?
+TEST_F(WidgetTest, DISABLED_GrabUngrab) {
+ Widget* toplevel = CreateTopLevelPlatformWidget();
+ Widget* child1 = CreateChildNativeWidgetWithParent(toplevel);
+ Widget* child2 = CreateChildNativeWidgetWithParent(toplevel);
+
+ toplevel->SetBounds(gfx::Rect(0, 0, 500, 500));
+
+ child1->SetBounds(gfx::Rect(10, 10, 300, 300));
+ View* view = new MouseView();
+ view->SetBounds(0, 0, 300, 300);
+ child1->GetRootView()->AddChildView(view);
+
+ child2->SetBounds(gfx::Rect(200, 10, 200, 200));
+ view = new MouseView();
+ view->SetBounds(0, 0, 200, 200);
+ child2->GetRootView()->AddChildView(view);
+
+ toplevel->Show();
+ RunPendingMessages();
+
+ // Click on child1
+ gfx::Point p1(45, 45);
+ ui::MouseEvent pressed(ui::ET_MOUSE_PRESSED, p1, p1,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ toplevel->OnMouseEvent(&pressed);
+
+ EXPECT_TRUE(toplevel->HasCapture());
+ EXPECT_TRUE(child1->HasCapture());
+ EXPECT_FALSE(child2->HasCapture());
+
+ ui::MouseEvent released(ui::ET_MOUSE_RELEASED, p1, p1,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ toplevel->OnMouseEvent(&released);
+
+ EXPECT_FALSE(toplevel->HasCapture());
+ EXPECT_FALSE(child1->HasCapture());
+ EXPECT_FALSE(child2->HasCapture());
+
+ RunPendingMessages();
+
+ // Click on child2
+ gfx::Point p2(315, 45);
+ ui::MouseEvent pressed2(ui::ET_MOUSE_PRESSED, p2, p2,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ toplevel->OnMouseEvent(&pressed2);
+ EXPECT_TRUE(pressed2.handled());
+ EXPECT_TRUE(toplevel->HasCapture());
+ EXPECT_TRUE(child2->HasCapture());
+ EXPECT_FALSE(child1->HasCapture());
+
+ ui::MouseEvent released2(ui::ET_MOUSE_RELEASED, p2, p2,
+ ui::EF_LEFT_MOUSE_BUTTON);
+ toplevel->OnMouseEvent(&released2);
+ EXPECT_FALSE(toplevel->HasCapture());
+ EXPECT_FALSE(child1->HasCapture());
+ EXPECT_FALSE(child2->HasCapture());
+
+ toplevel->CloseNow();
+}
+
+// Tests mouse move outside of the window into the "resize controller" and back
+// will still generate an OnMouseEntered and OnMouseExited event..
+TEST_F(WidgetTest, CheckResizeControllerEvents) {
+ Widget* toplevel = CreateTopLevelPlatformWidget();
+
+ toplevel->SetBounds(gfx::Rect(0, 0, 100, 100));
+
+ MouseView* view = new MouseView();
+ view->SetBounds(90, 90, 10, 10);
+ toplevel->GetRootView()->AddChildView(view);
+
+ toplevel->Show();
+ RunPendingMessages();
+
+ // Move to an outside position.
+ gfx::Point p1(200, 200);
+ ui::MouseEvent moved_out(ui::ET_MOUSE_MOVED, p1, p1, ui::EF_NONE);
+ toplevel->OnMouseEvent(&moved_out);
+ EXPECT_EQ(0, view->EnteredCalls());
+ EXPECT_EQ(0, view->ExitedCalls());
+
+ // Move onto the active view.
+ gfx::Point p2(95, 95);
+ ui::MouseEvent moved_over(ui::ET_MOUSE_MOVED, p2, p2, ui::EF_NONE);
+ toplevel->OnMouseEvent(&moved_over);
+ EXPECT_EQ(1, view->EnteredCalls());
+ EXPECT_EQ(0, view->ExitedCalls());
+
+ // Move onto the outer resizing border.
+ gfx::Point p3(102, 95);
+ ui::MouseEvent moved_resizer(ui::ET_MOUSE_MOVED, p3, p3, ui::EF_NONE);
+ toplevel->OnMouseEvent(&moved_resizer);
+ EXPECT_EQ(0, view->EnteredCalls());
+ EXPECT_EQ(1, view->ExitedCalls());
+
+ // Move onto the view again.
+ toplevel->OnMouseEvent(&moved_over);
+ EXPECT_EQ(1, view->EnteredCalls());
+ EXPECT_EQ(0, view->ExitedCalls());
+
+ RunPendingMessages();
+
+ toplevel->CloseNow();
+}
+
+} // namespace test
+} // namespace views
diff --git a/chromium/ui/views/widget/widget_observer.h b/chromium/ui/views/widget/widget_observer.h
index e156ef80c88..fc13afae682 100644
--- a/chromium/ui/views/widget/widget_observer.h
+++ b/chromium/ui/views/widget/widget_observer.h
@@ -36,6 +36,8 @@ class VIEWS_EXPORT WidgetObserver {
// widget has been destroyed.
virtual void OnWidgetDestroyed(Widget* widget) {}
+ virtual void OnWidgetVisibilityChanging(Widget* widget, bool visible) {}
+
virtual void OnWidgetVisibilityChanged(Widget* widget, bool visible) {}
virtual void OnWidgetActivationChanged(Widget* widget, bool active) {}
diff --git a/chromium/ui/views/widget/widget_unittest.cc b/chromium/ui/views/widget/widget_unittest.cc
index 1153538b8d8..1c8a7a2de21 100644
--- a/chromium/ui/views/widget/widget_unittest.cc
+++ b/chromium/ui/views/widget/widget_unittest.cc
@@ -2,6 +2,9 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
+#include <algorithm>
+#include <set>
+
#include "base/basictypes.h"
#include "base/bind.h"
#include "base/memory/scoped_ptr.h"
@@ -9,13 +12,13 @@
#include "base/run_loop.h"
#include "base/strings/utf_string_conversions.h"
#include "testing/gtest/include/gtest/gtest.h"
-#include "ui/base/events/event_utils.h"
+#include "ui/events/event_utils.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/point.h"
#include "ui/views/bubble/bubble_delegate.h"
#include "ui/views/controls/textfield/textfield.h"
#include "ui/views/test/test_views_delegate.h"
-#include "ui/views/test/views_test_base.h"
+#include "ui/views/test/widget_test.h"
#include "ui/views/views_delegate.h"
#include "ui/views/widget/native_widget_delegate.h"
#include "ui/views/widget/root_view.h"
@@ -23,9 +26,7 @@
#if defined(USE_AURA)
#include "ui/aura/client/aura_constants.h"
-#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
-#include "ui/aura/test/test_cursor_client.h"
#include "ui/aura/test/test_window_delegate.h"
#include "ui/aura/window.h"
#include "ui/views/widget/native_widget_aura.h"
@@ -39,99 +40,6 @@
namespace views {
namespace test {
-// A generic typedef to pick up relevant NativeWidget implementations.
-#if defined(USE_AURA)
-typedef NativeWidgetAura NativeWidgetPlatform;
-#elif defined(OS_WIN)
-typedef NativeWidgetWin NativeWidgetPlatform;
-#endif
-
-// A widget that assumes mouse capture always works. It won't on Aura in
-// testing, so we mock it.
-#if defined(USE_AURA)
-class NativeWidgetCapture : public NativeWidgetPlatform {
- public:
- explicit NativeWidgetCapture(internal::NativeWidgetDelegate* delegate)
- : NativeWidgetPlatform(delegate),
- mouse_capture_(false) {}
- virtual ~NativeWidgetCapture() {}
-
- virtual void SetCapture() OVERRIDE {
- mouse_capture_ = true;
- }
- virtual void ReleaseCapture() OVERRIDE {
- if (mouse_capture_)
- delegate()->OnMouseCaptureLost();
- mouse_capture_ = false;
- }
- virtual bool HasCapture() const OVERRIDE {
- return mouse_capture_;
- }
-
- private:
- bool mouse_capture_;
-
- DISALLOW_COPY_AND_ASSIGN(NativeWidgetCapture);
-};
-#endif
-
-// A typedef that inserts our mock-capture NativeWidget implementation for
-// relevant platforms.
-#if defined(USE_AURA)
-typedef NativeWidgetCapture NativeWidgetPlatformForTest;
-#elif defined(OS_WIN)
-typedef NativeWidgetWin NativeWidgetPlatformForTest;
-#endif
-
-// A view that always processes all mouse events.
-class MouseView : public View {
- public:
- MouseView()
- : View(),
- entered_(0),
- exited_(0),
- pressed_(0) {
- }
- virtual ~MouseView() {}
-
- virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE {
- pressed_++;
- return true;
- }
-
- virtual void OnMouseEntered(const ui::MouseEvent& event) OVERRIDE {
- entered_++;
- }
-
- virtual void OnMouseExited(const ui::MouseEvent& event) OVERRIDE {
- exited_++;
- }
-
- // Return the number of OnMouseEntered calls and reset the counter.
- int EnteredCalls() {
- int i = entered_;
- entered_ = 0;
- return i;
- }
-
- // Return the number of OnMouseExited calls and reset the counter.
- int ExitedCalls() {
- int i = exited_;
- exited_ = 0;
- return i;
- }
-
- int pressed() const { return pressed_; }
-
- private:
- int entered_;
- int exited_;
-
- int pressed_;
-
- DISALLOW_COPY_AND_ASSIGN(MouseView);
-};
-
// A view that keeps track of the events it receives, but consumes no events.
class EventCountView : public View {
public:
@@ -200,24 +108,6 @@ class ScrollableEventCountView : public EventCountView {
DISALLOW_COPY_AND_ASSIGN(ScrollableEventCountView);
};
-// A view that does a capture on gesture-begin events.
-class GestureCaptureView : public View {
- public:
- GestureCaptureView() {}
- virtual ~GestureCaptureView() {}
-
- private:
- // Overridden from View:
- virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE {
- if (event->type() == ui::ET_GESTURE_BEGIN) {
- GetWidget()->SetCapture(this);
- event->StopPropagation();
- }
- }
-
- DISALLOW_COPY_AND_ASSIGN(GestureCaptureView);
-};
-
// A view that implements GetMinimumSize.
class MinimumSizeFrameView : public NativeFrameView {
public:
@@ -265,147 +155,6 @@ class EventCountHandler : public ui::EventHandler {
DISALLOW_COPY_AND_ASSIGN(EventCountHandler);
};
-// A View that shows a different widget, sets capture on that widget, and
-// initiates a nested message-loop when it receives a mouse-press event.
-class NestedLoopCaptureView : public View {
- public:
- explicit NestedLoopCaptureView(Widget* widget) : widget_(widget) {}
- virtual ~NestedLoopCaptureView() {}
-
- private:
- // Overridden from View:
- virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE {
- // Start a nested loop.
- widget_->Show();
- widget_->SetCapture(widget_->GetContentsView());
- EXPECT_TRUE(widget_->HasCapture());
-
- base::MessageLoopForUI* loop = base::MessageLoopForUI::current();
- base::MessageLoop::ScopedNestableTaskAllower allow(loop);
-
- base::RunLoop run_loop;
-#if defined(USE_AURA)
- run_loop.set_dispatcher(aura::Env::GetInstance()->GetDispatcher());
-#endif
- run_loop.Run();
- return true;
- }
-
- Widget* widget_;
-
- DISALLOW_COPY_AND_ASSIGN(NestedLoopCaptureView);
-};
-
-// A View that closes the Widget and exits the current message-loop when it
-// receives a mouse-release event.
-class ExitLoopOnRelease : public View {
- public:
- ExitLoopOnRelease() {}
- virtual ~ExitLoopOnRelease() {}
-
- private:
- // Overridden from View:
- virtual void OnMouseReleased(const ui::MouseEvent& event) OVERRIDE {
- GetWidget()->Close();
- base::MessageLoop::current()->QuitNow();
- }
-
- DISALLOW_COPY_AND_ASSIGN(ExitLoopOnRelease);
-};
-
-class WidgetTest : public ViewsTestBase {
- public:
- WidgetTest() {}
- virtual ~WidgetTest() {}
-
- NativeWidget* CreatePlatformNativeWidget(
- internal::NativeWidgetDelegate* delegate) {
- return new NativeWidgetPlatformForTest(delegate);
- }
-
- Widget* CreateTopLevelPlatformWidget() {
- Widget* toplevel = new Widget;
- Widget::InitParams toplevel_params =
- CreateParams(Widget::InitParams::TYPE_WINDOW);
- toplevel_params.native_widget = CreatePlatformNativeWidget(toplevel);
- toplevel->Init(toplevel_params);
- return toplevel;
- }
-
- Widget* CreateTopLevelFramelessPlatformWidget() {
- Widget* toplevel = new Widget;
- Widget::InitParams toplevel_params =
- CreateParams(Widget::InitParams::TYPE_WINDOW_FRAMELESS);
- toplevel_params.native_widget = CreatePlatformNativeWidget(toplevel);
- toplevel->Init(toplevel_params);
- return toplevel;
- }
-
- Widget* CreateChildPlatformWidget(gfx::NativeView parent_native_view) {
- Widget* child = new Widget;
- Widget::InitParams child_params =
- CreateParams(Widget::InitParams::TYPE_CONTROL);
- child_params.native_widget = CreatePlatformNativeWidget(child);
- child_params.parent = parent_native_view;
- child->Init(child_params);
- child->SetContentsView(new View);
- return child;
- }
-
-#if defined(OS_WIN) && !defined(USE_AURA)
- // On Windows, it is possible for us to have a child window that is
- // TYPE_POPUP.
- Widget* CreateChildPopupPlatformWidget(gfx::NativeView parent_native_view) {
- Widget* child = new Widget;
- Widget::InitParams child_params =
- CreateParams(Widget::InitParams::TYPE_POPUP);
- child_params.child = true;
- child_params.native_widget = CreatePlatformNativeWidget(child);
- child_params.parent = parent_native_view;
- child->Init(child_params);
- child->SetContentsView(new View);
- return child;
- }
-#endif
-
- Widget* CreateTopLevelNativeWidget() {
- Widget* toplevel = new Widget;
- Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_WINDOW);
- toplevel->Init(params);
- return toplevel;
- }
-
- Widget* CreateChildNativeWidgetWithParent(Widget* parent) {
- Widget* child = new Widget;
- Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_CONTROL);
- params.parent = parent->GetNativeView();
- child->Init(params);
- child->SetContentsView(new View);
- return child;
- }
-
- Widget* CreateChildNativeWidget() {
- return CreateChildNativeWidgetWithParent(NULL);
- }
-
- View* GetMousePressedHandler(internal::RootView* root_view) {
- return root_view->mouse_pressed_handler_;
- }
-
- View* GetMouseMoveHandler(internal::RootView* root_view) {
- return root_view->mouse_move_handler_;
- }
-
- View* GetGestureHandler(internal::RootView* root_view) {
- return root_view->gesture_handler_;
- }
-};
-
-bool WidgetHasMouseCapture(const Widget* widget) {
- return static_cast<const internal::NativeWidgetPrivate*>(widget->
- native_widget())->HasCapture();
-}
-
ui::WindowShowState GetWidgetShowState(const Widget* widget) {
// Use IsMaximized/IsMinimized/IsFullScreen instead of GetWindowPlacement
// because the former is implemented on all platforms but the latter is not.
@@ -452,112 +201,6 @@ TEST_F(WidgetTest, GetTopLevelWidget_Native) {
// |child| should be automatically destroyed with |toplevel|.
}
-// Tests some grab/ungrab events.
-TEST_F(WidgetTest, DISABLED_GrabUngrab) {
- Widget* toplevel = CreateTopLevelPlatformWidget();
- Widget* child1 = CreateChildNativeWidgetWithParent(toplevel);
- Widget* child2 = CreateChildNativeWidgetWithParent(toplevel);
-
- toplevel->SetBounds(gfx::Rect(0, 0, 500, 500));
-
- child1->SetBounds(gfx::Rect(10, 10, 300, 300));
- View* view = new MouseView();
- view->SetBounds(0, 0, 300, 300);
- child1->GetRootView()->AddChildView(view);
-
- child2->SetBounds(gfx::Rect(200, 10, 200, 200));
- view = new MouseView();
- view->SetBounds(0, 0, 200, 200);
- child2->GetRootView()->AddChildView(view);
-
- toplevel->Show();
- RunPendingMessages();
-
- // Click on child1
- gfx::Point p1(45, 45);
- ui::MouseEvent pressed(ui::ET_MOUSE_PRESSED, p1, p1,
- ui::EF_LEFT_MOUSE_BUTTON);
- toplevel->OnMouseEvent(&pressed);
-
- EXPECT_TRUE(WidgetHasMouseCapture(toplevel));
- EXPECT_TRUE(WidgetHasMouseCapture(child1));
- EXPECT_FALSE(WidgetHasMouseCapture(child2));
-
- ui::MouseEvent released(ui::ET_MOUSE_RELEASED, p1, p1,
- ui::EF_LEFT_MOUSE_BUTTON);
- toplevel->OnMouseEvent(&released);
-
- EXPECT_FALSE(WidgetHasMouseCapture(toplevel));
- EXPECT_FALSE(WidgetHasMouseCapture(child1));
- EXPECT_FALSE(WidgetHasMouseCapture(child2));
-
- RunPendingMessages();
-
- // Click on child2
- gfx::Point p2(315, 45);
- ui::MouseEvent pressed2(ui::ET_MOUSE_PRESSED, p2, p2,
- ui::EF_LEFT_MOUSE_BUTTON);
- toplevel->OnMouseEvent(&pressed2);
- EXPECT_TRUE(pressed2.handled());
- EXPECT_TRUE(WidgetHasMouseCapture(toplevel));
- EXPECT_TRUE(WidgetHasMouseCapture(child2));
- EXPECT_FALSE(WidgetHasMouseCapture(child1));
-
- ui::MouseEvent released2(ui::ET_MOUSE_RELEASED, p2, p2,
- ui::EF_LEFT_MOUSE_BUTTON);
- toplevel->OnMouseEvent(&released2);
- EXPECT_FALSE(WidgetHasMouseCapture(toplevel));
- EXPECT_FALSE(WidgetHasMouseCapture(child1));
- EXPECT_FALSE(WidgetHasMouseCapture(child2));
-
- toplevel->CloseNow();
-}
-
-// Tests mouse move outside of the window into the "resize controller" and back
-// will still generate an OnMouseEntered and OnMouseExited event..
-TEST_F(WidgetTest, CheckResizeControllerEvents) {
- Widget* toplevel = CreateTopLevelPlatformWidget();
-
- toplevel->SetBounds(gfx::Rect(0, 0, 100, 100));
-
- MouseView* view = new MouseView();
- view->SetBounds(90, 90, 10, 10);
- toplevel->GetRootView()->AddChildView(view);
-
- toplevel->Show();
- RunPendingMessages();
-
- // Move to an outside position.
- gfx::Point p1(200, 200);
- ui::MouseEvent moved_out(ui::ET_MOUSE_MOVED, p1, p1, ui::EF_NONE);
- toplevel->OnMouseEvent(&moved_out);
- EXPECT_EQ(0, view->EnteredCalls());
- EXPECT_EQ(0, view->ExitedCalls());
-
- // Move onto the active view.
- gfx::Point p2(95, 95);
- ui::MouseEvent moved_over(ui::ET_MOUSE_MOVED, p2, p2, ui::EF_NONE);
- toplevel->OnMouseEvent(&moved_over);
- EXPECT_EQ(1, view->EnteredCalls());
- EXPECT_EQ(0, view->ExitedCalls());
-
- // Move onto the outer resizing border.
- gfx::Point p3(102, 95);
- ui::MouseEvent moved_resizer(ui::ET_MOUSE_MOVED, p3, p3, ui::EF_NONE);
- toplevel->OnMouseEvent(&moved_resizer);
- EXPECT_EQ(0, view->EnteredCalls());
- EXPECT_EQ(1, view->ExitedCalls());
-
- // Move onto the view again.
- toplevel->OnMouseEvent(&moved_over);
- EXPECT_EQ(1, view->EnteredCalls());
- EXPECT_EQ(0, view->ExitedCalls());
-
- RunPendingMessages();
-
- toplevel->CloseNow();
-}
-
// Test if a focus manager and an inputmethod work without CHECK failure
// when window activation changes.
TEST_F(WidgetTest, ChangeActivation) {
@@ -941,6 +584,99 @@ TEST_F(WidgetOwnershipTest,
}
////////////////////////////////////////////////////////////////////////////////
+// Test to verify using various Widget methods doesn't crash when the underlying
+// NativeView is destroyed.
+//
+class WidgetWithDestroyedNativeViewTest : public ViewsTestBase {
+ public:
+ WidgetWithDestroyedNativeViewTest() {}
+ virtual ~WidgetWithDestroyedNativeViewTest() {}
+
+ void InvokeWidgetMethods(Widget* widget) {
+ widget->GetNativeView();
+ widget->GetNativeWindow();
+ ui::Accelerator accelerator;
+ widget->GetAccelerator(0, &accelerator);
+ widget->GetTopLevelWidget();
+ widget->GetWindowBoundsInScreen();
+ widget->GetClientAreaBoundsInScreen();
+ widget->SetBounds(gfx::Rect(0, 0, 100, 80));
+ widget->SetSize(gfx::Size(10, 11));
+ widget->SetBoundsConstrained(gfx::Rect(0, 0, 120, 140));
+ widget->SetVisibilityChangedAnimationsEnabled(false);
+ widget->StackAtTop();
+ widget->IsClosed();
+ widget->Close();
+ widget->Show();
+ widget->Hide();
+ widget->Activate();
+ widget->Deactivate();
+ widget->IsActive();
+ widget->DisableInactiveRendering();
+ widget->SetAlwaysOnTop(true);
+ widget->Maximize();
+ widget->Minimize();
+ widget->Restore();
+ widget->IsMaximized();
+ widget->IsFullscreen();
+ widget->SetOpacity(0);
+ widget->SetUseDragFrame(true);
+ widget->FlashFrame(true);
+ widget->IsVisible();
+ widget->GetThemeProvider();
+ widget->GetNativeTheme();
+ widget->GetFocusManager();
+ widget->GetInputMethod();
+ widget->SchedulePaintInRect(gfx::Rect(0, 0, 1, 2));
+ widget->IsMouseEventsEnabled();
+ widget->SetNativeWindowProperty("xx", widget);
+ widget->GetNativeWindowProperty("xx");
+ widget->GetFocusTraversable();
+ widget->GetLayer();
+ widget->ReorderNativeViews();
+ widget->SetCapture(widget->GetRootView());
+ widget->ReleaseCapture();
+ widget->HasCapture();
+ widget->TooltipTextChanged(widget->GetRootView());
+ widget->GetWorkAreaBoundsInScreen();
+ // These three crash with NativeWidgetWin, so I'm assuming we don't need
+ // them to work for the other NativeWidget impls.
+ // widget->CenterWindow(gfx::Size(50, 60));
+ // widget->GetRestoredBounds();
+ // widget->ShowInactive();
+ }
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(WidgetWithDestroyedNativeViewTest);
+};
+
+TEST_F(WidgetWithDestroyedNativeViewTest, Test) {
+ {
+ Widget widget;
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
+ params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ widget.Init(params);
+ widget.Show();
+
+ widget.native_widget_private()->CloseNow();
+ InvokeWidgetMethods(&widget);
+ }
+#if defined(USE_AURA) && !defined(OS_CHROMEOS)
+ {
+ Widget widget;
+ Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP);
+ params.native_widget = new DesktopNativeWidgetAura(&widget);
+ params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ widget.Init(params);
+ widget.Show();
+
+ widget.native_widget_private()->CloseNow();
+ InvokeWidgetMethods(&widget);
+ }
+#endif
+}
+
+////////////////////////////////////////////////////////////////////////////////
// Widget observer tests.
//
@@ -1178,94 +914,6 @@ TEST_F(WidgetTest, ExitFullscreenRestoreState) {
RunPendingMessages();
}
-// Checks that if a mouse-press triggers a capture on a different widget (which
-// consumes the mouse-release event), then the target of the press does not have
-// capture.
-TEST_F(WidgetTest, CaptureWidgetFromMousePress) {
- // The test creates two widgets: |first| and |second|.
- // The View in |first| makes |second| visible, sets capture on it, and starts
- // a nested loop (like a menu does). The View in |second| terminates the
- // nested loop and closes the widget.
- // The test sends a mouse-press event to |first|, and posts a task to send a
- // release event to |second|, to make sure that the release event is
- // dispatched after the nested loop starts.
-
- Widget* first = CreateTopLevelFramelessPlatformWidget();
- Widget* second = CreateTopLevelFramelessPlatformWidget();
-
- View* container = new NestedLoopCaptureView(second);
- first->SetContentsView(container);
-
- second->SetContentsView(new ExitLoopOnRelease());
-
- first->SetSize(gfx::Size(100, 100));
- first->Show();
-
- gfx::Point location(20, 20);
- base::MessageLoop::current()->PostTask(FROM_HERE,
- base::Bind(&Widget::OnMouseEvent,
- base::Unretained(second),
- base::Owned(new ui::MouseEvent(ui::ET_MOUSE_RELEASED,
- location,
- location,
- ui::EF_LEFT_MOUSE_BUTTON))));
- ui::MouseEvent press(ui::ET_MOUSE_PRESSED, location, location,
- ui::EF_LEFT_MOUSE_BUTTON);
- first->OnMouseEvent(&press);
- EXPECT_FALSE(first->HasCapture());
- first->Close();
- RunPendingMessages();
-}
-
-TEST_F(WidgetTest, ResetCaptureOnGestureEnd) {
- Widget* toplevel = CreateTopLevelFramelessPlatformWidget();
- View* container = new View;
- toplevel->SetContentsView(container);
-
- View* gesture = new GestureCaptureView;
- gesture->SetBounds(0, 0, 30, 30);
- container->AddChildView(gesture);
-
- MouseView* mouse = new MouseView;
- mouse->SetBounds(30, 0, 30, 30);
- container->AddChildView(mouse);
-
- toplevel->SetSize(gfx::Size(100, 100));
- toplevel->Show();
-
- // Start a gesture on |gesture|.
- ui::GestureEvent begin(ui::ET_GESTURE_BEGIN,
- 15, 15, 0, base::TimeDelta(),
- ui::GestureEventDetails(ui::ET_GESTURE_BEGIN, 0, 0), 1);
- ui::GestureEvent end(ui::ET_GESTURE_END,
- 15, 15, 0, base::TimeDelta(),
- ui::GestureEventDetails(ui::ET_GESTURE_END, 0, 0), 1);
- toplevel->OnGestureEvent(&begin);
-
- // Now try to click on |mouse|. Since |gesture| will have capture, |mouse|
- // will not receive the event.
- gfx::Point click_location(45, 15);
-
- ui::MouseEvent press(ui::ET_MOUSE_PRESSED, click_location, click_location,
- ui::EF_LEFT_MOUSE_BUTTON);
- ui::MouseEvent release(ui::ET_MOUSE_RELEASED, click_location, click_location,
- ui::EF_LEFT_MOUSE_BUTTON);
-
- toplevel->OnMouseEvent(&press);
- toplevel->OnMouseEvent(&release);
- EXPECT_EQ(0, mouse->pressed());
-
- // The end of the gesture should release the capture, and pressing on |mouse|
- // should now reach |mouse|.
- toplevel->OnGestureEvent(&end);
- toplevel->OnMouseEvent(&press);
- toplevel->OnMouseEvent(&release);
- EXPECT_EQ(1, mouse->pressed());
-
- toplevel->Close();
- RunPendingMessages();
-}
-
#if defined(USE_AURA)
// The key-event propagation from Widget happens differently on aura and
// non-aura systems because of the difference in IME. So this test works only on
@@ -1437,27 +1085,28 @@ TEST_F(WidgetTest, DesktopNativeWidgetAuraNoPaintAfterHideTest) {
widget.Close();
}
-// This class provides functionality to test whether the destruction of full
-// screen child windows occurs correctly in desktop AURA without crashing.
+// This class provides functionality to create fullscreen and top level popup
+// windows. It additionally tests whether the destruction of these windows
+// occurs correctly in desktop AURA without crashing.
// It provides facilities to test the following cases:-
// 1. Child window destroyed which should lead to the destruction of the
// parent.
// 2. Parent window destroyed which should lead to the child being destroyed.
-class DesktopAuraFullscreenChildWindowDestructionTest
+class DesktopAuraTopLevelWindowTest
: public views::TestViewsDelegate,
public aura::WindowObserver {
public:
- DesktopAuraFullscreenChildWindowDestructionTest()
- : full_screen_widget_(NULL),
- child_window_(NULL),
- parent_destroyed_(false),
- child_destroyed_(false) {}
+ DesktopAuraTopLevelWindowTest()
+ : top_level_widget_(NULL),
+ owned_window_(NULL),
+ owner_destroyed_(false),
+ owned_window_destroyed_(false) {}
- virtual ~DesktopAuraFullscreenChildWindowDestructionTest() {
- EXPECT_TRUE(parent_destroyed_);
- EXPECT_TRUE(child_destroyed_);
- full_screen_widget_ = NULL;
- child_window_ = NULL;
+ virtual ~DesktopAuraTopLevelWindowTest() {
+ EXPECT_TRUE(owner_destroyed_);
+ EXPECT_TRUE(owned_window_destroyed_);
+ top_level_widget_ = NULL;
+ owned_window_ = NULL;
}
// views::TestViewsDelegate overrides.
@@ -1468,50 +1117,55 @@ class DesktopAuraFullscreenChildWindowDestructionTest
params->native_widget = new views::DesktopNativeWidgetAura(delegate);
}
- void CreateFullscreenChildWindow(const gfx::Rect& bounds) {
+ void CreateTopLevelWindow(const gfx::Rect& bounds, bool fullscreen) {
Widget::InitParams init_params;
init_params.type = Widget::InitParams::TYPE_WINDOW;
init_params.bounds = bounds;
init_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
init_params.layer_type = ui::LAYER_NOT_DRAWN;
+ init_params.accept_events = fullscreen;
widget_.Init(init_params);
- child_window_ = new aura::Window(&child_window_delegate_);
- child_window_->SetType(aura::client::WINDOW_TYPE_NORMAL);
- child_window_->Init(ui::LAYER_TEXTURED);
- child_window_->SetName("TestFullscreenChildWindow");
- child_window_->SetProperty(aura::client::kShowStateKey,
- ui::SHOW_STATE_FULLSCREEN);
- child_window_->SetDefaultParentByRootWindow(
+ owned_window_ = new aura::Window(&child_window_delegate_);
+ owned_window_->SetType(aura::client::WINDOW_TYPE_NORMAL);
+ owned_window_->SetName("TestTopLevelWindow");
+ if (fullscreen) {
+ owned_window_->SetProperty(aura::client::kShowStateKey,
+ ui::SHOW_STATE_FULLSCREEN);
+ } else {
+ owned_window_->SetType(aura::client::WINDOW_TYPE_MENU);
+ }
+ owned_window_->Init(ui::LAYER_TEXTURED);
+ owned_window_->SetDefaultParentByRootWindow(
widget_.GetNativeView()->GetRootWindow(), gfx::Rect(0, 0, 1900, 1600));
- child_window_->Show();
- child_window_->AddObserver(this);
+ owned_window_->Show();
+ owned_window_->AddObserver(this);
- ASSERT_TRUE(child_window_->parent() != NULL);
- child_window_->parent()->AddObserver(this);
+ ASSERT_TRUE(owned_window_->parent() != NULL);
+ owned_window_->parent()->AddObserver(this);
- full_screen_widget_ =
- views::Widget::GetWidgetForNativeView(child_window_->parent());
- ASSERT_TRUE(full_screen_widget_ != NULL);
+ top_level_widget_ =
+ views::Widget::GetWidgetForNativeView(owned_window_->parent());
+ ASSERT_TRUE(top_level_widget_ != NULL);
}
- void DestroyChildWindow() {
- ASSERT_TRUE(child_window_ != NULL);
- delete child_window_;
+ void DestroyOwnedWindow() {
+ ASSERT_TRUE(owned_window_ != NULL);
+ delete owned_window_;
}
- void DestroyParentWindow() {
- ASSERT_TRUE(full_screen_widget_ != NULL);
- full_screen_widget_->CloseNow();
+ void DestroyOwnerWindow() {
+ ASSERT_TRUE(top_level_widget_ != NULL);
+ top_level_widget_->CloseNow();
}
virtual void OnWindowDestroying(aura::Window* window) OVERRIDE {
window->RemoveObserver(this);
- if (window == child_window_) {
- child_destroyed_ = true;
- } else if (window == full_screen_widget_->GetNativeView()) {
- parent_destroyed_ = true;
+ if (window == owned_window_) {
+ owned_window_destroyed_ = true;
+ } else if (window == top_level_widget_->GetNativeView()) {
+ owner_destroyed_ = true;
} else {
ADD_FAILURE() << "Unexpected window destroyed callback: " << window;
}
@@ -1519,38 +1173,52 @@ class DesktopAuraFullscreenChildWindowDestructionTest
private:
views::Widget widget_;
- views::Widget* full_screen_widget_;
- aura::Window* child_window_;
- bool parent_destroyed_;
- bool child_destroyed_;
+ views::Widget* top_level_widget_;
+ aura::Window* owned_window_;
+ bool owner_destroyed_;
+ bool owned_window_destroyed_;
aura::test::TestWindowDelegate child_window_delegate_;
- DISALLOW_COPY_AND_ASSIGN(DesktopAuraFullscreenChildWindowDestructionTest);
+ DISALLOW_COPY_AND_ASSIGN(DesktopAuraTopLevelWindowTest);
};
-TEST_F(WidgetTest, DesktopAuraFullscreenChildDestroyedBeforeParentTest) {
+TEST_F(WidgetTest, DesktopAuraFullscreenWindowDestroyedBeforeOwnerTest) {
ViewsDelegate::views_delegate = NULL;
- DesktopAuraFullscreenChildWindowDestructionTest full_screen_child_test;
- ASSERT_NO_FATAL_FAILURE(full_screen_child_test.CreateFullscreenChildWindow(
- gfx::Rect(0, 0, 200, 200)));
+ DesktopAuraTopLevelWindowTest fullscreen_window;
+ ASSERT_NO_FATAL_FAILURE(fullscreen_window.CreateTopLevelWindow(
+ gfx::Rect(0, 0, 200, 200), true));
RunPendingMessages();
- ASSERT_NO_FATAL_FAILURE(full_screen_child_test.DestroyChildWindow());
+ ASSERT_NO_FATAL_FAILURE(fullscreen_window.DestroyOwnedWindow());
RunPendingMessages();
}
-TEST_F(WidgetTest, DesktopAuraFullscreenChildParentDestroyed) {
+TEST_F(WidgetTest, DesktopAuraFullscreenWindowOwnerDestroyed) {
ViewsDelegate::views_delegate = NULL;
- DesktopAuraFullscreenChildWindowDestructionTest full_screen_child_test;
- ASSERT_NO_FATAL_FAILURE(full_screen_child_test.CreateFullscreenChildWindow(
- gfx::Rect(0, 0, 200, 200)));
+ DesktopAuraTopLevelWindowTest fullscreen_window;
+ ASSERT_NO_FATAL_FAILURE(fullscreen_window.CreateTopLevelWindow(
+ gfx::Rect(0, 0, 200, 200), true));
RunPendingMessages();
- ASSERT_NO_FATAL_FAILURE(full_screen_child_test.DestroyParentWindow());
+ ASSERT_NO_FATAL_FAILURE(fullscreen_window.DestroyOwnerWindow());
RunPendingMessages();
}
+// TODO(erg): Disabled on desktop linux until http://crbug.com/288988 is fixed.
+#if !defined(OS_LINUX)
+TEST_F(WidgetTest, DesktopAuraTopLevelOwnedPopupTest) {
+ ViewsDelegate::views_delegate = NULL;
+ DesktopAuraTopLevelWindowTest popup_window;
+ ASSERT_NO_FATAL_FAILURE(popup_window.CreateTopLevelWindow(
+ gfx::Rect(0, 0, 200, 200), false));
+
+ RunPendingMessages();
+ ASSERT_NO_FATAL_FAILURE(popup_window.DestroyOwnedWindow());
+ RunPendingMessages();
+}
+#endif
+
// Test to ensure that the aura Window's visiblity state is set to visible if
// the underlying widget is hidden and then shown.
TEST_F(WidgetTest, TestWindowVisibilityAfterHide) {
@@ -1574,6 +1242,116 @@ TEST_F(WidgetTest, TestWindowVisibilityAfterHide) {
EXPECT_TRUE(widget.GetNativeView()->IsVisible());
}
+// The following code verifies we can correctly destroy a Widget from a mouse
+// enter/exit. We could test move/drag/enter/exit but in general we don't run
+// nested message loops from such events, nor has the code ever really dealt
+// with this situation.
+
+// Class that closes the widget (which ends up deleting it immediately) when the
+// appropriate event is received.
+class CloseWidgetView : public View {
+ public:
+ explicit CloseWidgetView(ui::EventType event_type)
+ : event_type_(event_type) {
+ }
+
+ // View overrides:
+ virtual bool OnMousePressed(const ui::MouseEvent& event) OVERRIDE {
+ if (!CloseWidget(event))
+ View::OnMousePressed(event);
+ return true;
+ }
+ virtual bool OnMouseDragged(const ui::MouseEvent& event) OVERRIDE {
+ if (!CloseWidget(event))
+ View::OnMouseDragged(event);
+ return true;
+ }
+ virtual void OnMouseReleased(const ui::MouseEvent& event) OVERRIDE {
+ if (!CloseWidget(event))
+ View::OnMouseReleased(event);
+ }
+ virtual void OnMouseMoved(const ui::MouseEvent& event) OVERRIDE {
+ if (!CloseWidget(event))
+ View::OnMouseMoved(event);
+ }
+ virtual void OnMouseEntered(const ui::MouseEvent& event) OVERRIDE {
+ if (!CloseWidget(event))
+ View::OnMouseEntered(event);
+ }
+
+ private:
+ bool CloseWidget(const ui::LocatedEvent& event) {
+ if (event.type() == event_type_) {
+ // Go through NativeWidgetPrivate to simulate what happens if the OS
+ // deletes the NativeWindow out from under us.
+ GetWidget()->native_widget_private()->CloseNow();
+ return true;
+ }
+ return false;
+ }
+
+ const ui::EventType event_type_;
+
+ DISALLOW_COPY_AND_ASSIGN(CloseWidgetView);
+};
+
+// Generates two moves (first generates enter, second real move), a press, drag
+// and release stopping at |last_event_type|.
+void GenerateMouseEvents(Widget* widget, ui::EventType last_event_type) {
+ const gfx::Rect screen_bounds(widget->GetWindowBoundsInScreen());
+ ui::MouseEvent move_event(ui::ET_MOUSE_MOVED, screen_bounds.CenterPoint(),
+ screen_bounds.CenterPoint(), 0);
+ aura::RootWindowHostDelegate* rwhd =
+ widget->GetNativeWindow()->GetRootWindow()->AsRootWindowHostDelegate();
+ rwhd->OnHostMouseEvent(&move_event);
+ if (last_event_type == ui::ET_MOUSE_ENTERED)
+ return;
+ rwhd->OnHostMouseEvent(&move_event);
+ if (last_event_type == ui::ET_MOUSE_MOVED)
+ return;
+
+ ui::MouseEvent press_event(ui::ET_MOUSE_PRESSED, screen_bounds.CenterPoint(),
+ screen_bounds.CenterPoint(), 0);
+ rwhd->OnHostMouseEvent(&press_event);
+ if (last_event_type == ui::ET_MOUSE_PRESSED)
+ return;
+
+ gfx::Point end_point(screen_bounds.CenterPoint());
+ end_point.Offset(1, 1);
+ ui::MouseEvent drag_event(ui::ET_MOUSE_DRAGGED, end_point, end_point, 0);
+ rwhd->OnHostMouseEvent(&drag_event);
+ if (last_event_type == ui::ET_MOUSE_DRAGGED)
+ return;
+
+ ui::MouseEvent release_event(ui::ET_MOUSE_RELEASED, end_point, end_point, 0);
+ rwhd->OnHostMouseEvent(&release_event);
+}
+
+// Creates a widget and invokes GenerateMouseEvents() with |last_event_type|.
+void RunCloseWidgetDuringDispatchTest(WidgetTest* test,
+ ui::EventType last_event_type) {
+ // |widget| is deleted by CloseWidgetView.
+ Widget* widget = new Widget;
+ Widget::InitParams params =
+ test->CreateParams(Widget::InitParams::TYPE_POPUP);
+ params.native_widget = new DesktopNativeWidgetAura(widget);
+ params.bounds = gfx::Rect(0, 0, 50, 100);
+ widget->Init(params);
+ widget->SetContentsView(new CloseWidgetView(last_event_type));
+ widget->Show();
+ GenerateMouseEvents(widget, last_event_type);
+}
+
+// Verifies deleting the widget from a mouse pressed event doesn't crash.
+TEST_F(WidgetTest, CloseWidgetDuringMousePress) {
+ RunCloseWidgetDuringDispatchTest(this, ui::ET_MOUSE_PRESSED);
+}
+
+// Verifies deleting the widget from a mouse released event doesn't crash.
+TEST_F(WidgetTest, CloseWidgetDuringMouseReleased) {
+ RunCloseWidgetDuringDispatchTest(this, ui::ET_MOUSE_RELEASED);
+}
+
#endif // !defined(OS_CHROMEOS)
// Tests that wheel events generated from scroll events are targetted to the
@@ -1773,64 +1551,6 @@ TEST_F(WidgetTest, SynthesizeMouseMoveEvent) {
EXPECT_EQ(1, v2->GetEventCount(ui::ET_MOUSE_ENTERED));
}
-TEST_F(WidgetTest, MouseEventsHandled) {
- Widget* widget = CreateTopLevelNativeWidget();
- View* root_view = widget->GetRootView();
-
-#if defined(USE_AURA)
- aura::test::TestCursorClient cursor_client(
- widget->GetNativeView()->GetRootWindow());
-#endif
-
- EventCountView* v1 = new EventCountView();
- v1->SetBounds(0, 0, 10, 10);
- root_view->AddChildView(v1);
- EventCountView* v2 = new EventCountView();
- v2->SetBounds(0, 10, 10, 10);
- root_view->AddChildView(v2);
-
- gfx::Point cursor_location1(5, 5);
- ui::MouseEvent move1(ui::ET_MOUSE_MOVED, cursor_location1, cursor_location1,
- ui::EF_NONE);
- widget->OnMouseEvent(&move1);
- EXPECT_EQ(1, v1->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(0, v1->GetEventCount(ui::ET_MOUSE_EXITED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_EXITED));
- v1->ResetCounts();
- v2->ResetCounts();
-
- gfx::Point cursor_location2(5, 15);
- ui::MouseEvent move2(ui::ET_MOUSE_MOVED, cursor_location2, cursor_location2,
- ui::EF_NONE);
- widget->OnMouseEvent(&move2);
- EXPECT_EQ(0, v1->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(1, v2->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(1, v1->GetEventCount(ui::ET_MOUSE_EXITED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_EXITED));
- v1->ResetCounts();
- v2->ResetCounts();
-
-#if defined(USE_AURA)
- // In Aura, we suppress mouse events if mouse events are disabled.
- cursor_client.DisableMouseEvents();
-
- widget->OnMouseEvent(&move1);
- EXPECT_EQ(0, v1->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(0, v1->GetEventCount(ui::ET_MOUSE_EXITED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_EXITED));
- v1->ResetCounts();
- v2->ResetCounts();
-
- widget->OnMouseEvent(&move2);
- EXPECT_EQ(0, v1->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_ENTERED));
- EXPECT_EQ(0, v1->GetEventCount(ui::ET_MOUSE_EXITED));
- EXPECT_EQ(0, v2->GetEventCount(ui::ET_MOUSE_EXITED));
-#endif
-}
-
// Used by SingleWindowClosing to count number of times WindowClosing() has
// been invoked.
class ClosingDelegate : public WidgetDelegate {
@@ -2063,7 +1783,15 @@ class RootViewTestView : public View {
};
// Checks if RootView::*_handler_ fields are unset when widget is hidden.
-TEST_F(WidgetTest, TestRootViewHandlersWhenHidden) {
+// Fails on chromium.webkit Windows bot, see crbug.com/264872.
+#if defined(OS_WIN)
+#define MAYBE_DisableTestRootViewHandlersWhenHidden\
+ DISABLED_TestRootViewHandlersWhenHidden
+#else
+#define MAYBE_DisableTestRootViewHandlersWhenHidden\
+ TestRootViewHandlersWhenHidden
+#endif
+TEST_F(WidgetTest, MAYBE_DisableTestRootViewHandlersWhenHidden) {
Widget* widget = CreateTopLevelNativeWidget();
widget->SetBounds(gfx::Rect(0, 0, 300, 300));
View* view = new RootViewTestView();
@@ -2112,5 +1840,37 @@ TEST_F(WidgetTest, TestRootViewHandlersWhenHidden) {
widget->Close();
}
+// Test the result of Widget::GetAllChildWidgets().
+TEST_F(WidgetTest, GetAllChildWidgets) {
+ // Create the following widget hierarchy:
+ //
+ // toplevel
+ // +-- w1
+ // +-- w11
+ // +-- w2
+ // +-- w21
+ // +-- w22
+ Widget* toplevel = CreateTopLevelPlatformWidget();
+ Widget* w1 = CreateChildPlatformWidget(toplevel->GetNativeView());
+ Widget* w11 = CreateChildPlatformWidget(w1->GetNativeView());
+ Widget* w2 = CreateChildPlatformWidget(toplevel->GetNativeView());
+ Widget* w21 = CreateChildPlatformWidget(w2->GetNativeView());
+ Widget* w22 = CreateChildPlatformWidget(w2->GetNativeView());
+
+ std::set<Widget*> expected;
+ expected.insert(toplevel);
+ expected.insert(w1);
+ expected.insert(w11);
+ expected.insert(w2);
+ expected.insert(w21);
+ expected.insert(w22);
+
+ std::set<Widget*> widgets;
+ Widget::GetAllChildWidgets(toplevel->GetNativeView(), &widgets);
+
+ EXPECT_EQ(expected.size(), widgets.size());
+ EXPECT_TRUE(std::equal(expected.begin(), expected.end(), widgets.begin()));
+}
+
} // namespace test
} // namespace views
diff --git a/chromium/ui/views/win/fullscreen_handler.cc b/chromium/ui/views/win/fullscreen_handler.cc
index 33a0475095a..2fe8ceaf2b5 100644
--- a/chromium/ui/views/win/fullscreen_handler.cc
+++ b/chromium/ui/views/win/fullscreen_handler.cc
@@ -5,6 +5,7 @@
#include "ui/views/win/fullscreen_handler.h"
#include "base/logging.h"
+#include "base/win/win_util.h"
#include "ui/gfx/rect.h"
#include "ui/views/win/scoped_fullscreen_visibility.h"
@@ -75,8 +76,8 @@ void FullscreenHandler::SetFullscreenImpl(bool fullscreen, bool for_metro) {
if (!for_metro) {
MONITORINFO monitor_info;
monitor_info.cbSize = sizeof(monitor_info);
- GetMonitorInfo(MonitorFromWindow(hwnd_, MONITOR_DEFAULTTONEAREST),
- &monitor_info);
+ base::win::GetMonitorInfoWrapper(
+ MonitorFromWindow(hwnd_, MONITOR_DEFAULTTONEAREST), &monitor_info);
gfx::Rect window_rect(monitor_info.rcMonitor);
SetWindowPos(hwnd_, NULL, window_rect.x(), window_rect.y(),
window_rect.width(), window_rect.height(),
diff --git a/chromium/ui/views/win/hwnd_message_handler.cc b/chromium/ui/views/win/hwnd_message_handler.cc
index 1a627092732..b29f62da5cb 100644
--- a/chromium/ui/views/win/hwnd_message_handler.cc
+++ b/chromium/ui/views/win/hwnd_message_handler.cc
@@ -9,17 +9,16 @@
#include "base/bind.h"
#include "base/debug/trace_event.h"
+#include "base/win/win_util.h"
#include "base/win/windows_version.h"
-#include "ui/base/events/event.h"
-#include "ui/base/events/event_utils.h"
#include "ui/base/gestures/gesture_sequence.h"
-#include "ui/base/keycodes/keyboard_code_conversion_win.h"
#include "ui/base/touch/touch_enabled.h"
-#include "ui/base/win/dpi.h"
-#include "ui/base/win/hwnd_util.h"
#include "ui/base/win/mouse_wheel_util.h"
#include "ui/base/win/shell.h"
#include "ui/base/win/touch_input.h"
+#include "ui/events/event.h"
+#include "ui/events/event_utils.h"
+#include "ui/events/keycodes/keyboard_code_conversion_win.h"
#include "ui/gfx/canvas.h"
#include "ui/gfx/canvas_skia_paint.h"
#include "ui/gfx/icon_util.h"
@@ -27,6 +26,8 @@
#include "ui/gfx/path.h"
#include "ui/gfx/path_win.h"
#include "ui/gfx/screen.h"
+#include "ui/gfx/win/dpi.h"
+#include "ui/gfx/win/hwnd_util.h"
#include "ui/native_theme/native_theme_win.h"
#include "ui/views/views_delegate.h"
#include "ui/views/widget/monitor_win.h"
@@ -180,7 +181,7 @@ bool GetMonitorAndRects(const RECT& rect,
return false;
MONITORINFO monitor_info = { 0 };
monitor_info.cbSize = sizeof(monitor_info);
- GetMonitorInfo(*monitor, &monitor_info);
+ base::win::GetMonitorInfoWrapper(*monitor, &monitor_info);
*monitor_rect = gfx::Rect(monitor_info.rcMonitor);
*work_area = gfx::Rect(monitor_info.rcWork);
return true;
@@ -374,7 +375,8 @@ class HWNDMessageHandler::ScopedRedrawLock {
HWNDMessageHandler::HWNDMessageHandler(HWNDMessageHandlerDelegate* delegate)
: delegate_(delegate),
fullscreen_handler_(new FullscreenHandler),
- close_widget_factory_(this),
+ weak_factory_(this),
+ waiting_for_close_now_(false),
remove_standard_frame_(false),
use_system_default_icon_(false),
restore_focus_when_enabled_(false),
@@ -383,22 +385,19 @@ HWNDMessageHandler::HWNDMessageHandler(HWNDMessageHandlerDelegate* delegate)
active_mouse_tracking_flags_(0),
is_right_mouse_pressed_on_caption_(false),
lock_updates_count_(0),
- destroyed_(NULL),
ignore_window_pos_changes_(false),
- ignore_pos_changes_factory_(this),
last_monitor_(NULL),
use_layered_buffer_(false),
layered_alpha_(255),
- paint_layered_window_factory_(this),
+ waiting_for_redraw_layered_window_contents_(false),
can_update_layered_window_(true),
is_first_nccalc_(true),
- autohide_factory_(this) {
+ autohide_factory_(this),
+ id_generator_(0) {
}
HWNDMessageHandler::~HWNDMessageHandler() {
delegate_ = NULL;
- if (destroyed_ != NULL)
- *destroyed_ = true;
// Prevent calls back into this class via WNDPROC now that we've been
// destroyed.
ClearUserData();
@@ -437,15 +436,15 @@ void HWNDMessageHandler::Close() {
// they can activate as foreground windows upon this window's destruction.
RestoreEnabledIfNecessary();
- if (!close_widget_factory_.HasWeakPtrs()) {
+ if (!waiting_for_close_now_) {
// And we delay the close so that if we are called from an ATL callback,
// we don't destroy the window before the callback returned (as the caller
// may delete ourselves on destroy and the ATL callback would still
// dereference us when the callback returns).
+ waiting_for_close_now_ = true;
base::MessageLoop::current()->PostTask(
FROM_HERE,
- base::Bind(&HWNDMessageHandler::CloseNow,
- close_widget_factory_.GetWeakPtr()));
+ base::Bind(&HWNDMessageHandler::CloseNow, weak_factory_.GetWeakPtr()));
}
}
@@ -454,6 +453,7 @@ void HWNDMessageHandler::CloseNow() {
// switch which will have reactivated the browser window and closed us, so
// we need to check to see if we're still a window before trying to destroy
// ourself.
+ waiting_for_close_now_ = false;
if (IsWindow(hwnd()))
DestroyWindow(hwnd());
}
@@ -503,7 +503,7 @@ void HWNDMessageHandler::GetWindowPlacement(
} else {
MONITORINFO mi;
mi.cbSize = sizeof(mi);
- const bool succeeded = GetMonitorInfo(
+ const bool succeeded = base::win::GetMonitorInfoWrapper(
MonitorFromWindow(hwnd(), MONITOR_DEFAULTTONEAREST), &mi) != 0;
DCHECK(succeeded);
@@ -543,7 +543,7 @@ void HWNDMessageHandler::CenterWindow(const gfx::Size& size) {
HWND parent = GetParent(hwnd());
if (!IsWindow(hwnd()))
parent = ::GetWindow(hwnd(), GW_OWNER);
- ui::CenterAndSizeWindow(parent, hwnd(), size);
+ gfx::CenterAndSizeWindow(parent, hwnd(), size);
}
void HWNDMessageHandler::SetRegion(HRGN region) {
@@ -687,6 +687,12 @@ bool HWNDMessageHandler::IsMaximized() const {
bool HWNDMessageHandler::RunMoveLoop(const gfx::Vector2d& drag_offset) {
ReleaseCapture();
MoveLoopMouseWatcher watcher(this);
+#if defined(USE_AURA)
+ // In Aura, we handle touch events asynchronously. So we need to allow nested
+ // tasks while in windows move loop.
+ base::MessageLoop::ScopedNestableTaskAllower allow_nested(
+ base::MessageLoop::current());
+#endif
SendMessage(hwnd(), WM_SYSCOMMAND, SC_MOVE | 0x0002, GetMessagePos());
// Windows doesn't appear to offer a way to determine whether the user
// canceled the move or not. We assume if the user released the mouse it was
@@ -795,11 +801,12 @@ void HWNDMessageHandler::SchedulePaintInRect(const gfx::Rect& rect) {
// receive calls to DidProcessMessage(). This only seems to affect layered
// windows, so we schedule a redraw manually using a task, since those never
// seem to be starved. Also, wtf.
- if (!paint_layered_window_factory_.HasWeakPtrs()) {
+ if (!waiting_for_redraw_layered_window_contents_) {
+ waiting_for_redraw_layered_window_contents_ = true;
base::MessageLoop::current()->PostTask(
FROM_HERE,
base::Bind(&HWNDMessageHandler::RedrawLayeredWindowContents,
- paint_layered_window_factory_.GetWeakPtr()));
+ weak_factory_.GetWeakPtr()));
}
} else {
// InvalidateRect() expects client coordinates.
@@ -843,7 +850,7 @@ void HWNDMessageHandler::DispatchKeyEventPostIME(const ui::KeyEvent& key) {
}
////////////////////////////////////////////////////////////////////////////////
-// HWNDMessageHandler, ui::WindowImpl overrides:
+// HWNDMessageHandler, gfx::WindowImpl overrides:
HICON HWNDMessageHandler::GetDefaultWindowIcon() const {
if (use_system_default_icon_)
@@ -870,7 +877,17 @@ LRESULT HWNDMessageHandler::OnWndProc(UINT message,
#endif
// Otherwise we handle everything else.
- if (!ProcessWindowMessage(window, message, w_param, l_param, result))
+ // NOTE: We inline ProcessWindowMessage() as 'this' may be destroyed during
+ // dispatch and ProcessWindowMessage() doesn't deal with that well.
+ const BOOL old_msg_handled = m_bMsgHandled;
+ base::WeakPtr<HWNDMessageHandler> ref(weak_factory_.GetWeakPtr());
+ const BOOL processed =
+ _ProcessWindowMessage(window, message, w_param, l_param, result, 0);
+ if (!ref)
+ return 0;
+ m_bMsgHandled = old_msg_handled;
+
+ if (!processed)
result = DefWindowProc(window, message, w_param, l_param);
// DefWindowProc() may have destroyed the window in a nested message loop.
@@ -880,14 +897,17 @@ LRESULT HWNDMessageHandler::OnWndProc(UINT message,
if (delegate_)
delegate_->PostHandleMSG(message, w_param, l_param);
if (message == WM_NCDESTROY) {
+#if !defined(USE_AURA)
base::MessageLoopForUI::current()->RemoveObserver(this);
+#endif
if (delegate_)
delegate_->HandleDestroyed();
}
// Only top level widget should store/restore focus.
if (message == WM_ACTIVATE && delegate_->CanSaveFocus())
- PostProcessActivateMessage(LOWORD(w_param));
+ PostProcessActivateMessage(LOWORD(w_param), !!HIWORD(w_param));
+
if (message == WM_ENABLE && restore_focus_when_enabled_) {
// This path should be executed only for top level as
// restore_focus_when_enabled_ is set in PostProcessActivateMessage.
@@ -938,9 +958,10 @@ void HWNDMessageHandler::SetInitialFocus() {
}
}
-void HWNDMessageHandler::PostProcessActivateMessage(int activation_state) {
+void HWNDMessageHandler::PostProcessActivateMessage(int activation_state,
+ bool minimized) {
DCHECK(delegate_->CanSaveFocus());
- if (WA_INACTIVE == activation_state) {
+ if (WA_INACTIVE == activation_state || minimized) {
// We might get activated/inactivated without being enabled, so we need to
// clear restore_focus_when_enabled_.
restore_focus_when_enabled_ = false;
@@ -1012,11 +1033,17 @@ void HWNDMessageHandler::ClientAreaSizeChanged() {
if (!IsMinimized()) {
if (delegate_->WidgetSizeIsClientSize()) {
GetClientRect(hwnd(), &r);
- // This is needed due to a hack that works around a "feature" in
- // Windows's handling of WM_NCCALCSIZE. See the comment near the end of
- // GetClientAreaInsets for more details.
- if (remove_standard_frame_ && !IsMaximized())
- r.bottom += kClientAreaBottomInsetHack;
+ gfx::Insets insets;
+ bool got_insets = GetClientAreaInsets(&insets);
+ if (got_insets) {
+ // This is needed due to a hack that works around a "feature" in
+ // Windows's handling of WM_NCCALCSIZE. See the comment near the end of
+ // GetClientAreaInsets for more details.
+ if ((remove_standard_frame_ && !IsMaximized()) ||
+ !fullscreen_handler_->fullscreen()) {
+ r.bottom += kClientAreaBottomInsetHack;
+ }
+ }
} else {
GetWindowRect(hwnd(), &r);
}
@@ -1073,11 +1100,6 @@ bool HWNDMessageHandler::GetClientAreaInsets(gfx::Insets* insets) const {
return true;
}
-#if defined(USE_AURA)
- // The -1 hack below breaks rendering in Aura.
- // See http://crbug.com/172099 http://crbug.com/267131
- *insets = gfx::Insets();
-#else
// This is weird, but highly essential. If we don't offset the bottom edge
// of the client rect, the window client area and window area will match,
// and when returning to glass rendering mode from non-glass, the client
@@ -1089,8 +1111,11 @@ bool HWNDMessageHandler::GetClientAreaInsets(gfx::Insets* insets) const {
// rect when using the opaque frame.
// Note: this is only required for non-fullscreen windows. Note that
// fullscreen windows are in restored state, not maximized.
- *insets = gfx::Insets(0, 0, fullscreen_handler_->fullscreen() ? 0 : 1, 0);
-#endif
+ // Note that previously we used to inset by 1 instead of outset, but that
+ // doesn't work with Aura: http://crbug.com/172099 http://crbug.com/277228
+ *insets = gfx::Insets(
+ 0, 0,
+ fullscreen_handler_->fullscreen() ? 0 : kClientAreaBottomInsetHack, 0);
return true;
}
@@ -1120,7 +1145,7 @@ void HWNDMessageHandler::ResetWindowRegion(bool force) {
HMONITOR monitor = MonitorFromWindow(hwnd(), MONITOR_DEFAULTTONEAREST);
MONITORINFO mi;
mi.cbSize = sizeof mi;
- GetMonitorInfo(monitor, &mi);
+ base::win::GetMonitorInfoWrapper(monitor, &mi);
CRect work_rect = mi.rcWork;
work_rect.OffsetRect(-window_rect.left, -window_rect.top);
new_region = CreateRectRgnIndirect(&work_rect);
@@ -1146,14 +1171,11 @@ LRESULT HWNDMessageHandler::DefWindowProcWithRedrawLock(UINT message,
LPARAM l_param) {
ScopedRedrawLock lock(this);
// The Widget and HWND can be destroyed in the call to DefWindowProc, so use
- // the |destroyed_| flag to avoid unlocking (and crashing) after destruction.
- bool destroyed = false;
- destroyed_ = &destroyed;
+ // the WeakPtrFactory to avoid unlocking (and crashing) after destruction.
+ base::WeakPtr<HWNDMessageHandler> ref(weak_factory_.GetWeakPtr());
LRESULT result = DefWindowProc(hwnd(), message, w_param, l_param);
- if (destroyed)
+ if (!ref)
lock.CancelUnlockOperation();
- else
- destroyed_ = NULL;
return result;
}
@@ -1188,6 +1210,10 @@ void HWNDMessageHandler::UnlockUpdates(bool force) {
}
void HWNDMessageHandler::RedrawInvalidRect() {
+// TODO(cpu): Remove the caller and this class as a message loop observer
+// because we don't need agressive repaints via RDW_UPDATENOW in Aura. The
+// general tracking bug for repaint issues is 177115.
+#if !defined(USE_AURA)
if (!use_layered_buffer_) {
RECT r = { 0, 0, 0, 0 };
if (GetUpdateRect(hwnd(), &r, FALSE) && !IsRectEmpty(&r)) {
@@ -1195,15 +1221,17 @@ void HWNDMessageHandler::RedrawInvalidRect() {
RDW_INVALIDATE | RDW_UPDATENOW | RDW_NOCHILDREN);
}
}
+#endif
}
void HWNDMessageHandler::RedrawLayeredWindowContents() {
+ waiting_for_redraw_layered_window_contents_ = false;
if (invalid_rect_.IsEmpty())
return;
// We need to clip to the dirty rect ourselves.
layered_window_contents_->sk_canvas()->save(SkCanvas::kClip_SaveFlag);
- double scale = ui::win::GetDeviceScaleFactor();
+ double scale = gfx::win::GetDeviceScaleFactor();
layered_window_contents_->sk_canvas()->scale(
SkScalar(scale),SkScalar(scale));
layered_window_contents_->ClipRect(invalid_rect_);
@@ -1313,11 +1341,13 @@ LRESULT HWNDMessageHandler::OnCreate(CREATESTRUCT* create_struct) {
// creation time.
ClientAreaSizeChanged();
+#if !defined(USE_AURA)
// We need to add ourselves as a message loop observer so that we can repaint
// aggressively if the contents of our window become invalid. Unfortunately
// WM_PAINT messages are starved and we get flickery redrawing when resizing
// if we do not do this.
base::MessageLoopForUI::current()->AddObserver(this);
+#endif
delegate_->HandleCreate();
@@ -1496,7 +1526,7 @@ LRESULT HWNDMessageHandler::OnMouseRange(UINT message,
w_param = SendMessage(hwnd(), WM_NCHITTEST, 0,
MAKELPARAM(screen_point.x, screen_point.y));
if (w_param == HTCAPTION || w_param == HTSYSMENU) {
- ui::ShowSystemMenuAtPoint(hwnd(), gfx::Point(screen_point));
+ gfx::ShowSystemMenuAtPoint(hwnd(), gfx::Point(screen_point));
return 0;
}
} else if (message == WM_NCLBUTTONDOWN && delegate_->IsUsingCustomFrame()) {
@@ -1556,7 +1586,12 @@ LRESULT HWNDMessageHandler::OnMouseRange(UINT message,
delegate_->HandleMouseEvent(ui::MouseWheelEvent(msg))) ? 0 : 1;
}
+ // There are cases where the code handling the message destroys the window,
+ // so use the weak ptr to check if destruction occured or not.
+ base::WeakPtr<HWNDMessageHandler> ref(weak_factory_.GetWeakPtr());
bool handled = delegate_->HandleMouseEvent(event);
+ if (!ref.get())
+ return 0;
if (!handled && message == WM_NCLBUTTONDOWN && w_param != HTSYSMENU &&
delegate_->IsUsingCustomFrame()) {
// TODO(msw): Eliminate undesired painting, or re-evaluate this workaround.
@@ -1567,7 +1602,8 @@ LRESULT HWNDMessageHandler::OnMouseRange(UINT message,
handled = true;
}
- SetMsgHandled(handled);
+ if (ref.get())
+ SetMsgHandled(handled);
return 0;
}
@@ -1591,6 +1627,8 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message,
// cleared before it is converted to BOOL.
BOOL active = static_cast<BOOL>(LOWORD(w_param));
+ bool inactive_rendering_disabled = delegate_->IsInactiveRenderingDisabled();
+
if (delegate_->CanActivate())
delegate_->HandleActivationChanged(!!active);
@@ -1603,7 +1641,6 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message,
return TRUE;
// On activation, lift any prior restriction against rendering as inactive.
- bool inactive_rendering_disabled = delegate_->IsInactiveRenderingDisabled();
if (active && inactive_rendering_disabled)
delegate_->EnableInactiveRendering();
@@ -2039,11 +2076,17 @@ void HWNDMessageHandler::OnThemeChanged() {
LRESULT HWNDMessageHandler::OnTouchEvent(UINT message,
WPARAM w_param,
LPARAM l_param) {
+ // Handle touch events only on Aura for now.
+#if !defined(USE_AURA)
+ SetMsgHandled(FALSE);
+ return 0;
+#endif
int num_points = LOWORD(w_param);
scoped_ptr<TOUCHINPUT[]> input(new TOUCHINPUT[num_points]);
if (ui::GetTouchInputInfoWrapper(reinterpret_cast<HTOUCHINPUT>(l_param),
num_points, input.get(),
sizeof(TOUCHINPUT))) {
+ TouchEvents touch_events;
for (int i = 0; i < num_points; ++i) {
ui::EventType touch_event_type = ui::ET_UNKNOWN;
@@ -2056,26 +2099,32 @@ LRESULT HWNDMessageHandler::OnTouchEvent(UINT message,
} else if (input[i].dwFlags & TOUCHEVENTF_MOVE) {
touch_event_type = ui::ET_TOUCH_MOVED;
}
- // Handle touch events only on Aura for now.
-#if defined(USE_AURA)
if (touch_event_type != ui::ET_UNKNOWN) {
POINT point;
point.x = TOUCH_COORD_TO_PIXEL(input[i].x) /
- ui::win::GetUndocumentedDPIScale();
+ gfx::win::GetUndocumentedDPITouchScale();
point.y = TOUCH_COORD_TO_PIXEL(input[i].y) /
- ui::win::GetUndocumentedDPIScale();
+ gfx::win::GetUndocumentedDPITouchScale();
ScreenToClient(hwnd(), &point);
ui::TouchEvent event(
touch_event_type,
gfx::Point(point.x, point.y),
- input[i].dwID % ui::GestureSequence::kMaxGesturePoints,
+ id_generator_.GetGeneratedID(input[i].dwID),
base::TimeDelta::FromMilliseconds(input[i].dwTime));
- delegate_->HandleTouchEvent(event);
+ touch_events.push_back(event);
+ if (touch_event_type == ui::ET_TOUCH_RELEASED)
+ id_generator_.ReleaseNumber(input[i].dwID);
}
-#endif
}
+ // Handle the touch events asynchronously. We need this because touch
+ // events on windows don't fire if we enter a modal loop in the context of
+ // a touch event.
+ base::MessageLoop::current()->PostTask(
+ FROM_HERE,
+ base::Bind(&HWNDMessageHandler::HandleTouchEvents,
+ weak_factory_.GetWeakPtr(), touch_events));
}
CloseTouchInputHandle(reinterpret_cast<HTOUCHINPUT>(l_param));
SetMsgHandled(FALSE);
@@ -2137,11 +2186,10 @@ void HWNDMessageHandler::OnWindowPosChanging(WINDOWPOS* window_pos) {
// likes to (incorrectly) recalculate what our position/size should be
// and send us further updates.
ignore_window_pos_changes_ = true;
- DCHECK(!ignore_pos_changes_factory_.HasWeakPtrs());
base::MessageLoop::current()->PostTask(
FROM_HERE,
base::Bind(&HWNDMessageHandler::StopIgnoringPosChanges,
- ignore_pos_changes_factory_.GetWeakPtr()));
+ weak_factory_.GetWeakPtr()));
}
last_monitor_ = monitor;
last_monitor_rect_ = monitor_rect;
@@ -2155,6 +2203,11 @@ void HWNDMessageHandler::OnWindowPosChanging(WINDOWPOS* window_pos) {
window_pos->flags &= ~SWP_SHOWWINDOW;
}
+ if (window_pos->flags & SWP_SHOWWINDOW)
+ delegate_->HandleVisibilityChanging(true);
+ else if (window_pos->flags & SWP_HIDEWINDOW)
+ delegate_->HandleVisibilityChanging(false);
+
SetMsgHandled(FALSE);
}
@@ -2174,4 +2227,9 @@ void HWNDMessageHandler::OnWindowPosChanged(WINDOWPOS* window_pos) {
SetMsgHandled(FALSE);
}
+void HWNDMessageHandler::HandleTouchEvents(const TouchEvents& touch_events) {
+ for (size_t i = 0; i < touch_events.size(); ++i)
+ delegate_->HandleTouchEvent(touch_events[i]);
+}
+
} // namespace views
diff --git a/chromium/ui/views/win/hwnd_message_handler.h b/chromium/ui/views/win/hwnd_message_handler.h
index c1c724cd1db..1751a829dbb 100644
--- a/chromium/ui/views/win/hwnd_message_handler.h
+++ b/chromium/ui/views/win/hwnd_message_handler.h
@@ -11,6 +11,7 @@
#include <windows.h>
#include <set>
+#include <vector>
#include "base/basictypes.h"
#include "base/compiler_specific.h"
@@ -20,9 +21,11 @@
#include "base/strings/string16.h"
#include "base/win/win_util.h"
#include "ui/base/accessibility/accessibility_types.h"
+#include "ui/events/event.h"
+#include "ui/base/sequential_id_generator.h"
#include "ui/base/ui_base_types.h"
-#include "ui/base/win/window_impl.h"
#include "ui/gfx/rect.h"
+#include "ui/gfx/win/window_impl.h"
#include "ui/views/ime/input_method_delegate.h"
#include "ui/views/views_export.h"
@@ -56,7 +59,7 @@ const int WM_NCUAHDRAWFRAME = 0xAF;
// implementation.
// TODO(beng): This object should eventually *become* the WindowImpl.
class VIEWS_EXPORT HWNDMessageHandler :
- public ui::WindowImpl,
+ public gfx::WindowImpl,
public internal::InputMethodDelegate,
public base::MessageLoopForUI::Observer {
public:
@@ -177,7 +180,7 @@ class VIEWS_EXPORT HWNDMessageHandler :
// Called after the WM_ACTIVATE message has been processed by the default
// windows procedure.
- void PostProcessActivateMessage(int activation_state);
+ void PostProcessActivateMessage(int activation_state, bool minimized);
// Enables disabled owner windows that may have been disabled due to this
// window's modality.
@@ -288,8 +291,8 @@ class VIEWS_EXPORT HWNDMessageHandler :
MSG_WM_CREATE(OnCreate)
MSG_WM_DESTROY(OnDestroy)
MSG_WM_DISPLAYCHANGE(OnDisplayChange)
- MSG_WM_ERASEBKGND(OnEraseBkgnd)
MSG_WM_ENTERSIZEMOVE(OnEnterSizeMove)
+ MSG_WM_ERASEBKGND(OnEraseBkgnd)
MSG_WM_EXITSIZEMOVE(OnExitSizeMove)
MSG_WM_GETMINMAXINFO(OnGetMinMaxInfo)
MSG_WM_INITMENU(OnInitMenu)
@@ -309,8 +312,8 @@ class VIEWS_EXPORT HWNDMessageHandler :
MSG_WM_SIZE(OnSize)
MSG_WM_SYSCOMMAND(OnSysCommand)
MSG_WM_THEMECHANGED(OnThemeChanged)
- MSG_WM_WINDOWPOSCHANGING(OnWindowPosChanging)
MSG_WM_WINDOWPOSCHANGED(OnWindowPosChanged)
+ MSG_WM_WINDOWPOSCHANGING(OnWindowPosChanging)
END_MSG_MAP()
// Message Handlers.
@@ -364,11 +367,20 @@ class VIEWS_EXPORT HWNDMessageHandler :
void OnWindowPosChanging(WINDOWPOS* window_pos);
void OnWindowPosChanged(WINDOWPOS* window_pos);
+ typedef std::vector<ui::TouchEvent> TouchEvents;
+ // Helper to handle the list of touch events passed in. We need this because
+ // touch events on windows don't fire if we enter a modal loop in the context
+ // of a touch event.
+ void HandleTouchEvents(const TouchEvents& touch_events);
+
HWNDMessageHandlerDelegate* delegate_;
scoped_ptr<FullscreenHandler> fullscreen_handler_;
- base::WeakPtrFactory<HWNDMessageHandler> close_widget_factory_;
+ base::WeakPtrFactory<HWNDMessageHandler> weak_factory_;
+
+ // Set to true in Close() and false is CloseNow().
+ bool waiting_for_close_now_;
bool remove_standard_frame_;
@@ -406,11 +418,6 @@ class VIEWS_EXPORT HWNDMessageHandler :
// If this is greater than zero, the widget should be locked against updates.
int lock_updates_count_;
- // This flag can be initialized and checked after certain operations (such as
- // DefWindowProc) to avoid stack-controlled functions (such as unlocking the
- // Window with a ScopedRedrawLock) after destruction.
- bool* destroyed_;
-
// Window resizing -----------------------------------------------------------
// When true, this flag makes us discard incoming SetWindowPos() requests that
@@ -418,10 +425,6 @@ class VIEWS_EXPORT HWNDMessageHandler :
// activation, etc.)
bool ignore_window_pos_changes_;
- // The following factory is used to ignore SetWindowPos() calls for short time
- // periods.
- base::WeakPtrFactory<HWNDMessageHandler> ignore_pos_changes_factory_;
-
// The last-seen monitor containing us, and its rect and work area. These are
// used to catch updates to the rect and work area and react accordingly.
HMONITOR last_monitor_;
@@ -457,8 +460,8 @@ class VIEWS_EXPORT HWNDMessageHandler :
// to be insufficient.
gfx::Rect invalid_rect_;
- // A factory that allows us to schedule a redraw for layered windows.
- base::WeakPtrFactory<HWNDMessageHandler> paint_layered_window_factory_;
+ // Set to true when waiting for RedrawLayeredWindowContents().
+ bool waiting_for_redraw_layered_window_contents_;
// True if we are allowed to update the layered window from the DIB backing
// store if necessary.
@@ -470,6 +473,9 @@ class VIEWS_EXPORT HWNDMessageHandler :
// A factory used to lookup appbar autohide edges.
base::WeakPtrFactory<HWNDMessageHandler> autohide_factory_;
+ // Generates touch-ids for touch-events.
+ ui::SequentialIDGenerator id_generator_;
+
DISALLOW_COPY_AND_ASSIGN(HWNDMessageHandler);
};
diff --git a/chromium/ui/views/win/hwnd_message_handler_delegate.h b/chromium/ui/views/win/hwnd_message_handler_delegate.h
index 58318509051..959822be50e 100644
--- a/chromium/ui/views/win/hwnd_message_handler_delegate.h
+++ b/chromium/ui/views/win/hwnd_message_handler_delegate.h
@@ -153,6 +153,10 @@ class VIEWS_EXPORT HWNDMessageHandlerDelegate {
// Called when the system's work area has changed.
virtual void HandleWorkAreaChanged() = 0;
+ // Called when the window's visibility is changing. |visible| holds the new
+ // state.
+ virtual void HandleVisibilityChanging(bool visible) = 0;
+
// Called when the window's visibility changed. |visible| holds the new state.
virtual void HandleVisibilityChanged(bool visible) = 0;
@@ -181,9 +185,8 @@ class VIEWS_EXPORT HWNDMessageHandlerDelegate {
// translation). Returns true if the event was sent to the input method.
virtual bool HandleUntranslatedKeyEvent(const ui::KeyEvent& event) = 0;
- // Called when a touch event is received. Returns true if the event was
- // handled by the delegate.
- virtual bool HandleTouchEvent(const ui::TouchEvent& event) = 0;
+ // Called when a touch event is received.
+ virtual void HandleTouchEvent(const ui::TouchEvent& event) = 0;
// Called when an IME message needs to be processed by the delegate. Returns
// true if the event was handled and no default processing should be
diff --git a/chromium/ui/views/window/dialog_client_view.cc b/chromium/ui/views/window/dialog_client_view.cc
index d592292ed8f..e03c8a1413d 100644
--- a/chromium/ui/views/window/dialog_client_view.cc
+++ b/chromium/ui/views/window/dialog_client_view.cc
@@ -6,7 +6,7 @@
#include <algorithm>
-#include "ui/base/keycodes/keyboard_codes.h"
+#include "ui/events/keycodes/keyboard_codes.h"
#include "ui/views/controls/button/blue_button.h"
#include "ui/views/controls/button/label_button.h"
#include "ui/views/layout/layout_constants.h"
@@ -207,7 +207,7 @@ void DialogClientView::Layout() {
}
// Layout the row containing the buttons and the extra view.
- if (has_dialog_buttons() || extra_view_) {
+ if (has_dialog_buttons() || ShouldShow(extra_view_)) {
bounds.Inset(GetButtonRowInsets());
const int height = GetButtonsAndExtraViewRowHeight();
gfx::Rect row_bounds(bounds.x(), bounds.bottom() - height,
@@ -283,6 +283,17 @@ void DialogClientView::ViewHierarchyChanged(
}
}
+void DialogClientView::NativeViewHierarchyChanged() {
+ FocusManager* focus_manager = GetFocusManager();
+ if (focus_manager_ != focus_manager) {
+ if (focus_manager_)
+ focus_manager_->RemoveFocusChangeListener(this);
+ focus_manager_ = focus_manager;
+ if (focus_manager_)
+ focus_manager_->AddFocusChangeListener(this);
+ }
+}
+
////////////////////////////////////////////////////////////////////////////////
// DialogClientView, ButtonListener implementation:
diff --git a/chromium/ui/views/window/dialog_client_view.h b/chromium/ui/views/window/dialog_client_view.h
index 448eae7b1c7..d780806094c 100644
--- a/chromium/ui/views/window/dialog_client_view.h
+++ b/chromium/ui/views/window/dialog_client_view.h
@@ -62,6 +62,7 @@ class VIEWS_EXPORT DialogClientView : public ClientView,
virtual bool AcceleratorPressed(const ui::Accelerator& accelerator) OVERRIDE;
virtual void ViewHierarchyChanged(
const ViewHierarchyChangedDetails& details) OVERRIDE;
+ virtual void NativeViewHierarchyChanged() OVERRIDE;
// ButtonListener implementation:
virtual void ButtonPressed(Button* sender, const ui::Event& event) OVERRIDE;
@@ -84,6 +85,8 @@ class VIEWS_EXPORT DialogClientView : public ClientView,
virtual void ChildVisibilityChanged(View* child) OVERRIDE;
private:
+ FRIEND_TEST_ALL_PREFIXES(DialogClientViewTest, FocusManager);
+
bool has_dialog_buttons() const { return ok_button_ || cancel_button_; }
// Create a dialog button of the appropriate type.
diff --git a/chromium/ui/views/window/dialog_client_view_unittest.cc b/chromium/ui/views/window/dialog_client_view_unittest.cc
index 9f8c8c4a380..28b001f2d28 100644
--- a/chromium/ui/views/window/dialog_client_view_unittest.cc
+++ b/chromium/ui/views/window/dialog_client_view_unittest.cc
@@ -4,10 +4,11 @@
#include "base/basictypes.h"
#include "base/strings/utf_string_conversions.h"
-#include "testing/gtest/include/gtest/gtest.h"
#include "ui/base/ui_base_types.h"
#include "ui/views/controls/button/label_button.h"
#include "ui/views/test/test_views.h"
+#include "ui/views/test/views_test_base.h"
+#include "ui/views/widget/widget.h"
#include "ui/views/window/dialog_client_view.h"
#include "ui/views/window/dialog_delegate.h"
@@ -37,7 +38,7 @@ class TestDialogClientView : public DialogClientView {
DISALLOW_COPY_AND_ASSIGN(TestDialogClientView);
};
-class DialogClientViewTest : public testing::Test,
+class DialogClientViewTest : public ViewsTestBase,
public DialogDelegateView {
public:
DialogClientViewTest()
@@ -51,6 +52,8 @@ class DialogClientViewTest : public testing::Test,
dialog_buttons_ = ui::DIALOG_BUTTON_NONE;
contents_.reset(new StaticSizedView(gfx::Size(100, 200)));
client_view_.reset(new TestDialogClientView(contents_.get(), this));
+
+ ViewsTestBase::SetUp();
}
// DialogDelegateView implementation.
@@ -233,4 +236,57 @@ TEST_F(DialogClientViewTest, LayoutWithFootnoteHeightForWidth) {
footnote_view->bounds().height());
}
+// Test that the DialogClientView's FocusManager is properly updated when the
+// DialogClientView belongs to a non top level widget and the widget is
+// reparented. The DialogClientView belongs to a non top level widget in the
+// case of constrained windows. The constrained window's widget is reparented
+// when a browser tab is dragged to a different browser window.
+TEST_F(DialogClientViewTest, FocusManager) {
+ scoped_ptr<Widget> toplevel1(new Widget);
+ Widget::InitParams toplevel1_params =
+ CreateParams(Widget::InitParams::TYPE_WINDOW);
+ toplevel1_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ toplevel1->Init(toplevel1_params);
+
+ scoped_ptr<Widget> toplevel2(new Widget);
+ Widget::InitParams toplevel2_params =
+ CreateParams(Widget::InitParams::TYPE_WINDOW);
+ toplevel2_params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
+ toplevel2->Init(toplevel2_params);
+
+ Widget* dialog = new Widget;
+ Widget::InitParams dialog_params =
+ CreateParams(Widget::InitParams::TYPE_WINDOW);
+ dialog_params.child = true;
+ dialog_params.delegate = new DialogDelegateView();
+ dialog_params.parent = toplevel1->GetNativeView();
+ dialog->Init(dialog_params);
+
+ // Test that the FocusManager has been properly set when the DialogClientView
+ // was parented to |dialog|.
+ DialogClientView* client_view =
+ static_cast<DialogClientView*>(dialog->client_view());
+ EXPECT_EQ(toplevel1->GetFocusManager(), client_view->focus_manager_);
+
+ // Test that the FocusManager is properly updated when the DialogClientView's
+ // top level widget is changed.
+ Widget::ReparentNativeView(dialog->GetNativeView(), NULL);
+ EXPECT_EQ(NULL, client_view->focus_manager_);
+ Widget::ReparentNativeView(dialog->GetNativeView(),
+ toplevel2->GetNativeView());
+ EXPECT_EQ(toplevel2->GetFocusManager(), client_view->focus_manager_);
+ Widget::ReparentNativeView(dialog->GetNativeView(),
+ toplevel1->GetNativeView());
+ EXPECT_NE(toplevel1->GetFocusManager(), toplevel2->GetFocusManager());
+ EXPECT_EQ(toplevel1->GetFocusManager(), client_view->focus_manager_);
+
+ // Test that the FocusManager is properly cleared when the DialogClientView is
+ // removed from |dialog| during the widget's destruction.
+ client_view->set_owned_by_client();
+ scoped_ptr<DialogClientView> owned_client_view(client_view);
+ toplevel1->CloseNow();
+ toplevel2->CloseNow();
+ EXPECT_EQ(NULL, owned_client_view->focus_manager_);
+}
+
} // namespace views
diff --git a/chromium/ui/views/window/dialog_delegate.cc b/chromium/ui/views/window/dialog_delegate.cc
index 9291fc74f78..04fcebbf645 100644
--- a/chromium/ui/views/window/dialog_delegate.cc
+++ b/chromium/ui/views/window/dialog_delegate.cc
@@ -7,7 +7,6 @@
#include "base/logging.h"
#include "grit/ui_strings.h"
#include "ui/base/l10n/l10n_util.h"
-#include "ui/base/ui_base_switches_util.h"
#include "ui/views/bubble/bubble_border.h"
#include "ui/views/bubble/bubble_frame_view.h"
#include "ui/views/controls/button/label_button.h"
@@ -30,8 +29,8 @@ DialogDelegate::~DialogDelegate() {
// static
bool DialogDelegate::UseNewStyle() {
- return switches::IsNewDialogStyleEnabled() &&
- Textfield::IsViewsTextfieldEnabled();
+ // The new dialog style cannot host native Windows textfield controls.
+ return Textfield::IsViewsTextfieldEnabled();
}
// static
@@ -52,12 +51,6 @@ Widget* DialogDelegate::CreateDialogWidget(DialogDelegate* dialog,
params.parent = parent;
params.top_level = true;
widget->Init(params);
- if (use_new_style) {
-#if defined(USE_AURA)
- // TODO(msw): Add a matching shadow type and remove the bubble frame border?
- corewm::SetShadowType(widget->GetNativeWindow(), corewm::SHADOW_TYPE_NONE);
-#endif
- }
return widget;
}
@@ -199,6 +192,10 @@ NonClientFrameView* DialogDelegate::CreateNewStyleFrameView(
}
if (force_opaque_border)
widget->set_frame_type(views::Widget::FRAME_TYPE_FORCE_CUSTOM);
+#if defined(USE_AURA)
+ // TODO(msw): Add a matching shadow type and remove the bubble frame border?
+ corewm::SetShadowType(widget->GetNativeWindow(), corewm::SHADOW_TYPE_NONE);
+#endif
return frame;
}
diff --git a/chromium/ui/views/window/frame_buttons.h b/chromium/ui/views/window/frame_buttons.h
new file mode 100644
index 00000000000..d534356754d
--- /dev/null
+++ b/chromium/ui/views/window/frame_buttons.h
@@ -0,0 +1,19 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef UI_VIEWS_WINDOW_FRAME_BUTTONS_H_
+#define UI_VIEWS_WINDOW_FRAME_BUTTONS_H_
+
+namespace views {
+
+// Identifies what a button in a window frame is.
+enum FrameButton {
+ FRAME_BUTTON_MINIMIZE,
+ FRAME_BUTTON_MAXIMIZE,
+ FRAME_BUTTON_CLOSE
+};
+
+} // namespace views
+
+#endif // UI_VIEWS_WINDOW_FRAME_BUTTONS_H_
diff --git a/chromium/ui/webui/resources/css/apps/common.css b/chromium/ui/webui/resources/css/apps/common.css
new file mode 100644
index 00000000000..4f3ef31745d
--- /dev/null
+++ b/chromium/ui/webui/resources/css/apps/common.css
@@ -0,0 +1,169 @@
+/* Copyright 2013 The Chromium Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file. */
+
+button.white-button,
+button.blue-button {
+ border: 5px solid transparent;
+ box-sizing: content-box;
+ cursor: default;
+ height: 21px;
+ line-height: 21px;
+ margin: 0;
+ min-height: 21px;
+ min-width: 55px;
+ padding: 0 10px;
+ position: relative;
+ outline: none;
+ text-align: center;
+ z-index: 1;
+}
+
+button.white-button {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button.png') 1x,
+ url('chrome://resources/images/2x/apps/button.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.white-button:hover {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button_hover.png') 1x,
+ url('chrome://resources/images/2x/apps/button_hover.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.white-button:active {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button_pressed.png') 1x,
+ url('chrome://resources/images/2x/apps/button_pressed.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.white-button:focus {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button_focused.png') 1x,
+ url('chrome://resources/images/2x/apps/button_focused.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.white-button:focus:hover {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button_focused_hover.png') 1x,
+ url('chrome://resources/images/2x/apps/button_focused_hover.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.white-button:focus:active {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button_focused_pressed.png') 1x,
+ url('chrome://resources/images/2x/apps/button_focused_pressed.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.white-button[disabled] {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/button_inactive.png') 1x,
+ url('chrome://resources/images/2x/apps/button_inactive.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button:hover {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button_hover.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button_hover.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button:active {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button_pressed.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button_pressed.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button:focus {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button_focused.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button_focused.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button:focus:hover {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button_focused_hover.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button_focused_hover.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button:focus:active {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button_focused_pressed.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button_focused_pressed.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+button.blue-button[disabled] {
+ border-image: -webkit-image-set(
+ url('chrome://resources/images/apps/blue_button_inactive.png') 1x,
+ url('chrome://resources/images/2x/apps/blue_button_inactive.png')
+ 2x) 5 fill / 5px / 2px repeat;
+}
+
+input[type='checkbox'] {
+ -webkit-appearance: none;
+ border: none;
+ outline: none;
+}
+
+input[type='checkbox']::after {
+ content: '';
+ display: block;
+ height: 16px;
+ left: -2px;
+ top: -2px;
+ width: 16px;
+}
+
+input[type='checkbox']:not(:checked)::after {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/checkbox.png') 1x,
+ url('chrome://resources/images/2x/apps/checkbox.png') 2x);
+}
+
+input[type='checkbox']:focus:not(:checked)::after {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/checkbox_focused.png') 1x,
+ url('chrome://resources/images/2x/apps/checkbox_focused.png') 2x);
+}
+
+input[type='checkbox']:disabled:not(:checked)::after {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/checkbox_inactive.png') 1x,
+ url('chrome://resources/images/2x/apps/checkbox_inactive.png') 2x);
+}
+
+input[type='checkbox']:checked::after {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/checkbox_checked.png') 1x,
+ url('chrome://resources/images/2x/apps/checkbox_checked.png') 2x);
+}
+
+input[type='checkbox']:focus:checked::after {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/checkbox_focused_checked.png') 1x,
+ url('chrome://resources/images/2x/apps/checkbox_focused_checked.png') 2x);
+}
+
+input[type='checkbox']:disabled:checked::after {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/checkbox_checked_inactive.png') 1x,
+ url('chrome://resources/images/2x/apps/checkbox_checked_inactive.png') 2x);
+}
diff --git a/chromium/ui/webui/resources/css/apps/topbutton_bar.css b/chromium/ui/webui/resources/css/apps/topbutton_bar.css
new file mode 100644
index 00000000000..35641e9d4b8
--- /dev/null
+++ b/chromium/ui/webui/resources/css/apps/topbutton_bar.css
@@ -0,0 +1,61 @@
+/* Copyright 2013 The Chromium Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file. */
+
+.topbutton-bar {
+ -webkit-box-align: center;
+ display: -webkit-box;
+}
+
+.topbutton-bar button {
+ -webkit-app-region: no-drag;
+ -webkit-box-shadow: none;
+ -webkit-margin-end: 10px;
+ background-color: transparent;
+ background-image: none;
+ background-position: center;
+ background-repeat: no-repeat;
+ border: 0;
+ display: block;
+ height: 32px;
+ min-width: 0;
+ outline: none;
+ padding: 0;
+ width: 32px;
+}
+
+.topbutton-bar button:active {
+ -webkit-box-shadow:
+ 0 1px 0 0 #c2c2c2 inset,
+ 0 0 0 1px #dedede inset;
+}
+
+.topbutton-bar button:hover,
+.topbutton-bar button:focus,
+.topbutton-bar button:active {
+ background-color: #ededed;
+}
+
+.topbutton-bar .maximize-button {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/topbar_button_maximize.png') 1x,
+ url('chrome://resources/images/2x/apps/topbar_button_maximize.png') 2x);
+}
+
+.topbutton-bar .minimize-button {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/topbar_button_minimize.png') 1x,
+ url('chrome://resources/images/2x/apps/topbar_button_minimize.png') 2x);
+}
+
+.topbutton-bar .close-button {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/topbar_button_close.png') 1x,
+ url('chrome://resources/images/2x/apps/topbar_button_close.png') 2x);
+}
+
+.topbutton-bar .gear-button {
+ background-image: -webkit-image-set(
+ url('chrome://resources/images/apps/topbar_button_settings.png') 1x,
+ url('chrome://resources/images/2x/apps/topbar_button_settings.png') 2x);
+}
diff --git a/chromium/ui/webui/resources/css/overlay.css b/chromium/ui/webui/resources/css/overlay.css
index af47453698c..5bf914cff52 100644
--- a/chromium/ui/webui/resources/css/overlay.css
+++ b/chromium/ui/webui/resources/css/overlay.css
@@ -151,7 +151,7 @@ html[dir='rtl'] .overlay .page .action-area {
/* On OSX 10.7, hidden scrollbars may prevent the user from realizing that the
* overlay contains scrollable content. To resolve this, style the scrollbars on
* OSX so they are always visible. See http://crbug.com/123010. */
-<if expr="is_macosx">
+<if expr="is_macosx or is_ios">
.overlay .page .content-area::-webkit-scrollbar {
-webkit-appearance: none;
width: 11px;
diff --git a/chromium/ui/webui/resources/css/tree.css b/chromium/ui/webui/resources/css/tree.css
index 64ae2126e27..3bd08f7019e 100644
--- a/chromium/ui/webui/resources/css/tree.css
+++ b/chromium/ui/webui/resources/css/tree.css
@@ -169,7 +169,7 @@ tree[icon-visibility=parent] .tree-row[has-children=false] > .tree-label {
font-size: inherit;
font-weight: inherit;
margin: -2px -8px -2px -3px;
-<if expr="not is_macosx">
+<if expr="not is_macosx and not is_ios">
outline: none;
</if>
padding: 1px 7px 1px 1px;
diff --git a/chromium/ui/webui/resources/css/widgets.css b/chromium/ui/webui/resources/css/widgets.css
index 5a69ea8ec13..68b7c26bc94 100644
--- a/chromium/ui/webui/resources/css/widgets.css
+++ b/chromium/ui/webui/resources/css/widgets.css
@@ -98,7 +98,7 @@ textarea {
/* Use min-height to accommodate addditional padding for touch as needed. */
min-height: 2em;
padding: 3px;
-<if expr="is_win or is_macosx">
+<if expr="is_win or is_macosx or is_ios">
/* For better alignment between adjacent buttons and inputs. */
padding-bottom: 4px;
</if>
diff --git a/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close.png b/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close.png
new file mode 100644
index 00000000000..260af771e93
--- /dev/null
+++ b/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close.png
Binary files differ
diff --git a/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_hover.png b/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_hover.png
new file mode 100644
index 00000000000..03e9b12f675
--- /dev/null
+++ b/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_hover.png
Binary files differ
diff --git a/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_pressed.png b/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_pressed.png
new file mode 100644
index 00000000000..4f31f86ec12
--- /dev/null
+++ b/chromium/ui/webui/resources/images/2x/apps/button_butter_bar_close_pressed.png
Binary files differ
diff --git a/chromium/ui/webui/resources/images/apps/button_butter_bar_close.png b/chromium/ui/webui/resources/images/apps/button_butter_bar_close.png
new file mode 100644
index 00000000000..b9143c3d676
--- /dev/null
+++ b/chromium/ui/webui/resources/images/apps/button_butter_bar_close.png
Binary files differ
diff --git a/chromium/ui/webui/resources/images/apps/button_butter_bar_close_hover.png b/chromium/ui/webui/resources/images/apps/button_butter_bar_close_hover.png
new file mode 100644
index 00000000000..02e91dbf180
--- /dev/null
+++ b/chromium/ui/webui/resources/images/apps/button_butter_bar_close_hover.png
Binary files differ
diff --git a/chromium/ui/webui/resources/images/apps/button_butter_bar_close_pressed.png b/chromium/ui/webui/resources/images/apps/button_butter_bar_close_pressed.png
new file mode 100644
index 00000000000..470271a0236
--- /dev/null
+++ b/chromium/ui/webui/resources/images/apps/button_butter_bar_close_pressed.png
Binary files differ
diff --git a/chromium/ui/webui/resources/images/guest_icon_standalone.png b/chromium/ui/webui/resources/images/guest_icon_standalone.png
deleted file mode 100644
index c4d29bcb6b3..00000000000
--- a/chromium/ui/webui/resources/images/guest_icon_standalone.png
+++ /dev/null
Binary files differ
diff --git a/chromium/ui/webui/resources/images/question_mark.png b/chromium/ui/webui/resources/images/question_mark.png
new file mode 100644
index 00000000000..994056b93be
--- /dev/null
+++ b/chromium/ui/webui/resources/images/question_mark.png
Binary files differ
diff --git a/chromium/ui/webui/resources/js/cr.js b/chromium/ui/webui/resources/js/cr.js
index 2a7ab7823b4..3ea3b91dd8a 100644
--- a/chromium/ui/webui/resources/js/cr.js
+++ b/chromium/ui/webui/resources/js/cr.js
@@ -280,21 +280,26 @@ this.cr = (function() {
};
}
+ var OriginalEvent = global.Event;
+
/**
* Creates a new event to be used with cr.EventTarget or DOM EventTarget
* objects.
* @param {string} type The name of the event.
* @param {boolean=} opt_bubbles Whether the event bubbles.
* Default is false.
- * @param {boolean=} opt_preventable Whether the default action of the event
- * can be prevented.
+ * @param {boolean=} opt_cancelable Whether the default action of the event
+ * can be prevented. Unlike the DOM event constructor, this defaults to
+ * true.
* @constructor
* @extends {Event}
*/
- function Event(type, opt_bubbles, opt_preventable) {
- var e = cr.doc.createEvent('Event');
- e.initEvent(type, !!opt_bubbles, !!opt_preventable);
- e.__proto__ = global.Event.prototype;
+ function Event(type, opt_bubbles, opt_cancelable) {
+ var e = new OriginalEvent(type, {
+ bubbles: opt_bubbles,
+ cancelable: opt_cancelable === undefined ? true : opt_cancelable
+ });
+ e.__proto__ = OriginalEvent.prototype;
return e;
};
@@ -319,7 +324,7 @@ this.cr = (function() {
return;
}
- Event.prototype = {__proto__: global.Event.prototype};
+ Event.prototype = {__proto__: OriginalEvent.prototype};
cr.doc = document;
diff --git a/chromium/ui/webui/resources/js/cr/event_target.js b/chromium/ui/webui/resources/js/cr/event_target.js
index 5bcb41d6138..d9bc681c75f 100644
--- a/chromium/ui/webui/resources/js/cr/event_target.js
+++ b/chromium/ui/webui/resources/js/cr/event_target.js
@@ -76,9 +76,6 @@ cr.define('cr', function() {
event.__defineGetter__('target', function() {
return self;
});
- event.preventDefault = function() {
- this.returnValue = false;
- };
var type = event.type;
var prevented = 0;
@@ -93,7 +90,7 @@ cr.define('cr', function() {
}
}
- return !prevented && event.returnValue;
+ return !prevented && !event.defaultPrevented;
}
};
diff --git a/chromium/ui/webui/resources/js/cr/ui/context_menu_button.js b/chromium/ui/webui/resources/js/cr/ui/context_menu_button.js
index 88dd605d380..7d324e3ce0f 100644
--- a/chromium/ui/webui/resources/js/cr/ui/context_menu_button.js
+++ b/chromium/ui/webui/resources/js/cr/ui/context_menu_button.js
@@ -67,6 +67,20 @@ cr.define('cr.ui', function() {
break;
}
MenuButton.prototype.handleEvent.call(this, e);
+ },
+
+ /**
+ * Override MenuButton showMenu to allow the mousedown to be fully handled
+ * before the menu is shown. This is important in case the mousedown
+ * triggers command changes.
+ * @param {boolean} shouldSetFocus Whether the menu should be focused after
+ * the menu is shown.
+ */
+ showMenu: function(shouldSetFocus) {
+ var self = this;
+ window.setTimeout(function() {
+ MenuButton.prototype.showMenu.call(self, shouldSetFocus);
+ });
}
};
diff --git a/chromium/ui/webui/resources/js/cr/ui/list.js b/chromium/ui/webui/resources/js/cr/ui/list.js
index 080aa9c23b8..a094834f637 100644
--- a/chromium/ui/webui/resources/js/cr/ui/list.js
+++ b/chromium/ui/webui/resources/js/cr/ui/list.js
@@ -1126,6 +1126,10 @@ cr.define('cr.ui', function() {
this.afterFiller_.style.height = afterFillerHeight + 'px';
+ // Restores the number of pixels scrolled, since it might be changed while
+ // DOM operations.
+ this.scrollTop = scrollTop;
+
// We don't set the lead or selected properties until after adding all
// items, in case they force relayout in response to these events.
var listItem = null;
diff --git a/chromium/ui/webui/resources/js/util.js b/chromium/ui/webui/resources/js/util.js
index e7beb676f40..bec9c3b4dec 100644
--- a/chromium/ui/webui/resources/js/util.js
+++ b/chromium/ui/webui/resources/js/util.js
@@ -302,3 +302,23 @@ function createElementWithClassName(type, className) {
elm.className = className;
return elm;
}
+
+/**
+ * webkitTransitionEnd does not always fire (e.g. when animation is aborted
+ * or when no paint happens during the animation). This function sets up
+ * a timer and emulate the event if it is not fired when the timer expires.
+ * @param {!HTMLElement} el The element to watch for webkitTransitionEnd.
+ * @param {number} timeOut The maximum wait time in milliseconds for the
+ * webkitTransitionEnd to happen.
+ */
+function ensureTransitionEndEvent(el, timeOut) {
+ var fired = false;
+ el.addEventListener('webkitTransitionEnd', function f(e) {
+ el.removeEventListener('webkitTransitionEnd', f);
+ fired = true;
+ });
+ window.setTimeout(function() {
+ if (!fired)
+ cr.dispatchSimpleEvent(el, 'webkitTransitionEnd');
+ }, timeOut);
+}
diff --git a/chromium/ui/webui/resources/js/webui_resource_test.js b/chromium/ui/webui/resources/js/webui_resource_test.js
new file mode 100644
index 00000000000..cce993d7af1
--- /dev/null
+++ b/chromium/ui/webui/resources/js/webui_resource_test.js
@@ -0,0 +1,204 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+/**
+ * Tests that an observation matches the expected value.
+ * @param {Object} expected The expected value.
+ * @param {Object} observed The actual value.
+ * @param {string=} opt_message Optional message to include with a test
+ * failure.
+ */
+function assertEquals(expected, observed, opt_message) {
+ if (observed !== expected) {
+ var message = 'Assertion Failed\n Observed: ' + observed +
+ '\n Expected: ' + expected;
+ if (opt_message)
+ message = message + '\n ' + opt_message;
+ throw new Error(message);
+ }
+}
+
+/**
+ * Verifies that a test result is true.
+ * @param {boolean} observed The observed value.
+ * @param {string=} opt_message Optional message to include with a test
+ * failure.
+ */
+function assertTrue(observed, opt_message) {
+ assertEquals(true, observed, opt_message);
+}
+
+/**
+ * Verifies that a test result is false.
+ * @param {boolean} observed The observed value.
+ * @param {string=} opt_message Optional message to include with a test
+ * failure.
+ */
+function assertFalse(observed, opt_message) {
+ assertEquals(false, observed, opt_message);
+}
+
+/**
+ * Verifies that the observed and reference values differ.
+ * @param {Object} reference The target value for comparison.
+ * @param {Object} observed The test result.
+ * @param {string=} opt_message Optional message to include with a test
+ * failure.
+ */
+function assertNotEqual(reference, observed, opt_message) {
+ if (observed === reference) {
+ var message = 'Assertion Failed\n Observed: ' + observed +
+ '\n Reference: ' + reference;
+ if (opt_message)
+ message = message + '\n ' + opt_message;
+ throw new Error(message);
+ }
+}
+
+/**
+ * Verifies that a test evaluation results in an exception.
+ * @param {!Function} f The test function.
+ */
+function assertThrows(f) {
+ var triggeredError = false;
+ try {
+ f();
+ } catch(err) {
+ triggeredError = true;
+ }
+ if (!triggeredError)
+ throw new Error('Assertion Failed: throw expected.');
+}
+
+/**
+ * Verifies that the contents of the expected and observed arrays match.
+ * @param {!Array} expected The expected result.
+ * @param {!Array} observed The actual result.
+ */
+function assertArrayEquals(expected, observed) {
+ var v1 = Array.prototype.slice.call(expected);
+ var v2 = Array.prototype.slice.call(observed);
+ var equal = v1.length == v2.length;
+ if (equal) {
+ for (var i = 0; i < v1.length; i++) {
+ if (v1[i] !== v2[i]) {
+ equal = false;
+ break;
+ }
+ }
+ }
+ if (!equal) {
+ var message =
+ ['Assertion Failed', 'Observed: ' + v2, 'Expected: ' + v1].join('\n ');
+ throw new Error(message);
+ }
+}
+
+/**
+ * Verifies that the expected and observed result have the same content.
+ * @param {*} expected The expected result.
+ * @param {*} observed The actual result.
+ */
+function assertDeepEquals(expected, observed, opt_message) {
+ if (typeof expected == 'object' && expected != null) {
+ assertNotEqual(null, observed);
+ for (var key in expected) {
+ assertTrue(key in observed, opt_message);
+ assertDeepEquals(expected[key], observed[key], opt_message);
+ }
+ for (var key in observed) {
+ assertTrue(key in expected, opt_message);
+ }
+ } else {
+ assertEquals(expected, observed, opt_message);
+ }
+}
+
+/**
+ * Defines runTests.
+ */
+(function(exports) {
+ /**
+ * List of test cases.
+ * @type {Array.<string>} List of function names for tests to run.
+ */
+ var testCases = [];
+
+ /**
+ * Indicates if all tests have run successfully.
+ * @type {boolean}
+ */
+ var cleanTestRun = true;
+
+ /**
+ * Armed during setup of a test to call the matching tear down code.
+ * @type {Function}
+ */
+ var pendingTearDown = null;
+
+ /**
+ * Runs all functions starting with test and reports success or
+ * failure of the test suite.
+ */
+ function runTests() {
+ for (var name in window) {
+ if (typeof window[name] == 'function' && /^test/.test(name))
+ testCases.push(name);
+ }
+ if (!testCases.length) {
+ console.error('Failed to find test cases.');
+ cleanTestRun = false;
+ }
+ continueTesting();
+ }
+
+ /**
+ * Runs the next test in the queue. Reports the test results if the queue is
+ * empty.
+ */
+ function continueTesting() {
+ if (pendingTearDown) {
+ pendingTearDown();
+ pendingTearDown = null;
+ }
+ if (testCases.length > 0) {
+ var fn = testCases.pop();
+ var isAsyncTest = window[fn].length;
+ try {
+ if (window.setUp)
+ window.setUp();
+ pendingTearDown = window.tearDown;
+ window[fn](continueTesting);
+ } catch(err) {
+ console.error('Failure in test ' + fn + '\n' + err);
+ console.log(err.stack);
+ cleanTestRun = false;
+ }
+ // Asynchronous tests must manually call continueTesting when complete.
+ if (!isAsyncTest)
+ continueTesting();
+ } else {
+ endTests(cleanTestRun);
+ }
+ if (testCases.length) {
+ domAutomationController.setAutomationId(1);
+ domAutomationController.send('PENDING');
+ }
+ };
+
+ exports.runTests = runTests;
+})(this);
+
+/**
+ * Signals completion of a test.
+ * @param {boolean} success Indicates if the test completed successfully.
+ */
+function endTests(success) {
+ domAutomationController.setAutomationId(1);
+ domAutomationController.send(success ? 'SUCCESS' : 'FAILURE');
+}
+
+window.onerror = function() {
+ endTests(false);
+};
diff --git a/chromium/ui/webui/resources/webui_resources.grd b/chromium/ui/webui/resources/webui_resources.grd
index 219ebbf1597..7cc6c7c47d1 100644
--- a/chromium/ui/webui/resources/webui_resources.grd
+++ b/chromium/ui/webui/resources/webui_resources.grd
@@ -17,6 +17,162 @@ without changes to the corresponding grd file. -->
<include name="IDR_WEBUI_I18N_TEMPLATE_JS" file="js/i18n_template.js" type="BINDATA" />
<include name="IDR_WEBUI_I18N_TEMPLATE2_JS" file="js/i18n_template2.js" flattenhtml="true" type="BINDATA" />
<include name="IDR_WEBUI_JSTEMPLATE_JS" file="js/jstemplate_compiled.js" flattenhtml="true" type="BINDATA" />
+
+ <!-- Component apps common image resources - 1x -->
+ <!-- White button -->
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON"
+ file="../../resources/default_100_percent/common/button.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_PRESSED"
+ file="../../resources/default_100_percent/common/button_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_HOVER"
+ file="../../resources/default_100_percent/common/button_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_DISABLED"
+ file="../../resources/default_100_percent/common/button_inactive.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_FOCUSED"
+ file="../../resources/default_100_percent/common/button_focused.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_FOCUSED_PRESSED"
+ file="../../resources/default_100_percent/common/button_focused_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_FOCUSED_HOVER"
+ file="../../resources/default_100_percent/common/button_focused_hover.png" type="BINDATA" />
+ <!-- Blue button -->
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON"
+ file="../../resources/default_100_percent/common/blue_button.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_PRESSED"
+ file="../../resources/default_100_percent/common/blue_button_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_HOVER"
+ file="../../resources/default_100_percent/common/blue_button_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_DISABLED"
+ file="../../resources/default_100_percent/common/blue_button_inactive.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_FOCUSED"
+ file="../../resources/default_100_percent/common/blue_button_focused.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_FOCUSED_PRESSED"
+ file="../../resources/default_100_percent/common/blue_button_focused_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_FOCUSED_HOVER"
+ file="../../resources/default_100_percent/common/blue_button_focused_hover.png" type="BINDATA" />
+ <!-- Checkbox (unchecked) -->
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX"
+ file="../../resources/default_100_percent/common/checkbox.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_HOVER"
+ file="../../resources/default_100_percent/common/checkbox_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_PRESSED"
+ file="../../resources/default_100_percent/common/checkbox_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED"
+ file="../../resources/default_100_percent/common/checkbox_focused.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_HOVER"
+ file="../../resources/default_100_percent/common/checkbox_focused_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_PRESSED"
+ file="../../resources/default_100_percent/common/checkbox_focused_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_INACTIVE"
+ file="../../resources/default_100_percent/common/checkbox_inactive.png" type="BINDATA" />
+ <!-- Checkbox (checked) -->
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED"
+ file="../../resources/default_100_percent/common/checkbox_checked.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_HOVER"
+ file="../../resources/default_100_percent/common/checkbox_checked_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_PRESSED"
+ file="../../resources/default_100_percent/common/checkbox_checked_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_CHECKED"
+ file="../../resources/default_100_percent/common/checkbox_focused_checked.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_CHECKED_HOVER"
+ file="../../resources/default_100_percent/common/checkbox_focused_checked_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_CHECKED_PRESSED"
+ file="../../resources/default_100_percent/common/checkbox_focused_checked_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_INACTIVE"
+ file="../../resources/default_100_percent/common/checkbox_checked_inactive.png" type="BINDATA" />
+ <!-- Misc buttons -->
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_CLOSE"
+ file="images/apps/topbar_button_close.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_MAXIMIZE"
+ file="images/apps/topbar_button_maximize.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_MINIMIZE"
+ file="images/apps/topbar_button_minimize.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_SETTINGS"
+ file="images/apps/topbar_button_settings.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_BUTTER_BAR_CLOSE"
+ file="images/apps/button_butter_bar_close.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_BUTTER_BAR_CLOSE_HOVER"
+ file="images/apps/button_butter_bar_close_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_BUTTER_BAR_CLOSE_PRESSED"
+ file="images/apps/button_butter_bar_close_pressed.png" type="BINDATA" />
+
+ <!-- Component apps common image resources - 2x -->
+ <!-- White button -->
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X"
+ file="../../resources/default_200_percent/common/button.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X_PRESSED"
+ file="../../resources/default_200_percent/common/button_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X_HOVER"
+ file="../../resources/default_200_percent/common/button_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X_DISABLED"
+ file="../../resources/default_200_percent/common/button_inactive.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X_FOCUSED"
+ file="../../resources/default_200_percent/common/button_focused.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X_FOCUSED_PRESSED"
+ file="../../resources/default_200_percent/common/button_focused_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_2X_FOCUSED_HOVER"
+ file="../../resources/default_200_percent/common/button_focused_hover.png" type="BINDATA" />
+ <!-- Blue button -->
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X"
+ file="../../resources/default_200_percent/common/blue_button.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X_PRESSED"
+ file="../../resources/default_200_percent/common/blue_button_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X_HOVER"
+ file="../../resources/default_200_percent/common/blue_button_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X_DISABLED"
+ file="../../resources/default_200_percent/common/blue_button_inactive.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X_FOCUSED"
+ file="../../resources/default_200_percent/common/blue_button_focused.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X_FOCUSED_PRESSED"
+ file="../../resources/default_200_percent/common/blue_button_focused_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BLUE_BUTTON_2X_FOCUSED_HOVER"
+ file="../../resources/default_200_percent/common/blue_button_focused_hover.png" type="BINDATA" />
+ <!-- Checkbox (unchecked) -->
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_2X"
+ file="../../resources/default_200_percent/common/checkbox.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_2X_HOVER"
+ file="../../resources/default_200_percent/common/checkbox_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_2X_PRESSED"
+ file="../../resources/default_200_percent/common/checkbox_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_2X_FOCUSED"
+ file="../../resources/default_200_percent/common/checkbox_focused.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_2X_FOCUSED_HOVER"
+ file="../../resources/default_200_percent/common/checkbox_focused_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_2X_FOCUSED_PRESSED"
+ file="../../resources/default_200_percent/common/checkbox_focused_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_INACTIVE_2X"
+ file="../../resources/default_200_percent/common/checkbox_inactive.png" type="BINDATA" />
+ <!-- Checkbox (checked) -->
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_2X"
+ file="../../resources/default_200_percent/common/checkbox_checked.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_2X_HOVER"
+ file="../../resources/default_200_percent/common/checkbox_checked_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_2X_PRESSED"
+ file="../../resources/default_200_percent/common/checkbox_checked_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_CHECKED_2X"
+ file="../../resources/default_200_percent/common/checkbox_focused_checked.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_CHECKED_2X_HOVER"
+ file="../../resources/default_200_percent/common/checkbox_focused_checked_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_FOCUSED_CHECKED_2X_PRESSED"
+ file="../../resources/default_200_percent/common/checkbox_focused_checked_pressed.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_CHECKBOX_CHECKED_INACTIVE_2X"
+ file="../../resources/default_200_percent/common/checkbox_checked_inactive.png" type="BINDATA" />
+ <!-- Misc buttons -->
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_2X_CLOSE"
+ file="images/2x/apps/topbar_button_close.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_2X_MAXIMIZE"
+ file="images/2x/apps/topbar_button_maximize.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_2X_MINIMIZE"
+ file="images/2x/apps/topbar_button_minimize.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_TOPBAR_BUTTON_2X_SETTINGS"
+ file="images/2x/apps/topbar_button_settings.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_BUTTER_BAR_CLOSE_2X"
+ file="images/2x/apps/button_butter_bar_close.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_BUTTER_BAR_CLOSE_HOVER_2X"
+ file="images/2x/apps/button_butter_bar_close_hover.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_APPS_BUTTON_BUTTER_BAR_CLOSE_PRESSED_2X"
+ file="images/2x/apps/button_butter_bar_close_pressed.png" type="BINDATA" />
+
+ <!-- Non-apps images -->
<include name="IDR_WEBUI_IMAGES_CHECK"
file="images/check.png" type="BINDATA" />
<include name="IDR_WEBUI_IMAGES_CHECKBOX_BLACK"
@@ -31,6 +187,8 @@ without changes to the corresponding grd file. -->
file="images/google-transparent.png" type="BINDATA" />
<include name="IDR_WEBUI_IMAGES_HELP"
file="images/help.png" type="BINDATA" />
+ <include name="IDR_WEBUI_IMAGES_QUESTION_MARK"
+ file="images/question_mark.png" type="BINDATA" />
<include name="IDR_WEBUI_IMAGES_SELECT"
file="images/select.png" type="BINDATA" />
<include name="IDR_WEBUI_IMAGES_SPINNER"
@@ -51,6 +209,10 @@ without changes to the corresponding grd file. -->
file="css/bubble_button.css" type="chrome_html" />
<structure name="IDR_WEBUI_CSS_BUTTER_BAR"
file="css/butter_bar.css" type="chrome_html" />
+ <structure name="IDR_WEBUI_CSS_APPS_COMMON"
+ file="css/apps/common.css" type="chrome_html" />
+ <structure name="IDR_WEBUI_CSS_APPS_TOPBUTTON_BAR"
+ file="css/apps/topbutton_bar.css" type="chrome_html" />
<structure name="IDR_WEBUI_CSS_DIALOGS"
file="css/dialogs.css" type="chrome_html" />
<structure name="IDR_WEBUI_CSS_LIST"
@@ -204,6 +366,8 @@ without changes to the corresponding grd file. -->
file="js/parse_html_subset.js" type="chrome_html" />
<structure name="IDR_WEBUI_JS_UTIL"
file="js/util.js" type="chrome_html" flattenhtml="true" />
+ <structure name="IDR_WEBUI_JS_WEBUI_RESOURCE_TEST"
+ file="js/webui_resource_test.js" type="chrome_html" />
<if expr="pp_ifdef('chromeos')">
<structure name="IDR_WEBUI_CSS_UI_ACCOUNT_TWEAKS"
file="css/chromeos/ui_account_tweaks.css"
diff --git a/chromium/ui/webui/web_ui_util.cc b/chromium/ui/webui/web_ui_util.cc
index 44108f759ea..e171da85b4f 100644
--- a/chromium/ui/webui/web_ui_util.cc
+++ b/chromium/ui/webui/web_ui_util.cc
@@ -79,12 +79,12 @@ bool ParseScaleFactor(const base::StringPiece& identifier,
ui::ScaleFactor* scale_factor) {
*scale_factor = ui::SCALE_FACTOR_100P;
if (identifier.empty()) {
- LOG(ERROR) << "Invalid scale factor format: " << identifier;
+ LOG(WARNING) << "Invalid scale factor format: " << identifier;
return false;
}
if (*identifier.rbegin() != 'x') {
- LOG(ERROR) << "Invalid scale factor format: " << identifier;
+ LOG(WARNING) << "Invalid scale factor format: " << identifier;
return false;
}
@@ -92,7 +92,7 @@ bool ParseScaleFactor(const base::StringPiece& identifier,
std::string stripped;
identifier.substr(0, identifier.length() - 1).CopyToString(&stripped);
if (!base::StringToDouble(stripped, &scale)) {
- LOG(ERROR) << "Invalid scale factor format: " << identifier;
+ LOG(WARNING) << "Invalid scale factor format: " << identifier;
return false;
}