diff options
author | oshima <oshima@chromium.org> | 2014-09-09 23:30:42 -0700 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2014-09-10 06:34:47 +0000 |
commit | 480242d63b091995b58c1e21940249d91af9544f (patch) | |
tree | d3d998db3ca8526aa1c4b1e7c162b729bf0243a6 | |
parent | e17158e079e4e51686d001ac288d9066c1ae310a (diff) | |
download | chromium_src-480242d63b091995b58c1e21940249d91af9544f.zip chromium_src-480242d63b091995b58c1e21940249d91af9544f.tar.gz chromium_src-480242d63b091995b58c1e21940249d91af9544f.tar.bz2 |
Supprot V2 app: step1
* Add AthenaAppDelegate
* Add factory functions to create various dialogs
* Add terminating callback to AthenaEnv
BUG=411415
TEST=AthenaEnvTest.TerminatingCallback
TBR=sky@chromium.org, jochen@chromium.org, reed@chromium.org
Review URL: https://codereview.chromium.org/544953003
Cr-Commit-Position: refs/heads/master@{#294123}
25 files changed, 739 insertions, 34 deletions
diff --git a/athena/activity/activity_frame_view.h b/athena/activity/activity_frame_view.h index ab473a5..06cdb58 100644 --- a/athena/activity/activity_frame_view.h +++ b/athena/activity/activity_frame_view.h @@ -6,7 +6,6 @@ #define ATHENA_ACTIVITY_ACTIVITY_FRAME_VIEW_H_ #include "athena/wm/public/window_manager_observer.h" -#include "base/memory/scoped_ptr.h" #include "ui/gfx/insets.h" #include "ui/views/window/non_client_view.h" @@ -24,7 +23,7 @@ class ActivityViewModel; class ActivityFrameView : public views::NonClientFrameView, public WindowManagerObserver { public: - // Internal class name. + // The frame class name. static const char kViewClassName[]; ActivityFrameView(views::Widget* frame, ActivityViewModel* view_model); diff --git a/athena/athena.gyp b/athena/athena.gyp index 88b2c8d..16ccb70 100644 --- a/athena/athena.gyp +++ b/athena/athena.gyp @@ -148,19 +148,20 @@ 'content/app_activity_registry.h', 'content/app_registry_impl.cc', 'content/content_activity_factory.cc', - 'extensions/extension_app_model_builder.cc', - 'content/public/app_registry.h', 'content/content_activity_factory.h', + 'content/public/app_registry.h', 'content/public/content_activity_factory_creator.h', - 'extensions/public/extension_app_model_builder.h', + 'content/public/dialogs.h', 'content/public/web_contents_view_delegate_creator.h', 'content/render_view_context_menu_impl.cc', 'content/render_view_context_menu_impl.h', 'content/web_activity.cc', 'content/web_activity.h', 'content/web_contents_view_delegate_factory_impl.cc', - 'extensions/public/extensions_delegate.h', + 'extensions/extension_app_model_builder.cc', 'extensions/extensions_delegate.cc', + 'extensions/public/extension_app_model_builder.h', + 'extensions/public/extensions_delegate.h', 'virtual_keyboard/public/virtual_keyboard_manager.h', 'virtual_keyboard/virtual_keyboard_manager_impl.cc', ], @@ -173,8 +174,11 @@ ], 'sources': [ 'content/chrome/content_activity_factory.cc', - 'extensions/chrome/athena_apps_client.h', + 'content/chrome/dialogs.cc', + 'extensions/chrome/athena_app_delegate.cc', + 'extensions/chrome/athena_app_delegate.h', 'extensions/chrome/athena_apps_client.cc', + 'extensions/chrome/athena_apps_client.h', 'extensions/chrome/extensions_delegate_impl.cc', ], }, @@ -186,6 +190,7 @@ ], 'sources': [ 'content/shell/content_activity_factory.cc', + 'content/shell/dialogs.cc', 'content/shell/shell_app_activity.cc', 'content/shell/shell_app_activity.h', 'extensions/shell/extensions_delegate_impl.cc', diff --git a/athena/content/chrome/DEPS b/athena/content/chrome/DEPS index 1ed430c..1f04aa2 100644 --- a/athena/content/chrome/DEPS +++ b/athena/content/chrome/DEPS @@ -1,3 +1,4 @@ include_rules = [ + "+chrome/browser", "+extensions/browser/app_window/app_window.h", ] diff --git a/athena/content/chrome/dialogs.cc b/athena/content/chrome/dialogs.cc new file mode 100644 index 0000000..0423060 --- /dev/null +++ b/athena/content/chrome/dialogs.cc @@ -0,0 +1,24 @@ +// Copyright 2014 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. + +#include "athena/content/public/dialogs.h" + +#include "chrome/browser/file_select_helper.h" +#include "chrome/browser/ui/browser_dialogs.h" + +namespace athena { + +content::ColorChooser* OpenColorChooser( + content::WebContents* web_contents, + SkColor initial_color, + const std::vector<content::ColorSuggestion>& suggestions) { + return chrome::ShowColorChooser(web_contents, initial_color); +} + +void OpenFileChooser(content::WebContents* web_contents, + const content::FileChooserParams& params) { + return FileSelectHelper::RunFileChooser(web_contents, params); +} + +} // namespace athena diff --git a/athena/content/public/DEPS b/athena/content/public/DEPS index 27d5887..8951814 100644 --- a/athena/content/public/DEPS +++ b/athena/content/public/DEPS @@ -1,4 +1,5 @@ include_rules = [ "-athena/content", "+athena/athena_export.h", + "+third_party/skia/include/core/SkColor.h", ] diff --git a/athena/content/public/dialogs.h b/athena/content/public/dialogs.h new file mode 100644 index 0000000..16d39bb --- /dev/null +++ b/athena/content/public/dialogs.h @@ -0,0 +1,34 @@ +// Copyright 2014 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. + +#ifndef ATHENA_CONTENT_PUBLIC_DIALOGS_H_ +#define ATHENA_CONTENT_PUBLIC_DIALOGS_H_ + +#include <vector> + +#include "third_party/skia/include/core/SkColor.h" + +namespace content { +class ColorChooser; +class JavaScriptDialogManager; +class WebContents; +struct ColorSuggestion; +struct FileChooserParams; +} + +namespace athena { + +// Open Color chooser window. +content::ColorChooser* OpenColorChooser( + content::WebContents* web_contents, + SkColor color, + const std::vector<content::ColorSuggestion>& suggestions); + +// Open FileChooser window. +void OpenFileChooser(content::WebContents* web_contents, + const content::FileChooserParams& params); + +} // namespace athena + +#endif // ATHENA_CONTENT_PUBLIC_DIALOGS_H_ diff --git a/athena/content/shell/dialogs.cc b/athena/content/shell/dialogs.cc new file mode 100644 index 0000000..63b09e0 --- /dev/null +++ b/athena/content/shell/dialogs.cc @@ -0,0 +1,23 @@ +// Copyright 2014 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. + +#include "athena/content/public/dialogs.h" +#include "base/logging.h" + +namespace athena { + +content::ColorChooser* OpenColorChooser( + content::WebContents* web_contents, + SkColor initial_color, + const std::vector<content::ColorSuggestion>& suggestions) { + NOTIMPLEMENTED(); + return NULL; +} + +void OpenFileChooser(content::WebContents* web_contents, + const content::FileChooserParams& params) { + NOTIMPLEMENTED(); +} + +} // namespace athena diff --git a/athena/content/web_activity.cc b/athena/content/web_activity.cc index 85ede62..50d71c9 100644 --- a/athena/content/web_activity.cc +++ b/athena/content/web_activity.cc @@ -6,6 +6,7 @@ #include "athena/activity/public/activity_factory.h" #include "athena/activity/public/activity_manager.h" +#include "athena/content/public/dialogs.h" #include "athena/input/public/accelerator_manager.h" #include "base/bind.h" #include "base/command_line.h" @@ -302,6 +303,20 @@ class AthenaWebView : public views::WebView { layer->SetOpacity(0.f); } + virtual content::ColorChooser* OpenColorChooser( + content::WebContents* web_contents, + SkColor color, + const std::vector<content::ColorSuggestion>& suggestions) OVERRIDE { + return athena::OpenColorChooser(web_contents, color, suggestions); + } + + // Called when a file selection is to be done. + virtual void RunFileChooser( + content::WebContents* web_contents, + const content::FileChooserParams& params) OVERRIDE { + return athena::OpenFileChooser(web_contents, params); + } + private: void CreateProgressBar() { CHECK(!progress_bar_); diff --git a/athena/env/athena_env_impl.cc b/athena/env/athena_env_impl.cc index 130f8af..bd299a2 100644 --- a/athena/env/athena_env_impl.cc +++ b/athena/env/athena_env_impl.cc @@ -4,6 +4,8 @@ #include "athena/env/public/athena_env.h" +#include <vector> + #include "athena/util/fill_layout_manager.h" #include "base/sys_info.h" #include "ui/aura/client/aura_constants.h" @@ -249,13 +251,50 @@ class AthenaEnvImpl : public AthenaEnv, } private: - virtual aura::WindowTreeHost* GetHost() OVERRIDE { return host_.get(); } + struct Finder { + explicit Finder(const base::Closure& c) : closure(c) {} + bool operator()(const base::Closure& other) { + return closure.Equals(other); + } + base::Closure closure; + }; // AthenaEnv: + virtual aura::WindowTreeHost* GetHost() OVERRIDE { return host_.get(); } + virtual void SetDisplayWorkAreaInsets(const gfx::Insets& insets) OVERRIDE { screen_->SetWorkAreaInsets(insets); } + virtual void AddTerminatingCallback(const base::Closure& closure) OVERRIDE { + if (closure.is_null()) + return; + DCHECK(terminating_callbacks_.end() == + std::find_if(terminating_callbacks_.begin(), + terminating_callbacks_.end(), + Finder(closure))); + terminating_callbacks_.push_back(closure); + } + + virtual void RemoveTerminatingCallback( + const base::Closure& closure) OVERRIDE { + std::vector<base::Closure>::iterator iter = + std::find_if(terminating_callbacks_.begin(), + terminating_callbacks_.end(), + Finder(closure)); + if (iter != terminating_callbacks_.end()) + terminating_callbacks_.erase(iter); + } + + virtual void OnTerminating() OVERRIDE { + for (std::vector<base::Closure>::iterator iter = + terminating_callbacks_.begin(); + iter != terminating_callbacks_.end(); + ++iter) { + iter->Run(); + } + } + // ui::DisplayConfigurator::Observer: virtual void OnDisplayModeChanged(const std::vector< ui::DisplayConfigurator::DisplayState>& displays) OVERRIDE { @@ -290,6 +329,8 @@ class AthenaEnvImpl : public AthenaEnv, scoped_ptr<ui::DisplayConfigurator> display_configurator_; scoped_ptr<ui::UserActivityPowerManagerNotifier> user_activity_notifier_; + std::vector<base::Closure> terminating_callbacks_; + DISALLOW_COPY_AND_ASSIGN(AthenaEnvImpl); }; diff --git a/athena/env/athena_env_unittest.cc b/athena/env/athena_env_unittest.cc index 1c092a2..e852f45 100644 --- a/athena/env/athena_env_unittest.cc +++ b/athena/env/athena_env_unittest.cc @@ -11,6 +11,96 @@ namespace athena { +typedef test::AthenaTestBase AthenaEnvTest; + +namespace { + +class TerminatingCallback { + public: + TerminatingCallback() + : on_terminating_count_(0), + on_terminating_2_count_(0) { + } + + void OnTerminating() { + on_terminating_count_ ++; + } + + void OnTerminating2() { + on_terminating_2_count_ ++; + } + + int on_terminating_count() const { return on_terminating_count_; } + int on_terminating_2_count() const { return on_terminating_2_count_; } + + void Reset() { + on_terminating_count_ = 0; + on_terminating_2_count_ = 0; + } + + private: + int on_terminating_count_; + int on_terminating_2_count_; + + DISALLOW_COPY_AND_ASSIGN(TerminatingCallback); +}; + +} // namespace + +TEST_F(AthenaEnvTest, TerminatingCallback) { + TerminatingCallback callback_1; + TerminatingCallback callback_2; + AthenaEnv* env = AthenaEnv::Get(); + base::Closure cb_1_1 = + base::Bind(&TerminatingCallback::OnTerminating, + base::Unretained(&callback_1)); + base::Closure cb_1_2 = + base::Bind(&TerminatingCallback::OnTerminating2, + base::Unretained(&callback_1)); + base::Closure cb_2_1 = + base::Bind(&TerminatingCallback::OnTerminating, + base::Unretained(&callback_2)); + + env->AddTerminatingCallback(cb_1_1); + env->AddTerminatingCallback(cb_1_2); + env->AddTerminatingCallback(cb_2_1); + env->OnTerminating(); + + EXPECT_EQ(1, callback_1.on_terminating_count()); + EXPECT_EQ(1, callback_1.on_terminating_2_count()); + EXPECT_EQ(1, callback_2.on_terminating_count()); + + // Remove callbacks. + callback_1.Reset(); + callback_2.Reset(); + env->RemoveTerminatingCallback(cb_1_2); + env->OnTerminating(); + EXPECT_EQ(1, callback_1.on_terminating_count()); + EXPECT_EQ(0, callback_1.on_terminating_2_count()); + EXPECT_EQ(1, callback_2.on_terminating_count()); + + callback_1.Reset(); + callback_2.Reset(); + env->RemoveTerminatingCallback(cb_1_1); + env->OnTerminating(); + EXPECT_EQ(0, callback_1.on_terminating_count()); + EXPECT_EQ(0, callback_1.on_terminating_2_count()); + EXPECT_EQ(1, callback_2.on_terminating_count()); + + // Add removed callback. + callback_1.Reset(); + callback_2.Reset(); + env->AddTerminatingCallback(cb_1_2); + env->OnTerminating(); + EXPECT_EQ(0, callback_1.on_terminating_count()); + EXPECT_EQ(1, callback_1.on_terminating_2_count()); + EXPECT_EQ(1, callback_2.on_terminating_count()); + + // Adding empty callback should not fail. + env->AddTerminatingCallback(base::Closure()); + env->OnTerminating(); +} + namespace { class AthenaShutdownTest : public test::AthenaTestBase { diff --git a/athena/env/public/athena_env.h b/athena/env/public/athena_env.h index 703a87f..b3bc8aa 100644 --- a/athena/env/public/athena_env.h +++ b/athena/env/public/athena_env.h @@ -6,15 +6,16 @@ #define ATHENA_ENV_PUBLIC_ATHENA_ENV_H_ #include "athena/athena_export.h" - -namespace gfx { -class Insets; -} +#include "base/callback_forward.h" namespace aura { class WindowTreeHost; } +namespace gfx { +class Insets; +} + namespace athena { // AthenaEnv creates/shuts down the environment necessary to @@ -32,6 +33,13 @@ class ATHENA_EXPORT AthenaEnv { // Sets the insets for the primary displays's work area. virtual void SetDisplayWorkAreaInsets(const gfx::Insets& insets) = 0; + + // Adds the callback called when the athena is about to exit. + virtual void AddTerminatingCallback(const base::Closure& closure) = 0; + virtual void RemoveTerminatingCallback(const base::Closure& closure) = 0; + + // Called when the athena is about to exist. + virtual void OnTerminating() = 0; }; } // namespace athena diff --git a/athena/extensions/chrome/DEPS b/athena/extensions/chrome/DEPS index 33a05ca1..e9caa68 100644 --- a/athena/extensions/chrome/DEPS +++ b/athena/extensions/chrome/DEPS @@ -1,5 +1,8 @@ include_rules = [ + "+athena/env/public", "+chrome/browser", "+chrome/common/extensions", + "+content/public/browser", "+net/base", + "+ui/base", ] diff --git a/athena/extensions/chrome/athena_app_delegate.cc b/athena/extensions/chrome/athena_app_delegate.cc new file mode 100644 index 0000000..64d8d0a --- /dev/null +++ b/athena/extensions/chrome/athena_app_delegate.cc @@ -0,0 +1,183 @@ +// Copyright 2014 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. + +#include "athena/extensions/chrome/athena_app_delegate.h" + +#include "athena/activity/public/activity_factory.h" +#include "athena/activity/public/activity_manager.h" +#include "athena/env/public/athena_env.h" +#include "base/memory/scoped_ptr.h" +#include "base/strings/stringprintf.h" +#include "chrome/browser/chrome_notification_types.h" +#include "chrome/browser/extensions/chrome_extension_web_contents_observer.h" +#include "chrome/browser/favicon/favicon_tab_helper.h" +#include "chrome/browser/file_select_helper.h" +#include "chrome/browser/media/media_capture_devices_dispatcher.h" +#include "chrome/browser/platform_util.h" +#include "chrome/browser/profiles/profile.h" +#include "chrome/browser/shell_integration.h" +#include "chrome/browser/ui/browser.h" +#include "chrome/browser/ui/browser_dialogs.h" +#include "chrome/browser/ui/browser_tabstrip.h" +#include "chrome/browser/ui/browser_window.h" +#include "chrome/browser/ui/scoped_tabbed_browser_displayer.h" +#include "chrome/browser/ui/web_contents_sizer.h" +#include "chrome/common/extensions/chrome_extension_messages.h" +#include "content/public/browser/browser_context.h" +#include "content/public/browser/notification_service.h" +#include "content/public/browser/render_view_host.h" +#include "content/public/browser/web_contents.h" +#include "content/public/browser/web_contents_delegate.h" +#include "extensions/common/constants.h" +#include "extensions/grit/extensions_browser_resources.h" +#include "ui/base/resource/resource_bundle.h" + +#if defined(ENABLE_PRINTING) +#if defined(ENABLE_FULL_PRINTING) +#include "chrome/browser/printing/print_preview_message_handler.h" +#include "chrome/browser/printing/print_view_manager.h" +#else +#include "chrome/browser/printing/print_view_manager_basic.h" +#endif // defined(ENABLE_FULL_PRINTING) +#endif // defined(ENABLE_PRINTING) + +namespace athena { +namespace { + +content::WebContents* OpenURLInActivity( + content::BrowserContext* context, + const content::OpenURLParams& params) { + // Force all links to open in a new activity. + Activity* activity = ActivityFactory::Get()->CreateWebActivity( + context, base::string16(), params.url); + ActivityManager::Get()->AddActivity(activity); + // TODO(oshima): Get the web cotnents from activity. + return NULL; +} + +} // namespace + +// This is a extra step to open a new Activity when a link is simply clicked +// on an app activity (which usually replaces the content). +class AthenaAppDelegate::NewWindowContentsDelegate + : public content::WebContentsDelegate { + public: + NewWindowContentsDelegate() {} + virtual ~NewWindowContentsDelegate() {} + + // content::WebContentsDelegate: + virtual content::WebContents* OpenURLFromTab( + content::WebContents* source, + const content::OpenURLParams& params) OVERRIDE { + if (!source) + return NULL; + + return OpenURLInActivity(source->GetBrowserContext(), params); + } + + private: + DISALLOW_COPY_AND_ASSIGN(NewWindowContentsDelegate); +}; + +AthenaAppDelegate::AthenaAppDelegate() + : new_window_contents_delegate_(new NewWindowContentsDelegate()) { +} + +AthenaAppDelegate::~AthenaAppDelegate() { + if (!terminating_callback_.is_null()) + AthenaEnv::Get()->RemoveTerminatingCallback(terminating_callback_); +} + +void AthenaAppDelegate::InitWebContents(content::WebContents* web_contents) { + FaviconTabHelper::CreateForWebContents(web_contents); + +#if defined(ENABLE_PRINTING) +#if defined(ENABLE_FULL_PRINTING) + printing::PrintViewManager::CreateForWebContents(web_contents); + printing::PrintPreviewMessageHandler::CreateForWebContents(web_contents); +#else + printing::PrintViewManagerBasic::CreateForWebContents(web_contents); +#endif // defined(ENABLE_FULL_PRINTING) +#endif // defined(ENABLE_PRINTING) + extensions::ChromeExtensionWebContentsObserver::CreateForWebContents( + web_contents); +} + +void AthenaAppDelegate::ResizeWebContents(content::WebContents* web_contents, + const gfx::Size& size) { + ::ResizeWebContents(web_contents, size); +} + +content::WebContents* AthenaAppDelegate::OpenURLFromTab( + content::BrowserContext* context, + content::WebContents* source, + const content::OpenURLParams& params) { + return OpenURLInActivity(context, params); +} + +void AthenaAppDelegate::AddNewContents(content::BrowserContext* context, + content::WebContents* new_contents, + WindowOpenDisposition disposition, + const gfx::Rect& initial_pos, + bool user_gesture, + bool* was_blocked) { + new_contents->SetDelegate(new_window_contents_delegate_.get()); +} + +content::ColorChooser* AthenaAppDelegate::ShowColorChooser( + content::WebContents* web_contents, + SkColor initial_color) { + return chrome::ShowColorChooser(web_contents, initial_color); +} + +void AthenaAppDelegate::RunFileChooser( + content::WebContents* tab, + const content::FileChooserParams& params) { + FileSelectHelper::RunFileChooser(tab, params); +} + +void AthenaAppDelegate::RequestMediaAccessPermission( + content::WebContents* web_contents, + const content::MediaStreamRequest& request, + const content::MediaResponseCallback& callback, + const extensions::Extension* extension) { + MediaCaptureDevicesDispatcher::GetInstance()->ProcessMediaAccessRequest( + web_contents, request, callback, extension); +} + +int AthenaAppDelegate::PreferredIconSize() { + // TODO(oshima): Find out what to use. + return extension_misc::EXTENSION_ICON_SMALL; +} + +gfx::ImageSkia AthenaAppDelegate::GetAppDefaultIcon() { + return *ResourceBundle::GetSharedInstance().GetImageSkiaNamed( + IDR_APP_DEFAULT_ICON); +} + +void AthenaAppDelegate::SetWebContentsBlocked( + content::WebContents* web_contents, + bool blocked) { + // RenderViewHost may be NULL during shutdown. + content::RenderViewHost* host = web_contents->GetRenderViewHost(); + if (host) { + host->Send(new ChromeViewMsg_SetVisuallyDeemphasized(host->GetRoutingID(), + blocked)); + } +} + +bool AthenaAppDelegate::IsWebContentsVisible( + content::WebContents* web_contents) { + return platform_util::IsVisible(web_contents->GetNativeView()); +} + +void AthenaAppDelegate::SetTerminatingCallback(const base::Closure& callback) { + if (!terminating_callback_.is_null()) + AthenaEnv::Get()->RemoveTerminatingCallback(terminating_callback_); + terminating_callback_ = callback; + if (!terminating_callback_.is_null()) + AthenaEnv::Get()->AddTerminatingCallback(terminating_callback_); +} + +} // namespace athena diff --git a/athena/extensions/chrome/athena_app_delegate.h b/athena/extensions/chrome/athena_app_delegate.h new file mode 100644 index 0000000..0c41a7b --- /dev/null +++ b/athena/extensions/chrome/athena_app_delegate.h @@ -0,0 +1,64 @@ +// Copyright 2014 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. + +#ifndef ATHENA_EXTENSIONS_CHROME_ATHENA_APP_DELEGATE_H_ +#define ATHENA_EXTENSIONS_CHROME_ATHENA_APP_DELEGATE_H_ + +#include "base/callback.h" +#include "base/memory/scoped_ptr.h" +#include "extensions/browser/app_window/app_delegate.h" +#include "ui/base/window_open_disposition.h" + +namespace athena { + +class AthenaAppDelegate : public extensions::AppDelegate { + public: + AthenaAppDelegate(); + virtual ~AthenaAppDelegate(); + + private: + class NewWindowContentsDelegate; + + // extensions::AppDelegate: + virtual void InitWebContents(content::WebContents* web_contents) OVERRIDE; + virtual void ResizeWebContents(content::WebContents* web_contents, + const gfx::Size& size) OVERRIDE; + virtual content::WebContents* OpenURLFromTab( + content::BrowserContext* context, + content::WebContents* source, + const content::OpenURLParams& params) OVERRIDE; + virtual void AddNewContents(content::BrowserContext* context, + content::WebContents* new_contents, + WindowOpenDisposition disposition, + const gfx::Rect& initial_pos, + bool user_gesture, + bool* was_blocked) OVERRIDE; + virtual content::ColorChooser* ShowColorChooser( + content::WebContents* web_contents, + SkColor initial_color) OVERRIDE; + virtual void RunFileChooser( + content::WebContents* tab, + const content::FileChooserParams& params) OVERRIDE; + virtual void RequestMediaAccessPermission( + content::WebContents* web_contents, + const content::MediaStreamRequest& request, + const content::MediaResponseCallback& callback, + const extensions::Extension* extension) OVERRIDE; + virtual int PreferredIconSize() OVERRIDE; + virtual gfx::ImageSkia GetAppDefaultIcon() OVERRIDE; + virtual void SetWebContentsBlocked(content::WebContents* web_contents, + bool blocked) OVERRIDE; + virtual bool IsWebContentsVisible( + content::WebContents* web_contents) OVERRIDE; + virtual void SetTerminatingCallback(const base::Closure& callback) OVERRIDE; + + scoped_ptr<NewWindowContentsDelegate> new_window_contents_delegate_; + base::Closure terminating_callback_; + + DISALLOW_COPY_AND_ASSIGN(AthenaAppDelegate); +}; + +} // namespace athena + +#endif // ATHENA_EXTENSIONS_CHROME_ATHENA_APP_DELEGATE_H_ diff --git a/athena/extensions/chrome/athena_apps_client.cc b/athena/extensions/chrome/athena_apps_client.cc index 5339ff4..37a0531 100644 --- a/athena/extensions/chrome/athena_apps_client.cc +++ b/athena/extensions/chrome/athena_apps_client.cc @@ -6,11 +6,11 @@ #include "athena/activity/public/activity_factory.h" #include "athena/activity/public/activity_manager.h" +#include "athena/extensions/chrome/athena_app_delegate.h" #include "base/memory/singleton.h" #include "chrome/browser/browser_process.h" #include "chrome/browser/devtools/devtools_window.h" #include "chrome/browser/profiles/profile_manager.h" -#include "chrome/browser/ui/apps/chrome_app_delegate.h" #include "chrome/browser/ui/views/apps/chrome_native_app_window_views.h" #include "chrome/common/extensions/features/feature_channel.h" #include "extensions/browser/app_window/app_window.h" @@ -35,7 +35,7 @@ AthenaAppsClient::GetLoadedBrowserContexts() { extensions::AppWindow* AthenaAppsClient::CreateAppWindow( content::BrowserContext* context, const extensions::Extension* extension) { - return new extensions::AppWindow(context, new ChromeAppDelegate, extension); + return new extensions::AppWindow(context, new AthenaAppDelegate, extension); } extensions::NativeAppWindow* AthenaAppsClient::CreateNativeAppWindow( diff --git a/athena/main/DEPS b/athena/main/DEPS index 4316d72..da4ff5d 100644 --- a/athena/main/DEPS +++ b/athena/main/DEPS @@ -44,9 +44,12 @@ specific_include_rules = { ], # TODO(oshima): Remove this. "placeholder\.*": [ - "+third_party/skia", + "+third_party/skia/include", "+ui/gfx", "+ui/views", ], + "athena_frame_view\.*": [ + "+third_party/skia/include", + ], } diff --git a/athena/main/athena_frame_view.cc b/athena/main/athena_frame_view.cc new file mode 100644 index 0000000..5422a0c --- /dev/null +++ b/athena/main/athena_frame_view.cc @@ -0,0 +1,92 @@ +// Copyright 2014 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. + +#include "athena/main/athena_frame_view.h" + +#include "base/strings/utf_string_conversions.h" +#include "third_party/skia/include/core/SkColor.h" +#include "ui/base/hit_test.h" +#include "ui/views/background.h" +#include "ui/views/controls/label.h" +#include "ui/views/view.h" +#include "ui/views/widget/widget.h" +#include "ui/views/widget/widget_delegate.h" +#include "ui/views/window/client_view.h" + +namespace athena { +namespace { + +// The height of the top border necessary to display the title without the icon. +const int kDefaultTitleHeight = 13; + +// The default background color for athena's frame. This is placeholder. +const SkColor kDefaultTitleBackground = 0xFFcccccc; + +} // namespace + +// static +const char AthenaFrameView::kViewClassName[] = "AthenaFrameView"; + +AthenaFrameView::AthenaFrameView(views::Widget* frame) : frame_(frame) { + set_background( + views::Background::CreateSolidBackground(kDefaultTitleBackground)); + UpdateWindowTitle(); +} + +AthenaFrameView::~AthenaFrameView() { +} + +gfx::Rect AthenaFrameView::GetBoundsForClientView() const { + gfx::Rect client_bounds = bounds(); + client_bounds.Inset(NonClientBorderInsets()); + return client_bounds; +} + +gfx::Rect AthenaFrameView::GetWindowBoundsForClientBounds( + const gfx::Rect& client_bounds) const { + gfx::Rect window_bounds = client_bounds; + window_bounds.Inset(-NonClientBorderInsets()); + return window_bounds; +} + +int AthenaFrameView::NonClientHitTest(const gfx::Point& point) { + if (!bounds().Contains(point)) + return HTNOWHERE; + int client_hit_test = frame_->client_view()->NonClientHitTest(point); + if (client_hit_test != HTNOWHERE) + return client_hit_test; + int window_hit_test = + GetHTComponentForFrame(point, 0, NonClientBorderThickness(), 0, 0, false); + return (window_hit_test == HTNOWHERE) ? HTCAPTION : client_hit_test; +} + +gfx::Size AthenaFrameView::GetPreferredSize() const { + gfx::Size pref = frame_->client_view()->GetPreferredSize(); + gfx::Rect bounds(0, 0, pref.width(), pref.height()); + return frame_->non_client_view() + ->GetWindowBoundsForClientBounds(bounds) + .size(); +} + +const char* AthenaFrameView::GetClassName() const { + return kViewClassName; +} + +gfx::Insets AthenaFrameView::NonClientBorderInsets() const { + int border_thickness = NonClientBorderThickness(); + return gfx::Insets(NonClientTopBorderHeight(), + border_thickness, + border_thickness, + border_thickness); +} + +int AthenaFrameView::NonClientBorderThickness() const { + return 0; +} + +int AthenaFrameView::NonClientTopBorderHeight() const { + return kDefaultTitleHeight; +} + +} // namespace athena diff --git a/athena/main/athena_frame_view.h b/athena/main/athena_frame_view.h new file mode 100644 index 0000000..3037ea9 --- /dev/null +++ b/athena/main/athena_frame_view.h @@ -0,0 +1,56 @@ +// Copyright 2014 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. + +#ifndef ATHENA_COMMON_ATHENA_FRAME_VIEW_H_ +#define ATHENA_COMMON_ATHENA_FRAME_VIEW_H_ + +#include "ui/views/window/non_client_view.h" + +namespace views { +class Widget; +} + +namespace athena { + +// A NonClientFrameView used for non activity window. +// TODO(oshima): Move this to athena/util and share the code. +class AthenaFrameView : public views::NonClientFrameView { + public: + // The frame class name. + static const char kViewClassName[]; + + explicit AthenaFrameView(views::Widget* frame); + virtual ~AthenaFrameView(); + + // views::NonClientFrameView overrides: + virtual gfx::Rect GetBoundsForClientView() const OVERRIDE; + virtual gfx::Rect GetWindowBoundsForClientBounds( + const gfx::Rect& client_bounds) const OVERRIDE; + virtual int NonClientHitTest(const gfx::Point& point) OVERRIDE; + virtual void GetWindowMask(const gfx::Size& size, + gfx::Path* window_mask) OVERRIDE {} + virtual void ResetWindowControls() OVERRIDE {} + virtual void UpdateWindowIcon() OVERRIDE {} + virtual void UpdateWindowTitle() OVERRIDE {} + + // views::View overrides: + virtual gfx::Size GetPreferredSize() const OVERRIDE; + virtual const char* GetClassName() const OVERRIDE; + virtual void Layout() OVERRIDE {} + + private: + gfx::Insets NonClientBorderInsets() const; + + virtual int NonClientTopBorderHeight() const; + virtual int NonClientBorderThickness() const; + + // Not owned. + views::Widget* frame_; + + DISALLOW_COPY_AND_ASSIGN(AthenaFrameView); +}; + +} // namespace athena + +#endif // ATHENA_COMMON_ATHENA_FRAME_VIEW_H_ diff --git a/athena/main/athena_launcher.cc b/athena/main/athena_launcher.cc index 304b0f7..c94d671 100644 --- a/athena/main/athena_launcher.cc +++ b/athena/main/athena_launcher.cc @@ -13,12 +13,12 @@ #include "athena/extensions/public/extensions_delegate.h" #include "athena/home/public/home_card.h" #include "athena/input/public/input_manager.h" +#include "athena/main/athena_views_delegate.h" #include "athena/main/placeholder.h" #include "athena/main/placeholder.h" #include "athena/main/url_search_provider.h" #include "athena/resource_manager/public/resource_manager.h" #include "athena/screen/public/screen_manager.h" -#include "athena/screen/public/screen_manager.h" #include "athena/system/public/system_ui.h" #include "athena/virtual_keyboard/public/virtual_keyboard_manager.h" #include "athena/wm/public/window_manager.h" @@ -30,7 +30,6 @@ #include "ui/keyboard/keyboard_controller.h" #include "ui/keyboard/keyboard_controller_observer.h" #include "ui/native_theme/native_theme_switches.h" -#include "ui/views/views_delegate.h" #include "ui/wm/core/visibility_controller.h" #if defined(USE_X11) @@ -78,22 +77,6 @@ class VirtualKeyboardObserver : public keyboard::KeyboardControllerObserver { DISALLOW_COPY_AND_ASSIGN(VirtualKeyboardObserver); }; -class AthenaViewsDelegate : public views::ViewsDelegate { - public: - AthenaViewsDelegate() {} - virtual ~AthenaViewsDelegate() {} - - private: - // views::ViewsDelegate: - virtual void OnBeforeWidgetInit( - views::Widget::InitParams* params, - views::internal::NativeWidgetDelegate* delegate) OVERRIDE { - params->context = athena::ScreenManager::Get()->GetContext(); - } - - DISALLOW_COPY_AND_ASSIGN(AthenaViewsDelegate); -}; - void StartAthenaEnv(scoped_refptr<base::TaskRunner> file_runner) { athena::AthenaEnv::Create(); diff --git a/athena/main/athena_main.cc b/athena/main/athena_main.cc index 7507ff5..beb1932 100644 --- a/athena/main/athena_main.cc +++ b/athena/main/athena_main.cc @@ -105,6 +105,7 @@ class AthenaBrowserMainDelegate : public extensions::ShellBrowserMainDelegate { } virtual void Shutdown() OVERRIDE { + athena::AthenaEnv::Get()->OnTerminating(); athena::ShutdownAthena(); } diff --git a/athena/main/athena_main.gyp b/athena/main/athena_main.gyp index 7c61c43..9dd5afe 100644 --- a/athena/main/athena_main.gyp +++ b/athena/main/athena_main.gyp @@ -36,9 +36,13 @@ 'sources': [ 'athena_content_client.cc', 'athena_content_client.h', + 'athena_frame_view.cc', + 'athena_frame_view.h', 'athena_launcher.cc', 'athena_renderer_pdf_helper.cc', 'athena_renderer_pdf_helper.h', + 'athena_views_delegate.cc', + 'athena_views_delegate.h', 'placeholder.cc', 'placeholder.h', 'public/athena_launcher.h', diff --git a/athena/main/athena_views_delegate.cc b/athena/main/athena_views_delegate.cc new file mode 100644 index 0000000..3f30cda --- /dev/null +++ b/athena/main/athena_views_delegate.cc @@ -0,0 +1,23 @@ +// Copyright 2014 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. + +#include "athena/main/athena_views_delegate.h" + +#include "athena/main/athena_frame_view.h" +#include "athena/screen/public/screen_manager.h" + +namespace athena { + +void AthenaViewsDelegate::OnBeforeWidgetInit( + views::Widget::InitParams* params, + views::internal::NativeWidgetDelegate* delegate) { + params->context = athena::ScreenManager::Get()->GetContext(); +} + +views::NonClientFrameView* AthenaViewsDelegate::CreateDefaultNonClientFrameView( + views::Widget* widget) { + return new AthenaFrameView(widget); +} + +} // namespace athena diff --git a/athena/main/athena_views_delegate.h b/athena/main/athena_views_delegate.h new file mode 100644 index 0000000..b5d8586 --- /dev/null +++ b/athena/main/athena_views_delegate.h @@ -0,0 +1,29 @@ +// Copyright 2014 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. +#ifndef ATHENA_MAIN_ATHENA_VIEWS_DELEGATE_H_ +#define ATHENA_MAIN_ATHENA_VIEWS_DELEGATE_H_ + +#include "ui/views/views_delegate.h" + +namespace athena { + +class AthenaViewsDelegate : public views::ViewsDelegate { + public: + AthenaViewsDelegate() {} + virtual ~AthenaViewsDelegate() {} + + private: + // views::ViewsDelegate: + virtual void OnBeforeWidgetInit( + views::Widget::InitParams* params, + views::internal::NativeWidgetDelegate* delegate) OVERRIDE; + virtual views::NonClientFrameView* CreateDefaultNonClientFrameView( + views::Widget* widget) OVERRIDE; + + DISALLOW_COPY_AND_ASSIGN(AthenaViewsDelegate); +}; + +} // namespace athena + +#endif // ATHENA_MAIN_ATHENA_VIEWS_DELEGATE_H_ diff --git a/chrome/browser/ui/views/athena/DEPS b/chrome/browser/ui/views/athena/DEPS index da36512..f0b35c4 100644 --- a/chrome/browser/ui/views/athena/DEPS +++ b/chrome/browser/ui/views/athena/DEPS @@ -1,4 +1,5 @@ include_rules = [ + "+athena/env/public", "+athena/extensions/public", "+athena/main/public", ] diff --git a/chrome/browser/ui/views/athena/chrome_browser_main_extra_parts_athena.cc b/chrome/browser/ui/views/athena/chrome_browser_main_extra_parts_athena.cc index bbc00c3..ad2b243 100644 --- a/chrome/browser/ui/views/athena/chrome_browser_main_extra_parts_athena.cc +++ b/chrome/browser/ui/views/athena/chrome_browser_main_extra_parts_athena.cc @@ -4,23 +4,32 @@ #include "chrome/browser/ui/views/athena/chrome_browser_main_extra_parts_athena.h" +#include "athena/env/public/athena_env.h" #include "athena/extensions/public/extensions_delegate.h" #include "athena/main/public/athena_launcher.h" #include "base/command_line.h" #include "base/macros.h" #include "chrome/browser/browser_process.h" #include "chrome/browser/chrome_browser_main_extra_parts.h" +#include "chrome/browser/chrome_notification_types.h" #include "chrome/browser/lifetime/application_lifetime.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/profiles/profile_manager.h" #include "chrome/common/chrome_switches.h" #include "content/public/browser/browser_thread.h" +#include "content/public/browser/notification_observer.h" +#include "content/public/browser/notification_registrar.h" +#include "content/public/browser/notification_service.h" namespace { -class ChromeBrowserMainExtraPartsAthena : public ChromeBrowserMainExtraParts { +class ChromeBrowserMainExtraPartsAthena : public ChromeBrowserMainExtraParts, + public content::NotificationObserver { public: ChromeBrowserMainExtraPartsAthena() { + registrar_.Add(this, + chrome::NOTIFICATION_APP_TERMINATING, + content::NotificationService::AllSources()); } virtual ~ChromeBrowserMainExtraPartsAthena() {} @@ -44,6 +53,19 @@ class ChromeBrowserMainExtraPartsAthena : public ChromeBrowserMainExtraParts { } virtual void PostMainMessageLoopRun() OVERRIDE { athena::ShutdownAthena(); } + // content::NotificationObserver: + virtual void Observe(int type, + const content::NotificationSource& source, + const content::NotificationDetails& details) OVERRIDE { + switch (type) { + case chrome::NOTIFICATION_APP_TERMINATING: + athena::AthenaEnv::Get()->OnTerminating(); + break; + } + } + + content::NotificationRegistrar registrar_; + DISALLOW_COPY_AND_ASSIGN(ChromeBrowserMainExtraPartsAthena); }; |