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

Side by Side Diff: chrome/browser/ui/cocoa/passwords/account_chooser_view_controller.mm

Issue 1610653002: Integrate the account chooser dialog on Mac. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 11 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 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 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 "chrome/browser/ui/cocoa/passwords/account_chooser_view_controller.h" 5 #import "chrome/browser/ui/cocoa/passwords/account_chooser_view_controller.h"
6 6
7 #include <cmath> 7 #include <cmath>
8 8
9 #include "base/strings/sys_string_conversions.h" 9 #include "base/strings/sys_string_conversions.h"
10 #include "chrome/browser/profiles/profile.h"
11 #import "chrome/browser/ui/cocoa/bubble_combobox.h"
12 #import "chrome/browser/ui/cocoa/passwords/account_avatar_fetcher_manager.h" 10 #import "chrome/browser/ui/cocoa/passwords/account_avatar_fetcher_manager.h"
13 #import "chrome/browser/ui/cocoa/passwords/passwords_bubble_utils.h" 11 #import "chrome/browser/ui/cocoa/passwords/passwords_bubble_utils.h"
14 #include "chrome/browser/ui/passwords/account_chooser_more_combobox_model.h" 12 #include "chrome/browser/ui/passwords/password_dialog_controller.h"
15 #include "chrome/browser/ui/passwords/manage_passwords_bubble_model.h"
16 #include "chrome/grit/generated_resources.h" 13 #include "chrome/grit/generated_resources.h"
17 #include "components/password_manager/core/common/credential_manager_types.h" 14 #include "components/password_manager/core/common/credential_manager_types.h"
15 #include "ui/base/cocoa/controls/hyperlink_text_view.h"
18 #include "ui/base/l10n/l10n_util.h" 16 #include "ui/base/l10n/l10n_util.h"
19 17
20 @implementation CredentialItemCell { 18 @implementation CredentialItemCell {
21 base::scoped_nsobject<CredentialItemView> view_; 19 base::scoped_nsobject<CredentialItemView> view_;
22 } 20 }
23 - (id)initWithView:(CredentialItemView*)view { 21 - (id)initWithView:(CredentialItemView*)view {
24 if ((self = [super init])) 22 if ((self = [super init]))
25 view_.reset([view retain]); 23 view_.reset([view retain]);
26 return self; 24 return self;
27 } 25 }
28 - (void)drawInteriorWithFrame:(NSRect)cellFrame inView:(NSView*)controlView { 26 - (void)drawInteriorWithFrame:(NSRect)cellFrame inView:(NSView*)controlView {
29 [controlView addSubview:view_]; 27 [controlView addSubview:view_];
30 [view_ setFrame:cellFrame]; 28 [view_ setFrame:cellFrame];
31 } 29 }
32 - (id)copyWithZone:(NSZone*)zone { 30 - (id)copyWithZone:(NSZone*)zone {
33 return [[CredentialItemCell alloc] initWithView:view_]; 31 return [[CredentialItemCell alloc] initWithView:view_];
34 } 32 }
35 - (CredentialItemView*)view { 33 - (CredentialItemView*)view {
36 return view_.get(); 34 return view_.get();
37 } 35 }
38 @end 36 @end
39 37
40 @interface ManagePasswordsBubbleAccountChooserViewController() 38 @interface AccountChooserViewController()
41 - (id)initWithModel:(ManagePasswordsBubbleModel*)model
42 avatarManager:(AccountAvatarFetcherManager*)avatarManager
43 delegate:(id<ManagePasswordsBubbleContentViewDelegate>)delegate;
44 - (void)onCancelClicked:(id)sender; 39 - (void)onCancelClicked:(id)sender;
45 - (void)onLearnMoreClicked:(id)sender; 40 + (NSArray*)credentialItemsFromBridge:(AccountChooserBridge*)bridge
46 - (void)onSettingsClicked:(id)sender; 41 delegate:(id<CredentialItemDelegate>)delegate;
47 + (NSArray*)credentialItemsForModel:(ManagePasswordsBubbleModel*)model
48 delegate:(id<CredentialItemDelegate>)delegate;
49 @property(nonatomic, readonly) NSButton* cancelButton;
50 @property(nonatomic, readonly) BubbleCombobox* moreButton;
51 @property(nonatomic, readonly) NSTableView* credentialsView;
52 @end 42 @end
53 43
54 @implementation ManagePasswordsBubbleAccountChooserViewController 44 @implementation AccountChooserViewController
55 45
56 @synthesize cancelButton = cancelButton_; 46 - (id)initWithBridge:(AccountChooserBridge*)bridge {
57 @synthesize moreButton = moreButton_;
58 @synthesize credentialsView = credentialsView_;
59
60 - (id)initWithModel:(ManagePasswordsBubbleModel*)model
61 avatarManager:(AccountAvatarFetcherManager*)avatarManager
62 delegate:(id<ManagePasswordsBubbleContentViewDelegate>)delegate {
63 DCHECK(model);
64 if (([super initWithDelegate:delegate])) {
65 model_ = model;
66 avatarManager_.reset([avatarManager retain]);
67 }
68 return self;
69 }
70
71 - (id)initWithModel:(ManagePasswordsBubbleModel*)model
72 delegate:(id<ManagePasswordsBubbleContentViewDelegate>)delegate {
73 base::scoped_nsobject<AccountAvatarFetcherManager> avatarManager( 47 base::scoped_nsobject<AccountAvatarFetcherManager> avatarManager(
74 [[AccountAvatarFetcherManager alloc] 48 [[AccountAvatarFetcherManager alloc]
75 initWithRequestContext:model->GetProfile()->GetRequestContext()]); 49 initWithRequestContext:bridge->GetRequestContext()]);
76 return 50 return [self initWithBridge:bridge avatarManager:avatarManager];
77 [self initWithModel:model avatarManager:avatarManager delegate:delegate];
78 } 51 }
79 52
80 - (void)dealloc { 53 - (void)dealloc {
81 [credentialsView_ setDelegate:nil]; 54 [credentialsView_ setDelegate:nil];
82 [credentialsView_ setDataSource:nil]; 55 [credentialsView_ setDataSource:nil];
83 [super dealloc]; 56 [super dealloc];
84 } 57 }
85 58
86 - (void)loadView { 59 - (void)loadView {
87 base::scoped_nsobject<NSView> view([[NSView alloc] initWithFrame:NSZeroRect]); 60 base::scoped_nsobject<NSView> view([[NSView alloc] initWithFrame:NSZeroRect]);
88 61
89 // ------------------------------------ 62 // ------------------------------------
90 // | | 63 // | |
91 // | Choose an account etc etc | 64 // | Choose an account etc etc |
92 // | | 65 // | |
93 // | ---- | 66 // | ---- |
94 // | | | credential view | 67 // | | | credential view |
95 // | ---- | 68 // | ---- |
96 // | | | credential view | 69 // | | | credential view |
97 // | ---- | 70 // | ---- |
98 // | | 71 // | |
99 // | [ More v] [ Cancel ] | 72 // | [ Cancel ] |
100 // ------------------------------------ 73 // ------------------------------------
101 74
102 // Create the views. 75 // Create the views.
103 // Title. 76 // Title.
104 NSTextField* title = 77 std::pair<base::string16, gfx::Range> title_text =
105 [self addTitleLabel:base::SysUTF16ToNSString(model_->title()) 78 bridge_->GetDialogController()->GetAccoutChooserTitle();
106 toView:view]; 79 titleView_ = TitleLabelWithLink(title_text.first, title_text.second, self);
107 [title setAlignment:base::i18n::IsRTL() ? NSRightTextAlignment 80 // Force the text to wrap to fit in the bubble size.
108 : NSLeftTextAlignment]; 81 [titleView_ setVerticallyResizable:YES];
82 const CGFloat width = kDesiredBubbleWidth - 2*kFramePadding;
83 [titleView_ setFrameSize:NSMakeSize(width, MAXFLOAT)];
84 [titleView_ sizeToFit];
85 [view addSubview:titleView_];
109 86
110 // Credentials list. 87 // Credentials list.
111 credentialItems_.reset( 88 credentialItems_.reset(
112 [[[self class] credentialItemsForModel:model_ delegate:self] retain]); 89 [[[self class] credentialItemsFromBridge:bridge_ delegate:self] retain]);
113 base::scoped_nsobject<NSTableView> credentialsView( 90 base::scoped_nsobject<NSTableView> credentialsView(
114 [[NSTableView alloc] initWithFrame:NSZeroRect]); 91 [[NSTableView alloc] initWithFrame:NSZeroRect]);
115 [credentialsView 92 [credentialsView
116 setSelectionHighlightStyle:NSTableViewSelectionHighlightStyleNone]; 93 setSelectionHighlightStyle:NSTableViewSelectionHighlightStyleNone];
117 NSTableColumn* column = 94 NSTableColumn* column =
118 [[[NSTableColumn alloc] initWithIdentifier:@""] autorelease]; 95 [[[NSTableColumn alloc] initWithIdentifier:@""] autorelease];
119 [credentialsView addTableColumn:column]; 96 [credentialsView addTableColumn:column];
120 [credentialsView setDelegate:self]; 97 [credentialsView setDelegate:self];
121 [credentialsView setDataSource:self]; 98 [credentialsView setDataSource:self];
122 [credentialsView setFocusRingType:NSFocusRingTypeNone]; 99 [credentialsView setFocusRingType:NSFocusRingTypeNone];
123 credentialsView_ = credentialsView; 100 credentialsView_ = credentialsView;
124 [view addSubview:credentialsView_]; 101 [view addSubview:credentialsView_];
125 102
126 // "Cancel" button. 103 // "Cancel" button.
127 cancelButton_ = 104 cancelButton_ = DialogButton(l10n_util::GetNSString(
128 [self addButton:l10n_util::GetNSString( 105 IDS_CREDENTIAL_MANAGEMENT_ACCOUNT_CHOOSER_NO_THANKS));
129 IDS_CREDENTIAL_MANAGEMENT_ACCOUNT_CHOOSER_NO_THANKS) 106 [cancelButton_ setTarget:self];
130 toView:view 107 [cancelButton_ setAction:@selector(onCancelClicked:)];
131 target:self 108 [view addSubview:cancelButton_];
132 action:@selector(onCancelClicked:)];
133
134 // "More" button.
135 AccountChooserMoreComboboxModel comboboxModel;
136 moreButton_ = [[BubbleCombobox alloc] initWithFrame:NSZeroRect
137 pullsDown:YES
138 model:&comboboxModel];
139 [moreButton_ sizeToFit];
140 NSMenuItem* learnMoreItem = [moreButton_
141 itemAtIndex:AccountChooserMoreComboboxModel::INDEX_LEARN_MORE];
142 [learnMoreItem setTarget:self];
143 [learnMoreItem setAction:@selector(onLearnMoreClicked:)];
144 NSMenuItem* settingsItem =
145 [moreButton_ itemAtIndex:AccountChooserMoreComboboxModel::INDEX_SETTINGS];
146 [settingsItem setTarget:self];
147 [settingsItem setAction:@selector(onSettingsClicked:)];
148 [view addSubview:moreButton_];
149 109
150 // Lay out the views. 110 // Lay out the views.
151 const CGFloat width = 111 [cancelButton_ setFrameOrigin:NSMakePoint(
152 std::max(NSWidth([title frame]), NSWidth([credentialsView_ frame])); 112 kFramePadding + width - NSWidth([cancelButton_ frame]),
153 [cancelButton_ 113 kFramePadding)];
154 setFrameOrigin:NSMakePoint(base::i18n::IsRTL()
155 ? kFramePadding
156 : kFramePadding + width -
157 NSWidth([cancelButton_ frame]),
158 kFramePadding)];
159 [moreButton_
160 setFrameOrigin:NSMakePoint(base::i18n::IsRTL()
161 ? NSMaxX([cancelButton_ frame]) +
162 kRelatedControlHorizontalPadding
163 : NSMinX([cancelButton_ frame]) -
164 kRelatedControlHorizontalPadding -
165 NSWidth([moreButton_ frame]),
166 std::ceil(kFramePadding +
167 (NSHeight([cancelButton_ frame]) -
168 NSHeight([moreButton_ frame])) /
169 2.0f))];
170 114
171 // The credentials TableView expands to fill available space. 115 // The credentials TableView expands to fill available space.
172 [column setMaxWidth:width]; 116 [column setMaxWidth:width];
173 [credentialsView 117 [credentialsView
174 setFrameSize:NSMakeSize(width, NSHeight([credentialsView_ frame]))]; 118 setFrameSize:NSMakeSize(width, NSHeight([credentialsView_ frame]))];
175 [credentialsView_ 119 [credentialsView_
176 setFrameOrigin:NSMakePoint(kFramePadding, 120 setFrameOrigin:NSMakePoint(kFramePadding,
177 NSMaxY([cancelButton_ frame]) + 121 NSMaxY([cancelButton_ frame]) +
178 kUnrelatedControlVerticalPadding)]; 122 kUnrelatedControlVerticalPadding)];
179 123
180 [title setFrameOrigin:NSMakePoint( 124 [titleView_ setFrameOrigin:NSMakePoint(
181 base::i18n::IsRTL() 125 kFramePadding,
182 ? kFramePadding + width - NSWidth([title frame]) 126 NSMaxY([credentialsView_ frame]) + kUnrelatedControlVerticalPadding)];
183 : kFramePadding,
184 NSMaxY([credentialsView_ frame]) +
185 kUnrelatedControlVerticalPadding)];
186 127
187 // Compute the frame to hold all the views. 128 const CGFloat frameHeight = NSMaxY([titleView_ frame]) + kFramePadding;
188 const CGFloat frameWidth = width + 2 * kFramePadding; 129 [view setFrame:NSMakeRect(0, 0, kDesiredBubbleWidth, frameHeight)];
189 const CGFloat frameHeight = NSMaxY([title frame]) + kFramePadding;
190 [view setFrame:NSMakeRect(0, 0, frameWidth, frameHeight)];
191 130
192 [self setView:view]; 131 [self setView:view];
193 } 132 }
194 133
195 - (void)onCancelClicked:(id)sender { 134 - (BOOL)textView:(NSTextView*)textView
196 model_->OnCancelClicked(); 135 clickedOnLink:(id)link
197 [delegate_ viewShouldDismiss]; 136 atIndex:(NSUInteger)charIndex {
137 bridge_->GetDialogController()->OnSmartLockLinkClicked();
138 return YES;
198 } 139 }
199 140
200 - (void)onLearnMoreClicked:(id)sender { 141 - (void)onCancelClicked:(id)sender {
201 // TODO(dconnelly): Open some help center article that's not written yet. 142 bridge_->PerformClose();
202 [delegate_ viewShouldDismiss];
203 }
204
205 - (void)onSettingsClicked:(id)sender {
206 model_->OnManageLinkClicked();
207 [delegate_ viewShouldDismiss];
208 } 143 }
209 144
210 - (void)fetchAvatar:(const GURL&)avatarURL forView:(CredentialItemView*)view { 145 - (void)fetchAvatar:(const GURL&)avatarURL forView:(CredentialItemView*)view {
211 [avatarManager_ fetchAvatar:avatarURL forView:view]; 146 [avatarManager_ fetchAvatar:avatarURL forView:view];
212 } 147 }
213 148
214 + (NSArray*)credentialItemsForModel:(ManagePasswordsBubbleModel*)model 149 + (NSArray*)credentialItemsFromBridge:(AccountChooserBridge*)bridge
215 delegate:(id<CredentialItemDelegate>)delegate { 150 delegate:(id<CredentialItemDelegate>)delegate {
216 base::scoped_nsobject<NSMutableArray> items([[NSMutableArray alloc] init]); 151 base::scoped_nsobject<NSMutableArray> items([[NSMutableArray alloc] init]);
217 for (auto form : model->local_credentials()) { 152 PasswordDialogController* controller = bridge->GetDialogController();
153 for (const auto& form : controller->GetLocalForms()) {
218 base::scoped_nsobject<CredentialItemView> item([[CredentialItemView alloc] 154 base::scoped_nsobject<CredentialItemView> item([[CredentialItemView alloc]
219 initWithPasswordForm:*form 155 initWithPasswordForm:*form
220 credentialType:password_manager::CredentialType:: 156 credentialType:password_manager::CredentialType::
221 CREDENTIAL_TYPE_PASSWORD 157 CREDENTIAL_TYPE_PASSWORD
222 style:password_manager_mac::CredentialItemStyle:: 158 style:password_manager_mac::CredentialItemStyle::
223 ACCOUNT_CHOOSER 159 ACCOUNT_CHOOSER
224 delegate:delegate]); 160 delegate:delegate]);
225 [item setAutoresizingMask:NSViewWidthSizable]; 161 [item setAutoresizingMask:NSViewWidthSizable];
226 [items addObject:item]; 162 [items addObject:item];
227 } 163 }
228 for (auto form : model->federated_credentials()) { 164 for (const auto& form : controller->GetFederationsForms()) {
229 base::scoped_nsobject<CredentialItemView> item([[CredentialItemView alloc] 165 base::scoped_nsobject<CredentialItemView> item([[CredentialItemView alloc]
230 initWithPasswordForm:*form 166 initWithPasswordForm:*form
231 credentialType:password_manager::CredentialType:: 167 credentialType:password_manager::CredentialType::
232 CREDENTIAL_TYPE_FEDERATED 168 CREDENTIAL_TYPE_FEDERATED
233 style:password_manager_mac::CredentialItemStyle:: 169 style:password_manager_mac::CredentialItemStyle::
234 ACCOUNT_CHOOSER 170 ACCOUNT_CHOOSER
235 delegate:delegate]); 171 delegate:delegate]);
236 [item setAutoresizingMask:NSViewWidthSizable]; 172 [item setAutoresizingMask:NSViewWidthSizable];
237 [items addObject:item]; 173 [items addObject:item];
238 } 174 }
(...skipping 15 matching lines...) Expand all
254 - (NSCell*)tableView:(NSTableView*)tableView 190 - (NSCell*)tableView:(NSTableView*)tableView
255 dataCellForTableColumn:(NSTableColumn*)tableColumn 191 dataCellForTableColumn:(NSTableColumn*)tableColumn
256 row:(NSInteger)row { 192 row:(NSInteger)row {
257 return [[[CredentialItemCell alloc] 193 return [[[CredentialItemCell alloc]
258 initWithView:[credentialItems_.get() objectAtIndex:row]] autorelease]; 194 initWithView:[credentialItems_.get() objectAtIndex:row]] autorelease];
259 } 195 }
260 196
261 - (void)tableViewSelectionDidChange:(NSNotification *)notification { 197 - (void)tableViewSelectionDidChange:(NSNotification *)notification {
262 CredentialItemView* item = 198 CredentialItemView* item =
263 [credentialItems_.get() objectAtIndex:[credentialsView_ selectedRow]]; 199 [credentialItems_.get() objectAtIndex:[credentialsView_ selectedRow]];
264 model_->OnChooseCredentials(item.passwordForm, item.credentialType); 200 bridge_->GetDialogController()->OnChooseCredentials(item.passwordForm,
265 [delegate_ viewShouldDismiss]; 201 item.credentialType);
266 } 202 }
267 203
268 @end 204 @end
205
206 @implementation AccountChooserViewController(Testing)
207
208 - (id)initWithBridge:(AccountChooserBridge*)bridge
209 avatarManager:(AccountAvatarFetcherManager*)avatarManager {
210 DCHECK(bridge);
211 if (self = [super initWithNibName:nil bundle:nil]) {
212 bridge_ = bridge;
213 avatarManager_.reset([avatarManager retain]);
214 }
215 return self;
216 }
217
218 - (NSButton*)cancelButton {
219 return cancelButton_;
220 }
221
222 - (NSTableView*)credentialsView {
223 return credentialsView_;
224 }
225
226 - (NSTextView*)titleView {
227 return titleView_;
228 }
229
230 @end
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698