Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(130)

Side by Side Diff: ios/chrome/browser/ui/payments/payment_request_edit_view_controller.mm

Issue 2908033002: [Payment Request] Refactors edit view controller (Closed)
Patch Set: Initial Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2017 The Chromium Authors. All rights reserved. 1 // Copyright 2017 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/payments/payment_request_edit_view_controller.h" 5 #import "ios/chrome/browser/ui/payments/payment_request_edit_view_controller.h"
6 6
7 #include "base/logging.h" 7 #include "base/logging.h"
8 #import "base/mac/foundation_util.h" 8 #import "base/mac/foundation_util.h"
9 #include "base/strings/sys_string_conversions.h" 9 #include "base/strings/sys_string_conversions.h"
10 #include "components/strings/grit/components_strings.h" 10 #include "components/strings/grit/components_strings.h"
11 #import "ios/chrome/browser/ui/autofill/autofill_edit_accessory_view.h" 11 #import "ios/chrome/browser/ui/autofill/autofill_edit_accessory_view.h"
12 #import "ios/chrome/browser/ui/autofill/cells/autofill_edit_item.h" 12 #import "ios/chrome/browser/ui/autofill/cells/autofill_edit_item.h"
13 #import "ios/chrome/browser/ui/collection_view/cells/MDCCollectionViewCell+Chrom e.h" 13 #import "ios/chrome/browser/ui/collection_view/cells/MDCCollectionViewCell+Chrom e.h"
14 #import "ios/chrome/browser/ui/collection_view/cells/collection_view_footer_item .h" 14 #import "ios/chrome/browser/ui/collection_view/cells/collection_view_footer_item .h"
15 #import "ios/chrome/browser/ui/collection_view/cells/collection_view_item+collec tion_view_controller.h" 15 #import "ios/chrome/browser/ui/collection_view/cells/collection_view_item+collec tion_view_controller.h"
16 #import "ios/chrome/browser/ui/collection_view/cells/collection_view_switch_item .h"
16 #import "ios/chrome/browser/ui/colors/MDCPalette+CrAdditions.h" 17 #import "ios/chrome/browser/ui/colors/MDCPalette+CrAdditions.h"
17 #import "ios/chrome/browser/ui/payments/cells/payments_selector_edit_item.h" 18 #import "ios/chrome/browser/ui/payments/cells/payments_selector_edit_item.h"
18 #import "ios/chrome/browser/ui/payments/cells/payments_text_item.h" 19 #import "ios/chrome/browser/ui/payments/cells/payments_text_item.h"
19 #import "ios/chrome/browser/ui/payments/payment_request_edit_view_controller+int ernal.h" 20 #import "ios/chrome/browser/ui/payments/payment_request_edit_view_controller_act ions.h"
20 #import "ios/chrome/browser/ui/payments/payment_request_editor_field.h" 21 #import "ios/chrome/browser/ui/payments/payment_request_editor_field.h"
21 #import "ios/chrome/browser/ui/uikit_ui_util.h" 22 #import "ios/chrome/browser/ui/uikit_ui_util.h"
22 #include "ios/chrome/grit/ios_theme_resources.h" 23 #include "ios/chrome/grit/ios_theme_resources.h"
23 #import "ios/third_party/material_components_ios/src/components/Typography/src/M aterialTypography.h" 24 #import "ios/third_party/material_components_ios/src/components/Typography/src/M aterialTypography.h"
24 #include "ui/base/l10n/l10n_util.h" 25 #include "ui/base/l10n/l10n_util.h"
25 26
26 #if !defined(__has_feature) || !__has_feature(objc_arc) 27 #if !defined(__has_feature) || !__has_feature(objc_arc)
27 #error "This file requires ARC support." 28 #error "This file requires ARC support."
28 #endif 29 #endif
29 30
(...skipping 15 matching lines...) Expand all
45 AutofillEditCell* cell = base::mac::ObjCCast<AutofillEditCell>(view); 46 AutofillEditCell* cell = base::mac::ObjCCast<AutofillEditCell>(view);
46 if (cell) 47 if (cell)
47 return cell; 48 return cell;
48 } 49 }
49 50
50 // There has to be a cell associated with this text field. 51 // There has to be a cell associated with this text field.
51 NOTREACHED(); 52 NOTREACHED();
52 return nil; 53 return nil;
53 } 54 }
54 55
56 CollectionViewSwitchCell* CollectionViewSwitchCellForSwitchField(
57 UISwitch* switchField) {
58 for (UIView* view = switchField; view; view = [view superview]) {
59 CollectionViewSwitchCell* cell =
60 base::mac::ObjCCast<CollectionViewSwitchCell>(view);
61 if (cell)
62 return cell;
63 }
64
65 // There should be a cell associated with this switch field.
66 NOTREACHED();
67 return nil;
68 }
69
55 typedef NS_ENUM(NSInteger, SectionIdentifier) { 70 typedef NS_ENUM(NSInteger, SectionIdentifier) {
56 SectionIdentifierHeader = kSectionIdentifierEnumZero, 71 SectionIdentifierHeader = kSectionIdentifierEnumZero,
57 SectionIdentifierFooter, 72 SectionIdentifierFooter,
58 SectionIdentifierFirstField, // Must be the last section identifier. 73 SectionIdentifierFirstField, // Must be the last section identifier.
59 }; 74 };
60 75
61 typedef NS_ENUM(NSInteger, ItemType) { 76 typedef NS_ENUM(NSInteger, ItemType) {
62 ItemTypeHeader = kItemTypeEnumZero, 77 ItemTypeHeader = kItemTypeEnumZero,
63 ItemTypeFooter, 78 ItemTypeFooter,
64 ItemTypeTextField, // This is a repeated item type. 79 ItemTypeTextField, // This is a repeated item type.
65 ItemTypeSelectorField, // This is a repeated item type. 80 ItemTypeSelectorField, // This is a repeated item type.
81 ItemTypeSwitchField, // This is a repeated item type.
66 ItemTypeErrorMessage, // This is a repeated item type. 82 ItemTypeErrorMessage, // This is a repeated item type.
67 }; 83 };
68 84
69 } // namespace 85 } // namespace
70 86
71 @interface PaymentRequestEditViewController ()<AutofillEditAccessoryDelegate, 87 @interface PaymentRequestEditViewController ()<
72 UITextFieldDelegate, 88 PaymentRequestEditViewControllerActions,
lpromero 2017/05/30 12:35:45 Sort alphabetically.
Moe 2017/05/31 03:21:11 Done.
73 UIPickerViewDataSource, 89 AutofillEditAccessoryDelegate,
74 UIPickerViewDelegate> { 90 UITextFieldDelegate,
91 UIPickerViewDataSource,
92 UIPickerViewDelegate> {
75 // The currently focused cell. May be nil. 93 // The currently focused cell. May be nil.
76 __weak AutofillEditCell* _currentEditingCell; 94 __weak AutofillEditCell* _currentEditingCell;
77 95
78 AutofillEditAccessoryView* _accessoryView; 96 AutofillEditAccessoryView* _accessoryView;
79 } 97 }
80 98
81 // The map of autofill types to the fields definitions for the editor. 99 // The map of section identifiers to the fields definitions for the editor.
82 @property(nonatomic, strong) 100 @property(nonatomic, strong)
83 NSMutableDictionary<NSNumber*, EditorField*>* fieldsMap; 101 NSMutableDictionary<NSNumber*, EditorField*>* fieldsMap;
84 102
85 // The list of field definitions for the editor. 103 // The list of field definitions for the editor.
86 @property(nonatomic, strong) NSArray<EditorField*>* fields; 104 @property(nonatomic, strong) NSArray<EditorField*>* fields;
87 105
88 // The map of autofill types to lists of UIPickerView options. 106 // The map of autofill types to lists of UIPickerView options.
89 @property(nonatomic, strong) 107 @property(nonatomic, strong)
90 NSMutableDictionary<NSNumber*, NSArray<NSString*>*>* options; 108 NSMutableDictionary<NSNumber*, NSArray<NSString*>*>* options;
91 109
(...skipping 13 matching lines...) Expand all
105 // Enables or disables the accessory view's previous and next buttons depending 123 // Enables or disables the accessory view's previous and next buttons depending
106 // on whether there is a text field before and after the currently focused text 124 // on whether there is a text field before and after the currently focused text
107 // field. 125 // field.
108 - (void)updateAccessoryViewButtonsStates; 126 - (void)updateAccessoryViewButtonsStates;
109 127
110 // Adds an error message item in the section |sectionIdentifier| if 128 // Adds an error message item in the section |sectionIdentifier| if
111 // |errorMessage| is non-empty. Otherwise removes such an item if one exists. 129 // |errorMessage| is non-empty. Otherwise removes such an item if one exists.
112 - (void)addOrRemoveErrorMessage:(NSString*)errorMessage 130 - (void)addOrRemoveErrorMessage:(NSString*)errorMessage
113 inSectionWithIdentifier:(NSInteger)sectionIdentifier; 131 inSectionWithIdentifier:(NSInteger)sectionIdentifier;
114 132
133 // Validates each field. If there is a validation error, displays an error
134 // message item in the same section as the field and returns NO. Otherwise
135 // removes the error message item in that section if one exists and sets the
136 // value on the field. Returns YES if all the fields are validated successfully.
137 - (BOOL)validateForm;
138
139 // Returns the index path for the cell associated with the currently focused
140 // text field.
141 - (NSIndexPath*)indexPathForCurrentTextField;
142
115 @end 143 @end
116 144
117 @implementation PaymentRequestEditViewController 145 @implementation PaymentRequestEditViewController
118 146
119 @synthesize dataSource = _dataSource; 147 @synthesize dataSource = _dataSource;
120 @synthesize delegate = _delegate; 148 @synthesize delegate = _delegate;
121 @synthesize validatorDelegate = _validatorDelegate; 149 @synthesize validatorDelegate = _validatorDelegate;
122 @synthesize fieldsMap = _fieldsMap; 150 @synthesize fieldsMap = _fieldsMap;
123 @synthesize fields = _fields; 151 @synthesize fields = _fields;
124 @synthesize options = _options; 152 @synthesize options = _options;
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after
193 221
194 [self.pickerViews removeAllObjects]; 222 [self.pickerViews removeAllObjects];
195 223
196 CollectionViewItem* headerItem = [_dataSource headerItem]; 224 CollectionViewItem* headerItem = [_dataSource headerItem];
197 if (headerItem) { 225 if (headerItem) {
198 [headerItem setType:ItemTypeHeader]; 226 [headerItem setType:ItemTypeHeader];
199 [model addSectionWithIdentifier:SectionIdentifierHeader]; 227 [model addSectionWithIdentifier:SectionIdentifierHeader];
200 [model addItem:headerItem toSectionWithIdentifier:SectionIdentifierHeader]; 228 [model addItem:headerItem toSectionWithIdentifier:SectionIdentifierHeader];
201 } 229 }
202 230
231 self.fieldsMap =
232 [[NSMutableDictionary alloc] initWithCapacity:self.fields.count];
233
203 // Iterate over the fields and add the respective sections and items. 234 // Iterate over the fields and add the respective sections and items.
204 [self.fields enumerateObjectsUsingBlock:^(EditorField* field, 235 [self.fields enumerateObjectsUsingBlock:^(EditorField* field,
205 NSUInteger index, BOOL* stop) { 236 NSUInteger index, BOOL* stop) {
206 NSInteger sectionIdentifier = SectionIdentifierFirstField + index; 237 NSInteger sectionIdentifier = SectionIdentifierFirstField + index;
207 [model addSectionWithIdentifier:sectionIdentifier]; 238 [model addSectionWithIdentifier:sectionIdentifier];
208 switch (field.fieldType) { 239 switch (field.fieldType) {
209 case EditorFieldTypeTextField: { 240 case EditorFieldTypeTextField: {
210 AutofillEditItem* item = 241 AutofillEditItem* item =
211 [[AutofillEditItem alloc] initWithType:ItemTypeTextField]; 242 [[AutofillEditItem alloc] initWithType:ItemTypeTextField];
212 item.textFieldName = field.label; 243 item.textFieldName = field.label;
213 item.textFieldEnabled = field.enabled; 244 item.textFieldEnabled = field.enabled;
214 item.textFieldValue = field.value; 245 item.textFieldValue = field.value;
215 item.required = field.isRequired; 246 item.required = field.isRequired;
216 item.autofillUIType = field.autofillUIType; 247 item.autofillUIType = field.autofillUIType;
248 item.identifyingIcon = [_dataSource iconIdentifyingEditorFied:field];
217 [model addItem:item toSectionWithIdentifier:sectionIdentifier]; 249 [model addItem:item toSectionWithIdentifier:sectionIdentifier];
218 field.item = item; 250 field.item = item;
219 251
220 break; 252 break;
221 } 253 }
222 case EditorFieldTypeSelector: { 254 case EditorFieldTypeSelector: {
223 PaymentsSelectorEditItem* item = [[PaymentsSelectorEditItem alloc] 255 PaymentsSelectorEditItem* item = [[PaymentsSelectorEditItem alloc]
224 initWithType:ItemTypeSelectorField]; 256 initWithType:ItemTypeSelectorField];
225 item.name = field.label; 257 item.name = field.label;
226 item.value = field.displayValue; 258 item.value = field.displayValue;
227 item.required = field.isRequired; 259 item.required = field.isRequired;
228 item.autofillUIType = field.autofillUIType; 260 item.autofillUIType = field.autofillUIType;
229 item.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator; 261 item.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator;
230 [model addItem:item toSectionWithIdentifier:sectionIdentifier]; 262 [model addItem:item toSectionWithIdentifier:sectionIdentifier];
231 field.item = item; 263 field.item = item;
232 break; 264 break;
233 } 265 }
266 case EditorFieldTypeSwitch: {
267 CollectionViewSwitchItem* item =
268 [[CollectionViewSwitchItem alloc] initWithType:ItemTypeSwitchField];
269 item.text = field.label;
270 item.on = [field.value boolValue];
271 [model addItem:item toSectionWithIdentifier:sectionIdentifier];
272 field.item = item;
273 break;
274 }
234 default: 275 default:
235 NOTREACHED(); 276 NOTREACHED();
236 } 277 }
237 278
238 field.sectionIdentifier = sectionIdentifier; 279 field.sectionIdentifier = sectionIdentifier;
280 NSNumber* key = [NSNumber numberWithInt:sectionIdentifier];
281 [self.fieldsMap setObject:field forKey:key];
239 }]; 282 }];
240 283
241 [self loadFooterItems]; 284 [model addSectionWithIdentifier:SectionIdentifierFooter];
285 CollectionViewFooterItem* footerItem =
286 [[CollectionViewFooterItem alloc] initWithType:ItemTypeFooter];
287 footerItem.text = l10n_util::GetNSString(IDS_PAYMENTS_REQUIRED_FIELD_MESSAGE);
288 [model addItem:footerItem toSectionWithIdentifier:SectionIdentifierFooter];
242 } 289 }
243 290
244 - (void)viewDidLoad { 291 - (void)viewDidLoad {
245 [super viewDidLoad]; 292 [super viewDidLoad];
246 293
247 self.collectionView.accessibilityIdentifier = 294 self.collectionView.accessibilityIdentifier =
248 kPaymentRequestEditCollectionViewAccessibilityID; 295 kPaymentRequestEditCollectionViewAccessibilityID;
249 296
250 // Customize collection view settings. 297 // Customize collection view settings.
251 self.styler.cellStyle = MDCCollectionViewCellStyleCard; 298 self.styler.cellStyle = MDCCollectionViewCellStyleCard;
252 self.styler.separatorInset = 299 self.styler.separatorInset =
253 UIEdgeInsetsMake(0, kSeparatorEdgeInset, 0, kSeparatorEdgeInset); 300 UIEdgeInsetsMake(0, kSeparatorEdgeInset, 0, kSeparatorEdgeInset);
254 } 301 }
255 302
256 #pragma mark - PaymentRequestEditConsumer 303 #pragma mark - PaymentRequestEditConsumer
257 304
258 - (void)setEditorFields:(NSArray<EditorField*>*)fields { 305 - (void)setEditorFields:(NSArray<EditorField*>*)fields {
259 self.fields = fields; 306 self.fields = fields;
260 self.fieldsMap = [[NSMutableDictionary alloc] initWithCapacity:fields.count];
261 // Iterate over the fields and populate the map.
262 [self.fields enumerateObjectsUsingBlock:^(EditorField* field,
263 NSUInteger index, BOOL* stop) {
264 NSNumber* key = [NSNumber numberWithInt:field.autofillUIType];
265 [self.fieldsMap setObject:field forKey:key];
266 }];
267 } 307 }
268 308
269 - (void)setOptions:(NSArray<NSString*>*)options 309 - (void)setOptions:(NSArray<NSString*>*)options
270 forEditorField:(EditorField*)field { 310 forEditorField:(EditorField*)field {
271 DCHECK(field.fieldType == EditorFieldTypeTextField); 311 DCHECK(field.fieldType == EditorFieldTypeTextField);
272 AutofillEditItem* item = 312 AutofillEditItem* item =
273 base::mac::ObjCCastStrict<AutofillEditItem>(field.item); 313 base::mac::ObjCCastStrict<AutofillEditItem>(field.item);
274 item.textFieldEnabled = field.enabled; 314 item.textFieldEnabled = field.enabled;
275 item.textFieldValue = field.value; 315 item.textFieldValue = field.value;
276 316
(...skipping 20 matching lines...) Expand all
297 337
298 - (void)textFieldDidBeginEditing:(UITextField*)textField { 338 - (void)textFieldDidBeginEditing:(UITextField*)textField {
299 _currentEditingCell = AutofillEditCellForTextField(textField); 339 _currentEditingCell = AutofillEditCellForTextField(textField);
300 [textField setInputAccessoryView:_accessoryView]; 340 [textField setInputAccessoryView:_accessoryView];
301 [self updateAccessoryViewButtonsStates]; 341 [self updateAccessoryViewButtonsStates];
302 } 342 }
303 343
304 - (void)textFieldDidEndEditing:(UITextField*)textField { 344 - (void)textFieldDidEndEditing:(UITextField*)textField {
305 DCHECK(_currentEditingCell == AutofillEditCellForTextField(textField)); 345 DCHECK(_currentEditingCell == AutofillEditCellForTextField(textField));
306 346
307 CollectionViewModel* model = self.collectionViewModel; 347 NSIndexPath* indexPath = [self indexPathForCurrentTextField];
348 NSInteger sectionIdentifier = [self.collectionViewModel
349 sectionIdentifierForSection:[indexPath section]];
308 350
309 NSIndexPath* indexPath = [self indexPathForCurrentTextField]; 351 // Find the respective editor field, update its value, and validate it.
310 AutofillEditItem* item = base::mac::ObjCCastStrict<AutofillEditItem>( 352 NSNumber* key = [NSNumber numberWithInt:sectionIdentifier];
311 [model itemAtIndexPath:indexPath]);
312
313 // Find and validate the respective editor field.
314 NSNumber* key = [NSNumber numberWithInt:item.autofillUIType];
315 EditorField* field = self.fieldsMap[key]; 353 EditorField* field = self.fieldsMap[key];
316 DCHECK(field); 354 DCHECK(field);
317 field.value = textField.text; 355 field.value = textField.text;
318 NSString* errorMessage = 356 NSString* errorMessage =
319 [_validatorDelegate paymentRequestEditViewController:self 357 [_validatorDelegate paymentRequestEditViewController:self
320 validateField:field]; 358 validateField:field];
321 NSInteger sectionIdentifier =
322 [model sectionIdentifierForSection:[indexPath section]];
323 [self addOrRemoveErrorMessage:errorMessage 359 [self addOrRemoveErrorMessage:errorMessage
324 inSectionWithIdentifier:sectionIdentifier]; 360 inSectionWithIdentifier:sectionIdentifier];
325 361
326 [textField setInputAccessoryView:nil]; 362 [textField setInputAccessoryView:nil];
327 _currentEditingCell = nil; 363 _currentEditingCell = nil;
328 } 364 }
329 365
330 - (BOOL)textFieldShouldReturn:(UITextField*)textField { 366 - (BOOL)textFieldShouldReturn:(UITextField*)textField {
331 DCHECK([_currentEditingCell textField] == textField); 367 DCHECK([_currentEditingCell textField] == textField);
332 AutofillEditCell* nextCell = [self nextTextFieldWithOffset:1]; 368 AutofillEditCell* nextCell = [self nextTextFieldWithOffset:1];
333 if (nextCell) 369 if (nextCell)
334 [self nextPressed]; 370 [self nextPressed];
335 else 371 else
336 [self closePressed]; 372 [self closePressed];
337 373
338 return NO; 374 return NO;
339 } 375 }
340 376
377 // This method is called as the text is being typed in, pasted, or deleted. Asks
378 // the delegate if the text should be changed. Should always return YES. During
379 // typing/pasting text, |newText| contains one or more new characters. When user
380 // deletes text, |newText| is empty. |range| is the range of characters to be
381 // replaced.
382 - (BOOL)textField:(UITextField*)textField
383 shouldChangeCharactersInRange:(NSRange)range
384 replacementString:(NSString*)newText {
385 CollectionViewModel* model = self.collectionViewModel;
386
387 DCHECK(_currentEditingCell == AutofillEditCellForTextField(textField));
388
389 NSIndexPath* indexPath = [self indexPathForCurrentTextField];
390 NSInteger sectionIdentifier =
391 [model sectionIdentifierForSection:[indexPath section]];
392 AutofillEditItem* item = base::mac::ObjCCastStrict<AutofillEditItem>(
393 [model itemAtIndexPath:indexPath]);
394
395 // Find the respective editor field and update its value.
396 NSNumber* key = [NSNumber numberWithInt:sectionIdentifier];
397 EditorField* field = self.fieldsMap[key];
398 DCHECK(field);
399 // Obtain the text being typed.
400 NSString* updatedText =
401 [textField.text stringByReplacingCharactersInRange:range
402 withString:newText];
403 field.value = updatedText;
404
405 // Get the icon that identifies the field value and reload the cell if the
406 // icon changes.
407 UIImage* oldIcon = item.identifyingIcon;
408 item.identifyingIcon = [_dataSource iconIdentifyingEditorFied:field];
409 if (item.identifyingIcon != oldIcon)
410 [self reconfigureCellsForItems:@[ item ]];
411
412 return YES;
413 }
414
341 #pragma mark - AutofillEditAccessoryDelegate 415 #pragma mark - AutofillEditAccessoryDelegate
342 416
343 - (void)nextPressed { 417 - (void)nextPressed {
344 AutofillEditCell* nextCell = [self nextTextFieldWithOffset:1]; 418 AutofillEditCell* nextCell = [self nextTextFieldWithOffset:1];
345 if (nextCell) 419 if (nextCell)
346 [nextCell.textField becomeFirstResponder]; 420 [nextCell.textField becomeFirstResponder];
347 } 421 }
348 422
349 - (void)previousPressed { 423 - (void)previousPressed {
350 AutofillEditCell* previousCell = [self nextTextFieldWithOffset:-1]; 424 AutofillEditCell* previousCell = [self nextTextFieldWithOffset:-1];
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
407 base::mac::ObjCCast<AutofillEditCell>(cell); 481 base::mac::ObjCCast<AutofillEditCell>(cell);
408 autofillEditCell.textField.delegate = self; 482 autofillEditCell.textField.delegate = self;
409 autofillEditCell.textField.clearButtonMode = UITextFieldViewModeNever; 483 autofillEditCell.textField.clearButtonMode = UITextFieldViewModeNever;
410 autofillEditCell.textLabel.font = [MDCTypography body2Font]; 484 autofillEditCell.textLabel.font = [MDCTypography body2Font];
411 autofillEditCell.textLabel.textColor = [[MDCPalette greyPalette] tint900]; 485 autofillEditCell.textLabel.textColor = [[MDCPalette greyPalette] tint900];
412 autofillEditCell.textField.font = [MDCTypography body1Font]; 486 autofillEditCell.textField.font = [MDCTypography body1Font];
413 autofillEditCell.textField.textColor = 487 autofillEditCell.textField.textColor =
414 [[MDCPalette cr_bluePalette] tint600]; 488 [[MDCPalette cr_bluePalette] tint600];
415 break; 489 break;
416 } 490 }
491 case ItemTypeSwitchField: {
492 CollectionViewSwitchCell* switchCell =
493 base::mac::ObjCCastStrict<CollectionViewSwitchCell>(cell);
494 [switchCell.switchView addTarget:self
495 action:@selector(switchToggled:)
496 forControlEvents:UIControlEventValueChanged];
497 break;
498 }
417 case ItemTypeErrorMessage: { 499 case ItemTypeErrorMessage: {
418 PaymentsTextCell* errorMessageCell = 500 PaymentsTextCell* errorMessageCell =
419 base::mac::ObjCCastStrict<PaymentsTextCell>(cell); 501 base::mac::ObjCCastStrict<PaymentsTextCell>(cell);
420 errorMessageCell.textLabel.font = [MDCTypography body1Font]; 502 errorMessageCell.textLabel.font = [MDCTypography body1Font];
421 errorMessageCell.textLabel.textColor = 503 errorMessageCell.textLabel.textColor =
422 [[MDCPalette cr_redPalette] tint600]; 504 [[MDCPalette cr_redPalette] tint600];
423 break; 505 break;
424 } 506 }
425 case ItemTypeFooter: { 507 case ItemTypeFooter: {
426 CollectionViewFooterCell* footerCell = 508 CollectionViewFooterCell* footerCell =
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
464 #pragma mark MDCCollectionViewStylingDelegate 546 #pragma mark MDCCollectionViewStylingDelegate
465 547
466 - (CGFloat)collectionView:(UICollectionView*)collectionView 548 - (CGFloat)collectionView:(UICollectionView*)collectionView
467 cellHeightAtIndexPath:(NSIndexPath*)indexPath { 549 cellHeightAtIndexPath:(NSIndexPath*)indexPath {
468 CollectionViewItem* item = 550 CollectionViewItem* item =
469 [self.collectionViewModel itemAtIndexPath:indexPath]; 551 [self.collectionViewModel itemAtIndexPath:indexPath];
470 switch (item.type) { 552 switch (item.type) {
471 case ItemTypeHeader: 553 case ItemTypeHeader:
472 case ItemTypeFooter: 554 case ItemTypeFooter:
473 case ItemTypeTextField: 555 case ItemTypeTextField:
556 case ItemTypeSwitchField:
474 case ItemTypeErrorMessage: 557 case ItemTypeErrorMessage:
475 return [MDCCollectionViewCell 558 return [MDCCollectionViewCell
476 cr_preferredHeightForWidth:CGRectGetWidth(collectionView.bounds) 559 cr_preferredHeightForWidth:CGRectGetWidth(collectionView.bounds)
477 forItem:item]; 560 forItem:item];
478 case ItemTypeSelectorField: 561 case ItemTypeSelectorField:
479 return MDCCellDefaultOneLineHeight; 562 return MDCCellDefaultOneLineHeight;
480 default: 563 default:
481 NOTREACHED(); 564 NOTREACHED();
482 return MDCCellDefaultOneLineHeight; 565 return MDCCellDefaultOneLineHeight;
483 } 566 }
484 } 567 }
485 568
486 - (BOOL)collectionView:(UICollectionView*)collectionView 569 - (BOOL)collectionView:(UICollectionView*)collectionView
487 hidesInkViewAtIndexPath:(NSIndexPath*)indexPath { 570 hidesInkViewAtIndexPath:(NSIndexPath*)indexPath {
488 NSInteger type = [self.collectionViewModel itemTypeForIndexPath:indexPath]; 571 NSInteger type = [self.collectionViewModel itemTypeForIndexPath:indexPath];
489 switch (type) { 572 switch (type) {
490 case ItemTypeHeader: 573 case ItemTypeHeader:
491 case ItemTypeFooter: 574 case ItemTypeFooter:
492 case ItemTypeErrorMessage: 575 case ItemTypeErrorMessage:
576 case ItemTypeTextField:
577 case ItemTypeSwitchField:
493 return YES; 578 return YES;
494 default: 579 default:
495 return NO; 580 return NO;
496 } 581 }
497 } 582 }
498 583
499 - (BOOL)collectionView:(UICollectionView*)collectionView 584 - (BOOL)collectionView:(UICollectionView*)collectionView
500 shouldHideItemBackgroundAtIndexPath:(NSIndexPath*)indexPath { 585 shouldHideItemBackgroundAtIndexPath:(NSIndexPath*)indexPath {
501 NSInteger type = [self.collectionViewModel itemTypeForIndexPath:indexPath]; 586 NSInteger type = [self.collectionViewModel itemTypeForIndexPath:indexPath];
502 switch (type) { 587 switch (type) {
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after
575 errorMessageItem.text = errorMessage; 660 errorMessageItem.text = errorMessage;
576 errorMessageItem.image = NativeImage(IDR_IOS_PAYMENTS_WARNING); 661 errorMessageItem.image = NativeImage(IDR_IOS_PAYMENTS_WARNING);
577 errorMessageItem.accessibilityIdentifier = kWarningMessageAccessibilityID; 662 errorMessageItem.accessibilityIdentifier = kWarningMessageAccessibilityID;
578 [model addItem:errorMessageItem toSectionWithIdentifier:sectionIdentifier]; 663 [model addItem:errorMessageItem toSectionWithIdentifier:sectionIdentifier];
579 NSIndexPath* indexPath = [model indexPathForItemType:ItemTypeErrorMessage 664 NSIndexPath* indexPath = [model indexPathForItemType:ItemTypeErrorMessage
580 sectionIdentifier:sectionIdentifier]; 665 sectionIdentifier:sectionIdentifier];
581 [self.collectionView insertItemsAtIndexPaths:@[ indexPath ]]; 666 [self.collectionView insertItemsAtIndexPaths:@[ indexPath ]];
582 } 667 }
583 } 668 }
584 669
585 #pragma mark - Keyboard handling
586
587 - (void)keyboardDidShow {
588 [self.collectionView
589 scrollToItemAtIndexPath:[self.collectionView
590 indexPathForCell:_currentEditingCell]
591 atScrollPosition:UICollectionViewScrollPositionCenteredVertically
592 animated:YES];
593 }
594
595 @end
596
597 @implementation PaymentRequestEditViewController (Internal)
598
599 - (BOOL)validateForm { 670 - (BOOL)validateForm {
600 for (EditorField* field in self.fields) { 671 for (EditorField* field in self.fields) {
601 NSString* errorMessage = 672 NSString* errorMessage =
602 [_validatorDelegate paymentRequestEditViewController:self 673 [_validatorDelegate paymentRequestEditViewController:self
603 validateField:field]; 674 validateField:field];
604 [self addOrRemoveErrorMessage:errorMessage 675 [self addOrRemoveErrorMessage:errorMessage
605 inSectionWithIdentifier:field.sectionIdentifier]; 676 inSectionWithIdentifier:field.sectionIdentifier];
606 if (errorMessage.length) 677 if (errorMessage.length)
607 return NO; 678 return NO;
608 } 679 }
609 return YES; 680 return YES;
610 } 681 }
611 682
612 - (void)loadFooterItems {
613 CollectionViewModel* model = self.collectionViewModel;
614
615 [model addSectionWithIdentifier:SectionIdentifierFooter];
616 CollectionViewFooterItem* footerItem =
617 [[CollectionViewFooterItem alloc] initWithType:ItemTypeFooter];
618 footerItem.text = l10n_util::GetNSString(IDS_PAYMENTS_REQUIRED_FIELD_MESSAGE);
619 [model addItem:footerItem toSectionWithIdentifier:SectionIdentifierFooter];
620 }
621
622 - (NSIndexPath*)indexPathForCurrentTextField { 683 - (NSIndexPath*)indexPathForCurrentTextField {
623 DCHECK(_currentEditingCell); 684 DCHECK(_currentEditingCell);
624 NSIndexPath* indexPath = 685 NSIndexPath* indexPath =
625 [[self collectionView] indexPathForCell:_currentEditingCell]; 686 [[self collectionView] indexPathForCell:_currentEditingCell];
626 DCHECK(indexPath); 687 DCHECK(indexPath);
627 return indexPath; 688 return indexPath;
628 } 689 }
629 690
691 #pragma mark - Keyboard handling
692
693 - (void)keyboardDidShow {
694 [self.collectionView
695 scrollToItemAtIndexPath:[self.collectionView
696 indexPathForCell:_currentEditingCell]
697 atScrollPosition:UICollectionViewScrollPositionCenteredVertically
698 animated:YES];
699 }
700
701 #pragma mark Switch Actions
702
703 - (void)switchToggled:(UISwitch*)sender {
704 CollectionViewSwitchCell* switchCell =
705 CollectionViewSwitchCellForSwitchField(sender);
706 NSIndexPath* indexPath = [[self collectionView] indexPathForCell:switchCell];
707 DCHECK(indexPath);
708
709 NSInteger sectionIdentifier = [self.collectionViewModel
710 sectionIdentifierForSection:[indexPath section]];
711
712 // Update editor field's value.
713 NSNumber* key = [NSNumber numberWithInt:sectionIdentifier];
714 EditorField* field = self.fieldsMap[key];
715 DCHECK(field);
716 field.value = [sender isOn] ? @"YES" : @"NO";
717 }
718
630 #pragma mark - PaymentRequestEditViewControllerActions methods 719 #pragma mark - PaymentRequestEditViewControllerActions methods
631 720
632 - (void)onCancel { 721 - (void)onCancel {
722 [self.delegate paymentRequestEditViewControllerDidCancel:self];
633 } 723 }
634 724
635 - (void)onDone { 725 - (void)onDone {
636 [_currentEditingCell.textField resignFirstResponder]; 726 [_currentEditingCell.textField resignFirstResponder];
727
728 if (![self validateForm])
729 return;
730
731 [self.delegate paymentRequestEditViewController:self
732 didFinishEditingFields:self.fields];
637 } 733 }
638 734
639 @end 735 @end
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698