Chromium Code Reviews| 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/gtk/infobars/extension_infobar_gtk.h" | 5 #include "chrome/browser/ui/gtk/infobars/extension_infobar_gtk.h" |
| 6 | 6 |
| 7 #include "chrome/browser/extensions/extension_context_menu_model.h" | |
| 7 #include "chrome/browser/extensions/extension_host.h" | 8 #include "chrome/browser/extensions/extension_host.h" |
| 9 #include "chrome/browser/platform_util.h" | |
| 10 #include "chrome/browser/ui/gtk/browser_window_gtk.h" | |
| 11 #include "chrome/browser/ui/gtk/custom_button.h" | |
| 12 #include "chrome/browser/ui/gtk/gtk_chrome_button.h" | |
| 13 #include "chrome/browser/ui/gtk/gtk_util.h" | |
| 8 #include "chrome/common/extensions/extension.h" | 14 #include "chrome/common/extensions/extension.h" |
| 9 #include "chrome/common/extensions/extension_icon_set.h" | 15 #include "chrome/common/extensions/extension_icon_set.h" |
| 10 #include "chrome/common/extensions/extension_resource.h" | 16 #include "chrome/common/extensions/extension_resource.h" |
| 11 #include "content/browser/renderer_host/render_view_host.h" | 17 #include "content/browser/renderer_host/render_view_host.h" |
| 12 #include "content/browser/renderer_host/render_widget_host_view.h" | 18 #include "content/browser/renderer_host/render_widget_host_view.h" |
| 13 #include "grit/theme_resources.h" | 19 #include "grit/theme_resources.h" |
| 14 #include "ui/base/resource/resource_bundle.h" | 20 #include "ui/base/resource/resource_bundle.h" |
| 21 #include "ui/gfx/canvas_skia.h" | |
| 15 #include "ui/gfx/gtk_util.h" | 22 #include "ui/gfx/gtk_util.h" |
| 23 #include "ui/gfx/image/image.h" | |
| 16 | 24 |
| 17 ExtensionInfoBarGtk::ExtensionInfoBarGtk(TabContentsWrapper* owner, | 25 ExtensionInfoBarGtk::ExtensionInfoBarGtk(TabContentsWrapper* owner, |
| 18 ExtensionInfoBarDelegate* delegate) | 26 ExtensionInfoBarDelegate* delegate) |
| 19 : InfoBarGtk(owner, delegate), | 27 : InfoBarGtk(owner, delegate), |
| 20 tracker_(this), | 28 tracker_(this), |
| 21 delegate_(delegate), | 29 delegate_(delegate), |
| 22 view_(NULL) { | 30 view_(NULL) { |
| 31 // Always render the close button as if we were doing chrome style widget | |
| 32 // rendering. For extension infobars, we force chrome style rendering because | |
| 33 // extension authors are going to expect to match the declared gradient in | |
| 34 // extensions_infobar.css, and the close button provided by some GTK+ themes | |
| 35 // won't look good on this background. | |
| 36 close_button_->ForceChromeTheme(); | |
| 37 | |
| 23 BuildWidgets(); | 38 BuildWidgets(); |
| 24 } | 39 } |
| 25 | 40 |
| 26 ExtensionInfoBarGtk::~ExtensionInfoBarGtk() { | 41 ExtensionInfoBarGtk::~ExtensionInfoBarGtk() {} |
| 27 // This view is not owned by us, so unparent. | 42 |
| 28 gtk_widget_unparent(view_->native_view()); | 43 void ExtensionInfoBarGtk::PlatformSpecificHide(bool animate) { |
| 44 // This view is not owned by us; we can't unparent it because we aren't the | |
| 45 // owning container. | |
| 46 gtk_container_remove(GTK_CONTAINER(alignment_), view_->native_view()); | |
| 47 } | |
| 48 | |
| 49 void ExtensionInfoBarGtk::GetTopColor(InfoBarDelegate::Type type, | |
| 50 double* r, double* g, double *b) { | |
|
Evan Stade
2011/08/31 20:00:12
s/ */* /
Elliot Glaysher
2011/08/31 20:37:32
Fixed here and in every InfobarGtk subclass that h
| |
| 51 // Extension infobars are always drawn with chrome-theme colors. | |
| 52 *r = *g = *b = 233.0 / 255.0; | |
|
Evan Stade
2011/08/31 20:00:12
huh? aren't they drawn by a renderer, basically ma
Elliot Glaysher
2011/08/31 20:37:32
Only the render area is. If we don't do this, ther
Evan Stade
2011/08/31 20:47:49
shouldn't we at least match the chrome theme then?
| |
| 53 } | |
| 54 | |
| 55 void ExtensionInfoBarGtk::GetBottomColor(InfoBarDelegate::Type type, | |
| 56 double* r, double* g, double *b) { | |
| 57 *r = *g = *b = 218.0 / 255.0; | |
| 29 } | 58 } |
| 30 | 59 |
| 31 void ExtensionInfoBarGtk::OnImageLoaded( | 60 void ExtensionInfoBarGtk::OnImageLoaded( |
| 32 SkBitmap* image, const ExtensionResource& resource, int index) { | 61 SkBitmap* image, const ExtensionResource& resource, int index) { |
| 33 if (!delegate_) | 62 if (!delegate_) |
| 34 return; // The delegate can go away while we asynchronously load images. | 63 return; // The delegate can go away while we asynchronously load images. |
| 35 | 64 |
| 36 // ResourceBundle& rb = ResourceBundle::GetSharedInstance(); | 65 // TODO(erg): IDR_EXTENSIONS_SECTION should have an IDR_INFOBAR_EXTENSIONS |
| 37 // | 66 // icon of the correct size with real subpixel shading and such. |
| 38 // SkBitmap* icon; | 67 SkBitmap* icon = image; |
| 39 // if (!image || image->empty()) | 68 ResourceBundle& rb = ResourceBundle::GetSharedInstance(); |
| 40 // icon = rb.GetBitmapNamed(IDR_EXTENSIONS_SECTION); | 69 if (!image || image->empty()) |
| 41 // else | 70 icon = rb.GetBitmapNamed(IDR_EXTENSIONS_SECTION); |
| 42 // icon = image; | 71 |
| 43 // TODO(finnur): Use the above code. | 72 SkBitmap* drop_image = rb.GetBitmapNamed(IDR_APP_DROPARROW); |
| 44 // We now have the icon for the menu button, show the menu button and layout. | 73 |
| 74 int image_size = Extension::EXTENSION_ICON_BITTY; | |
| 75 // The margin between the extension icon and the drop-down arrow bitmap. | |
| 76 static const int kDropArrowLeftMargin = 3; | |
| 77 scoped_ptr<gfx::CanvasSkia> canvas(new gfx::CanvasSkia( | |
| 78 image_size + kDropArrowLeftMargin + drop_image->width(), image_size, | |
|
Evan Stade
2011/08/31 20:00:12
I think there are more readable ways to distribute
| |
| 79 false)); | |
| 80 canvas->DrawBitmapInt(*icon, 0, 0, icon->width(), icon->height(), 0, 0, | |
| 81 image_size, image_size, false); | |
| 82 canvas->DrawBitmapInt(*drop_image, image_size + kDropArrowLeftMargin, | |
| 83 image_size / 2); | |
| 84 | |
| 85 SkBitmap bitmap = canvas->ExtractBitmap(); | |
| 86 GdkPixbuf* pixbuf = gfx::GdkPixbufFromSkBitmap(&bitmap); | |
| 87 gtk_image_set_from_pixbuf(GTK_IMAGE(icon_), pixbuf); | |
| 88 g_object_unref(pixbuf); | |
| 45 } | 89 } |
| 46 | 90 |
| 47 void ExtensionInfoBarGtk::BuildWidgets() { | 91 void ExtensionInfoBarGtk::BuildWidgets() { |
| 92 button_ = gtk_chrome_button_new(); | |
| 93 gtk_chrome_button_set_use_gtk_rendering(GTK_CHROME_BUTTON(button_), FALSE); | |
| 94 g_object_set_data(G_OBJECT(button_), "left-align-popup", | |
| 95 reinterpret_cast<void*>(true)); | |
| 96 | |
| 97 icon_ = gtk_image_new(); | |
| 98 gtk_misc_set_alignment(GTK_MISC(icon_), 0.5, 0.5); | |
| 99 gtk_button_set_image(GTK_BUTTON(button_), icon_); | |
| 100 gtk_util::CenterWidgetInHBox(hbox_, button_, false, 0); | |
| 101 | |
| 48 // Start loading the image for the menu button. | 102 // Start loading the image for the menu button. |
| 49 const Extension* extension = delegate_->extension_host()->extension(); | 103 const Extension* extension = delegate_->extension_host()->extension(); |
| 50 ExtensionResource icon_resource = extension->GetIconResource( | 104 ExtensionResource icon_resource = extension->GetIconResource( |
| 51 Extension::EXTENSION_ICON_BITTY, ExtensionIconSet::MATCH_EXACTLY); | 105 Extension::EXTENSION_ICON_BITTY, ExtensionIconSet::MATCH_EXACTLY); |
| 52 if (!icon_resource.relative_path().empty()) { | 106 if (!icon_resource.relative_path().empty()) { |
| 53 // Create a tracker to load the image. It will report back on OnImageLoaded. | 107 // Create a tracker to load the image. It will report back on OnImageLoaded. |
| 54 tracker_.LoadImage(extension, icon_resource, | 108 tracker_.LoadImage(extension, icon_resource, |
| 55 gfx::Size(Extension::EXTENSION_ICON_BITTY, | 109 gfx::Size(Extension::EXTENSION_ICON_BITTY, |
| 56 Extension::EXTENSION_ICON_BITTY), | 110 Extension::EXTENSION_ICON_BITTY), |
| 57 ImageLoadingTracker::DONT_CACHE); | 111 ImageLoadingTracker::DONT_CACHE); |
| 58 } else { | 112 } else { |
| 59 OnImageLoaded(NULL, icon_resource, 0); // |image|, ..., |index|. | 113 OnImageLoaded(NULL, icon_resource, 0); |
| 60 } | 114 } |
| 61 | 115 |
| 116 // Pad the bottom of the infobar by one pixel for the border. | |
| 117 alignment_ = gtk_alignment_new(0.0, 0.0, 1.0, 1.0); | |
| 118 gtk_alignment_set_padding(GTK_ALIGNMENT(alignment_), 0, 1, 0, 0); | |
| 119 gtk_box_pack_start(GTK_BOX(hbox_), alignment_, TRUE, TRUE, 0); | |
| 120 | |
| 62 ExtensionHost* extension_host = delegate_->extension_host(); | 121 ExtensionHost* extension_host = delegate_->extension_host(); |
| 63 view_ = extension_host->view(); | 122 view_ = extension_host->view(); |
| 123 | |
| 64 if (gtk_widget_get_parent(view_->native_view())) { | 124 if (gtk_widget_get_parent(view_->native_view())) { |
| 65 gtk_widget_reparent(view_->native_view(), hbox_); | 125 gtk_widget_reparent(view_->native_view(), alignment_); |
| 66 gtk_box_set_child_packing(GTK_BOX(hbox_), view_->native_view(), | |
| 67 TRUE, TRUE, 0, GTK_PACK_START); | |
| 68 } else { | 126 } else { |
| 69 gtk_box_pack_start(GTK_BOX(hbox_), view_->native_view(), TRUE, TRUE, 0); | 127 gtk_container_add(GTK_CONTAINER(alignment_), view_->native_view()); |
| 70 } | 128 } |
| 71 | 129 |
| 72 g_signal_connect(view_->native_view(), "size_allocate", | 130 signals_.Connect(button_, "button-press-event", |
| 131 G_CALLBACK(OnButtonPressThunk), this); | |
| 132 signals_.Connect(view_->native_view(), "size_allocate", | |
| 73 G_CALLBACK(&OnSizeAllocateThunk), this); | 133 G_CALLBACK(&OnSizeAllocateThunk), this); |
| 74 } | 134 } |
| 75 | 135 |
| 136 void ExtensionInfoBarGtk::StoppedShowing() { | |
| 137 gtk_chrome_button_unset_paint_state(GTK_CHROME_BUTTON(button_)); | |
| 138 } | |
| 139 | |
| 140 Browser* ExtensionInfoBarGtk::GetBrowser() { | |
| 141 // Get the Browser object this infobar is attached to. | |
| 142 GtkWindow* parent = platform_util::GetTopLevel(icon_); | |
| 143 if (!parent) | |
| 144 return NULL; | |
| 145 | |
| 146 return BrowserWindowGtk::GetBrowserWindowForNativeWindow(parent)->browser(); | |
| 147 } | |
| 148 | |
| 149 MenuGtk* ExtensionInfoBarGtk::BuildContextMenu() { | |
| 150 const Extension* extension = delegate_->extension(); | |
| 151 if (!extension->ShowConfigureContextMenus()) | |
| 152 return NULL; | |
| 153 | |
| 154 Browser* browser = GetBrowser(); | |
| 155 if (!browser) | |
| 156 return NULL; | |
| 157 | |
| 158 context_menu_model_ = | |
| 159 new ExtensionContextMenuModel(extension, browser, NULL); | |
| 160 context_menu_.reset( | |
| 161 new MenuGtk(this, context_menu_model_.get())); | |
|
Evan Stade
2011/08/31 20:00:12
this doesn't fit on one line?
| |
| 162 return context_menu_.get(); | |
| 163 } | |
| 164 | |
| 76 void ExtensionInfoBarGtk::OnSizeAllocate(GtkWidget* widget, | 165 void ExtensionInfoBarGtk::OnSizeAllocate(GtkWidget* widget, |
| 77 GtkAllocation* allocation) { | 166 GtkAllocation* allocation) { |
| 78 gfx::Size new_size(allocation->width, allocation->height); | 167 gfx::Size new_size(allocation->width, allocation->height); |
| 79 | 168 |
| 80 delegate_->extension_host()->view()->render_view_host()->view() | 169 delegate_->extension_host()->view()->render_view_host()->view() |
| 81 ->SetSize(new_size); | 170 ->SetSize(new_size); |
| 82 } | 171 } |
| 83 | 172 |
| 173 gboolean ExtensionInfoBarGtk::OnButtonPress(GtkWidget* widget, | |
| 174 GdkEventButton* event) { | |
| 175 if (event->button != 1) | |
| 176 return FALSE; | |
| 177 | |
| 178 MenuGtk* menu = BuildContextMenu(); | |
| 179 if (!menu) | |
| 180 return FALSE; | |
| 181 | |
| 182 gtk_chrome_button_set_paint_state(GTK_CHROME_BUTTON(widget), | |
| 183 GTK_STATE_ACTIVE); | |
| 184 menu->PopupForWidget(widget, event->button, event->time); | |
| 185 | |
| 186 return TRUE; | |
| 187 } | |
| 188 | |
| 84 InfoBar* ExtensionInfoBarDelegate::CreateInfoBar(TabContentsWrapper* owner) { | 189 InfoBar* ExtensionInfoBarDelegate::CreateInfoBar(TabContentsWrapper* owner) { |
| 85 return new ExtensionInfoBarGtk(owner, this); | 190 return new ExtensionInfoBarGtk(owner, this); |
| 86 } | 191 } |
| OLD | NEW |