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

Unified Diff: ios/chrome/browser/ui/authentication/signin_promo_view.mm

Issue 2749703003: Adding mediator for Sign-in promo (Closed)
Patch Set: Visual constraints Created 3 years, 9 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 side-by-side diff with in-line comments
Download patch
Index: ios/chrome/browser/ui/authentication/signin_promo_view.mm
diff --git a/ios/chrome/browser/ui/authentication/signin_promo_view.mm b/ios/chrome/browser/ui/authentication/signin_promo_view.mm
new file mode 100644
index 0000000000000000000000000000000000000000..14d58a1ed9ae6d3b0d457195574a46b0b1042a29
--- /dev/null
+++ b/ios/chrome/browser/ui/authentication/signin_promo_view.mm
@@ -0,0 +1,280 @@
+// Copyright 2017 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/authentication/signin_promo_view.h"
+
+#include "base/logging.h"
+#import "ios/chrome/browser/ui/colors/MDCPalette+CrAdditions.h"
+#import "ios/chrome/browser/ui/uikit_ui_util.h"
+#include "ios/chrome/grit/ios_strings.h"
+#import "ios/third_party/material_components_ios/src/components/Buttons/src/MaterialButtons.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 {
+// Horizontal padding for label and buttons.
+const CGFloat kHorizontalPadding = 40;
+// Vertical padding for the image and the label.
+const CGFloat kVerticalPadding = 12;
+// Vertical padding for buttons.
+const CGFloat kButtonVerticalPadding = 6;
+// Image size for warm start.
+const CGFloat kProfileImageFixedSize = 48;
+// Image size for cold start.
+const CGFloat kChromeImageFixedSize = 24;
msarda 2017/03/22 12:18:39 I expect the profile image and the chrome image sh
lpromero 2017/03/24 10:36:20 That would be simpler for us. Try to push back to
jlebel 2017/03/24 20:59:08 I don't understand my code already handles the 2 s
+// Button height.
+const CGFloat kButtonHeight = 36;
+}
+
+@implementation SigninPromoView {
+ SigninPromoViewMode _mode;
lpromero 2017/03/24 10:36:20 These 5 ivars are not needed, as they are generate
jlebel 2017/03/24 20:59:09 Done.
+ UIImageView* _imageView;
+ UILabel* _textLabel;
+ MDCFlatButton* _primaryButton;
+ MDCFlatButton* _secondaryButton;
+
+ NSArray<NSLayoutConstraint*>* _coldStartConstraints;
msarda 2017/03/22 12:18:39 s/_coldStartConstraints/_secondaryButtonVisibleCon
lpromero 2017/03/24 10:36:20 Actually, I like the abstraction the names give.
jlebel 2017/03/24 20:59:09 Acknowledged.
+ NSArray<NSLayoutConstraint*>* _warmStartConstraints;
msarda 2017/03/22 12:18:39 s/_coldStartConstraints/_secondaryButtonHiddenCons
jlebel 2017/03/24 20:59:09 Acknowledged.
+}
+
+@synthesize mode = _mode;
+@synthesize imageView = _imageView;
+@synthesize textLabel = _textLabel;
+@synthesize primaryButton = _primaryButton;
+@synthesize secondaryButton = _secondaryButton;
+
+- (instancetype)initWithCoder:(NSCoder*)aDecoder {
lpromero 2017/03/24 10:36:20 No need for this (see similar comment above or bel
jlebel 2017/03/24 20:59:09 Done.
+ NOTREACHED();
+ return nil;
+}
+
+- (instancetype)initWithFrame:(CGRect)frame {
+ self = [super initWithFrame:frame];
+ if (self) {
+ self.translatesAutoresizingMaskIntoConstraints = NO;
+ self.isAccessibilityElement = YES;
+ [self addSubviews];
+ [self setDefaultViewStyling];
+ [self setViewConstraints];
msarda 2017/03/22 12:18:39 Consider calling [self setMode:SigninPromoViewCold
lpromero 2017/03/24 10:36:20 Ha! Mihai, you advised against calling methods in
jlebel 2017/03/24 20:59:09 I can't call -[SigninPromoView setMode:] in the in
+ _mode = SigninPromoViewColdStartMode;
+ [self activateColdMode];
+ }
+ return self;
+}
+
+- (void)addSubviews {
+ self.clipsToBounds = YES;
+
+ _imageView = [[UIImageView alloc] init];
+ _imageView.translatesAutoresizingMaskIntoConstraints = NO;
+ [self addSubview:_imageView];
+
+ _textLabel = [[UILabel alloc] init];
+ _textLabel.translatesAutoresizingMaskIntoConstraints = NO;
+ [self addSubview:_textLabel];
+
+ _primaryButton = [[MDCFlatButton alloc] init];
+ _primaryButton.translatesAutoresizingMaskIntoConstraints = NO;
+ _primaryButton.accessibilityIdentifier = @"signin_promo_primary_button";
+ [self addSubview:_primaryButton];
+
+ _secondaryButton = [[MDCFlatButton alloc] init];
+ _secondaryButton.translatesAutoresizingMaskIntoConstraints = NO;
+ _secondaryButton.accessibilityIdentifier = @"signin_promo_secondary_button";
+ [self addSubview:_secondaryButton];
+}
+
+- (void)setDefaultViewStyling {
+ _imageView.contentMode = UIViewContentModeCenter;
+ _imageView.layer.masksToBounds = YES;
+ _imageView.contentMode = UIViewContentModeScaleAspectFit;
+
+ _textLabel.font = [MDCTypography buttonFont];
+ _textLabel.textColor = [[MDCPalette greyPalette] tint900];
+ _textLabel.numberOfLines = 0;
+ _textLabel.textAlignment = NSTextAlignmentCenter;
+
+ [_primaryButton setBackgroundColor:[[MDCPalette cr_bluePalette] tint500]
+ forState:UIControlStateNormal];
+ _primaryButton.customTitleColor = [UIColor whiteColor];
+ _primaryButton.inkColor = [UIColor colorWithWhite:1 alpha:0.2];
+
+ _secondaryButton.customTitleColor = [[MDCPalette cr_bluePalette] tint500];
+ _secondaryButton.uppercaseTitle = NO;
+}
+
+- (void)setViewConstraints {
+ NSDictionary* metrics = @{
+ @"kButtonHeight" : @(kButtonHeight),
+ @"kButtonVerticalPadding" : @(kButtonVerticalPadding),
+ @"kButtonVerticalPaddingx2" : @(kButtonVerticalPadding * 2),
+ @"kChromeImageFixedSize" : @(kChromeImageFixedSize),
+ @"kHorizontalPadding" : @(kHorizontalPadding),
+ @"kProfileImageFixedSize" : @(kProfileImageFixedSize),
+ @"kVerticalPadding" : @(kVerticalPadding),
+ @"kVerticalPaddingx2" : @(kVerticalPadding * 2),
+ @"kVerticalPaddingkButtonVerticalPadding" :
+ @(kVerticalPadding + kButtonVerticalPadding),
+ };
+ NSDictionary* views = @{
+ @"imageView" : _imageView,
+ @"primaryButton" : _primaryButton,
+ @"secondaryButton" : _secondaryButton,
+ @"textLabel" : _textLabel,
+ };
+
+ // Constraints in shared between modes.
msarda 2017/03/22 12:18:39 Constraints shared between modes.
jlebel 2017/03/24 20:59:09 Done.
+ NSString* formatString =
+ @"V:|-kVerticalPaddingx2-[imageView]-kVerticalPadding-[textLabel]-"
+ @"kVerticalPaddingkButtonVerticalPadding-[primaryButton(kButtonHeight)]";
msarda 2017/03/22 12:18:39 Personal pref: Consider removing the @ on this sec
lpromero 2017/03/24 10:36:20 Agreed, I thought it was a second string.
jlebel 2017/03/24 20:59:09 Done.
+ [NSLayoutConstraint
+ activateConstraints:
+ [NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:NSLayoutFormatAlignAllCenterX
+ metrics:metrics
+ views:views]];
+
+ formatString = @"H:|-kHorizontalPadding-[primaryButton]-kHorizontalPadding-|";
msarda 2017/03/22 12:18:39 You can put all these visual constraints in a sing
jlebel 2017/03/24 20:59:08 Done.
+ [NSLayoutConstraint
msarda 2017/03/22 12:18:39 I think this code would be so much simpler to read
jlebel 2017/03/24 20:59:09 I will do that in another patch.
msarda 2017/03/27 09:34:16 I have a strong preference for this as I think it
+ activateConstraints:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+
+ // Constraints for cold start mode.
+ NSMutableArray* constraints = [NSMutableArray array];
+ formatString = @"V:[primaryButton]-kVerticalPaddingkButtonVerticalPadding-|";
+ [constraints addObjectsFromArray:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+ formatString = @"H:[imageView(kChromeImageFixedSize)]";
+ [constraints addObjectsFromArray:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+ formatString = @"V:[imageView(kChromeImageFixedSize)]";
+ [constraints addObjectsFromArray:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+ _coldStartConstraints = [constraints copy];
+
+ // Constraints for warm start mode.
+ constraints = [NSMutableArray array];
+ formatString = @"V:[primaryButton]-kButtonVerticalPaddingx2-[secondaryButton("
+ @"kButtonHeight)]-kVerticalPaddingkButtonVerticalPadding-|";
+ [constraints addObjectsFromArray:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+ formatString =
+ @"H:|-kHorizontalPadding-[secondaryButton]-kHorizontalPadding-|";
+ [constraints addObjectsFromArray:
+ [NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:NSLayoutFormatAlignAllCenterX
lpromero 2017/03/24 10:36:20 Isn't tis option already done with line 138?
jlebel 2017/03/24 20:59:09 I didn't know it applied to the secondary button e
lpromero 2017/03/27 13:14:46 Oh good catch. Line 138 might not set this then.
+ metrics:metrics
+ views:views]];
+ formatString = @"H:[imageView(kProfileImageFixedSize)]";
+ [constraints addObjectsFromArray:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+ formatString = @"V:[imageView(kProfileImageFixedSize)]";
+ [constraints addObjectsFromArray:[NSLayoutConstraint
+ constraintsWithVisualFormat:formatString
+ options:0
+ metrics:metrics
+ views:views]];
+ _warmStartConstraints = [constraints copy];
+ _mode = SigninPromoViewWarmStartMode;
msarda 2017/03/22 12:18:39 I think this line needs to be removed.
jlebel 2017/03/24 20:59:09 Done.
+}
+
+- (void)setMode:(SigninPromoViewMode)mode {
+ if (mode == _mode) {
+ return;
+ }
+ _mode = mode;
+ switch (_mode) {
+ case SigninPromoViewColdStartMode:
+ [self activateColdMode];
+ return;
+ case SigninPromoViewWarmStartMode:
+ [self activateWarmMode];
+ return;
+ }
+ NOTREACHED();
+}
+
+- (void)activateColdMode {
msarda 2017/03/22 12:18:39 DCHECK(_mode, COLD);
jlebel 2017/03/24 20:59:09 Done.
+ // TODO(jlebel) Needs to set the chrome/chromium icon in |imageView|.
msarda 2017/03/22 12:18:39 Please remove this TODO as it is the job of the co
jlebel 2017/03/24 20:59:09 I'm going to follow Louis suggestion and keep it t
+ [NSLayoutConstraint deactivateConstraints:_warmStartConstraints];
+ [NSLayoutConstraint activateConstraints:_coldStartConstraints];
+ _secondaryButton.hidden = YES;
+}
+
+- (void)activateWarmMode {
msarda 2017/03/22 12:18:39 DCHECK(_mode, WARM);
jlebel 2017/03/24 20:59:09 Done.
+ [NSLayoutConstraint deactivateConstraints:_coldStartConstraints];
+ [NSLayoutConstraint activateConstraints:_warmStartConstraints];
+ _secondaryButton.hidden = NO;
+}
+
+- (void)setProfileImage:(UIImage*)image {
lpromero 2017/03/24 10:36:20 Can you add a comment in the header that this is a
jlebel 2017/03/24 20:59:09 Should I rephrase: "Should be called only with the
+ if (SigninPromoViewColdStartMode == _mode) {
+ return;
+ }
+ _imageView.image = CircularImageFromImage(image, kProfileImageFixedSize);
+}
+
+- (void)accessibilityPrimaryAction:(id)unused {
+ [_primaryButton sendActionsForControlEvents:UIControlEventTouchUpInside];
+}
+
+- (void)accessibilitySecondaryAction:(id)unused {
+ [_secondaryButton sendActionsForControlEvents:UIControlEventTouchUpInside];
+}
+
+- (CGFloat)horizontalPadding {
lpromero 2017/03/24 10:36:20 Doesn't seem used.
jlebel 2017/03/24 20:59:09 It is used. It is explained in the header why this
lpromero 2017/03/27 13:14:46 Sounds good.
+ return kHorizontalPadding;
+}
+
+#pragma mark - NSObject(Accessibility)
+
+- (NSArray<UIAccessibilityCustomAction*>*)accessibilityCustomActions {
+ NSString* primaryActionName =
+ [_primaryButton titleForState:UIControlStateNormal];
+ UIAccessibilityCustomAction* primaryCustomAction =
+ [[UIAccessibilityCustomAction alloc]
+ initWithName:primaryActionName
+ target:self
+ selector:@selector(accessibilityPrimaryAction:)];
+ if (_mode == SigninPromoViewColdStartMode) {
+ return @[ primaryCustomAction ];
+ }
+ NSString* secondaryActionName =
+ [_secondaryButton titleForState:UIControlStateNormal];
+ UIAccessibilityCustomAction* secondaryCustomAction =
+ [[UIAccessibilityCustomAction alloc]
+ initWithName:secondaryActionName
+ target:self
+ selector:@selector(accessibilitySecondaryAction:)];
+ return @[ primaryCustomAction, secondaryCustomAction ];
+}
+
+- (NSString*)accessibilityLabel {
+ return _textLabel.text;
+}
+
+@end

Powered by Google App Engine
This is Rietveld 408576698