summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--chrome/browser/views/browser_bubble.cc58
-rw-r--r--chrome/browser/views/browser_bubble.h91
-rw-r--r--chrome/browser/views/browser_bubble_win.cc57
-rw-r--r--chrome/browser/views/browser_views.vcproj12
-rw-r--r--chrome/browser/views/frame/browser_view.cc19
-rw-r--r--chrome/browser/views/frame/browser_view.h12
6 files changed, 248 insertions, 1 deletions
diff --git a/chrome/browser/views/browser_bubble.cc b/chrome/browser/views/browser_bubble.cc
new file mode 100644
index 0000000..cfab7ca
--- /dev/null
+++ b/chrome/browser/views/browser_bubble.cc
@@ -0,0 +1,58 @@
+// Copyright (c) 2009 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 "chrome/browser/views/browser_bubble.h"
+
+#include "app/l10n_util.h"
+#include "views/widget/root_view.h"
+
+BrowserBubble::BrowserBubble(views::View* view, views::Widget* frame,
+ const gfx::Point& origin)
+ : frame_(frame),
+ view_(view),
+ visible_(false),
+ delegate_(NULL) {
+ gfx::Size size = view->GetPreferredSize();
+ bounds_.SetRect(origin.x(), origin.y(), size.width(), size.height());
+ InitPopup();
+}
+
+BrowserBubble::~BrowserBubble() {
+ DestroyPopup();
+}
+
+void BrowserBubble::BrowserWindowMoved() {
+ if (delegate_)
+ delegate_->BubbleBrowserWindowMoved(this);
+ else
+ Hide();
+}
+
+void BrowserBubble::BrowserWindowClosed() {
+ if (delegate_)
+ delegate_->BubbleBrowserWindowClosed(this);
+ else
+ Hide();
+}
+
+void BrowserBubble::SetBounds(int x, int y, int w, int h) {
+ // If the UI layout is RTL, we need to mirror the position of the bubble
+ // relative to the parent.
+ if (l10n_util::GetTextDirection() == l10n_util::RIGHT_TO_LEFT) {
+ gfx::Rect frame_bounds;
+ frame_->GetBounds(&frame_bounds, false);
+ x = frame_bounds.width() - x - w;
+ }
+ bounds_.SetRect(x, y, w, h);
+ Reposition();
+}
+
+void BrowserBubble::Reposition() {
+ gfx::Point top_left;
+ views::View::ConvertPointToScreen(frame_->GetRootView(), &top_left);
+ MovePopup(top_left.x() + bounds_.x(),
+ top_left.y() + bounds_.y(),
+ bounds_.width(),
+ bounds_.height());
+}
diff --git a/chrome/browser/views/browser_bubble.h b/chrome/browser/views/browser_bubble.h
new file mode 100644
index 0000000..49ce7fe
--- /dev/null
+++ b/chrome/browser/views/browser_bubble.h
@@ -0,0 +1,91 @@
+// Copyright (c) 2009 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 CHROME_BROWSER_VIEWS_BROWSER_BUBBLE_
+#define CHROME_BROWSER_VIEWS_BROWSER_BUBBLE_
+
+#include "views/view.h"
+#include "views/widget/widget.h"
+
+// A class for creating a floating window that is "attached" to a particular
+// Browser. If you don't install a delegate, the bubble will hide
+// automatically when the browser moves. The bubble is only shown manually.
+// Users are expected to delete the bubble when finished with it.
+class BrowserBubble {
+ public:
+ // Delegate to browser bubble events.
+ class Delegate {
+ public:
+ // Called when the Browser Window that this bubble is attached to moves.
+ virtual void BubbleBrowserWindowMoved(BrowserBubble* bubble) = 0;
+ virtual void BubbleBrowserWindowClosed(BrowserBubble* bubble) = 0;
+ };
+
+ // Note that the bubble will size itself to the preferred size of |view|.
+ // |view| is the embedded view, |frame| is widget that the bubble is being
+ // positioned relative to, |origin| is the location that the bubble will
+ // be positioned relative to |frame|.
+ BrowserBubble(views::View* view, views::Widget* frame,
+ const gfx::Point& origin);
+ virtual ~BrowserBubble();
+
+ // Get/Set the delegate.
+ Delegate* delegate() const { return delegate_; }
+ void set_delegate(Delegate* del) { delegate_ = del; }
+
+ // Notifications from BrowserView.
+ // With no delegate, both of these default to Hiding the bubble.
+ virtual void BrowserWindowMoved();
+ virtual void BrowserWindowClosed();
+
+ // Show or hide the bubble.
+ void Show();
+ void Hide();
+ bool is_visible() const { return visible_; }
+
+ // The contained view.
+ views::View* view() const { return view_; }
+
+ // Set the bounds of the bubble relative to the browser window.
+ void SetBounds(int x, int y, int w, int h);
+ int width() { return bounds_.width(); }
+ int height() { return bounds_.height(); }
+
+ // Reposition the bubble - as we are using a WS_POPUP for the bubble,
+ // we have to manually position it when the browser window moves.
+ void Reposition();
+
+ protected:
+ // Create the popup widget.
+ virtual void InitPopup();
+
+ // Destroy the popup widget.
+ virtual void DestroyPopup();
+
+ // Move the popup to an absolute position.
+ void MovePopup(int x, int y, int w, int h);
+
+ private:
+ // The frame that this bubble is attached to.
+ views::Widget* frame_;
+
+ // The view that is displayed in this bubble.
+ views::View* view_;
+
+ // The actual widget that this bubble is in.
+ scoped_ptr<views::Widget> popup_;
+
+ // The bounds relative to the frame.
+ gfx::Rect bounds_;
+
+ // Current visibility.
+ bool visible_;
+
+ // The delegate isn't owned by the bubble.
+ Delegate* delegate_;
+
+ DISALLOW_COPY_AND_ASSIGN(BrowserBubble);
+};
+
+#endif // CHROME_BROWSER_VIEWS_BROWSER_BUBBLE_
diff --git a/chrome/browser/views/browser_bubble_win.cc b/chrome/browser/views/browser_bubble_win.cc
new file mode 100644
index 0000000..7471baa
--- /dev/null
+++ b/chrome/browser/views/browser_bubble_win.cc
@@ -0,0 +1,57 @@
+// Copyright (c) 2009 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 "chrome/browser/views/browser_bubble.h"
+
+#include "app/l10n_util_win.h"
+#include "chrome/browser/views/frame/browser_view.h"
+#include "views/widget/widget_win.h"
+
+void BrowserBubble::InitPopup() {
+ gfx::NativeView native_view = frame_->GetNativeView();
+ views::WidgetWin* pop = new views::WidgetWin();
+ pop->set_delete_on_destroy(false);
+ pop->set_window_style(WS_POPUP);
+ pop->set_window_ex_style(WS_EX_LAYERED |
+ WS_EX_TOOLWINDOW |
+ l10n_util::GetExtendedTooltipStyles());
+ pop->SetLayeredAlpha(0xFF);
+ pop->Init(native_view, bounds_, false);
+ pop->SetContentsView(view_);
+ popup_.reset(pop);
+ Reposition();
+
+ BrowserView* browser_view = BrowserView::GetBrowserViewForHWND(native_view);
+ DCHECK(browser_view);
+ if (browser_view)
+ browser_view->AttachBrowserBubble(this);
+}
+
+void BrowserBubble::DestroyPopup() {
+ gfx::NativeView native_view = frame_->GetNativeView();
+ BrowserView* browser_view = BrowserView::GetBrowserViewForHWND(native_view);
+ if (browser_view)
+ browser_view->DetachBrowserBubble(this);
+}
+
+void BrowserBubble::MovePopup(int x, int y, int w, int h) {
+ views::WidgetWin* pop = static_cast<views::WidgetWin*>(popup_.get());
+ pop->MoveWindow(x, y, w, h);
+}
+
+void BrowserBubble::Show() {
+ if (visible_)
+ return;
+ views::WidgetWin* pop = static_cast<views::WidgetWin*>(popup_.get());
+ pop->Show();
+ visible_ = true;
+}
+
+void BrowserBubble::Hide() {
+ if (!visible_)
+ return;
+ views::WidgetWin* pop = static_cast<views::WidgetWin*>(popup_.get());
+ pop->Hide();
+ visible_ = false;
+}
diff --git a/chrome/browser/views/browser_views.vcproj b/chrome/browser/views/browser_views.vcproj
index 75e2939..3039f3c 100644
--- a/chrome/browser/views/browser_views.vcproj
+++ b/chrome/browser/views/browser_views.vcproj
@@ -490,6 +490,18 @@
>
</File>
<File
+ RelativePath=".\browser_bubble.cc"
+ >
+ </File>
+ <File
+ RelativePath=".\browser_bubble.h"
+ >
+ </File>
+ <File
+ RelativePath=".\browser_bubble_win.cc"
+ >
+ </File>
+ <File
RelativePath=".\bug_report_view.cc"
>
</File>
diff --git a/chrome/browser/views/frame/browser_view.cc b/chrome/browser/views/frame/browser_view.cc
index e12d4b1..72957ed 100644
--- a/chrome/browser/views/frame/browser_view.cc
+++ b/chrome/browser/views/frame/browser_view.cc
@@ -27,6 +27,7 @@
#include "chrome/browser/views/bookmark_bar_view.h"
#include "chrome/browser/views/bookmark_bubble_view.h"
#include "chrome/browser/views/bookmark_manager_view.h"
+#include "chrome/browser/views/browser_bubble.h"
#include "chrome/browser/views/bug_report_view.h"
#include "chrome/browser/views/chrome_views_delegate.h"
#include "chrome/browser/views/clear_browsing_data.h"
@@ -330,6 +331,11 @@ void BrowserView::WindowMoved() {
status_bubble_->Reposition();
+ BubbleSet::iterator bubble = browser_bubbles_.begin();
+ for (; bubble != browser_bubbles_.end(); ++bubble) {
+ (*bubble)->BrowserWindowMoved();
+ }
+
BookmarkBubbleView::Hide();
// Close the omnibox popup, if any.
@@ -507,6 +513,14 @@ void BrowserView::RegisterBrowserViewPrefs(PrefService* prefs) {
kDefaultHungPluginDetectFrequency);
}
+void BrowserView::AttachBrowserBubble(BrowserBubble* bubble) {
+ browser_bubbles_.insert(bubble);
+}
+
+void BrowserView::DetachBrowserBubble(BrowserBubble* bubble) {
+ browser_bubbles_.erase(bubble);
+}
+
///////////////////////////////////////////////////////////////////////////////
// BrowserView, BrowserWindow implementation:
@@ -540,6 +554,11 @@ void BrowserView::SetBounds(const gfx::Rect& bounds) {
void BrowserView::Close() {
frame_->Close();
+
+ BubbleSet::iterator bubble = browser_bubbles_.begin();
+ for (; bubble != browser_bubbles_.end(); ++bubble) {
+ (*bubble)->BrowserWindowClosed();
+ }
}
void BrowserView::Activate() {
diff --git a/chrome/browser/views/frame/browser_view.h b/chrome/browser/views/frame/browser_view.h
index 74b04c2..a7a5d31 100644
--- a/chrome/browser/views/frame/browser_view.h
+++ b/chrome/browser/views/frame/browser_view.h
@@ -5,6 +5,8 @@
#ifndef CHROME_BROWSER_VIEWS_FRAME_BROWSER_VIEW_H_
#define CHROME_BROWSER_VIEWS_FRAME_BROWSER_VIEW_H_
+#include <set>
+
#include "chrome/browser/browser.h"
#include "chrome/browser/browser_window.h"
#include "chrome/browser/hang_monitor/hung_plugin_action.h"
@@ -19,6 +21,7 @@
class BookmarkBarView;
class Browser;
+class BrowserBubble;
class BrowserToolbarView;
class EncodingMenuControllerDelegate;
class ExtensionShelf;
@@ -163,6 +166,10 @@ class BrowserView : public BrowserWindow,
// Register preferences specific to this view.
static void RegisterBrowserViewPrefs(PrefService* prefs);
+ // Attach/Detach a BrowserBubble to the browser.
+ void AttachBrowserBubble(BrowserBubble *bubble);
+ void DetachBrowserBubble(BrowserBubble *bubble);
+
// Overridden from BrowserWindow:
virtual void Show();
virtual void SetBounds(const gfx::Rect& bounds);
@@ -280,7 +287,7 @@ class BrowserView : public BrowserWindow,
int LayoutDownloadShelf(int bottom);
// Layout the Status Bubble.
void LayoutStatusBubble(int top);
- // Layout the Extension Bottom Bar
+ // Layout the Extension Shelf
int LayoutExtensionShelf();
// Prepare to show the Bookmark Bar for the specified TabContents. Returns
@@ -409,6 +416,9 @@ class BrowserView : public BrowserWindow,
// A bottom bar for showing extensions.
ExtensionShelf* extension_shelf_;
+ typedef std::set<BrowserBubble*> BubbleSet;
+ BubbleSet browser_bubbles_;
+
DISALLOW_COPY_AND_ASSIGN(BrowserView);
};