OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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 #include "chrome/browser/ui/webui/ntp/app_launcher_handler.h" | 5 #include "chrome/browser/ui/webui/ntp/app_launcher_handler.h" |
6 | 6 |
7 #include <string> | 7 #include <string> |
8 #include <vector> | 8 #include <vector> |
9 | 9 |
10 #include "base/auto_reset.h" | 10 #include "base/auto_reset.h" |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
67 base::StringToInt(launch_source, &bucket_num); | 67 base::StringToInt(launch_source, &bucket_num); |
68 extension_misc::AppLaunchBucket bucket = | 68 extension_misc::AppLaunchBucket bucket = |
69 static_cast<extension_misc::AppLaunchBucket>(bucket_num); | 69 static_cast<extension_misc::AppLaunchBucket>(bucket_num); |
70 CHECK(bucket < extension_misc::APP_LAUNCH_BUCKET_BOUNDARY); | 70 CHECK(bucket < extension_misc::APP_LAUNCH_BUCKET_BOUNDARY); |
71 return bucket; | 71 return bucket; |
72 } | 72 } |
73 | 73 |
74 } // namespace | 74 } // namespace |
75 | 75 |
76 AppLauncherHandler::AppLauncherHandler(ExtensionService* extension_service) | 76 AppLauncherHandler::AppLauncherHandler(ExtensionService* extension_service) |
77 : extensions_service_(extension_service), | 77 : extension_service_(extension_service), |
78 promo_active_(false), | 78 promo_active_(false), |
79 ignore_changes_(false) { | 79 ignore_changes_(false) { |
80 } | 80 } |
81 | 81 |
82 AppLauncherHandler::~AppLauncherHandler() {} | 82 AppLauncherHandler::~AppLauncherHandler() {} |
83 | 83 |
84 // Serializes |notification| into a new DictionaryValue which the caller then | 84 // Serializes |notification| into a new DictionaryValue which the caller then |
85 // owns. | 85 // owns. |
86 static DictionaryValue* SerializeNotification( | 86 static DictionaryValue* SerializeNotification( |
87 const AppNotification& notification) { | 87 const AppNotification& notification) { |
88 DictionaryValue* dictionary = new DictionaryValue(); | 88 DictionaryValue* dictionary = new DictionaryValue(); |
89 dictionary->SetString("title", notification.title); | 89 dictionary->SetString("title", notification.title); |
90 dictionary->SetString("body", notification.body); | 90 dictionary->SetString("body", notification.body); |
91 if (!notification.linkUrl.is_empty()) { | 91 if (!notification.linkUrl.is_empty()) { |
92 dictionary->SetString("linkUrl", notification.linkUrl.spec()); | 92 dictionary->SetString("linkUrl", notification.linkUrl.spec()); |
93 dictionary->SetString("linkText", notification.linkText); | 93 dictionary->SetString("linkText", notification.linkText); |
94 } | 94 } |
95 return dictionary; | 95 return dictionary; |
96 } | 96 } |
97 | 97 |
98 // static | 98 // static |
| 99 bool AppLauncherHandler::IsAppExcludedFromList(const Extension* extension) { |
| 100 // Don't include the WebStore and the Cloud Print app. |
| 101 // The WebStore launcher gets special treatment in ntp/apps.js. |
| 102 // The Cloud Print app should never be displayed in the NTP. |
| 103 bool ntp3 = |
| 104 !CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4); |
| 105 if (!extension->is_app() || |
| 106 (ntp3 && extension->id() == extension_misc::kWebStoreAppId) || |
| 107 (extension->id() == extension_misc::kCloudPrintAppId)) { |
| 108 return false; |
| 109 } |
| 110 return true; |
| 111 } |
| 112 |
99 void AppLauncherHandler::CreateAppInfo(const Extension* extension, | 113 void AppLauncherHandler::CreateAppInfo(const Extension* extension, |
100 const AppNotification* notification, | 114 const AppNotification* notification, |
101 ExtensionService* service, | 115 ExtensionService* service, |
102 DictionaryValue* value) { | 116 DictionaryValue* value) { |
103 bool enabled = service->IsExtensionEnabled(extension->id()); | 117 bool enabled = service->IsExtensionEnabled(extension->id()) && |
| 118 !service->GetTerminatedExtension(extension->id()); |
104 GURL icon_big = | 119 GURL icon_big = |
105 ExtensionIconSource::GetIconURL(extension, | 120 ExtensionIconSource::GetIconURL(extension, |
106 Extension::EXTENSION_ICON_LARGE, | 121 Extension::EXTENSION_ICON_LARGE, |
107 ExtensionIconSet::MATCH_EXACTLY, | 122 ExtensionIconSet::MATCH_EXACTLY, |
108 !enabled); | 123 !enabled); |
109 GURL icon_small = | 124 GURL icon_small = |
110 ExtensionIconSource::GetIconURL(extension, | 125 ExtensionIconSource::GetIconURL(extension, |
111 Extension::EXTENSION_ICON_BITTY, | 126 Extension::EXTENSION_ICON_BITTY, |
112 ExtensionIconSet::MATCH_BIGGER, | 127 ExtensionIconSet::MATCH_BIGGER, |
113 !enabled); | 128 !enabled); |
(...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
225 void AppLauncherHandler::Observe(int type, | 240 void AppLauncherHandler::Observe(int type, |
226 const NotificationSource& source, | 241 const NotificationSource& source, |
227 const NotificationDetails& details) { | 242 const NotificationDetails& details) { |
228 if (ignore_changes_) | 243 if (ignore_changes_) |
229 return; | 244 return; |
230 | 245 |
231 switch (type) { | 246 switch (type) { |
232 case chrome::NOTIFICATION_APP_NOTIFICATION_STATE_CHANGED: { | 247 case chrome::NOTIFICATION_APP_NOTIFICATION_STATE_CHANGED: { |
233 const std::string& id = *Details<const std::string>(details).ptr(); | 248 const std::string& id = *Details<const std::string>(details).ptr(); |
234 const AppNotification* notification = | 249 const AppNotification* notification = |
235 extensions_service_->app_notification_manager()->GetLast(id); | 250 extension_service_->app_notification_manager()->GetLast(id); |
236 ListValue args; | 251 ListValue args; |
237 args.Append(new StringValue(id)); | 252 args.Append(new StringValue(id)); |
238 if (notification) | 253 if (notification) |
239 args.Append(SerializeNotification(*notification)); | 254 args.Append(SerializeNotification(*notification)); |
240 web_ui_->CallJavascriptFunction("appNotificationChanged", args); | 255 web_ui_->CallJavascriptFunction("appNotificationChanged", args); |
241 break; | 256 break; |
242 } | 257 } |
243 case chrome::NOTIFICATION_EXTENSION_LOADED: | 258 case chrome::NOTIFICATION_EXTENSION_LOADED: |
244 case chrome::NOTIFICATION_EXTENSION_UNLOADED: { | 259 case chrome::NOTIFICATION_EXTENSION_UNLOADED: { |
245 const Extension* extension = | 260 const Extension* extension = |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
286 } | 301 } |
287 break; | 302 break; |
288 } | 303 } |
289 default: | 304 default: |
290 NOTREACHED(); | 305 NOTREACHED(); |
291 } | 306 } |
292 } | 307 } |
293 | 308 |
294 void AppLauncherHandler::FillAppDictionary(DictionaryValue* dictionary) { | 309 void AppLauncherHandler::FillAppDictionary(DictionaryValue* dictionary) { |
295 ListValue* list = new ListValue(); | 310 ListValue* list = new ListValue(); |
296 const ExtensionList* extensions = extensions_service_->extensions(); | 311 const ExtensionList* extensions = extension_service_->extensions(); |
297 ExtensionList::const_iterator it; | 312 ExtensionList::const_iterator it; |
298 for (it = extensions->begin(); it != extensions->end(); ++it) { | 313 for (it = extensions->begin(); it != extensions->end(); ++it) { |
299 // Don't include the WebStore and the Cloud Print app. | 314 if (!IsAppExcludedFromList(*it)) { |
300 // The WebStore launcher gets special treatment in ntp/apps.js. | 315 DictionaryValue* app_info = GetAppInfo(*it); |
301 // The Cloud Print app should never be displayed in the NTP. | |
302 const Extension* extension = *it; | |
303 DictionaryValue* app_info = GetAppInfo(extension); | |
304 if (app_info) | |
305 list->Append(app_info); | 316 list->Append(app_info); |
| 317 } |
306 } | 318 } |
307 | 319 |
308 extensions = extensions_service_->disabled_extensions(); | 320 extensions = extension_service_->disabled_extensions(); |
309 for (it = extensions->begin(); it != extensions->end(); ++it) { | 321 for (it = extensions->begin(); it != extensions->end(); ++it) { |
310 bool ntp3 = | 322 if (!IsAppExcludedFromList(*it)) { |
311 !CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4); | |
312 if ((*it)->is_app() && | |
313 !(ntp3 && (*it)->id() == extension_misc::kWebStoreAppId) && | |
314 ((*it)->id() != extension_misc::kCloudPrintAppId)) { | |
315 DictionaryValue* app_info = new DictionaryValue(); | 323 DictionaryValue* app_info = new DictionaryValue(); |
316 CreateAppInfo(*it, | 324 CreateAppInfo(*it, |
317 NULL, | 325 NULL, |
318 extensions_service_, | 326 extension_service_, |
319 app_info); | 327 app_info); |
320 list->Append(app_info); | 328 list->Append(app_info); |
321 } | 329 } |
| 330 } |
| 331 |
| 332 extensions = extension_service_->terminated_extensions(); |
| 333 for (it = extensions->begin(); it != extensions->end(); ++it) { |
| 334 if (!IsAppExcludedFromList(*it)) { |
| 335 DictionaryValue* app_info = new DictionaryValue(); |
| 336 CreateAppInfo(*it, |
| 337 NULL, |
| 338 extension_service_, |
| 339 app_info); |
| 340 list->Append(app_info); |
| 341 } |
322 } | 342 } |
323 | 343 |
324 dictionary->Set("apps", list); | 344 dictionary->Set("apps", list); |
325 | 345 |
326 // TODO(estade): remove these settings when the old NTP is removed. The new | 346 // TODO(estade): remove these settings when the old NTP is removed. The new |
327 // NTP does it in js. | 347 // NTP does it in js. |
328 #if defined(OS_MACOSX) | 348 #if defined(OS_MACOSX) |
329 // App windows are not yet implemented on mac. | 349 // App windows are not yet implemented on mac. |
330 dictionary->SetBoolean("disableAppWindowLaunch", true); | 350 dictionary->SetBoolean("disableAppWindowLaunch", true); |
331 dictionary->SetBoolean("disableCreateAppShortcut", true); | 351 dictionary->SetBoolean("disableCreateAppShortcut", true); |
332 #endif | 352 #endif |
333 | 353 |
334 #if defined(OS_CHROMEOS) | 354 #if defined(OS_CHROMEOS) |
335 // Making shortcut does not make sense on ChromeOS because it does not have | 355 // Making shortcut does not make sense on ChromeOS because it does not have |
336 // a desktop. | 356 // a desktop. |
337 dictionary->SetBoolean("disableCreateAppShortcut", true); | 357 dictionary->SetBoolean("disableCreateAppShortcut", true); |
338 #endif | 358 #endif |
339 | 359 |
340 dictionary->SetBoolean( | 360 dictionary->SetBoolean( |
341 "showLauncher", | 361 "showLauncher", |
342 extensions_service_->apps_promo()->ShouldShowAppLauncher( | 362 extension_service_->apps_promo()->ShouldShowAppLauncher( |
343 extensions_service_->GetAppIds())); | 363 extension_service_->GetAppIds())); |
344 | 364 |
345 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) { | 365 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) { |
346 PrefService* prefs = web_ui_->GetProfile()->GetPrefs(); | 366 PrefService* prefs = web_ui_->GetProfile()->GetPrefs(); |
347 const ListValue* app_page_names = prefs->GetList(prefs::kNTPAppPageNames); | 367 const ListValue* app_page_names = prefs->GetList(prefs::kNTPAppPageNames); |
348 if (app_page_names && app_page_names->GetSize()) { | 368 if (app_page_names && app_page_names->GetSize()) { |
349 dictionary->Set("appPageNames", | 369 dictionary->Set("appPageNames", |
350 static_cast<ListValue*>(app_page_names->DeepCopy())); | 370 static_cast<ListValue*>(app_page_names->DeepCopy())); |
351 } | 371 } |
352 } | 372 } |
353 } | 373 } |
354 | 374 |
355 DictionaryValue* AppLauncherHandler::GetAppInfo(const Extension* extension) { | 375 DictionaryValue* AppLauncherHandler::GetAppInfo(const Extension* extension) { |
356 bool ntp3 = | 376 AppNotificationManager* notification_manager = |
357 !CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4); | 377 extension_service_->app_notification_manager(); |
358 if (!extension->is_app() || | |
359 (ntp3 && extension->id() == extension_misc::kWebStoreAppId) || | |
360 (extension->id() == extension_misc::kCloudPrintAppId)) { | |
361 return NULL; | |
362 } | |
363 | |
364 DictionaryValue* app_info = new DictionaryValue(); | 378 DictionaryValue* app_info = new DictionaryValue(); |
365 AppNotificationManager* notification_manager = | |
366 extensions_service_->app_notification_manager(); | |
367 CreateAppInfo(extension, | 379 CreateAppInfo(extension, |
368 notification_manager->GetLast(extension->id()), | 380 notification_manager->GetLast(extension->id()), |
369 extensions_service_, | 381 extension_service_, |
370 app_info); | 382 app_info); |
371 return app_info; | 383 return app_info; |
372 } | 384 } |
373 | 385 |
374 void AppLauncherHandler::FillPromoDictionary(DictionaryValue* dictionary) { | 386 void AppLauncherHandler::FillPromoDictionary(DictionaryValue* dictionary) { |
375 dictionary->SetString("promoHeader", AppsPromo::GetPromoHeaderText()); | 387 dictionary->SetString("promoHeader", AppsPromo::GetPromoHeaderText()); |
376 dictionary->SetString("promoButton", AppsPromo::GetPromoButtonText()); | 388 dictionary->SetString("promoButton", AppsPromo::GetPromoButtonText()); |
377 dictionary->SetString("promoLink", AppsPromo::GetPromoLink().spec()); | 389 dictionary->SetString("promoLink", AppsPromo::GetPromoLink().spec()); |
378 dictionary->SetString("promoLogo", AppsPromo::GetPromoLogo().spec()); | 390 dictionary->SetString("promoLogo", AppsPromo::GetPromoLogo().spec()); |
379 dictionary->SetString("promoExpire", AppsPromo::GetPromoExpireText()); | 391 dictionary->SetString("promoExpire", AppsPromo::GetPromoExpireText()); |
380 } | 392 } |
381 | 393 |
382 void AppLauncherHandler::HandleGetApps(const ListValue* args) { | 394 void AppLauncherHandler::HandleGetApps(const ListValue* args) { |
383 DictionaryValue dictionary; | 395 DictionaryValue dictionary; |
384 | 396 |
385 // Tell the client whether to show the promo for this view. We don't do this | 397 // Tell the client whether to show the promo for this view. We don't do this |
386 // in the case of PREF_CHANGED because: | 398 // in the case of PREF_CHANGED because: |
387 // | 399 // |
388 // a) At that point in time, depending on the pref that changed, it can look | 400 // a) At that point in time, depending on the pref that changed, it can look |
389 // like the set of apps installed has changed, and we will mark the promo | 401 // like the set of apps installed has changed, and we will mark the promo |
390 // expired. | 402 // expired. |
391 // b) Conceptually, it doesn't really make sense to count a | 403 // b) Conceptually, it doesn't really make sense to count a |
392 // prefchange-triggered refresh as a promo 'view'. | 404 // prefchange-triggered refresh as a promo 'view'. |
393 AppsPromo* apps_promo = extensions_service_->apps_promo(); | 405 AppsPromo* apps_promo = extension_service_->apps_promo(); |
394 PrefService* prefs = web_ui_->GetProfile()->GetPrefs(); | 406 PrefService* prefs = web_ui_->GetProfile()->GetPrefs(); |
395 bool apps_promo_just_expired = false; | 407 bool apps_promo_just_expired = false; |
396 if (apps_promo->ShouldShowPromo(extensions_service_->GetAppIds(), | 408 if (apps_promo->ShouldShowPromo(extension_service_->GetAppIds(), |
397 &apps_promo_just_expired)) { | 409 &apps_promo_just_expired)) { |
398 apps_promo->MaximizeAppsIfNecessary(); | 410 apps_promo->MaximizeAppsIfNecessary(); |
399 dictionary.SetBoolean("showPromo", true); | 411 dictionary.SetBoolean("showPromo", true); |
400 FillPromoDictionary(&dictionary); | 412 FillPromoDictionary(&dictionary); |
401 promo_active_ = true; | 413 promo_active_ = true; |
402 } else { | 414 } else { |
403 dictionary.SetBoolean("showPromo", false); | 415 dictionary.SetBoolean("showPromo", false); |
404 promo_active_ = false; | 416 promo_active_ = false; |
405 } | 417 } |
406 | 418 |
(...skipping 18 matching lines...) Expand all Loading... |
425 NotificationService::AllSources()); | 437 NotificationService::AllSources()); |
426 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED, | 438 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED, |
427 NotificationService::AllSources()); | 439 NotificationService::AllSources()); |
428 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LAUNCHER_REORDERED, | 440 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LAUNCHER_REORDERED, |
429 NotificationService::AllSources()); | 441 NotificationService::AllSources()); |
430 registrar_.Add(this, chrome::NOTIFICATION_WEB_STORE_PROMO_LOADED, | 442 registrar_.Add(this, chrome::NOTIFICATION_WEB_STORE_PROMO_LOADED, |
431 NotificationService::AllSources()); | 443 NotificationService::AllSources()); |
432 } | 444 } |
433 if (pref_change_registrar_.IsEmpty()) { | 445 if (pref_change_registrar_.IsEmpty()) { |
434 pref_change_registrar_.Init( | 446 pref_change_registrar_.Init( |
435 extensions_service_->extension_prefs()->pref_service()); | 447 extension_service_->extension_prefs()->pref_service()); |
436 pref_change_registrar_.Add(ExtensionPrefs::kExtensionsPref, this); | 448 pref_change_registrar_.Add(ExtensionPrefs::kExtensionsPref, this); |
437 pref_change_registrar_.Add(prefs::kNTPAppPageNames, this); | 449 pref_change_registrar_.Add(prefs::kNTPAppPageNames, this); |
438 } | 450 } |
439 } | 451 } |
440 | 452 |
441 void AppLauncherHandler::HandleLaunchApp(const ListValue* args) { | 453 void AppLauncherHandler::HandleLaunchApp(const ListValue* args) { |
442 std::string extension_id; | 454 std::string extension_id; |
443 double source = -1.0; | 455 double source = -1.0; |
444 bool alt_key = false; | 456 bool alt_key = false; |
445 bool ctrl_key = false; | 457 bool ctrl_key = false; |
(...skipping 11 matching lines...) Expand all Loading... |
457 CHECK(args->GetDouble(6, &button)); | 469 CHECK(args->GetDouble(6, &button)); |
458 } | 470 } |
459 | 471 |
460 extension_misc::AppLaunchBucket launch_bucket = | 472 extension_misc::AppLaunchBucket launch_bucket = |
461 static_cast<extension_misc::AppLaunchBucket>( | 473 static_cast<extension_misc::AppLaunchBucket>( |
462 static_cast<int>(source)); | 474 static_cast<int>(source)); |
463 CHECK(launch_bucket >= 0 && | 475 CHECK(launch_bucket >= 0 && |
464 launch_bucket < extension_misc::APP_LAUNCH_BUCKET_BOUNDARY); | 476 launch_bucket < extension_misc::APP_LAUNCH_BUCKET_BOUNDARY); |
465 | 477 |
466 const Extension* extension = | 478 const Extension* extension = |
467 extensions_service_->GetExtensionById(extension_id, false); | 479 extension_service_->GetExtensionById(extension_id, false); |
468 | 480 |
469 // Prompt the user to re-enable the application if disabled. | 481 // Prompt the user to re-enable the application if disabled. |
470 if (!extension) { | 482 if (!extension) { |
471 PromptToEnableApp(extension_id); | 483 PromptToEnableApp(extension_id); |
472 return; | 484 return; |
473 } | 485 } |
474 | 486 |
475 Profile* profile = extensions_service_->profile(); | 487 Profile* profile = extension_service_->profile(); |
476 | 488 |
477 // If the user pressed special keys when clicking, override the saved | 489 // If the user pressed special keys when clicking, override the saved |
478 // preference for launch container. | 490 // preference for launch container. |
479 bool middle_button = (button == 1.0); | 491 bool middle_button = (button == 1.0); |
480 WindowOpenDisposition disposition = | 492 WindowOpenDisposition disposition = |
481 disposition_utils::DispositionFromClick(middle_button, alt_key, | 493 disposition_utils::DispositionFromClick(middle_button, alt_key, |
482 ctrl_key, meta_key, shift_key); | 494 ctrl_key, meta_key, shift_key); |
483 | 495 |
484 if (extension_id != extension_misc::kWebStoreAppId) { | 496 if (extension_id != extension_misc::kWebStoreAppId) { |
485 RecordAppLaunchByID(promo_active_, launch_bucket); | 497 RecordAppLaunchByID(promo_active_, launch_bucket); |
486 extensions_service_->apps_promo()->ExpireDefaultApps(); | 498 extension_service_->apps_promo()->ExpireDefaultApps(); |
487 } | 499 } |
488 | 500 |
489 if (disposition == NEW_FOREGROUND_TAB || disposition == NEW_BACKGROUND_TAB) { | 501 if (disposition == NEW_FOREGROUND_TAB || disposition == NEW_BACKGROUND_TAB) { |
490 // TODO(jamescook): Proper support for background tabs. | 502 // TODO(jamescook): Proper support for background tabs. |
491 Browser::OpenApplication( | 503 Browser::OpenApplication( |
492 profile, extension, extension_misc::LAUNCH_TAB, disposition); | 504 profile, extension, extension_misc::LAUNCH_TAB, disposition); |
493 } else if (disposition == NEW_WINDOW) { | 505 } else if (disposition == NEW_WINDOW) { |
494 // Force a new window open. | 506 // Force a new window open. |
495 Browser::OpenApplication( | 507 Browser::OpenApplication( |
496 profile, extension, extension_misc::LAUNCH_WINDOW, disposition); | 508 profile, extension, extension_misc::LAUNCH_WINDOW, disposition); |
497 } else { | 509 } else { |
498 // Look at preference to find the right launch container. If no preference | 510 // Look at preference to find the right launch container. If no preference |
499 // is set, launch as a regular tab. | 511 // is set, launch as a regular tab. |
500 extension_misc::LaunchContainer launch_container = | 512 extension_misc::LaunchContainer launch_container = |
501 extensions_service_->extension_prefs()->GetLaunchContainer( | 513 extension_service_->extension_prefs()->GetLaunchContainer( |
502 extension, ExtensionPrefs::LAUNCH_REGULAR); | 514 extension, ExtensionPrefs::LAUNCH_REGULAR); |
503 | 515 |
504 // To give a more "launchy" experience when using the NTP launcher, we close | 516 // To give a more "launchy" experience when using the NTP launcher, we close |
505 // it automatically. | 517 // it automatically. |
506 Browser* browser = BrowserList::GetLastActive(); | 518 Browser* browser = BrowserList::GetLastActive(); |
507 TabContents* old_contents = NULL; | 519 TabContents* old_contents = NULL; |
508 if (browser) | 520 if (browser) |
509 old_contents = browser->GetSelectedTabContents(); | 521 old_contents = browser->GetSelectedTabContents(); |
510 | 522 |
511 TabContents* new_contents = Browser::OpenApplication( | 523 TabContents* new_contents = Browser::OpenApplication( |
512 profile, extension, launch_container, | 524 profile, extension, launch_container, |
513 old_contents ? CURRENT_TAB : NEW_FOREGROUND_TAB); | 525 old_contents ? CURRENT_TAB : NEW_FOREGROUND_TAB); |
514 | 526 |
515 // This will also destroy the handler, so do not perform any actions after. | 527 // This will also destroy the handler, so do not perform any actions after. |
516 if (new_contents != old_contents && browser && browser->tab_count() > 1) | 528 if (new_contents != old_contents && browser && browser->tab_count() > 1) |
517 browser->CloseTabContents(old_contents); | 529 browser->CloseTabContents(old_contents); |
518 } | 530 } |
519 } | 531 } |
520 | 532 |
521 void AppLauncherHandler::HandleSetLaunchType(const ListValue* args) { | 533 void AppLauncherHandler::HandleSetLaunchType(const ListValue* args) { |
522 std::string extension_id; | 534 std::string extension_id; |
523 double launch_type; | 535 double launch_type; |
524 CHECK(args->GetString(0, &extension_id)); | 536 CHECK(args->GetString(0, &extension_id)); |
525 CHECK(args->GetDouble(1, &launch_type)); | 537 CHECK(args->GetDouble(1, &launch_type)); |
526 | 538 |
527 const Extension* extension = | 539 const Extension* extension = |
528 extensions_service_->GetExtensionById(extension_id, true); | 540 extension_service_->GetExtensionById(extension_id, true); |
529 CHECK(extension); | 541 CHECK(extension); |
530 | 542 |
531 // Don't update the page; it already knows about the launch type change. | 543 // Don't update the page; it already knows about the launch type change. |
532 scoped_ptr<AutoReset<bool> > auto_reset; | 544 scoped_ptr<AutoReset<bool> > auto_reset; |
533 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) | 545 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) |
534 auto_reset.reset(new AutoReset<bool>(&ignore_changes_, true)); | 546 auto_reset.reset(new AutoReset<bool>(&ignore_changes_, true)); |
535 | 547 |
536 extensions_service_->extension_prefs()->SetLaunchType( | 548 extension_service_->extension_prefs()->SetLaunchType( |
537 extension_id, | 549 extension_id, |
538 static_cast<ExtensionPrefs::LaunchType>( | 550 static_cast<ExtensionPrefs::LaunchType>( |
539 static_cast<int>(launch_type))); | 551 static_cast<int>(launch_type))); |
540 } | 552 } |
541 | 553 |
542 void AppLauncherHandler::HandleUninstallApp(const ListValue* args) { | 554 void AppLauncherHandler::HandleUninstallApp(const ListValue* args) { |
543 std::string extension_id; | 555 std::string extension_id; |
544 CHECK(args->GetString(0, &extension_id)); | 556 CHECK(args->GetString(0, &extension_id)); |
545 | 557 |
546 const Extension* extension = extensions_service_->GetExtensionById( | 558 const Extension* extension = extension_service_->GetExtensionById( |
547 extension_id, true); | 559 extension_id, true); |
548 if (!extension) | 560 if (!extension) |
549 return; | 561 return; |
550 | 562 |
551 if (!Extension::UserMayDisable(extension->location())) { | 563 if (!Extension::UserMayDisable(extension->location())) { |
552 LOG(ERROR) << "Attempt to uninstall an extension that is non-usermanagable " | 564 LOG(ERROR) << "Attempt to uninstall an extension that is non-usermanagable " |
553 << "was made. Extension id : " << extension->id(); | 565 << "was made. Extension id : " << extension->id(); |
554 return; | 566 return; |
555 } | 567 } |
556 if (!extension_id_prompting_.empty()) | 568 if (!extension_id_prompting_.empty()) |
(...skipping 11 matching lines...) Expand all Loading... |
568 GetExtensionUninstallDialog()->ConfirmUninstall(this, extension); | 580 GetExtensionUninstallDialog()->ConfirmUninstall(this, extension); |
569 } | 581 } |
570 } | 582 } |
571 | 583 |
572 void AppLauncherHandler::HandleHideAppsPromo(const ListValue* args) { | 584 void AppLauncherHandler::HandleHideAppsPromo(const ListValue* args) { |
573 // If the user has intentionally hidden the promotion, we'll uninstall all the | 585 // If the user has intentionally hidden the promotion, we'll uninstall all the |
574 // default apps (we know the user hasn't installed any apps on their own at | 586 // default apps (we know the user hasn't installed any apps on their own at |
575 // this point, or the promotion wouldn't have been shown). | 587 // this point, or the promotion wouldn't have been shown). |
576 ignore_changes_ = true; | 588 ignore_changes_ = true; |
577 UninstallDefaultApps(); | 589 UninstallDefaultApps(); |
578 extensions_service_->apps_promo()->HidePromo(); | 590 extension_service_->apps_promo()->HidePromo(); |
579 ignore_changes_ = false; | 591 ignore_changes_ = false; |
580 HandleGetApps(NULL); | 592 HandleGetApps(NULL); |
581 } | 593 } |
582 | 594 |
583 void AppLauncherHandler::HandleCreateAppShortcut(const ListValue* args) { | 595 void AppLauncherHandler::HandleCreateAppShortcut(const ListValue* args) { |
584 std::string extension_id; | 596 std::string extension_id; |
585 if (!args->GetString(0, &extension_id)) { | 597 if (!args->GetString(0, &extension_id)) { |
586 NOTREACHED(); | 598 NOTREACHED(); |
587 return; | 599 return; |
588 } | 600 } |
589 | 601 |
590 const Extension* extension = | 602 const Extension* extension = |
591 extensions_service_->GetExtensionById(extension_id, true); | 603 extension_service_->GetExtensionById(extension_id, true); |
592 CHECK(extension); | 604 CHECK(extension); |
593 | 605 |
594 Browser* browser = BrowserList::GetLastActive(); | 606 Browser* browser = BrowserList::GetLastActive(); |
595 if (!browser) | 607 if (!browser) |
596 return; | 608 return; |
597 browser->window()->ShowCreateChromeAppShortcutsDialog( | 609 browser->window()->ShowCreateChromeAppShortcutsDialog( |
598 browser->profile(), extension); | 610 browser->profile(), extension); |
599 } | 611 } |
600 | 612 |
601 void AppLauncherHandler::HandleReorderApps(const ListValue* args) { | 613 void AppLauncherHandler::HandleReorderApps(const ListValue* args) { |
602 CHECK(args->GetSize() == 2); | 614 CHECK(args->GetSize() == 2); |
603 | 615 |
604 std::string dragged_app_id; | 616 std::string dragged_app_id; |
605 ListValue* app_order; | 617 ListValue* app_order; |
606 CHECK(args->GetString(0, &dragged_app_id)); | 618 CHECK(args->GetString(0, &dragged_app_id)); |
607 CHECK(args->GetList(1, &app_order)); | 619 CHECK(args->GetList(1, &app_order)); |
608 | 620 |
609 std::vector<std::string> extension_ids; | 621 std::vector<std::string> extension_ids; |
610 for (size_t i = 0; i < app_order->GetSize(); ++i) { | 622 for (size_t i = 0; i < app_order->GetSize(); ++i) { |
611 std::string value; | 623 std::string value; |
612 if (app_order->GetString(i, &value)) | 624 if (app_order->GetString(i, &value)) |
613 extension_ids.push_back(value); | 625 extension_ids.push_back(value); |
614 } | 626 } |
615 | 627 |
616 // Don't update the page; it already knows the apps have been reordered. | 628 // Don't update the page; it already knows the apps have been reordered. |
617 scoped_ptr<AutoReset<bool> > auto_reset; | 629 scoped_ptr<AutoReset<bool> > auto_reset; |
618 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) | 630 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) |
619 auto_reset.reset(new AutoReset<bool>(&ignore_changes_, true)); | 631 auto_reset.reset(new AutoReset<bool>(&ignore_changes_, true)); |
620 | 632 |
621 extensions_service_->extension_prefs()->SetAppDraggedByUser(dragged_app_id); | 633 extension_service_->extension_prefs()->SetAppDraggedByUser(dragged_app_id); |
622 extensions_service_->extension_prefs()->SetAppLauncherOrder(extension_ids); | 634 extension_service_->extension_prefs()->SetAppLauncherOrder(extension_ids); |
623 } | 635 } |
624 | 636 |
625 void AppLauncherHandler::HandleSetPageIndex(const ListValue* args) { | 637 void AppLauncherHandler::HandleSetPageIndex(const ListValue* args) { |
626 std::string extension_id; | 638 std::string extension_id; |
627 double page_index; | 639 double page_index; |
628 CHECK(args->GetString(0, &extension_id)); | 640 CHECK(args->GetString(0, &extension_id)); |
629 CHECK(args->GetDouble(1, &page_index)); | 641 CHECK(args->GetDouble(1, &page_index)); |
630 | 642 |
631 // Don't update the page; it already knows the apps have been reordered. | 643 // Don't update the page; it already knows the apps have been reordered. |
632 scoped_ptr<AutoReset<bool> > auto_reset; | 644 scoped_ptr<AutoReset<bool> > auto_reset; |
633 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) | 645 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kNewTabPage4)) |
634 auto_reset.reset(new AutoReset<bool>(&ignore_changes_, true)); | 646 auto_reset.reset(new AutoReset<bool>(&ignore_changes_, true)); |
635 | 647 |
636 extensions_service_->extension_prefs()->SetPageIndex(extension_id, | 648 extension_service_->extension_prefs()->SetPageIndex(extension_id, |
637 static_cast<int>(page_index)); | 649 static_cast<int>(page_index)); |
638 } | 650 } |
639 | 651 |
640 void AppLauncherHandler::HandlePromoSeen(const ListValue* args) { | 652 void AppLauncherHandler::HandlePromoSeen(const ListValue* args) { |
641 UMA_HISTOGRAM_ENUMERATION(extension_misc::kAppsPromoHistogram, | 653 UMA_HISTOGRAM_ENUMERATION(extension_misc::kAppsPromoHistogram, |
642 extension_misc::PROMO_SEEN, | 654 extension_misc::PROMO_SEEN, |
643 extension_misc::PROMO_BUCKET_BOUNDARY); | 655 extension_misc::PROMO_BUCKET_BOUNDARY); |
644 } | 656 } |
645 | 657 |
646 void AppLauncherHandler::HandleSaveAppPageName(const ListValue* args) { | 658 void AppLauncherHandler::HandleSaveAppPageName(const ListValue* args) { |
(...skipping 27 matching lines...) Expand all Loading... |
674 icon.url = GURL(); | 686 icon.url = GURL(); |
675 icon.width = icon.height = 16; | 687 icon.width = icon.height = 16; |
676 web_app->icons.push_back(icon); | 688 web_app->icons.push_back(icon); |
677 | 689 |
678 Profile* profile = web_ui_->GetProfile(); | 690 Profile* profile = web_ui_->GetProfile(); |
679 FaviconService* favicon_service = | 691 FaviconService* favicon_service = |
680 profile->GetFaviconService(Profile::EXPLICIT_ACCESS); | 692 profile->GetFaviconService(Profile::EXPLICIT_ACCESS); |
681 if (!favicon_service) { | 693 if (!favicon_service) { |
682 LOG(ERROR) << "No favicon service"; | 694 LOG(ERROR) << "No favicon service"; |
683 scoped_refptr<CrxInstaller> installer( | 695 scoped_refptr<CrxInstaller> installer( |
684 extensions_service_->MakeCrxInstaller(NULL)); | 696 extension_service_->MakeCrxInstaller(NULL)); |
685 installer->InstallWebApp(*web_app); | 697 installer->InstallWebApp(*web_app); |
686 return; | 698 return; |
687 } | 699 } |
688 | 700 |
689 // TODO(gbillock): get page thumb from thumbnail db/history svc? | 701 // TODO(gbillock): get page thumb from thumbnail db/history svc? |
690 FaviconService::Handle h = favicon_service->GetFaviconForURL( | 702 FaviconService::Handle h = favicon_service->GetFaviconForURL( |
691 launch_url, history::FAVICON, &favicon_consumer_, | 703 launch_url, history::FAVICON, &favicon_consumer_, |
692 NewCallback(this, &AppLauncherHandler::OnFaviconForApp)); | 704 NewCallback(this, &AppLauncherHandler::OnFaviconForApp)); |
693 favicon_consumer_.SetClientData(favicon_service, h, web_app.release()); | 705 favicon_consumer_.SetClientData(favicon_service, h, web_app.release()); |
694 } | 706 } |
695 | 707 |
696 void AppLauncherHandler::OnFaviconForApp(FaviconService::Handle handle, | 708 void AppLauncherHandler::OnFaviconForApp(FaviconService::Handle handle, |
697 history::FaviconData data) { | 709 history::FaviconData data) { |
698 scoped_ptr<WebApplicationInfo> web_app( | 710 scoped_ptr<WebApplicationInfo> web_app( |
699 favicon_consumer_.GetClientDataForCurrentRequest()); | 711 favicon_consumer_.GetClientDataForCurrentRequest()); |
700 CHECK(!web_app->icons.empty()); | 712 CHECK(!web_app->icons.empty()); |
701 if (data.is_valid() && gfx::PNGCodec::Decode(data.image_data->front(), | 713 if (data.is_valid() && gfx::PNGCodec::Decode(data.image_data->front(), |
702 data.image_data->size(), | 714 data.image_data->size(), |
703 &(web_app->icons[0].data))) { | 715 &(web_app->icons[0].data))) { |
704 web_app->icons[0].url = GURL(); | 716 web_app->icons[0].url = GURL(); |
705 web_app->icons[0].width = web_app->icons[0].data.width(); | 717 web_app->icons[0].width = web_app->icons[0].data.width(); |
706 web_app->icons[0].height = web_app->icons[0].data.height(); | 718 web_app->icons[0].height = web_app->icons[0].data.height(); |
707 } | 719 } |
708 | 720 |
709 scoped_refptr<CrxInstaller> installer( | 721 scoped_refptr<CrxInstaller> installer( |
710 extensions_service_->MakeCrxInstaller(NULL)); | 722 extension_service_->MakeCrxInstaller(NULL)); |
711 installer->InstallWebApp(*web_app); | 723 installer->InstallWebApp(*web_app); |
712 } | 724 } |
713 | 725 |
714 // static | 726 // static |
715 void AppLauncherHandler::RegisterUserPrefs(PrefService* pref_service) { | 727 void AppLauncherHandler::RegisterUserPrefs(PrefService* pref_service) { |
716 // TODO(csilv): We will want this to be a syncable preference instead. | 728 // TODO(csilv): We will want this to be a syncable preference instead. |
717 pref_service->RegisterListPref(prefs::kNTPAppPageNames, | 729 pref_service->RegisterListPref(prefs::kNTPAppPageNames, |
718 PrefService::UNSYNCABLE_PREF); | 730 PrefService::UNSYNCABLE_PREF); |
719 } | 731 } |
720 | 732 |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
757 DCHECK(profile->GetExtensionService()); | 769 DCHECK(profile->GetExtensionService()); |
758 if (!profile->GetExtensionService()->IsInstalledApp(url)) | 770 if (!profile->GetExtensionService()->IsInstalledApp(url)) |
759 return; | 771 return; |
760 | 772 |
761 UMA_HISTOGRAM_ENUMERATION(extension_misc::kAppLaunchHistogram, bucket, | 773 UMA_HISTOGRAM_ENUMERATION(extension_misc::kAppLaunchHistogram, bucket, |
762 extension_misc::APP_LAUNCH_BUCKET_BOUNDARY); | 774 extension_misc::APP_LAUNCH_BUCKET_BOUNDARY); |
763 } | 775 } |
764 | 776 |
765 void AppLauncherHandler::PromptToEnableApp(const std::string& extension_id) { | 777 void AppLauncherHandler::PromptToEnableApp(const std::string& extension_id) { |
766 const Extension* extension = | 778 const Extension* extension = |
767 extensions_service_->GetExtensionById(extension_id, true); | 779 extension_service_->GetExtensionById(extension_id, true); |
768 CHECK(extension); | 780 if (!extension) { |
| 781 extension = extension_service_->GetTerminatedExtension(extension_id); |
| 782 CHECK(extension); |
| 783 // If the app was terminated, reload it first. (This reallocates the |
| 784 // Extension object.) |
| 785 extension_service_->ReloadExtension(extension_id); |
| 786 extension = extension_service_->GetExtensionById(extension_id, true); |
| 787 } |
769 | 788 |
770 ExtensionPrefs* extension_prefs = extensions_service_->extension_prefs(); | 789 ExtensionPrefs* extension_prefs = extension_service_->extension_prefs(); |
771 if (!extension_prefs->DidExtensionEscalatePermissions(extension_id)) { | 790 if (!extension_prefs->DidExtensionEscalatePermissions(extension_id)) { |
772 // Enable the extension immediately if its privileges weren't escalated. | 791 // Enable the extension immediately if its privileges weren't escalated. |
773 extensions_service_->EnableExtension(extension_id); | 792 // This is a no-op if the extension was previously terminated. |
| 793 extension_service_->EnableExtension(extension_id); |
774 | 794 |
775 // Launch app asynchronously so the image will update. | 795 // Launch app asynchronously so the image will update. |
776 StringValue* app_id = Value::CreateStringValue(extension->id()); | 796 StringValue* app_id = Value::CreateStringValue(extension_id); |
777 web_ui_->CallJavascriptFunction("launchAppAfterEnable", *app_id); | 797 web_ui_->CallJavascriptFunction("launchAppAfterEnable", *app_id); |
778 return; | 798 return; |
779 } | 799 } |
780 | 800 |
781 if (!extension_id_prompting_.empty()) | 801 if (!extension_id_prompting_.empty()) |
782 return; // Only one prompt at a time. | 802 return; // Only one prompt at a time. |
783 | 803 |
784 extension_id_prompting_ = extension_id; | 804 extension_id_prompting_ = extension_id; |
785 GetExtensionInstallUI()->ConfirmReEnable(this, extension); | 805 GetExtensionInstallUI()->ConfirmReEnable(this, extension); |
786 } | 806 } |
787 | 807 |
788 void AppLauncherHandler::ExtensionDialogAccepted() { | 808 void AppLauncherHandler::ExtensionDialogAccepted() { |
789 // Do the uninstall work here. | 809 // Do the uninstall work here. |
790 DCHECK(!extension_id_prompting_.empty()); | 810 DCHECK(!extension_id_prompting_.empty()); |
791 | 811 |
792 // The extension can be uninstalled in another window while the UI was | 812 // The extension can be uninstalled in another window while the UI was |
793 // showing. Do nothing in that case. | 813 // showing. Do nothing in that case. |
794 const Extension* extension = | 814 const Extension* extension = |
795 extensions_service_->GetExtensionById(extension_id_prompting_, true); | 815 extension_service_->GetExtensionById(extension_id_prompting_, true); |
796 if (!extension) | 816 if (!extension) |
797 return; | 817 return; |
798 | 818 |
799 extensions_service_->UninstallExtension(extension_id_prompting_, | 819 extension_service_->UninstallExtension(extension_id_prompting_, |
800 false /* external_uninstall */, NULL); | 820 false /* external_uninstall */, NULL); |
801 | 821 |
802 extension_id_prompting_ = ""; | 822 extension_id_prompting_ = ""; |
803 } | 823 } |
804 | 824 |
805 void AppLauncherHandler::ExtensionDialogCanceled() { | 825 void AppLauncherHandler::ExtensionDialogCanceled() { |
806 extension_id_prompting_ = ""; | 826 extension_id_prompting_ = ""; |
807 } | 827 } |
808 | 828 |
809 void AppLauncherHandler::InstallUIProceed() { | 829 void AppLauncherHandler::InstallUIProceed() { |
810 // Do the re-enable work here. | 830 // Do the re-enable work here. |
811 DCHECK(!extension_id_prompting_.empty()); | 831 DCHECK(!extension_id_prompting_.empty()); |
812 | 832 |
813 // The extension can be uninstalled in another window while the UI was | 833 // The extension can be uninstalled in another window while the UI was |
814 // showing. Do nothing in that case. | 834 // showing. Do nothing in that case. |
815 const Extension* extension = | 835 const Extension* extension = |
816 extensions_service_->GetExtensionById(extension_id_prompting_, true); | 836 extension_service_->GetExtensionById(extension_id_prompting_, true); |
817 if (!extension) | 837 if (!extension) |
818 return; | 838 return; |
819 | 839 |
820 extensions_service_->GrantPermissionsAndEnableExtension(extension); | 840 extension_service_->GrantPermissionsAndEnableExtension(extension); |
821 | 841 |
822 // We bounce this off the NTP so the browser can update the apps icon. | 842 // We bounce this off the NTP so the browser can update the apps icon. |
823 // If we don't launch the app asynchronously, then the app's disabled | 843 // If we don't launch the app asynchronously, then the app's disabled |
824 // icon disappears but isn't replaced by the enabled icon, making a poor | 844 // icon disappears but isn't replaced by the enabled icon, making a poor |
825 // visual experience. | 845 // visual experience. |
826 StringValue* app_id = Value::CreateStringValue(extension->id()); | 846 StringValue* app_id = Value::CreateStringValue(extension->id()); |
827 web_ui_->CallJavascriptFunction("launchAppAfterEnable", *app_id); | 847 web_ui_->CallJavascriptFunction("launchAppAfterEnable", *app_id); |
828 | 848 |
829 extension_id_prompting_ = ""; | 849 extension_id_prompting_ = ""; |
830 } | 850 } |
831 | 851 |
832 void AppLauncherHandler::InstallUIAbort(bool user_initiated) { | 852 void AppLauncherHandler::InstallUIAbort(bool user_initiated) { |
833 // We record the histograms here because ExtensionDialogCanceled is also | 853 // We record the histograms here because ExtensionDialogCanceled is also |
834 // called when the extension uninstall dialog is canceled. | 854 // called when the extension uninstall dialog is canceled. |
835 const Extension* extension = | 855 const Extension* extension = |
836 extensions_service_->GetExtensionById(extension_id_prompting_, true); | 856 extension_service_->GetExtensionById(extension_id_prompting_, true); |
837 std::string histogram_name = user_initiated ? | 857 std::string histogram_name = user_initiated ? |
838 "Extensions.Permissions_ReEnableCancel" : | 858 "Extensions.Permissions_ReEnableCancel" : |
839 "Extensions.Permissions_ReEnableAbort"; | 859 "Extensions.Permissions_ReEnableAbort"; |
840 ExtensionService::RecordPermissionMessagesHistogram( | 860 ExtensionService::RecordPermissionMessagesHistogram( |
841 extension, histogram_name.c_str()); | 861 extension, histogram_name.c_str()); |
842 | 862 |
843 ExtensionDialogCanceled(); | 863 ExtensionDialogCanceled(); |
844 } | 864 } |
845 | 865 |
846 ExtensionUninstallDialog* AppLauncherHandler::GetExtensionUninstallDialog() { | 866 ExtensionUninstallDialog* AppLauncherHandler::GetExtensionUninstallDialog() { |
847 if (!extension_uninstall_dialog_.get()) { | 867 if (!extension_uninstall_dialog_.get()) { |
848 extension_uninstall_dialog_.reset( | 868 extension_uninstall_dialog_.reset( |
849 new ExtensionUninstallDialog(web_ui_->GetProfile())); | 869 new ExtensionUninstallDialog(web_ui_->GetProfile())); |
850 } | 870 } |
851 return extension_uninstall_dialog_.get(); | 871 return extension_uninstall_dialog_.get(); |
852 } | 872 } |
853 | 873 |
854 ExtensionInstallUI* AppLauncherHandler::GetExtensionInstallUI() { | 874 ExtensionInstallUI* AppLauncherHandler::GetExtensionInstallUI() { |
855 if (!extension_install_ui_.get()) { | 875 if (!extension_install_ui_.get()) { |
856 extension_install_ui_.reset( | 876 extension_install_ui_.reset( |
857 new ExtensionInstallUI(web_ui_->GetProfile())); | 877 new ExtensionInstallUI(web_ui_->GetProfile())); |
858 } | 878 } |
859 return extension_install_ui_.get(); | 879 return extension_install_ui_.get(); |
860 } | 880 } |
861 | 881 |
862 void AppLauncherHandler::UninstallDefaultApps() { | 882 void AppLauncherHandler::UninstallDefaultApps() { |
863 AppsPromo* apps_promo = extensions_service_->apps_promo(); | 883 AppsPromo* apps_promo = extension_service_->apps_promo(); |
864 const ExtensionIdSet& app_ids = apps_promo->old_default_apps(); | 884 const ExtensionIdSet& app_ids = apps_promo->old_default_apps(); |
865 for (ExtensionIdSet::const_iterator iter = app_ids.begin(); | 885 for (ExtensionIdSet::const_iterator iter = app_ids.begin(); |
866 iter != app_ids.end(); ++iter) { | 886 iter != app_ids.end(); ++iter) { |
867 if (extensions_service_->GetExtensionById(*iter, true)) | 887 if (extension_service_->GetExtensionById(*iter, true)) |
868 extensions_service_->UninstallExtension(*iter, false, NULL); | 888 extension_service_->UninstallExtension(*iter, false, NULL); |
869 } | 889 } |
870 } | 890 } |
OLD | NEW |