blob: 429122866181b81de29300c072d1f113c5a12917 [file] [log] [blame]
// Copyright 2016 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 "ios/chrome/browser/ui/settings/material_cell_catalog_view_controller.h"
#import <UIKit/UIKit.h>
#import "base/mac/foundation_util.h"
#include "components/autofill/core/browser/autofill_data_util.h"
#include "components/autofill/core/browser/credit_card.h"
#include "components/grit/components_scaled_resources.h"
#import "ios/chrome/browser/ui/authentication/account_control_item.h"
#import "ios/chrome/browser/ui/authentication/signin_promo_item.h"
#import "ios/chrome/browser/ui/authentication/signin_promo_view_configurator.h"
#import "ios/chrome/browser/ui/authentication/signin_promo_view_delegate.h"
#import "ios/chrome/browser/ui/authentication/signin_promo_view_mediator.h"
#import "ios/chrome/browser/ui/autofill/cells/cvc_item.h"
#import "ios/chrome/browser/ui/autofill/cells/legacy_autofill_edit_item.h"
#import "ios/chrome/browser/ui/autofill/cells/status_item.h"
#import "ios/chrome/browser/ui/collection_view/cells/MDCCollectionViewCell+Chrome.h"
#import "ios/chrome/browser/ui/collection_view/cells/collection_view_account_item.h"
#import "ios/chrome/browser/ui/collection_view/cells/collection_view_cell_style.h"
#import "ios/chrome/browser/ui/collection_view/cells/collection_view_footer_item.h"
#import "ios/chrome/browser/ui/collection_view/collection_view_model.h"
#import "ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_footer_item.h"
#import "ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_item.h"
#import "ios/chrome/browser/ui/icons/chrome_icon.h"
#import "ios/chrome/browser/ui/payments/cells/accepted_payment_methods_item.h"
#import "ios/chrome/browser/ui/payments/cells/autofill_profile_item.h"
#import "ios/chrome/browser/ui/payments/cells/payments_text_item.h"
#import "ios/chrome/browser/ui/payments/cells/price_item.h"
#import "ios/chrome/browser/ui/settings/cells/account_signin_item.h"
#import "ios/chrome/browser/ui/settings/cells/autofill_data_item.h"
#import "ios/chrome/browser/ui/settings/cells/card_multiline_item.h"
#import "ios/chrome/browser/ui/settings/cells/copied_to_chrome_item.h"
#import "ios/chrome/browser/ui/settings/cells/encryption_item.h"
#import "ios/chrome/browser/ui/settings/cells/import_data_multiline_detail_item.h"
#import "ios/chrome/browser/ui/settings/cells/legacy/legacy_settings_detail_item.h"
#import "ios/chrome/browser/ui/settings/cells/legacy/legacy_settings_switch_item.h"
#import "ios/chrome/browser/ui/settings/cells/passphrase_error_item.h"
#import "ios/chrome/browser/ui/settings/cells/password_details_item.h"
#import "ios/chrome/browser/ui/settings/cells/settings_image_detail_text_item.h"
#import "ios/chrome/browser/ui/settings/cells/settings_search_item.h"
#import "ios/chrome/browser/ui/settings/cells/settings_text_item.h"
#import "ios/chrome/browser/ui/settings/cells/sync_switch_item.h"
#import "ios/chrome/browser/ui/settings/cells/text_and_error_item.h"
#import "ios/chrome/browser/ui/util/uikit_ui_util.h"
#import "ios/public/provider/chrome/browser/chrome_browser_provider.h"
#import "ios/public/provider/chrome/browser/signin/signin_resources_provider.h"
#import "ios/third_party/material_components_ios/src/components/CollectionCells/src/MaterialCollectionCells.h"
#import "ios/third_party/material_components_ios/src/components/Palettes/src/MaterialPalettes.h"
#import "ios/third_party/material_components_ios/src/components/Typography/src/MaterialTypography.h"
#if !defined(__has_feature) || !__has_feature(objc_arc)
#error "This file requires ARC support."
#endif
namespace {
typedef NS_ENUM(NSInteger, SectionIdentifier) {
SectionIdentifierTextCell = kSectionIdentifierEnumZero,
SectionIdentifierDetailCell,
SectionIdentifierMultilineCell,
SectionIdentifierSwitchCell,
SectionIdentifierNativeAppCell,
SectionIdentifierAutofill,
SectionIdentifierPayments,
SectionIdentifierPaymentsNoBackground,
SectionIdentifierCopiedToChrome,
SectionIdentifierPasswordDetails,
SectionIdentifierSettingsSearchCell,
SectionIdentifierAccountCell,
SectionIdentifierAccountControlCell,
SectionIdentifierFooters,
SectionIdentifierSync,
SectionIdentifierContentSuggestionsCell,
};
typedef NS_ENUM(NSInteger, ItemType) {
ItemTypeTextCheckmark = kItemTypeEnumZero,
ItemTypeTextDetail,
ItemTypeText,
ItemTypeTextError,
ItemTypeDetailBasic,
ItemTypeDetailLeftMedium,
ItemTypeDetailRightMedium,
ItemTypeDetailLeftLong,
ItemTypeDetailRightLong,
ItemTypeDetailBothLong,
ItemTypeMultilineBasic,
ItemTypeImportDataMultiline,
ItemTypeSwitchBasic,
ItemTypeSwitchDynamicHeight,
ItemTypeSwitchSync,
ItemTypeHeader,
ItemTypeAccountDetail,
ItemTypeAccountCheckMark,
ItemTypeAccountSignIn,
ItemTypeColdStateSigninPromo,
ItemTypeWarmStateSigninPromo,
ItemTypeApp,
ItemTypePaymentsSingleLine,
ItemTypePaymentsDynamicHeight,
ItemTypeCopiedToChrome,
ItemTypePasswordDetailsShortHidden,
ItemTypePasswordDetailsShortVisible,
ItemTypePasswordDetailsLong,
ItemTypeSettingsSearch,
ItemTypeAutofillDynamicHeight,
ItemTypeAutofillCVC,
ItemTypeAutofillStatus,
ItemTypeAccountControlDynamicHeight,
ItemTypeFooter,
ItemTypeSyncEncryption,
ItemTypeSyncEncryptionChecked,
ItemTypeSyncPassphraseError,
ItemTypeContentSuggestions,
ItemTypeImageDetailTextItem,
};
// Image fixed horizontal size.
const CGFloat kHorizontalImageFixedSize = 40;
// Credit Card icon size.
const CGFloat kCardIssuerNetworkIconDimension = 25.0;
} // namespace
@implementation MaterialCellCatalogViewController
- (instancetype)init {
UICollectionViewLayout* layout = [[MDCCollectionViewFlowLayout alloc] init];
self =
[super initWithLayout:layout style:CollectionViewControllerStyleAppBar];
if (self) {
// TODO(crbug.com/764578): -loadModel should not be called from
// initializer. A possible fix is to move this call to -viewDidLoad.
[self loadModel];
}
return self;
}
- (void)loadModel {
[super loadModel];
CollectionViewModel* model = self.collectionViewModel;
// Text cells.
[model addSectionWithIdentifier:SectionIdentifierTextCell];
SettingsTextItem* textHeader =
[[SettingsTextItem alloc] initWithType:ItemTypeHeader];
textHeader.text = @"SettingsTextCell";
textHeader.textFont = [textHeader.textFont fontWithSize:12];
textHeader.textColor = [[MDCPalette greyPalette] tint500];
[model setHeader:textHeader
forSectionWithIdentifier:SectionIdentifierTextCell];
SettingsTextItem* textCell =
[[SettingsTextItem alloc] initWithType:ItemTypeTextCheckmark];
textCell.text = @"Text cell 1";
textCell.accessoryType = MDCCollectionViewCellAccessoryCheckmark;
[model addItem:textCell toSectionWithIdentifier:SectionIdentifierTextCell];
SettingsTextItem* textCell2 =
[[SettingsTextItem alloc] initWithType:ItemTypeTextDetail];
textCell2.text =
@"Text cell with text that is so long it must truncate at some point "
@"except that maybe it sometimes doesn't in landscape mode.";
textCell2.accessoryType = MDCCollectionViewCellAccessoryDetailButton;
[model addItem:textCell2 toSectionWithIdentifier:SectionIdentifierTextCell];
SettingsTextItem* smallTextCell =
[[SettingsTextItem alloc] initWithType:ItemTypeText];
smallTextCell.text = @"Text cell with small font but height of 48.";
smallTextCell.textFont = [smallTextCell.textFont fontWithSize:8];
[model addItem:smallTextCell
toSectionWithIdentifier:SectionIdentifierTextCell];
// Text and Error cell.
TextAndErrorItem* textAndErrorItem =
[[TextAndErrorItem alloc] initWithType:ItemTypeTextError];
textAndErrorItem.text = @"Text and Error cell";
textAndErrorItem.shouldDisplayError = YES;
textAndErrorItem.accessoryType =
MDCCollectionViewCellAccessoryDisclosureIndicator;
[model addItem:textAndErrorItem
toSectionWithIdentifier:SectionIdentifierTextCell];
// Detail cells.
[model addSectionWithIdentifier:SectionIdentifierDetailCell];
LegacySettingsDetailItem* detailBasic =
[[LegacySettingsDetailItem alloc] initWithType:ItemTypeDetailBasic];
detailBasic.text = @"Preload Webpages";
detailBasic.detailText = @"Only on Wi-Fi";
detailBasic.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator;
[model addItem:detailBasic
toSectionWithIdentifier:SectionIdentifierDetailCell];
LegacySettingsDetailItem* detailMediumLeft =
[[LegacySettingsDetailItem alloc] initWithType:ItemTypeDetailLeftMedium];
detailMediumLeft.text = @"A long string but it should fit";
detailMediumLeft.detailText = @"Detail";
[model addItem:detailMediumLeft
toSectionWithIdentifier:SectionIdentifierDetailCell];
LegacySettingsDetailItem* detailMediumRight =
[[LegacySettingsDetailItem alloc] initWithType:ItemTypeDetailRightMedium];
detailMediumRight.text = @"Main";
detailMediumRight.detailText = @"A long string but it should fit";
[model addItem:detailMediumRight
toSectionWithIdentifier:SectionIdentifierDetailCell];
LegacySettingsDetailItem* detailLongLeft =
[[LegacySettingsDetailItem alloc] initWithType:ItemTypeDetailLeftLong];
detailLongLeft.text =
@"This is a very long main text that is intended to overflow "
@"except maybe on landscape but now it's longer so it won't fit.";
detailLongLeft.detailText = @"Detail Text";
detailLongLeft.iconImageName = @"ntp_history_icon";
[model addItem:detailLongLeft
toSectionWithIdentifier:SectionIdentifierDetailCell];
LegacySettingsDetailItem* detailLongRight =
[[LegacySettingsDetailItem alloc] initWithType:ItemTypeDetailRightLong];
detailLongRight.text = @"Main Text";
detailLongRight.detailText =
@"This is a very long detail text that is intended to overflow "
@"except maybe on landscape but now it's longer so it won't fit.";
detailLongRight.iconImageName = @"ntp_history_icon";
[model addItem:detailLongRight
toSectionWithIdentifier:SectionIdentifierDetailCell];
LegacySettingsDetailItem* detailLongBoth =
[[LegacySettingsDetailItem alloc] initWithType:ItemTypeDetailBothLong];
detailLongBoth.text =
@"This is a very long main text that is intended to overflow "
@"except maybe on landscape but now it's longer so it won't fit.";
detailLongBoth.detailText =
@"This is a very long detail text that is intended to overflow "
@"except maybe on landscape but now it's longer so it won't fit.";
detailLongBoth.iconImageName = @"ntp_history_icon";
[model addItem:detailLongBoth
toSectionWithIdentifier:SectionIdentifierDetailCell];
// Multiline cells.
[model addSectionWithIdentifier:SectionIdentifierMultilineCell];
CardMultilineItem* multilineItem =
[[CardMultilineItem alloc] initWithType:ItemTypeMultilineBasic];
multilineItem.text =
@"Lorem ipsum dolor sit amet, consectetur "
@"adipiscing elit, sed do eiusmod tempor "
@"incididunt ut labore et dolore magna aliqua.";
[model addItem:multilineItem
toSectionWithIdentifier:SectionIdentifierMultilineCell];
ImportDataMultilineDetailItem* multilineDetailItem =
[[ImportDataMultilineDetailItem alloc]
initWithType:ItemTypeImportDataMultiline];
multilineDetailItem.text =
@"Lorem ipsum dolor sit amet, consectetur "
@"adipiscing elit, sed do eiusmod tempor "
@"incididunt ut labore et dolore magna aliqua.";
multilineDetailItem.detailText =
@"Lorem ipsum dolor sit amet, consectetur "
@"adipiscing elit, sed do eiusmod tempor "
@"incididunt ut labore et dolore magna aliqua.";
[model addItem:multilineDetailItem
toSectionWithIdentifier:SectionIdentifierMultilineCell];
[model addItem:[self settingsImageDetailTextItem]
toSectionWithIdentifier:SectionIdentifierMultilineCell];
SettingsImageDetailTextItem* settingsImageDetailTextItem =
[self settingsImageDetailTextItem];
settingsImageDetailTextItem.text = @"Short title";
[model addItem:settingsImageDetailTextItem
toSectionWithIdentifier:SectionIdentifierMultilineCell];
settingsImageDetailTextItem = [self settingsImageDetailTextItem];
settingsImageDetailTextItem.detailText = @"Short detail text";
[model addItem:settingsImageDetailTextItem
toSectionWithIdentifier:SectionIdentifierMultilineCell];
settingsImageDetailTextItem = [self settingsImageDetailTextItem];
settingsImageDetailTextItem.detailText =
@"Text multiline that works nice with a very very very very very long "
@"text Text multiline that works nice with a very very very very very "
@"long text Text multiline that works nice with a very very very very "
@"very long text";
[model addItem:settingsImageDetailTextItem
toSectionWithIdentifier:SectionIdentifierMultilineCell];
// Switch cells.
[model addSectionWithIdentifier:SectionIdentifierSwitchCell];
[model addItem:[self basicSwitchItem]
toSectionWithIdentifier:SectionIdentifierSwitchCell];
[model addItem:[self longTextSwitchItem]
toSectionWithIdentifier:SectionIdentifierSwitchCell];
[model addItem:[self syncSwitchItem]
toSectionWithIdentifier:SectionIdentifierSwitchCell];
// Autofill cells.
[model addSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self autofillItemWithMainAndTrailingText]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self autofillItemWithLeadingTextOnly]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self autofillItemWithAllText]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self autofillEditItem]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self autofillEditItemWithIcon]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self cvcItem]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self cvcItemWithDate]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self cvcItemWithError]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self statusItemVerifying]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self statusItemVerified]
toSectionWithIdentifier:SectionIdentifierAutofill];
[model addItem:[self statusItemError]
toSectionWithIdentifier:SectionIdentifierAutofill];
// Payments cells.
[model addSectionWithIdentifier:SectionIdentifierPayments];
[model addItem:[self paymentsItemWithWrappingTextandOptionalImage]
toSectionWithIdentifier:SectionIdentifierPayments];
PriceItem* priceItem1 =
[[PriceItem alloc] initWithType:ItemTypePaymentsSingleLine];
priceItem1.item = @"Total";
priceItem1.notification = @"Updated";
priceItem1.price = @"USD $100.00";
[model addItem:priceItem1 toSectionWithIdentifier:SectionIdentifierPayments];
PriceItem* priceItem2 =
[[PriceItem alloc] initWithType:ItemTypePaymentsSingleLine];
priceItem2.item = @"Price label is long and should get clipped";
priceItem2.notification = @"Updated";
priceItem2.price = @"USD $1,000,000.00";
[model addItem:priceItem2 toSectionWithIdentifier:SectionIdentifierPayments];
PriceItem* priceItem3 =
[[PriceItem alloc] initWithType:ItemTypePaymentsSingleLine];
priceItem3.item = @"Price label is long and should get clipped";
priceItem3.notification = @"Should get clipped too";
priceItem3.price = @"USD $1,000,000.00";
[model addItem:priceItem3 toSectionWithIdentifier:SectionIdentifierPayments];
PriceItem* priceItem4 =
[[PriceItem alloc] initWithType:ItemTypePaymentsSingleLine];
priceItem4.item = @"Price label is long and should get clipped";
priceItem4.notification = @"Should get clipped too";
priceItem4.price = @"USD $1,000,000,000.00";
[model addItem:priceItem4 toSectionWithIdentifier:SectionIdentifierPayments];
AutofillProfileItem* profileItem1 =
[[AutofillProfileItem alloc] initWithType:ItemTypePaymentsDynamicHeight];
profileItem1.name = @"Profile Name gets wrapped if it's too long";
profileItem1.address = @"Profile Address also gets wrapped if it's too long";
profileItem1.phoneNumber = @"123-456-7890";
profileItem1.email = @"foo@bar.com";
profileItem1.notification = @"Some fields are missing";
[model addItem:profileItem1
toSectionWithIdentifier:SectionIdentifierPayments];
AutofillProfileItem* profileItem2 =
[[AutofillProfileItem alloc] initWithType:ItemTypePaymentsDynamicHeight];
profileItem1.name = @"All fields are optional";
profileItem2.phoneNumber = @"123-456-7890";
profileItem2.notification = @"Some fields are missing";
[model addItem:profileItem2
toSectionWithIdentifier:SectionIdentifierPayments];
AutofillProfileItem* profileItem3 =
[[AutofillProfileItem alloc] initWithType:ItemTypePaymentsDynamicHeight];
profileItem3.address = @"All fields are optional";
profileItem3.email = @"foo@bar.com";
[model addItem:profileItem3
toSectionWithIdentifier:SectionIdentifierPayments];
// Payments cells with no background.
[model addSectionWithIdentifier:SectionIdentifierPaymentsNoBackground];
[model addItem:[self acceptedPaymentMethodsItem]
toSectionWithIdentifier:SectionIdentifierPaymentsNoBackground];
// CopiedToChrome cells.
[model addSectionWithIdentifier:SectionIdentifierCopiedToChrome];
CopiedToChromeItem* copiedToChromeItem =
[[CopiedToChromeItem alloc] initWithType:ItemTypeCopiedToChrome];
[model addItem:copiedToChromeItem
toSectionWithIdentifier:SectionIdentifierCopiedToChrome];
// Password Details cells.
[model addSectionWithIdentifier:SectionIdentifierPasswordDetails];
[model addItem:[self passwordDetailsShortHiddenItem]
toSectionWithIdentifier:SectionIdentifierPasswordDetails];
[model addItem:[self passwordDetailsShortVisibleItem]
toSectionWithIdentifier:SectionIdentifierPasswordDetails];
[model addItem:[self passwordDetailsLongItem]
toSectionWithIdentifier:SectionIdentifierPasswordDetails];
// Search cells.
[model addSectionWithIdentifier:SectionIdentifierSettingsSearchCell];
[model addItem:[self settingsSearchItem]
toSectionWithIdentifier:SectionIdentifierSettingsSearchCell];
// Account cells.
[model addSectionWithIdentifier:SectionIdentifierAccountCell];
[model addItem:[self accountItemDetailWithError]
toSectionWithIdentifier:SectionIdentifierAccountCell];
[model addItem:[self accountItemCheckMark]
toSectionWithIdentifier:SectionIdentifierAccountCell];
[model addItem:[self accountSignInItem]
toSectionWithIdentifier:SectionIdentifierAccountCell];
[model addItem:[self coldStateSigninPromoItem]
toSectionWithIdentifier:SectionIdentifierAccountCell];
[model addItem:[self warmStateSigninPromoItem]
toSectionWithIdentifier:SectionIdentifierAccountCell];
// Sync cells.
[model addSectionWithIdentifier:SectionIdentifierSync];
[model addItem:[self syncEncryptionItem]
toSectionWithIdentifier:SectionIdentifierSync];
[model addItem:[self syncEncryptionCheckedItem]
toSectionWithIdentifier:SectionIdentifierSync];
[model addItem:[self syncPassphraseErrorItem]
toSectionWithIdentifier:SectionIdentifierSync];
// Account control cells.
[model addSectionWithIdentifier:SectionIdentifierAccountControlCell];
[model addItem:[self accountControlItem]
toSectionWithIdentifier:SectionIdentifierAccountControlCell];
[model addItem:[self accountControlItemWithExtraLongText]
toSectionWithIdentifier:SectionIdentifierAccountControlCell];
// Content Suggestions cells.
[model addSectionWithIdentifier:SectionIdentifierContentSuggestionsCell];
[model addItem:[self contentSuggestionsItem]
toSectionWithIdentifier:SectionIdentifierContentSuggestionsCell];
[model addItem:[self contentSuggestionsFooterItem]
toSectionWithIdentifier:SectionIdentifierContentSuggestionsCell];
// Footers.
[model addSectionWithIdentifier:SectionIdentifierFooters];
[model addItem:[self shortFooterItem]
toSectionWithIdentifier:SectionIdentifierFooters];
[model addItem:[self longFooterItem]
toSectionWithIdentifier:SectionIdentifierFooters];
}
- (void)viewDidLoad {
[super viewDidLoad];
self.title = @"Collection Cell Catalog";
}
#pragma mark MDCCollectionViewStylingDelegate
- (CGFloat)collectionView:(nonnull UICollectionView*)collectionView
cellHeightAtIndexPath:(nonnull NSIndexPath*)indexPath {
CollectionViewItem* item =
[self.collectionViewModel itemAtIndexPath:indexPath];
switch (item.type) {
case ItemTypeImageDetailTextItem:
case ItemTypeContentSuggestions:
case ItemTypeFooter:
case ItemTypeSwitchDynamicHeight:
case ItemTypeSwitchSync:
case ItemTypeAccountControlDynamicHeight:
case ItemTypeTextCheckmark:
case ItemTypeTextDetail:
case ItemTypeText:
case ItemTypeTextError:
case ItemTypeMultilineBasic:
case ItemTypeImportDataMultiline:
case ItemTypePasswordDetailsShortHidden:
case ItemTypePasswordDetailsShortVisible:
case ItemTypePasswordDetailsLong:
case ItemTypeAutofillCVC:
case ItemTypeAutofillStatus:
case ItemTypePaymentsDynamicHeight:
case ItemTypeAutofillDynamicHeight:
case ItemTypeColdStateSigninPromo:
case ItemTypeWarmStateSigninPromo:
case ItemTypeSyncEncryption:
case ItemTypeSyncEncryptionChecked:
return [MDCCollectionViewCell
cr_preferredHeightForWidth:CGRectGetWidth(collectionView.bounds)
forItem:item];
case ItemTypeApp:
return MDCCellDefaultOneLineWithAvatarHeight;
case ItemTypeAccountDetail:
return MDCCellDefaultTwoLineHeight;
case ItemTypeAccountCheckMark:
return MDCCellDefaultTwoLineHeight;
case ItemTypeAccountSignIn:
return MDCCellDefaultThreeLineHeight;
default:
return MDCCellDefaultOneLineHeight;
}
}
- (MDCCollectionViewCellStyle)collectionView:(UICollectionView*)collectionView
cellStyleForSection:(NSInteger)section {
NSInteger sectionIdentifier =
[self.collectionViewModel sectionIdentifierForSection:section];
switch (sectionIdentifier) {
case SectionIdentifierFooters:
// Display the Learn More footer in the default style with no "card" UI
// and no section padding.
return MDCCollectionViewCellStyleDefault;
default:
return self.styler.cellStyle;
}
}
- (BOOL)collectionView:(UICollectionView*)collectionView
shouldHideItemBackgroundAtIndexPath:(NSIndexPath*)indexPath {
NSInteger sectionIdentifier =
[self.collectionViewModel sectionIdentifierForSection:indexPath.section];
switch (sectionIdentifier) {
case SectionIdentifierPaymentsNoBackground:
case SectionIdentifierFooters:
// Display the Learn More footer without any background image or
// shadowing.
return YES;
default:
return NO;
}
}
- (BOOL)collectionView:(nonnull UICollectionView*)collectionView
hidesInkViewAtIndexPath:(nonnull NSIndexPath*)indexPath {
NSInteger sectionIdentifier =
[self.collectionViewModel sectionIdentifierForSection:indexPath.section];
if (sectionIdentifier == SectionIdentifierFooters)
return YES;
CollectionViewItem* item =
[self.collectionViewModel itemAtIndexPath:indexPath];
switch (item.type) {
case ItemTypeApp:
case ItemTypeColdStateSigninPromo:
case ItemTypeSwitchBasic:
case ItemTypeSwitchDynamicHeight:
case ItemTypeSwitchSync:
case ItemTypeWarmStateSigninPromo:
return YES;
default:
return NO;
}
}
#pragma mark Item models
- (CollectionViewItem*)accountItemDetailWithError {
CollectionViewAccountItem* accountItemDetail =
[[CollectionViewAccountItem alloc] initWithType:ItemTypeAccountDetail];
accountItemDetail.cellStyle = CollectionViewCellStyle::kUIKit;
// TODO(crbug.com/754032): ios_default_avatar image is from a downstream iOS
// internal repository. It should be used through a provider API instead.
accountItemDetail.image = [UIImage imageNamed:@"ios_default_avatar"];
accountItemDetail.text = @"Account User Name";
accountItemDetail.detailText =
@"Syncing to AccountUserNameAccount@example.com";
accountItemDetail.accessoryType =
MDCCollectionViewCellAccessoryDisclosureIndicator;
accountItemDetail.shouldDisplayError = YES;
return accountItemDetail;
}
- (CollectionViewItem*)accountItemCheckMark {
CollectionViewAccountItem* accountItemCheckMark =
[[CollectionViewAccountItem alloc] initWithType:ItemTypeAccountCheckMark];
accountItemCheckMark.cellStyle = CollectionViewCellStyle::kUIKit;
// TODO(crbug.com/754032): ios_default_avatar image is from a downstream iOS
// internal repository. It should be used through a provider API instead.
accountItemCheckMark.image = [UIImage imageNamed:@"ios_default_avatar"];
accountItemCheckMark.text = @"Lorem ipsum dolor sit amet, consectetur "
@"adipiscing elit, sed do eiusmod tempor "
@"incididunt ut labore et dolore magna aliqua.";
accountItemCheckMark.detailText =
@"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do "
@"eiusmod tempor incididunt ut labore et dolore magna aliqua.";
accountItemCheckMark.accessoryType = MDCCollectionViewCellAccessoryCheckmark;
return accountItemCheckMark;
}
- (CollectionViewItem*)accountSignInItem {
AccountSignInItem* accountSignInItem =
[[AccountSignInItem alloc] initWithType:ItemTypeAccountSignIn];
accountSignInItem.image =
CircularImageFromImage(ios::GetChromeBrowserProvider()
->GetSigninResourcesProvider()
->GetDefaultAvatar(),
kHorizontalImageFixedSize);
return accountSignInItem;
}
- (CollectionViewItem*)coldStateSigninPromoItem {
SigninPromoItem* signinPromoItem =
[[SigninPromoItem alloc] initWithType:ItemTypeWarmStateSigninPromo];
signinPromoItem.configurator =
[[SigninPromoViewConfigurator alloc] initWithUserEmail:nil
userFullName:nil
userImage:nil
hasCloseButton:YES];
return signinPromoItem;
}
- (CollectionViewItem*)warmStateSigninPromoItem {
SigninPromoItem* signinPromoItem =
[[SigninPromoItem alloc] initWithType:ItemTypeColdStateSigninPromo];
signinPromoItem.configurator = [[SigninPromoViewConfigurator alloc]
initWithUserEmail:@"jonhdoe@example.com"
userFullName:@"John Doe"
userImage:nil
hasCloseButton:NO];
return signinPromoItem;
}
- (CollectionViewItem*)accountControlItem {
AccountControlItem* item = [[AccountControlItem alloc]
initWithType:ItemTypeAccountControlDynamicHeight];
item.cellStyle = CollectionViewCellStyle::kUIKit;
item.image = [UIImage imageNamed:@"settings_sync"];
item.text = @"Account Sync Settings";
item.detailText = @"Detail text";
item.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator;
return item;
}
- (CollectionViewItem*)accountControlItemWithExtraLongText {
AccountControlItem* item = [[AccountControlItem alloc]
initWithType:ItemTypeAccountControlDynamicHeight];
item.cellStyle = CollectionViewCellStyle::kUIKit;
item.image = [ChromeIcon infoIcon];
item.text = @"Account Control Settings";
item.detailText =
@"Detail text detail text detail text detail text detail text.";
item.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator;
return item;
}
#pragma mark Private
- (CollectionViewItem*)basicSwitchItem {
LegacySettingsSwitchItem* item =
[[LegacySettingsSwitchItem alloc] initWithType:ItemTypeSwitchBasic];
item.text = @"Enable awesomeness.";
item.on = YES;
return item;
}
- (CollectionViewItem*)longTextSwitchItem {
LegacySettingsSwitchItem* item = [[LegacySettingsSwitchItem alloc]
initWithType:ItemTypeSwitchDynamicHeight];
item.text = @"Enable awesomeness. This is a very long text that is intended "
@"to overflow.";
item.on = YES;
return item;
}
- (CollectionViewItem*)syncSwitchItem {
SyncSwitchItem* item =
[[SyncSwitchItem alloc] initWithType:ItemTypeSwitchSync];
item.text = @"Cell used in Sync Settings";
item.detailText =
@"This is a very long text that is intended to overflow to two lines.";
item.on = NO;
return item;
}
- (CollectionViewItem*)paymentsItemWithWrappingTextandOptionalImage {
PaymentsTextItem* item =
[[PaymentsTextItem alloc] initWithType:ItemTypePaymentsDynamicHeight];
item.text = @"If you want to display a long text that wraps to the next line "
@"and may need to feature an image this is the cell to use.";
item.leadingImage = [UIImage imageNamed:@"app_icon_placeholder"];
return item;
}
- (CollectionViewItem*)acceptedPaymentMethodsItem {
AcceptedPaymentMethodsItem* item = [[AcceptedPaymentMethodsItem alloc]
initWithType:ItemTypePaymentsDynamicHeight];
item.message = @"Cards accepted:";
NSMutableArray* cardTypeIcons = [NSMutableArray array];
const char* cardTypes[]{autofill::kVisaCard,
autofill::kMasterCard,
autofill::kAmericanExpressCard,
autofill::kJCBCard,
autofill::kDinersCard,
autofill::kDiscoverCard};
for (const std::string& cardType : cardTypes) {
autofill::data_util::PaymentRequestData data =
autofill::data_util::GetPaymentRequestData(cardType);
UIImage* cardTypeIcon =
ResizeImage(NativeImage(data.icon_resource_id),
CGSizeMake(kCardIssuerNetworkIconDimension,
kCardIssuerNetworkIconDimension),
ProjectionMode::kAspectFillNoClipping);
[cardTypeIcons addObject:cardTypeIcon];
}
item.methodTypeIcons = cardTypeIcons;
return item;
}
- (CollectionViewItem*)autofillItemWithMainAndTrailingText {
AutofillDataItem* item =
[[AutofillDataItem alloc] initWithType:ItemTypeAutofillDynamicHeight];
item.text = @"Main Text";
item.trailingDetailText = @"Trailing Detail Text";
item.accessoryType = MDCCollectionViewCellAccessoryNone;
return item;
}
- (CollectionViewItem*)autofillItemWithLeadingTextOnly {
AutofillDataItem* item =
[[AutofillDataItem alloc] initWithType:ItemTypeAutofillDynamicHeight];
item.text = @"Main Text";
item.leadingDetailText = @"Leading Detail Text";
item.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator;
return item;
}
- (CollectionViewItem*)autofillItemWithAllText {
AutofillDataItem* item =
[[AutofillDataItem alloc] initWithType:ItemTypeAutofillDynamicHeight];
item.text = @"Main Text";
item.leadingDetailText = @"Leading Detail Text";
item.trailingDetailText = @"Trailing Detail Text";
item.accessoryType = MDCCollectionViewCellAccessoryDisclosureIndicator;
return item;
}
- (CollectionViewItem*)autofillEditItem {
LegacyAutofillEditItem* item = [[LegacyAutofillEditItem alloc]
initWithType:ItemTypeAutofillDynamicHeight];
item.cellStyle = CollectionViewCellStyle::kUIKit;
item.textFieldName = @"Required Card Number";
item.textFieldValue = @"4111111111111111";
item.textFieldEnabled = YES;
item.required = YES;
return item;
}
- (CollectionViewItem*)autofillEditItemWithIcon {
LegacyAutofillEditItem* item = [[LegacyAutofillEditItem alloc]
initWithType:ItemTypeAutofillDynamicHeight];
item.cellStyle = CollectionViewCellStyle::kUIKit;
item.textFieldName = @"Card Number";
item.textFieldValue = @"4111111111111111";
item.textFieldEnabled = YES;
int resourceID =
autofill::data_util::GetPaymentRequestData(autofill::kVisaCard)
.icon_resource_id;
item.identifyingIcon =
ResizeImage(NativeImage(resourceID), CGSizeMake(30.0, 30.0),
ProjectionMode::kAspectFillNoClipping);
return item;
}
- (CollectionViewItem*)cvcItem {
CVCItem* item = [[CVCItem alloc] initWithType:ItemTypeAutofillCVC];
item.instructionsText =
@"This is a long text explaining to enter card details and what "
@"will happen afterwards.";
item.CVCImageResourceID = IDR_CREDIT_CARD_CVC_HINT;
return item;
}
- (CollectionViewItem*)cvcItemWithDate {
CVCItem* item = [[CVCItem alloc] initWithType:ItemTypeAutofillCVC];
item.instructionsText =
@"This is a long text explaining to enter card details and what "
@"will happen afterwards.";
item.CVCImageResourceID = IDR_CREDIT_CARD_CVC_HINT;
item.showDateInput = YES;
return item;
}
- (CollectionViewItem*)cvcItemWithError {
CVCItem* item = [[CVCItem alloc] initWithType:ItemTypeAutofillCVC];
item.instructionsText =
@"This is a long text explaining to enter card details and what "
@"will happen afterwards. Is this long enough to span 3 lines?";
item.errorMessage = @"Some error";
item.CVCImageResourceID = IDR_CREDIT_CARD_CVC_HINT_AMEX;
item.showNewCardButton = YES;
item.showCVCInputError = YES;
return item;
}
- (CollectionViewItem*)statusItemVerifying {
StatusItem* item = [[StatusItem alloc] initWithType:ItemTypeAutofillStatus];
item.text = @"Verifying…";
return item;
}
- (CollectionViewItem*)statusItemVerified {
StatusItem* item = [[StatusItem alloc] initWithType:ItemTypeAutofillStatus];
item.state = StatusItemState::VERIFIED;
item.text = @"Verified!";
return item;
}
- (CollectionViewItem*)statusItemError {
StatusItem* item = [[StatusItem alloc] initWithType:ItemTypeAutofillStatus];
item.state = StatusItemState::ERROR;
item.text = @"There was a really long error. We can't tell you more, but we "
@"will still display this long string.";
return item;
}
- (CollectionViewFooterItem*)shortFooterItem {
CollectionViewFooterItem* footerItem =
[[CollectionViewFooterItem alloc] initWithType:ItemTypeFooter];
footerItem.text = @"Hello";
return footerItem;
}
- (CollectionViewFooterItem*)longFooterItem {
CollectionViewFooterItem* footerItem =
[[CollectionViewFooterItem alloc] initWithType:ItemTypeFooter];
footerItem.text = @"Hello Hello Hello Hello Hello Hello Hello Hello Hello "
@"Hello Hello Hello Hello Hello Hello Hello Hello Hello "
@"Hello Hello Hello Hello Hello Hello Hello Hello Hello ";
footerItem.image = [UIImage imageNamed:@"app_icon_placeholder"];
return footerItem;
}
- (ContentSuggestionsItem*)contentSuggestionsItem {
ContentSuggestionsItem* articleItem = [[ContentSuggestionsItem alloc]
initWithType:ItemTypeContentSuggestions
title:@"This is an incredible article, you should read it!"
url:GURL()];
articleItem.publisher = @"Top Publisher.com";
return articleItem;
}
- (SettingsImageDetailTextItem*)settingsImageDetailTextItem {
SettingsImageDetailTextItem* settingsImageDetailTextItem =
[[SettingsImageDetailTextItem alloc]
initWithType:ItemTypeImageDetailTextItem];
settingsImageDetailTextItem.image =
[UIImage imageNamed:@"ios_default_avatar"];
settingsImageDetailTextItem.text =
@"Text multiline that works nice with a very very very very very long "
@"text";
return settingsImageDetailTextItem;
}
- (ContentSuggestionsFooterItem*)contentSuggestionsFooterItem {
ContentSuggestionsFooterItem* footerItem =
[[ContentSuggestionsFooterItem alloc]
initWithType:ItemTypeContentSuggestions
title:@"Footer title"
callback:nil];
return footerItem;
}
- (EncryptionItem*)syncEncryptionItem {
EncryptionItem* item =
[[EncryptionItem alloc] initWithType:ItemTypeSyncEncryption];
item.text =
@"These two cells have exactly the same text, but one has a checkmark "
@"and the other does not. They should lay out identically, and the "
@"presence of the checkmark should not cause the text to reflow.";
return item;
}
- (EncryptionItem*)syncEncryptionCheckedItem {
EncryptionItem* item =
[[EncryptionItem alloc] initWithType:ItemTypeSyncEncryptionChecked];
item.text =
@"These two cells have exactly the same text, but one has a checkmark "
@"and the other does not. They should lay out identically, and the "
@"presence of the checkmark should not cause the text to reflow.";
item.accessoryType = MDCCollectionViewCellAccessoryCheckmark;
return item;
}
- (PassphraseErrorItem*)syncPassphraseErrorItem {
PassphraseErrorItem* item =
[[PassphraseErrorItem alloc] initWithType:ItemTypeSyncPassphraseError];
item.text = @"Incorrect passphrase";
return item;
}
- (PasswordDetailsItem*)passwordDetailsShortHiddenItem {
PasswordDetailsItem* item = [[PasswordDetailsItem alloc]
initWithType:ItemTypePasswordDetailsShortHidden];
item.text = @"hunter2";
return item;
}
- (PasswordDetailsItem*)passwordDetailsShortVisibleItem {
PasswordDetailsItem* item = [[PasswordDetailsItem alloc]
initWithType:ItemTypePasswordDetailsShortVisible];
item.text = @"hunter2";
item.showingText = YES;
return item;
}
- (PasswordDetailsItem*)passwordDetailsLongItem {
PasswordDetailsItem* item =
[[PasswordDetailsItem alloc] initWithType:ItemTypePasswordDetailsLong];
item.text =
@"Lorem ipsum dolor sit amet, consectetur "
@"adipiscing elit, sed do eiusmod tempor "
@"incididunt ut labore et dolore magna aliqua.";
return item;
}
- (SettingsSearchItem*)settingsSearchItem {
SettingsSearchItem* item =
[[SettingsSearchItem alloc] initWithType:ItemTypeSettingsSearch];
item.placeholder = @"Search Here";
return item;
}
@end