OLD | NEW |
1 // Copyright 2012 The Chromium Authors. All rights reserved. | 1 // Copyright 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #import "ios/chrome/browser/ui/toolbar/web_toolbar_controller.h" | 5 #import "ios/chrome/browser/ui/toolbar/web_toolbar_controller.h" |
6 | 6 |
7 #import <CoreLocation/CoreLocation.h> | 7 #import <CoreLocation/CoreLocation.h> |
8 #include <QuartzCore/QuartzCore.h> | 8 #include <QuartzCore/QuartzCore.h> |
9 | 9 |
10 #include <stdint.h> | 10 #include <stdint.h> |
(...skipping 28 matching lines...) Expand all Loading... |
39 #import "ios/chrome/browser/ui/commands/generic_chrome_command.h" | 39 #import "ios/chrome/browser/ui/commands/generic_chrome_command.h" |
40 #include "ios/chrome/browser/ui/commands/ios_command_ids.h" | 40 #include "ios/chrome/browser/ui/commands/ios_command_ids.h" |
41 #import "ios/chrome/browser/ui/history/tab_history_popup_controller.h" | 41 #import "ios/chrome/browser/ui/history/tab_history_popup_controller.h" |
42 #import "ios/chrome/browser/ui/image_util.h" | 42 #import "ios/chrome/browser/ui/image_util.h" |
43 #import "ios/chrome/browser/ui/keyboard/hardware_keyboard_watcher.h" | 43 #import "ios/chrome/browser/ui/keyboard/hardware_keyboard_watcher.h" |
44 #include "ios/chrome/browser/ui/omnibox/location_bar_controller_impl.h" | 44 #include "ios/chrome/browser/ui/omnibox/location_bar_controller_impl.h" |
45 #include "ios/chrome/browser/ui/omnibox/omnibox_view_ios.h" | 45 #include "ios/chrome/browser/ui/omnibox/omnibox_view_ios.h" |
46 #import "ios/chrome/browser/ui/popup_menu/popup_menu_view.h" | 46 #import "ios/chrome/browser/ui/popup_menu/popup_menu_view.h" |
47 #import "ios/chrome/browser/ui/reversed_animation.h" | 47 #import "ios/chrome/browser/ui/reversed_animation.h" |
48 #include "ios/chrome/browser/ui/rtl_geometry.h" | 48 #include "ios/chrome/browser/ui/rtl_geometry.h" |
| 49 #import "ios/chrome/browser/ui/toolbar/keyboard_accessory_view.h" |
49 #import "ios/chrome/browser/ui/toolbar/toolbar_controller+protected.h" | 50 #import "ios/chrome/browser/ui/toolbar/toolbar_controller+protected.h" |
50 #import "ios/chrome/browser/ui/toolbar/toolbar_controller.h" | 51 #import "ios/chrome/browser/ui/toolbar/toolbar_controller.h" |
51 #import "ios/chrome/browser/ui/toolbar/toolbar_model_ios.h" | 52 #import "ios/chrome/browser/ui/toolbar/toolbar_model_ios.h" |
52 #include "ios/chrome/browser/ui/toolbar/toolbar_resource_macros.h" | 53 #include "ios/chrome/browser/ui/toolbar/toolbar_resource_macros.h" |
53 #include "ios/chrome/browser/ui/ui_util.h" | 54 #include "ios/chrome/browser/ui/ui_util.h" |
54 #import "ios/chrome/browser/ui/uikit_ui_util.h" | 55 #import "ios/chrome/browser/ui/uikit_ui_util.h" |
55 #import "ios/chrome/browser/ui/url_loader.h" | 56 #import "ios/chrome/browser/ui/url_loader.h" |
56 #import "ios/chrome/browser/ui/voice/text_to_speech_player.h" | 57 #import "ios/chrome/browser/ui/voice/text_to_speech_player.h" |
57 #import "ios/chrome/browser/ui/voice/voice_search_notification_names.h" | 58 #import "ios/chrome/browser/ui/voice/voice_search_notification_names.h" |
58 #import "ios/chrome/common/material_timing.h" | 59 #import "ios/chrome/common/material_timing.h" |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
108 // displayed. | 109 // displayed. |
109 const CGFloat kBackButtonTrailingPadding = 7.0; | 110 const CGFloat kBackButtonTrailingPadding = 7.0; |
110 const CGFloat kForwardButtonTrailingPadding = -1.0; | 111 const CGFloat kForwardButtonTrailingPadding = -1.0; |
111 const CGFloat kReloadButtonTrailingPadding = 4.0; | 112 const CGFloat kReloadButtonTrailingPadding = 4.0; |
112 | 113 |
113 // Cancel button sizing. | 114 // Cancel button sizing. |
114 const CGFloat kCancelButtonBottomMargin = 4.0; | 115 const CGFloat kCancelButtonBottomMargin = 4.0; |
115 const CGFloat kCancelButtonTopMargin = 4.0; | 116 const CGFloat kCancelButtonTopMargin = 4.0; |
116 const CGFloat kCancelButtonLeadingMargin = 7.0; | 117 const CGFloat kCancelButtonLeadingMargin = 7.0; |
117 const CGFloat kCancelButtonWidth = 40.0; | 118 const CGFloat kCancelButtonWidth = 40.0; |
118 const CGFloat kIpadButtonTitleFontSize = 20.0; | |
119 const CGFloat kIphoneButtonTitleFontSize = 15.0; | |
120 | 119 |
121 // Additional offset to adjust the y coordinate of the determinate progress bar | 120 // Additional offset to adjust the y coordinate of the determinate progress bar |
122 // up by. | 121 // up by. |
123 const CGFloat kDeterminateProgressBarYOffset = 1.0; | 122 const CGFloat kDeterminateProgressBarYOffset = 1.0; |
124 const CGFloat kMaterialProgressBarHeight = 2.0; | 123 const CGFloat kMaterialProgressBarHeight = 2.0; |
125 const CGFloat kLoadCompleteHideProgressBarDelay = 0.5; | 124 const CGFloat kLoadCompleteHideProgressBarDelay = 0.5; |
126 // The default position animation is 10 pixels toward the trailing side, so | 125 // The default position animation is 10 pixels toward the trailing side, so |
127 // that's a negative leading offset. | 126 // that's a negative leading offset. |
128 const LayoutOffset kPositionAnimationLeadingOffset = -10.0; | 127 const LayoutOffset kPositionAnimationLeadingOffset = -10.0; |
129 | 128 |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
215 | 214 |
216 CGRect RectShiftedDownAndResizedForStatusBar(CGRect rect) { | 215 CGRect RectShiftedDownAndResizedForStatusBar(CGRect rect) { |
217 if (IsIPadIdiom()) | 216 if (IsIPadIdiom()) |
218 return rect; | 217 return rect; |
219 rect.size.height -= StatusBarHeight(); | 218 rect.size.height -= StatusBarHeight(); |
220 return RectShiftedDownForStatusBar(rect); | 219 return RectShiftedDownForStatusBar(rect); |
221 } | 220 } |
222 | 221 |
223 } // namespace | 222 } // namespace |
224 | 223 |
225 // View for the accessory view above the keyboard. Subclassed to allow playing | |
226 // input clicks when pressed. | |
227 @interface KeyboardAccessoryView : UIInputView<UIInputViewAudioFeedback> | |
228 @end | |
229 | |
230 @implementation KeyboardAccessoryView | |
231 | |
232 - (BOOL)enableInputClicksWhenVisible { | |
233 return YES; | |
234 } | |
235 | |
236 @end | |
237 | |
238 // TODO(crbug.com/619982) Remove this block and add CAAnimationDelegate when we | 224 // TODO(crbug.com/619982) Remove this block and add CAAnimationDelegate when we |
239 // switch the main bots to Xcode 8. | 225 // switch the main bots to Xcode 8. |
240 #if defined(__IPHONE_10_0) && (__IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_10_0) | 226 #if defined(__IPHONE_10_0) && (__IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_10_0) |
241 @interface WebToolbarController ()<CAAnimationDelegate> | 227 @interface WebToolbarController ()<CAAnimationDelegate, |
| 228 KeyboardAccessoryViewDelegate> |
242 @end | 229 @end |
243 #endif | 230 #endif |
244 | 231 |
245 @interface WebToolbarController ()<LocationBarDelegate, | 232 @interface WebToolbarController ()<LocationBarDelegate, |
246 OmniboxPopupPositioner, | 233 OmniboxPopupPositioner, |
247 ToolbarFrameDelegate> { | 234 ToolbarFrameDelegate> { |
248 // Top-level view for web content. | 235 // Top-level view for web content. |
249 UIView* _webToolbar; | 236 UIView* _webToolbar; |
250 UIButton* _backButton; | 237 UIButton* _backButton; |
251 UIButton* _forwardButton; | 238 UIButton* _forwardButton; |
252 UIButton* _reloadButton; | 239 UIButton* _reloadButton; |
253 UIButton* _stopButton; | 240 UIButton* _stopButton; |
254 UIButton* _starButton; | 241 UIButton* _starButton; |
255 UIButton* _voiceSearchButton; | 242 UIButton* _voiceSearchButton; |
256 OmniboxTextFieldIOS* _omniBox; | 243 OmniboxTextFieldIOS* _omniBox; |
257 UIButton* _cancelButton; | 244 UIButton* _cancelButton; |
258 UIView* _keyBoardAccessoryView; | 245 KeyboardAccessoryView* _keyBoardAccessoryView; |
259 UIButton* _keyboardVoiceSearchButton; | |
260 // Progress bar used to show what fraction of the page has loaded. | 246 // Progress bar used to show what fraction of the page has loaded. |
261 MDCProgressView* _determinateProgressView; | 247 MDCProgressView* _determinateProgressView; |
262 UIImageView* _omniboxBackground; | 248 UIImageView* _omniboxBackground; |
263 BOOL _prerenderAnimating; | 249 BOOL _prerenderAnimating; |
264 UIImageView* _incognitoIcon; | 250 UIImageView* _incognitoIcon; |
265 UIView* _clippingView; | 251 UIView* _clippingView; |
266 | 252 |
267 std::unique_ptr<LocationBarController> _locationBar; | 253 std::unique_ptr<LocationBarController> _locationBar; |
268 BOOL _initialLayoutComplete; | 254 BOOL _initialLayoutComplete; |
269 // If |YES|, toolbar is incognito. | 255 // If |YES|, toolbar is incognito. |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
337 // Received when a TTS player has received audio data. | 323 // Received when a TTS player has received audio data. |
338 - (void)audioReadyForPlayback:(NSNotification*)notification; | 324 - (void)audioReadyForPlayback:(NSNotification*)notification; |
339 // Updates the TTS button depending on whether or not TTS is currently playing. | 325 // Updates the TTS button depending on whether or not TTS is currently playing. |
340 - (void)updateIsTTSPlaying:(NSNotification*)notify; | 326 - (void)updateIsTTSPlaying:(NSNotification*)notify; |
341 // Moves VoiceOver to the button used to perform a voice search. | 327 // Moves VoiceOver to the button used to perform a voice search. |
342 - (void)moveVoiceOverToVoiceSearchButton; | 328 - (void)moveVoiceOverToVoiceSearchButton; |
343 // Fade in and out toolbar items as the frame moves off screen. | 329 // Fade in and out toolbar items as the frame moves off screen. |
344 - (void)updateToolbarAlphaForFrame:(CGRect)frame; | 330 - (void)updateToolbarAlphaForFrame:(CGRect)frame; |
345 // Navigate to |query| from omnibox. | 331 // Navigate to |query| from omnibox. |
346 - (void)loadURLForQuery:(NSString*)query; | 332 - (void)loadURLForQuery:(NSString*)query; |
347 - (UIView*)keyboardButtonWithTitle:(NSString*)title frame:(CGRect)frame; | |
348 // Lazily instantiate the keyboard accessory view. | 333 // Lazily instantiate the keyboard accessory view. |
349 - (UIView*)keyboardAccessoryView; | 334 - (UIView*)keyboardAccessoryView; |
350 - (void)preloadVoiceSearch:(id)sender; | 335 - (void)preloadVoiceSearch:(id)sender; |
351 // Calculates the CGRect to use for the omnibox's frame. Also sets the frames | 336 // Calculates the CGRect to use for the omnibox's frame. Also sets the frames |
352 // of some buttons and |_webToolbar|. | 337 // of some buttons and |_webToolbar|. |
353 - (CGRect)newOmniboxFrame; | 338 - (CGRect)newOmniboxFrame; |
354 - (void)animateMaterialOmnibox; | 339 - (void)animateMaterialOmnibox; |
355 - (void)fadeInOmniboxTrailingView; | 340 - (void)fadeInOmniboxTrailingView; |
356 - (void)fadeInOmniboxLeadingView; | 341 - (void)fadeInOmniboxLeadingView; |
357 - (void)fadeOutOmniboxTrailingView; | 342 - (void)fadeOutOmniboxTrailingView; |
358 - (void)fadeOutOmniboxLeadingView; | 343 - (void)fadeOutOmniboxLeadingView; |
359 - (void)fadeInIncognitoIcon; | 344 - (void)fadeInIncognitoIcon; |
360 - (void)fadeOutIncognitoIcon; | 345 - (void)fadeOutIncognitoIcon; |
361 // Fade in the visible navigation buttons. | 346 // Fade in the visible navigation buttons. |
362 - (void)fadeInNavigationControls; | 347 - (void)fadeInNavigationControls; |
363 // Fade out the visible navigation buttons. | 348 // Fade out the visible navigation buttons. |
364 - (void)fadeOutNavigationControls; | 349 - (void)fadeOutNavigationControls; |
365 // When the collapse animation is complete, hide the Material background and | 350 // When the collapse animation is complete, hide the Material background and |
366 // restore the omnibox's background image. | 351 // restore the omnibox's background image. |
367 - (void)animationDidStop:(CAAnimation*)anim finished:(BOOL)flag; | 352 - (void)animationDidStop:(CAAnimation*)anim finished:(BOOL)flag; |
368 - (void)updateSnapshotWithWidth:(CGFloat)width forced:(BOOL)force; | 353 - (void)updateSnapshotWithWidth:(CGFloat)width forced:(BOOL)force; |
369 // Insert 'com' without the period if cursor is directly after a period. | 354 // Insert 'com' without the period if cursor is directly after a period. |
370 - (NSString*)updateTextForDotCom:(NSString*)text; | 355 - (NSString*)updateTextForDotCom:(NSString*)text; |
371 // Handle the user pressing a key in the keyboard accessory view. | |
372 - (void)pressKey:(id)sender; | |
373 @end | 356 @end |
374 | 357 |
375 @implementation WebToolbarController | 358 @implementation WebToolbarController |
376 | 359 |
377 @synthesize delegate = _delegate; | 360 @synthesize delegate = _delegate; |
378 @synthesize urlLoader = _urlLoader; | 361 @synthesize urlLoader = _urlLoader; |
379 | 362 |
380 - (instancetype)initWithDelegate:(id<WebToolbarDelegate>)delegate | 363 - (instancetype)initWithDelegate:(id<WebToolbarDelegate>)delegate |
381 urlLoader:(id<UrlLoader>)urlLoader | 364 urlLoader:(id<UrlLoader>)urlLoader |
382 browserState:(ios::ChromeBrowserState*)browserState | 365 browserState:(ios::ChromeBrowserState*)browserState |
(...skipping 502 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
885 if (IsIPadIdiom()) { | 868 if (IsIPadIdiom()) { |
886 // Update toolbar accessory views. | 869 // Update toolbar accessory views. |
887 BOOL isCompactTabletView = IsCompactTablet(self.view); | 870 BOOL isCompactTabletView = IsCompactTablet(self.view); |
888 [_voiceSearchButton setHidden:isCompactTabletView]; | 871 [_voiceSearchButton setHidden:isCompactTabletView]; |
889 [_starButton setHidden:isCompactTabletView]; | 872 [_starButton setHidden:isCompactTabletView]; |
890 [_reloadButton setHidden:isCompactTabletView]; | 873 [_reloadButton setHidden:isCompactTabletView]; |
891 [_stopButton setHidden:isCompactTabletView]; | 874 [_stopButton setHidden:isCompactTabletView]; |
892 [self updateToolbarState]; | 875 [self updateToolbarState]; |
893 | 876 |
894 // Update keyboard accessory views. | 877 // Update keyboard accessory views. |
895 BOOL hidden = [_keyboardVoiceSearchButton isHidden]; | 878 auto mode = _keyBoardAccessoryView.mode; |
896 _keyBoardAccessoryView = nil; | 879 _keyBoardAccessoryView = nil; |
897 [_omniBox setInputAccessoryView:[self keyboardAccessoryView]]; | 880 [_omniBox setInputAccessoryView:[self keyboardAccessoryView]]; |
898 [_keyboardVoiceSearchButton setHidden:hidden]; | 881 _keyBoardAccessoryView.mode = mode; |
899 if ([_omniBox isFirstResponder]) { | 882 if ([_omniBox isFirstResponder]) { |
900 [_omniBox reloadInputViews]; | 883 [_omniBox reloadInputViews]; |
901 } | 884 } |
902 | 885 |
903 // Re-layout toolbar and omnibox. | 886 // Re-layout toolbar and omnibox. |
904 [_webToolbar setFrame:[self specificControlsArea]]; | 887 [_webToolbar setFrame:[self specificControlsArea]]; |
905 [self layoutOmnibox]; | 888 [self layoutOmnibox]; |
906 } | 889 } |
907 } | 890 } |
908 | 891 |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
961 if (sender == _backButton) { | 944 if (sender == _backButton) { |
962 base::RecordAction(UserMetricsAction("MobileToolbarBack")); | 945 base::RecordAction(UserMetricsAction("MobileToolbarBack")); |
963 } else if (sender == _forwardButton) { | 946 } else if (sender == _forwardButton) { |
964 base::RecordAction(UserMetricsAction("MobileToolbarForward")); | 947 base::RecordAction(UserMetricsAction("MobileToolbarForward")); |
965 } else if (sender == _reloadButton) { | 948 } else if (sender == _reloadButton) { |
966 base::RecordAction(UserMetricsAction("MobileToolbarReload")); | 949 base::RecordAction(UserMetricsAction("MobileToolbarReload")); |
967 } else if (sender == _stopButton) { | 950 } else if (sender == _stopButton) { |
968 base::RecordAction(UserMetricsAction("MobileToolbarStop")); | 951 base::RecordAction(UserMetricsAction("MobileToolbarStop")); |
969 } else if (sender == _voiceSearchButton) { | 952 } else if (sender == _voiceSearchButton) { |
970 base::RecordAction(UserMetricsAction("MobileToolbarVoiceSearch")); | 953 base::RecordAction(UserMetricsAction("MobileToolbarVoiceSearch")); |
971 } else if (sender == _keyboardVoiceSearchButton) { | |
972 base::RecordAction(UserMetricsAction("MobileCustomRowVoiceSearch")); | |
973 } else if (sender == _starButton) { | 954 } else if (sender == _starButton) { |
974 base::RecordAction(UserMetricsAction("MobileToolbarToggleBookmark")); | 955 base::RecordAction(UserMetricsAction("MobileToolbarToggleBookmark")); |
975 } else { | 956 } else { |
976 [super recordUserMetrics:sender]; | 957 [super recordUserMetrics:sender]; |
977 } | 958 } |
978 } | 959 } |
979 | 960 |
980 - (IBAction)stackButtonTouchDown:(id)sender { | 961 - (IBAction)stackButtonTouchDown:(id)sender { |
981 [self.delegate prepareToEnterTabSwitcher:self]; | 962 [self.delegate prepareToEnterTabSwitcher:self]; |
982 } | 963 } |
(...skipping 290 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1273 kLocationAuthorizationStatusCount); | 1254 kLocationAuthorizationStatusCount); |
1274 } | 1255 } |
1275 } | 1256 } |
1276 [self cancelOmniboxEdit]; | 1257 [self cancelOmniboxEdit]; |
1277 } | 1258 } |
1278 | 1259 |
1279 - (void)locationBarHasBecomeFirstResponder { | 1260 - (void)locationBarHasBecomeFirstResponder { |
1280 [self.delegate locationBarDidBecomeFirstResponder:self]; | 1261 [self.delegate locationBarDidBecomeFirstResponder:self]; |
1281 [self animateMaterialOmnibox]; | 1262 [self animateMaterialOmnibox]; |
1282 | 1263 |
1283 [_keyboardVoiceSearchButton setHidden:NO]; | 1264 _keyBoardAccessoryView.mode = VOICE_SEARCH; |
1284 | 1265 |
1285 // Record the appropriate user action for focusing the omnibox. | 1266 // Record the appropriate user action for focusing the omnibox. |
1286 web::WebState* webState = [self.delegate currentWebState]; | 1267 web::WebState* webState = [self.delegate currentWebState]; |
1287 if (webState) { | 1268 if (webState) { |
1288 if (webState->GetVisibleURL() == GURL(kChromeUINewTabURL)) { | 1269 if (webState->GetVisibleURL() == GURL(kChromeUINewTabURL)) { |
1289 OmniboxEditModel* model = _locationBar->GetLocationEntry()->model(); | 1270 OmniboxEditModel* model = _locationBar->GetLocationEntry()->model(); |
1290 if (model->is_caret_visible()) { | 1271 if (model->is_caret_visible()) { |
1291 base::RecordAction( | 1272 base::RecordAction( |
1292 base::UserMetricsAction("MobileFocusedOmniboxOnNtp")); | 1273 base::UserMetricsAction("MobileFocusedOmniboxOnNtp")); |
1293 } else { | 1274 } else { |
(...skipping 17 matching lines...) Expand all Loading... |
1311 } | 1292 } |
1312 | 1293 |
1313 - (void)locationBarChanged { | 1294 - (void)locationBarChanged { |
1314 // Hide the voice search button once the user starts editing the omnibox but | 1295 // Hide the voice search button once the user starts editing the omnibox but |
1315 // show it if the omnibox is empty. | 1296 // show it if the omnibox is empty. |
1316 bool isEditingOrEmpty = _locationBar->GetLocationEntry()->IsEditingOrEmpty(); | 1297 bool isEditingOrEmpty = _locationBar->GetLocationEntry()->IsEditingOrEmpty(); |
1317 BOOL editingAndNotEmpty = isEditingOrEmpty && _omniBox.text.length != 0; | 1298 BOOL editingAndNotEmpty = isEditingOrEmpty && _omniBox.text.length != 0; |
1318 // If the voice search button is visible but about to be hidden (i.e. | 1299 // If the voice search button is visible but about to be hidden (i.e. |
1319 // the omnibox is no longer empty) then this is the first omnibox text so | 1300 // the omnibox is no longer empty) then this is the first omnibox text so |
1320 // record a user action. | 1301 // record a user action. |
1321 if (![_keyboardVoiceSearchButton isHidden] && editingAndNotEmpty) { | 1302 if (_keyBoardAccessoryView.mode == VOICE_SEARCH && editingAndNotEmpty) { |
1322 base::RecordAction(UserMetricsAction("MobileFirstTextInOmnibox")); | 1303 base::RecordAction(UserMetricsAction("MobileFirstTextInOmnibox")); |
1323 } | 1304 } |
1324 [_keyboardVoiceSearchButton setHidden:editingAndNotEmpty]; | 1305 if (editingAndNotEmpty) { |
| 1306 _keyBoardAccessoryView.mode = KEY_SHORTCUTS; |
| 1307 } else { |
| 1308 _keyBoardAccessoryView.mode = VOICE_SEARCH; |
| 1309 } |
1325 } | 1310 } |
1326 | 1311 |
1327 - (web::WebState*)getWebState { | 1312 - (web::WebState*)getWebState { |
1328 return [self.delegate currentWebState]; | 1313 return [self.delegate currentWebState]; |
1329 } | 1314 } |
1330 | 1315 |
1331 - (ToolbarModel*)toolbarModel { | 1316 - (ToolbarModel*)toolbarModel { |
1332 ToolbarModelIOS* toolbarModelIOS = [self.delegate toolbarModelIOS]; | 1317 ToolbarModelIOS* toolbarModelIOS = [self.delegate toolbarModelIOS]; |
1333 return toolbarModelIOS ? toolbarModelIOS->GetToolbarModel() : nullptr; | 1318 return toolbarModelIOS ? toolbarModelIOS->GetToolbarModel() : nullptr; |
1334 } | 1319 } |
(...skipping 131 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1466 [self focusOmnibox]; | 1451 [self focusOmnibox]; |
1467 [_omniBox insertTextWhileEditing:result]; | 1452 [_omniBox insertTextWhileEditing:result]; |
1468 // Notify the accessibility system to start reading the new contents of the | 1453 // Notify the accessibility system to start reading the new contents of the |
1469 // Omnibox. | 1454 // Omnibox. |
1470 UIAccessibilityPostNotification(UIAccessibilityScreenChangedNotification, | 1455 UIAccessibilityPostNotification(UIAccessibilityScreenChangedNotification, |
1471 _omniBox); | 1456 _omniBox); |
1472 } | 1457 } |
1473 } | 1458 } |
1474 | 1459 |
1475 #pragma mark - | 1460 #pragma mark - |
| 1461 #pragma mark KeyboardAccessoryViewDelegate |
| 1462 |
| 1463 - (void)keyboardAccessoryVoiceSearchTouchDown { |
| 1464 if (ios::GetChromeBrowserProvider() |
| 1465 ->GetVoiceSearchProvider() |
| 1466 ->IsVoiceSearchEnabled()) { |
| 1467 [self preloadVoiceSearch:_keyBoardAccessoryView]; |
| 1468 } |
| 1469 } |
| 1470 |
| 1471 - (void)keyboardAccessoryVoiceSearchTouchUpInside { |
| 1472 if (ios::GetChromeBrowserProvider() |
| 1473 ->GetVoiceSearchProvider() |
| 1474 ->IsVoiceSearchEnabled()) { |
| 1475 base::RecordAction(UserMetricsAction("MobileCustomRowVoiceSearch")); |
| 1476 GenericChromeCommand* command = |
| 1477 [[GenericChromeCommand alloc] initWithTag:IDC_VOICE_SEARCH]; |
| 1478 [_keyBoardAccessoryView chromeExecuteCommand:command]; |
| 1479 } else { |
| 1480 _keyBoardAccessoryView.mode = KEY_SHORTCUTS; |
| 1481 } |
| 1482 } |
| 1483 |
| 1484 - (void)keyPressed:(NSString*)title { |
| 1485 NSString* text = [self updateTextForDotCom:title]; |
| 1486 [_omniBox insertTextWhileEditing:text]; |
| 1487 } |
| 1488 |
| 1489 #pragma mark - |
1476 #pragma mark Private methods. | 1490 #pragma mark Private methods. |
1477 | 1491 |
1478 - (UIButton*)cancelButton { | 1492 - (UIButton*)cancelButton { |
1479 if (_cancelButton) | 1493 if (_cancelButton) |
1480 return _cancelButton; | 1494 return _cancelButton; |
1481 _cancelButton = [UIButton buttonWithType:UIButtonTypeCustom]; | 1495 _cancelButton = [UIButton buttonWithType:UIButtonTypeCustom]; |
1482 NSString* collapseName = _incognito ? @"collapse_incognito" : @"collapse"; | 1496 NSString* collapseName = _incognito ? @"collapse_incognito" : @"collapse"; |
1483 [_cancelButton setImage:[UIImage imageNamed:collapseName] | 1497 [_cancelButton setImage:[UIImage imageNamed:collapseName] |
1484 forState:UIControlStateNormal]; | 1498 forState:UIControlStateNormal]; |
1485 NSString* collapsePressedName = | 1499 NSString* collapsePressedName = |
(...skipping 334 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1820 // URL. | 1834 // URL. |
1821 ui::PageTransition transition = ui::PageTransitionFromInt( | 1835 ui::PageTransition transition = ui::PageTransitionFromInt( |
1822 ui::PAGE_TRANSITION_LINK | ui::PAGE_TRANSITION_FROM_ADDRESS_BAR); | 1836 ui::PAGE_TRANSITION_LINK | ui::PAGE_TRANSITION_FROM_ADDRESS_BAR); |
1823 [self.urlLoader loadURL:GURL(searchURL) | 1837 [self.urlLoader loadURL:GURL(searchURL) |
1824 referrer:web::Referrer() | 1838 referrer:web::Referrer() |
1825 transition:transition | 1839 transition:transition |
1826 rendererInitiated:NO]; | 1840 rendererInitiated:NO]; |
1827 } | 1841 } |
1828 } | 1842 } |
1829 | 1843 |
1830 - (UIView*)keyboardButtonWithTitle:(NSString*)title frame:(CGRect)frame { | 1844 - (UIView*)keyboardAccessoryView { |
1831 UIButton* button = [UIButton buttonWithType:UIButtonTypeCustom]; | 1845 if (!_keyBoardAccessoryView) { |
1832 UIFont* font = nil; | 1846 NSArray<NSString*>* buttonTitles = |
1833 UIImage* backgroundImage = nil; | 1847 [NSArray arrayWithObjects:@":", @".", @"-", @"/", kDotComTLD, nil]; |
1834 if (IsIPadIdiom()) { | 1848 _keyBoardAccessoryView = |
1835 font = GetUIFont(FONT_HELVETICA, false, kIpadButtonTitleFontSize); | 1849 [[KeyboardAccessoryView alloc] initWithButtons:buttonTitles |
1836 } else { | 1850 delegate:self]; |
1837 font = GetUIFont(FONT_HELVETICA, true, kIphoneButtonTitleFontSize); | 1851 [_keyBoardAccessoryView |
| 1852 setAutoresizingMask:UIViewAutoresizingFlexibleWidth]; |
| 1853 _hardwareKeyboardWatcher = [[HardwareKeyboardWatcher alloc] |
| 1854 initWithAccessoryView:_keyBoardAccessoryView]; |
1838 } | 1855 } |
1839 // TODO(leng): Consider moving these images to pak files as well. | |
1840 backgroundImage = [UIImage imageNamed:@"keyboard_button"]; | |
1841 | |
1842 button.frame = frame; | |
1843 [button setTitle:title forState:UIControlStateNormal]; | |
1844 [button setTitleColor:[UIColor blackColor] forState:UIControlStateNormal]; | |
1845 [button.titleLabel setFont:font]; | |
1846 [button setBackgroundImage:backgroundImage forState:UIControlStateNormal]; | |
1847 [button addTarget:self | |
1848 action:@selector(pressKey:) | |
1849 forControlEvents:UIControlEventTouchUpInside]; | |
1850 button.isAccessibilityElement = YES; | |
1851 [button setAccessibilityLabel:title]; | |
1852 | |
1853 return button; | |
1854 } | |
1855 | |
1856 - (UIView*)keyboardAccessoryView { | |
1857 const CGFloat kViewHeightTablet = 70.0; | |
1858 const CGFloat kViewHeightPhone = 43.0; | |
1859 const CGFloat kButtonInset = 5.0; | |
1860 const CGFloat kButtonSizeXTablet = 61.0; | |
1861 const CGFloat kButtonSizeXPhone = 46.0; | |
1862 const CGFloat kButtonSizeYTablet = 62.0; | |
1863 const CGFloat kButtonSizeYPhone = 35.0; | |
1864 const CGFloat kBetweenButtonSpacing = 15.0; | |
1865 const CGFloat kBetweenButtonSpacingPhone = 7.0; | |
1866 | |
1867 if (_keyBoardAccessoryView) | |
1868 return _keyBoardAccessoryView; | |
1869 | |
1870 const BOOL isTablet = IsIPadIdiom() && !IsCompactTablet(self.view); | |
1871 | |
1872 // TODO(pinkerton): purge this view when low memory. | |
1873 CGFloat width = [[UIScreen mainScreen] bounds].size.width; | |
1874 CGFloat height = isTablet ? kViewHeightTablet : kViewHeightPhone; | |
1875 CGRect frame = CGRectMake(0.0, 0.0, width, height); | |
1876 | |
1877 _keyBoardAccessoryView = | |
1878 [[KeyboardAccessoryView alloc] initWithFrame:frame | |
1879 inputViewStyle:UIInputViewStyleKeyboard]; | |
1880 [_keyBoardAccessoryView setAutoresizingMask:UIViewAutoresizingFlexibleWidth]; | |
1881 | |
1882 NSArray* buttonTitles = | |
1883 [NSArray arrayWithObjects:@":", @".", @"-", @"/", kDotComTLD, nil]; | |
1884 | |
1885 // Center buttons in available space by placing them within a parent view | |
1886 // that auto-centers. | |
1887 CGFloat betweenButtonSpacing = | |
1888 isTablet ? kBetweenButtonSpacing : kBetweenButtonSpacingPhone; | |
1889 const CGFloat buttonWidth = isTablet ? kButtonSizeXTablet : kButtonSizeXPhone; | |
1890 | |
1891 CGFloat totalWidth = (buttonTitles.count * buttonWidth) + | |
1892 ((buttonTitles.count - 1) * betweenButtonSpacing); | |
1893 CGFloat indent = floor((width - totalWidth) / 2.0); | |
1894 if (indent < kButtonInset) | |
1895 indent = kButtonInset; | |
1896 CGRect parentViewRect = CGRectMake(indent, 0.0, totalWidth, height); | |
1897 UIView* parentView = [[UIView alloc] initWithFrame:parentViewRect]; | |
1898 [parentView setAutoresizingMask:UIViewAutoresizingFlexibleLeftMargin | | |
1899 UIViewAutoresizingFlexibleRightMargin]; | |
1900 [_keyBoardAccessoryView addSubview:parentView]; | |
1901 | |
1902 // Create the buttons, starting at the left edge of |parentView|. | |
1903 CGRect currentFrame = | |
1904 CGRectMake(0.0, kButtonInset, buttonWidth, | |
1905 isTablet ? kButtonSizeYTablet : kButtonSizeYPhone); | |
1906 | |
1907 for (NSString* title in buttonTitles) { | |
1908 UIView* button = [self keyboardButtonWithTitle:title frame:currentFrame]; | |
1909 [parentView addSubview:button]; | |
1910 currentFrame.origin.x = CGRectGetMaxX(currentFrame) + betweenButtonSpacing; | |
1911 } | |
1912 | |
1913 // Create the voice search button and add it to _keyBoardAccessoryView over | |
1914 // the text buttons. | |
1915 _keyboardVoiceSearchButton = [UIButton buttonWithType:UIButtonTypeCustom]; | |
1916 [_keyboardVoiceSearchButton | |
1917 setAutoresizingMask:UIViewAutoresizingFlexibleWidth]; | |
1918 [_keyboardVoiceSearchButton setTag:IDC_VOICE_SEARCH]; | |
1919 SetA11yLabelAndUiAutomationName(_keyboardVoiceSearchButton, | |
1920 IDS_IOS_ACCNAME_VOICE_SEARCH, | |
1921 @"Voice Search"); | |
1922 // TODO(leng): Consider moving these icons into a pak file. | |
1923 UIImage* voiceRow = [UIImage imageNamed:@"custom_row_voice"]; | |
1924 UIImage* voiceRowPressed = [UIImage imageNamed:@"custom_row_voice_pressed"]; | |
1925 [_keyboardVoiceSearchButton setBackgroundImage:voiceRow | |
1926 forState:UIControlStateNormal]; | |
1927 [_keyboardVoiceSearchButton setBackgroundImage:voiceRowPressed | |
1928 forState:UIControlStateHighlighted]; | |
1929 | |
1930 UIImage* voiceIcon = [UIImage imageNamed:@"voice_icon_keyboard_accessory"]; | |
1931 [_keyboardVoiceSearchButton setAdjustsImageWhenHighlighted:NO]; | |
1932 [_keyboardVoiceSearchButton setImage:voiceIcon forState:UIControlStateNormal]; | |
1933 [_keyboardVoiceSearchButton setFrame:[_keyBoardAccessoryView bounds]]; | |
1934 | |
1935 // Only add the voice search actions if voice search is enabled. | |
1936 if (ios::GetChromeBrowserProvider() | |
1937 ->GetVoiceSearchProvider() | |
1938 ->IsVoiceSearchEnabled()) { | |
1939 [_keyboardVoiceSearchButton addTarget:self | |
1940 action:@selector(recordUserMetrics:) | |
1941 forControlEvents:UIControlEventTouchUpInside]; | |
1942 [_keyboardVoiceSearchButton addTarget:_keyboardVoiceSearchButton | |
1943 action:@selector(chromeExecuteCommand:) | |
1944 forControlEvents:UIControlEventTouchUpInside]; | |
1945 [_keyboardVoiceSearchButton addTarget:self | |
1946 action:@selector(preloadVoiceSearch:) | |
1947 forControlEvents:UIControlEventTouchDown]; | |
1948 } else { | |
1949 [_keyboardVoiceSearchButton addTarget:self | |
1950 action:@selector(ignoreVoiceSearch:) | |
1951 forControlEvents:UIControlEventTouchUpInside]; | |
1952 } | |
1953 | |
1954 [_keyBoardAccessoryView addSubview:_keyboardVoiceSearchButton]; | |
1955 | |
1956 // Reset the external keyboard watcher. | |
1957 _hardwareKeyboardWatcher = [[HardwareKeyboardWatcher alloc] | |
1958 initWithAccessoryView:_keyBoardAccessoryView]; | |
1959 | |
1960 return _keyBoardAccessoryView; | 1856 return _keyBoardAccessoryView; |
1961 } | 1857 } |
1962 | 1858 |
1963 - (void)preloadVoiceSearch:(id)sender { | 1859 - (void)preloadVoiceSearch:(id)sender { |
1964 DCHECK(ios::GetChromeBrowserProvider() | 1860 DCHECK(ios::GetChromeBrowserProvider() |
1965 ->GetVoiceSearchProvider() | 1861 ->GetVoiceSearchProvider() |
1966 ->IsVoiceSearchEnabled()); | 1862 ->IsVoiceSearchEnabled()); |
1967 [sender removeTarget:self | |
1968 action:@selector(preloadVoiceSearch:) | |
1969 forControlEvents:UIControlEventTouchDown]; | |
1970 | |
1971 // Use a GenericChromeCommand because |sender| already has a tag set for a | 1863 // Use a GenericChromeCommand because |sender| already has a tag set for a |
1972 // different command. | 1864 // different command. |
1973 GenericChromeCommand* command = | 1865 GenericChromeCommand* command = |
1974 [[GenericChromeCommand alloc] initWithTag:IDC_PRELOAD_VOICE_SEARCH]; | 1866 [[GenericChromeCommand alloc] initWithTag:IDC_PRELOAD_VOICE_SEARCH]; |
1975 [sender chromeExecuteCommand:command]; | 1867 [sender chromeExecuteCommand:command]; |
1976 } | 1868 } |
1977 | 1869 |
1978 // Called when the keyboard voice search button is tapped with voice search | |
1979 // disabled. Hides the voice search button but takes no other action. | |
1980 - (void)ignoreVoiceSearch:(id)sender { | |
1981 [_keyboardVoiceSearchButton setHidden:YES]; | |
1982 } | |
1983 | |
1984 - (CGFloat)omniboxLeading { | 1870 - (CGFloat)omniboxLeading { |
1985 // Compute what the leading (x-origin) position for the omniboox should be | 1871 // Compute what the leading (x-origin) position for the omniboox should be |
1986 // based on what other controls are active. | 1872 // based on what other controls are active. |
1987 InterfaceIdiom idiom = IsIPadIdiom() ? IPAD_IDIOM : IPHONE_IDIOM; | 1873 InterfaceIdiom idiom = IsIPadIdiom() ? IPAD_IDIOM : IPHONE_IDIOM; |
1988 | 1874 |
1989 CGFloat trailingPadding = 0.0; | 1875 CGFloat trailingPadding = 0.0; |
1990 | 1876 |
1991 LayoutRect leadingControlLayout = LayoutRectForRectInBoundingRect( | 1877 LayoutRect leadingControlLayout = LayoutRectForRectInBoundingRect( |
1992 [_backButton frame], [_webToolbar bounds]); | 1878 [_backButton frame], [_webToolbar bounds]); |
1993 LayoutRect forwardButtonLayout = | 1879 LayoutRect forwardButtonLayout = |
(...skipping 529 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2523 if ([text isEqualToString:kDotComTLD]) { | 2409 if ([text isEqualToString:kDotComTLD]) { |
2524 UITextRange* textRange = [_omniBox selectedTextRange]; | 2410 UITextRange* textRange = [_omniBox selectedTextRange]; |
2525 NSInteger pos = [_omniBox offsetFromPosition:[_omniBox beginningOfDocument] | 2411 NSInteger pos = [_omniBox offsetFromPosition:[_omniBox beginningOfDocument] |
2526 toPosition:textRange.start]; | 2412 toPosition:textRange.start]; |
2527 if (pos > 0 && [[_omniBox text] characterAtIndex:pos - 1] == '.') | 2413 if (pos > 0 && [[_omniBox text] characterAtIndex:pos - 1] == '.') |
2528 return [kDotComTLD substringFromIndex:1]; | 2414 return [kDotComTLD substringFromIndex:1]; |
2529 } | 2415 } |
2530 return text; | 2416 return text; |
2531 } | 2417 } |
2532 | 2418 |
2533 - (void)pressKey:(id)sender { | |
2534 DCHECK([sender isKindOfClass:[UIButton class]]); | |
2535 [[UIDevice currentDevice] playInputClick]; | |
2536 NSString* text = [self updateTextForDotCom:[sender currentTitle]]; | |
2537 [_omniBox insertTextWhileEditing:text]; | |
2538 } | |
2539 | |
2540 @end | 2419 @end |
2541 | 2420 |
2542 @implementation WebToolbarController (Testing) | 2421 @implementation WebToolbarController (Testing) |
2543 | 2422 |
2544 - (BOOL)isForwardButtonEnabled { | 2423 - (BOOL)isForwardButtonEnabled { |
2545 return [_forwardButton isEnabled]; | 2424 return [_forwardButton isEnabled]; |
2546 } | 2425 } |
2547 | 2426 |
2548 - (BOOL)isBackButtonEnabled { | 2427 - (BOOL)isBackButtonEnabled { |
2549 return [_backButton isEnabled]; | 2428 return [_backButton isEnabled]; |
(...skipping 21 matching lines...) Expand all Loading... |
2571 | 2450 |
2572 - (BOOL)isPrerenderAnimationRunning { | 2451 - (BOOL)isPrerenderAnimationRunning { |
2573 return _prerenderAnimating; | 2452 return _prerenderAnimating; |
2574 } | 2453 } |
2575 | 2454 |
2576 - (OmniboxTextFieldIOS*)omnibox { | 2455 - (OmniboxTextFieldIOS*)omnibox { |
2577 return _omniBox; | 2456 return _omniBox; |
2578 } | 2457 } |
2579 | 2458 |
2580 @end | 2459 @end |
OLD | NEW |