• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "ui/base/gtk/focus_store_gtk.h"
6 
7 #include <gtk/gtk.h>
8 
9 namespace ui {
10 
FocusStoreGtk()11 FocusStoreGtk::FocusStoreGtk()
12     : widget_(NULL),
13       destroy_handler_id_(0) {
14 }
15 
~FocusStoreGtk()16 FocusStoreGtk::~FocusStoreGtk() {
17   DisconnectDestroyHandler();
18 }
19 
Store(GtkWidget * widget)20 void FocusStoreGtk::Store(GtkWidget* widget) {
21   GtkWidget* focus_widget = NULL;
22   if (widget) {
23     // A detached widget won't have a toplevel window as an ancestor, so we
24     // can't assume that the query for toplevel will return a window.
25     GtkWidget* toplevel = gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW);
26     GtkWindow* window = GTK_IS_WINDOW(toplevel) ? GTK_WINDOW(toplevel) : NULL;
27     if (window)
28       focus_widget = gtk_window_get_focus(window);
29   }
30 
31   SetWidget(focus_widget);
32 }
33 
SetWidget(GtkWidget * widget)34 void FocusStoreGtk::SetWidget(GtkWidget* widget) {
35   DisconnectDestroyHandler();
36 
37   // We don't add a ref. The signal handler below effectively gives us a weak
38   // reference.
39   widget_ = widget;
40   if (widget_) {
41     // When invoked, |gtk_widget_destroyed| will set |widget_| to NULL.
42     destroy_handler_id_ = g_signal_connect(widget_, "destroy",
43                                            G_CALLBACK(gtk_widget_destroyed),
44                                            &widget_);
45   }
46 }
47 
DisconnectDestroyHandler()48 void FocusStoreGtk::DisconnectDestroyHandler() {
49   if (widget_) {
50     g_signal_handler_disconnect(widget_, destroy_handler_id_);
51     widget_ = NULL;
52   }
53 }
54 
55 }  // namespace ui
56