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

Side by Side Diff: chrome/browser/ui/cocoa/notifications/notification_builder_mac.mm

Issue 2799343003: Add support for native extension notifications (Closed)
Patch Set: Created 3 years, 8 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 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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/notifications/notification_builder_mac.h" 5 #import "chrome/browser/ui/cocoa/notifications/notification_builder_mac.h"
6 6
7 #import <AppKit/AppKit.h> 7 #import <AppKit/AppKit.h>
8 8
9 #include "base/mac/mac_util.h" 9 #include "base/mac/mac_util.h"
10 #include "base/mac/scoped_nsobject.h" 10 #include "base/mac/scoped_nsobject.h"
11 11
12 #include "chrome/browser/ui/cocoa/notifications/notification_constants_mac.h" 12 #include "chrome/browser/ui/cocoa/notifications/notification_constants_mac.h"
13 13
14 namespace { 14 namespace {
15 15
16 // Internal builder constants representing the different notification fields 16 // Internal builder constants representing the different notification fields
17 // They don't need to be exposed outside the builder. 17 // They don't need to be exposed outside the builder.
18 18
19 NSString* const kNotificationTitle = @"title"; 19 NSString* const kNotificationTitle = @"title";
20 NSString* const kNotificationSubTitle = @"subtitle"; 20 NSString* const kNotificationSubTitle = @"subtitle";
21 NSString* const kNotificationInformativeText = @"informativeText"; 21 NSString* const kNotificationInformativeText = @"informativeText";
22 NSString* const kNotificationImage = @"icon"; 22 NSString* const kNotificationImage = @"icon";
23 NSString* const kNotificationButtonOne = @"buttonOne"; 23 NSString* const kNotificationButtonOne = @"buttonOne";
24 NSString* const kNotificationButtonTwo = @"buttonTwo"; 24 NSString* const kNotificationButtonTwo = @"buttonTwo";
25 NSString* const kNotificationTag = @"tag"; 25 NSString* const kNotificationTag = @"tag";
26 NSString* const kNotificationCloseButtonTag = @"closeButton"; 26 NSString* const kNotificationCloseButtonTag = @"closeButton";
27 NSString* const kNotificationOptionsButtonTag = @"optionsButton"; 27 NSString* const kNotificationOptionsButtonTag = @"optionsButton";
28 NSString* const kNotificationSettingsButtonTag = @"settingsButton"; 28 NSString* const kNotificationSettingsButtonTag = @"settingsButton";
29
30 // From NotificationCommon#Type hard coded in order to not
31 // pull in the enum into the XPC library.
32 const int kExtensionType = 2;
29 } // namespace 33 } // namespace
30 34
31 @implementation NotificationBuilder { 35 @implementation NotificationBuilder {
32 base::scoped_nsobject<NSMutableDictionary> notificationData_; 36 base::scoped_nsobject<NSMutableDictionary> notificationData_;
33 } 37 }
34 38
35 - (instancetype)initWithCloseLabel:(NSString*)closeLabel 39 - (instancetype)initWithCloseLabel:(NSString*)closeLabel
36 optionsLabel:(NSString*)optionsLabel 40 optionsLabel:(NSString*)optionsLabel
37 settingsLabel:(NSString*)settingsLabel { 41 settingsLabel:(NSString*)settingsLabel {
38 if ((self = [super init])) { 42 if ((self = [super init])) {
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after
135 if ([[NSImage class] conformsToProtocol:@protocol(NSSecureCoding)]) { 139 if ([[NSImage class] conformsToProtocol:@protocol(NSSecureCoding)]) {
136 NSImage* image = [notificationData_ objectForKey:kNotificationImage]; 140 NSImage* image = [notificationData_ objectForKey:kNotificationImage];
137 [toast setContentImage:image]; 141 [toast setContentImage:image];
138 } else { // NSImage only conforms to NSSecureCoding from 10.10 onwards. 142 } else { // NSImage only conforms to NSSecureCoding from 10.10 onwards.
139 base::scoped_nsobject<NSImage> image([[NSImage alloc] 143 base::scoped_nsobject<NSImage> image([[NSImage alloc]
140 initWithData:[notificationData_ objectForKey:kNotificationImage]]); 144 initWithData:[notificationData_ objectForKey:kNotificationImage]]);
141 [toast setContentImage:image]; 145 [toast setContentImage:image];
142 } 146 }
143 } 147 }
144 148
149 // Type (needed to define the buttons)
150 NSNumber* type = [notificationData_
151 objectForKey:notification_constants::kNotificationType];
152
145 // Buttons 153 // Buttons
146 if ([toast respondsToSelector:@selector(_showsButtons)]) { 154 if ([toast respondsToSelector:@selector(_showsButtons)]) {
147 DCHECK([notificationData_ objectForKey:kNotificationCloseButtonTag]); 155 DCHECK([notificationData_ objectForKey:kNotificationCloseButtonTag]);
148 DCHECK([notificationData_ objectForKey:kNotificationSettingsButtonTag]); 156 DCHECK([notificationData_ objectForKey:kNotificationSettingsButtonTag]);
149 DCHECK([notificationData_ objectForKey:kNotificationOptionsButtonTag]); 157 DCHECK([notificationData_ objectForKey:kNotificationOptionsButtonTag]);
150 158
151 [toast setValue:@YES forKey:@"_showsButtons"]; 159 [toast setValue:@YES forKey:@"_showsButtons"];
152 // A default close button label is provided by the platform but we 160 // A default close button label is provided by the platform but we
153 // explicitly override it in case the user decides to not 161 // explicitly override it in case the user decides to not
154 // use the OS language in Chrome. 162 // use the OS language in Chrome.
155 [toast setOtherButtonTitle:[notificationData_ 163 [toast setOtherButtonTitle:[notificationData_
156 objectForKey:kNotificationCloseButtonTag]]; 164 objectForKey:kNotificationCloseButtonTag]];
157 165
166 // Extensions don't have a settings button.
167 BOOL showSettingsButton = (type.unsignedIntegerValue != kExtensionType);
Peter Beverloo 2017/04/07 02:26:53 Could we just give the notificationData_ dictionar
Miguel Garcia 2017/04/07 13:32:07 Yes, in fact we need to store the fact so the resp
168
158 // Display the Settings button as the action button if there are either no 169 // Display the Settings button as the action button if there are either no
159 // developer-provided action buttons, or the alternate action menu is not 170 // developer-provided action buttons, or the alternate action menu is not
160 // available on this Mac version. This avoids needlessly showing the menu. 171 // available on this Mac version. This avoids needlessly showing the menu.
161 // TODO(miguelg): Extensions should not have a settings button.
162 if (![notificationData_ objectForKey:kNotificationButtonOne] || 172 if (![notificationData_ objectForKey:kNotificationButtonOne] ||
163 ![toast respondsToSelector:@selector(_alwaysShowAlternateActionMenu)]) { 173 ![toast respondsToSelector:@selector(_alwaysShowAlternateActionMenu)]) {
164 [toast 174 if (showSettingsButton) {
165 setActionButtonTitle: 175 [toast setActionButtonTitle:
166 [notificationData_ objectForKey:kNotificationSettingsButtonTag]]; 176 [notificationData_
177 objectForKey:kNotificationSettingsButtonTag]];
178 } else {
179 [toast setHasActionButton:NO];
180 }
181
167 } else { 182 } else {
168 // Otherwise show the alternate menu, then show the developer actions and 183 // Otherwise show the alternate menu, then show the developer actions and
169 // finally the settings one. 184 // finally the settings one if needed.
170 DCHECK( 185 DCHECK(
171 [toast respondsToSelector:@selector(_alwaysShowAlternateActionMenu)]); 186 [toast respondsToSelector:@selector(_alwaysShowAlternateActionMenu)]);
172 DCHECK( 187 DCHECK(
173 [toast respondsToSelector:@selector(_alternateActionButtonTitles)]); 188 [toast respondsToSelector:@selector(_alternateActionButtonTitles)]);
174 [toast 189 [toast
175 setActionButtonTitle:[notificationData_ 190 setActionButtonTitle:[notificationData_
176 objectForKey:kNotificationOptionsButtonTag]]; 191 objectForKey:kNotificationOptionsButtonTag]];
177 [toast setValue:@YES forKey:@"_alwaysShowAlternateActionMenu"]; 192 [toast setValue:@YES forKey:@"_alwaysShowAlternateActionMenu"];
178 193
179 NSMutableArray* buttons = [NSMutableArray arrayWithCapacity:3]; 194 NSMutableArray* buttons = [NSMutableArray arrayWithCapacity:3];
180 [buttons 195 [buttons
181 addObject:[notificationData_ objectForKey:kNotificationButtonOne]]; 196 addObject:[notificationData_ objectForKey:kNotificationButtonOne]];
182 if ([notificationData_ objectForKey:kNotificationButtonTwo]) { 197 if ([notificationData_ objectForKey:kNotificationButtonTwo]) {
183 [buttons 198 [buttons
184 addObject:[notificationData_ objectForKey:kNotificationButtonTwo]]; 199 addObject:[notificationData_ objectForKey:kNotificationButtonTwo]];
185 } 200 }
186 [buttons addObject:[notificationData_ 201 if (showSettingsButton) {
187 objectForKey:kNotificationSettingsButtonTag]]; 202 [buttons addObject:[notificationData_
203 objectForKey:kNotificationSettingsButtonTag]];
204 }
205
188 [toast setValue:buttons forKey:@"_alternateActionButtonTitles"]; 206 [toast setValue:buttons forKey:@"_alternateActionButtonTitles"];
189 } 207 }
190 } 208 }
191 209
192 // Tag 210 // Tag
193 if ([toast respondsToSelector:@selector(setIdentifier:)] && 211 if ([toast respondsToSelector:@selector(setIdentifier:)] &&
194 [notificationData_ objectForKey:kNotificationTag]) { 212 [notificationData_ objectForKey:kNotificationTag]) {
195 [toast setValue:[notificationData_ objectForKey:kNotificationTag] 213 [toast setValue:[notificationData_ objectForKey:kNotificationTag]
196 forKey:@"identifier"]; 214 forKey:@"identifier"];
197 } 215 }
(...skipping 11 matching lines...) Expand all
209 227
210 DCHECK([notificationData_ 228 DCHECK([notificationData_
211 objectForKey:notification_constants::kNotificationProfileId]); 229 objectForKey:notification_constants::kNotificationProfileId]);
212 NSString* profileId = [notificationData_ 230 NSString* profileId = [notificationData_
213 objectForKey:notification_constants::kNotificationProfileId]; 231 objectForKey:notification_constants::kNotificationProfileId];
214 232
215 DCHECK([notificationData_ 233 DCHECK([notificationData_
216 objectForKey:notification_constants::kNotificationIncognito]); 234 objectForKey:notification_constants::kNotificationIncognito]);
217 NSNumber* incognito = [notificationData_ 235 NSNumber* incognito = [notificationData_
218 objectForKey:notification_constants::kNotificationIncognito]; 236 objectForKey:notification_constants::kNotificationIncognito];
219 NSNumber* type = [notificationData_
220 objectForKey:notification_constants::kNotificationType];
221 237
222 toast.get().userInfo = @{ 238 toast.get().userInfo = @{
223 notification_constants::kNotificationOrigin : origin, 239 notification_constants::kNotificationOrigin : origin,
224 notification_constants::kNotificationId : notificationId, 240 notification_constants::kNotificationId : notificationId,
225 notification_constants::kNotificationProfileId : profileId, 241 notification_constants::kNotificationProfileId : profileId,
226 notification_constants::kNotificationIncognito : incognito, 242 notification_constants::kNotificationIncognito : incognito,
227 notification_constants::kNotificationType : type, 243 notification_constants::kNotificationType : type,
228 }; 244 };
229 245
230 return toast.autorelease(); 246 return toast.autorelease();
231 } 247 }
232 248
233 - (NSDictionary*)buildDictionary { 249 - (NSDictionary*)buildDictionary {
234 return [[notificationData_ copy] autorelease]; 250 return [[notificationData_ copy] autorelease];
235 } 251 }
236 252
237 @end 253 @end
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698