| OLD | NEW |
| 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2009 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 "views/controls/native/native_view_host_gtk.h" | 5 #include "views/controls/native/native_view_host_gtk.h" |
| 6 | 6 |
| 7 #include <gtk/gtk.h> | 7 #include <gtk/gtk.h> |
| 8 | 8 |
| 9 #include "base/logging.h" | 9 #include "base/logging.h" |
| 10 #include "views/controls/native/native_view_host.h" | 10 #include "views/controls/native/native_view_host.h" |
| (...skipping 29 matching lines...) Expand all Loading... |
| 40 | 40 |
| 41 if (!destroy_signal_id_) { | 41 if (!destroy_signal_id_) { |
| 42 destroy_signal_id_ = g_signal_connect(G_OBJECT(host_->native_view()), | 42 destroy_signal_id_ = g_signal_connect(G_OBJECT(host_->native_view()), |
| 43 "destroy", G_CALLBACK(CallDestroy), | 43 "destroy", G_CALLBACK(CallDestroy), |
| 44 this); | 44 this); |
| 45 } | 45 } |
| 46 | 46 |
| 47 // Always layout though. | 47 // Always layout though. |
| 48 host_->Layout(); | 48 host_->Layout(); |
| 49 | 49 |
| 50 // We own the native view as long as it's attached, so that we can safely |
| 51 // reparent it in multiple passes. |
| 52 gtk_widget_ref(host_->native_view()); |
| 53 |
| 50 // TODO(port): figure out focus. | 54 // TODO(port): figure out focus. |
| 51 } | 55 } |
| 52 | 56 |
| 53 void NativeViewHostGtk::NativeViewDetaching() { | 57 void NativeViewHostGtk::NativeViewDetaching() { |
| 54 DCHECK(host_->native_view()); | 58 DCHECK(host_->native_view()); |
| 55 | 59 |
| 56 g_signal_handler_disconnect(G_OBJECT(host_->native_view()), | 60 g_signal_handler_disconnect(G_OBJECT(host_->native_view()), |
| 57 destroy_signal_id_); | 61 destroy_signal_id_); |
| 58 destroy_signal_id_ = 0; | 62 destroy_signal_id_ = 0; |
| 59 | 63 |
| 60 // TODO(port): focus. | 64 // TODO(port): focus. |
| 61 // FocusManager::UninstallFocusSubclass(native_view()); | 65 // FocusManager::UninstallFocusSubclass(native_view()); |
| 62 installed_clip_ = false; | 66 installed_clip_ = false; |
| 67 |
| 68 // Release ownership back to the caller. |
| 69 gtk_widget_unref(host_->native_view()); |
| 63 } | 70 } |
| 64 | 71 |
| 65 void NativeViewHostGtk::AddedToWidget() { | 72 void NativeViewHostGtk::AddedToWidget() { |
| 66 if (gtk_widget_get_parent(fixed_)) | 73 if (gtk_widget_get_parent(fixed_)) |
| 67 GetHostWidget()->ReparentChild(fixed_); | 74 GetHostWidget()->ReparentChild(fixed_); |
| 68 else | 75 else |
| 69 GetHostWidget()->AddChild(fixed_); | 76 GetHostWidget()->AddChild(fixed_); |
| 70 | 77 |
| 71 if (!host_->native_view()) | 78 if (!host_->native_view()) |
| 72 return; | 79 return; |
| 73 | 80 |
| 74 if (gtk_widget_get_parent(host_->native_view())) | 81 if (gtk_widget_get_parent(host_->native_view())) |
| 75 gtk_widget_reparent(host_->native_view(), fixed_); | 82 gtk_widget_reparent(host_->native_view(), fixed_); |
| 76 else | 83 else |
| 77 gtk_container_add(GTK_CONTAINER(fixed_), host_->native_view()); | 84 gtk_container_add(GTK_CONTAINER(fixed_), host_->native_view()); |
| 78 | 85 |
| 79 if (host_->IsVisibleInRootView()) | 86 if (host_->IsVisibleInRootView()) |
| 80 gtk_widget_show(fixed_); | 87 gtk_widget_show(fixed_); |
| 81 else | 88 else |
| 82 gtk_widget_hide(fixed_); | 89 gtk_widget_hide(fixed_); |
| 83 host_->Layout(); | 90 host_->Layout(); |
| 84 } | 91 } |
| 85 | 92 |
| 86 void NativeViewHostGtk::RemovedFromWidget() { | 93 void NativeViewHostGtk::RemovedFromWidget() { |
| 87 if (!host_->native_view()) | 94 if (!host_->native_view()) |
| 88 return; | 95 return; |
| 89 | 96 |
| 90 // TODO(beng): We leak host_->native_view() here. Fix: make all widgets not be | |
| 91 // refcounted. | |
| 92 DestroyFixed(); | 97 DestroyFixed(); |
| 93 } | 98 } |
| 94 | 99 |
| 95 void NativeViewHostGtk::InstallClip(int x, int y, int w, int h) { | 100 void NativeViewHostGtk::InstallClip(int x, int y, int w, int h) { |
| 96 DCHECK(w > 0 && h > 0); | 101 DCHECK(w > 0 && h > 0); |
| 97 installed_clip_bounds_.SetRect(x, y, w, h); | 102 installed_clip_bounds_.SetRect(x, y, w, h); |
| 98 installed_clip_ = true; | 103 installed_clip_ = true; |
| 99 | 104 |
| 100 // We only re-create the fixed with a window when a cliprect is installed. | 105 // We only re-create the fixed with a window when a cliprect is installed. |
| 101 // Because the presence of a X Window will prevent transparency from working | 106 // Because the presence of a X Window will prevent transparency from working |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 149 } | 154 } |
| 150 | 155 |
| 151 void NativeViewHostGtk::SetFocus() { | 156 void NativeViewHostGtk::SetFocus() { |
| 152 NOTIMPLEMENTED(); | 157 NOTIMPLEMENTED(); |
| 153 } | 158 } |
| 154 | 159 |
| 155 //////////////////////////////////////////////////////////////////////////////// | 160 //////////////////////////////////////////////////////////////////////////////// |
| 156 // NativeViewHostGtk, private: | 161 // NativeViewHostGtk, private: |
| 157 | 162 |
| 158 void NativeViewHostGtk::CreateFixed(bool needs_window) { | 163 void NativeViewHostGtk::CreateFixed(bool needs_window) { |
| 159 bool native_view_addrefed = DestroyFixed(); | 164 DestroyFixed(); |
| 160 | 165 |
| 161 fixed_ = gtk_fixed_new(); | 166 fixed_ = gtk_fixed_new(); |
| 162 gtk_fixed_set_has_window(GTK_FIXED(fixed_), needs_window); | 167 gtk_fixed_set_has_window(GTK_FIXED(fixed_), needs_window); |
| 163 // Defeat refcounting. We need to own the fixed. | 168 // Defeat refcounting. We need to own the fixed. |
| 164 gtk_widget_ref(fixed_); | 169 gtk_widget_ref(fixed_); |
| 165 | 170 |
| 166 WidgetGtk* widget_gtk = GetHostWidget(); | 171 WidgetGtk* widget_gtk = GetHostWidget(); |
| 167 if (widget_gtk) | 172 if (widget_gtk) |
| 168 widget_gtk->AddChild(fixed_); | 173 widget_gtk->AddChild(fixed_); |
| 169 if (host_->native_view()) | 174 if (host_->native_view()) |
| 170 gtk_container_add(GTK_CONTAINER(fixed_), host_->native_view()); | 175 gtk_container_add(GTK_CONTAINER(fixed_), host_->native_view()); |
| 171 if (native_view_addrefed) | |
| 172 gtk_widget_unref(host_->native_view()); | |
| 173 } | 176 } |
| 174 | 177 |
| 175 bool NativeViewHostGtk::DestroyFixed() { | 178 void NativeViewHostGtk::DestroyFixed() { |
| 176 bool native_view_addrefed = false; | |
| 177 if (!fixed_) | 179 if (!fixed_) |
| 178 return native_view_addrefed; | 180 return; |
| 179 | 181 |
| 180 gtk_widget_hide(fixed_); | 182 gtk_widget_hide(fixed_); |
| 181 GetHostWidget()->RemoveChild(fixed_); | 183 GetHostWidget()->RemoveChild(fixed_); |
| 182 | 184 |
| 183 if (host_->native_view()) { | 185 if (host_->native_view()) { |
| 184 // We can't allow the hosted NativeView's refcount to drop to zero. | 186 // We can safely remove the widget from its container since we own the |
| 185 gtk_widget_ref(host_->native_view()); | 187 // widget from the moment it is attached. |
| 186 native_view_addrefed = true; | |
| 187 gtk_container_remove(GTK_CONTAINER(fixed_), host_->native_view()); | 188 gtk_container_remove(GTK_CONTAINER(fixed_), host_->native_view()); |
| 188 } | 189 } |
| 189 | 190 |
| 190 gtk_widget_destroy(fixed_); | 191 gtk_widget_destroy(fixed_); |
| 191 fixed_ = NULL; | 192 fixed_ = NULL; |
| 192 return native_view_addrefed; | |
| 193 } | 193 } |
| 194 | 194 |
| 195 WidgetGtk* NativeViewHostGtk::GetHostWidget() const { | 195 WidgetGtk* NativeViewHostGtk::GetHostWidget() const { |
| 196 return static_cast<WidgetGtk*>(host_->GetWidget()); | 196 return static_cast<WidgetGtk*>(host_->GetWidget()); |
| 197 } | 197 } |
| 198 | 198 |
| 199 // static | 199 // static |
| 200 void NativeViewHostGtk::CallDestroy(GtkObject* object, | 200 void NativeViewHostGtk::CallDestroy(GtkObject* object, |
| 201 NativeViewHostGtk* host) { | 201 NativeViewHostGtk* host) { |
| 202 return host->host_->NativeViewDestroyed(); | 202 return host->host_->NativeViewDestroyed(); |
| 203 } | 203 } |
| 204 | 204 |
| 205 //////////////////////////////////////////////////////////////////////////////// | 205 //////////////////////////////////////////////////////////////////////////////// |
| 206 // NativeViewHostWrapper, public: | 206 // NativeViewHostWrapper, public: |
| 207 | 207 |
| 208 // static | 208 // static |
| 209 NativeViewHostWrapper* NativeViewHostWrapper::CreateWrapper( | 209 NativeViewHostWrapper* NativeViewHostWrapper::CreateWrapper( |
| 210 NativeViewHost* host) { | 210 NativeViewHost* host) { |
| 211 return new NativeViewHostGtk(host); | 211 return new NativeViewHostGtk(host); |
| 212 } | 212 } |
| 213 | 213 |
| 214 } // namespace views | 214 } // namespace views |
| OLD | NEW |