[gnome-boxes] Switch to client-side decoration



commit 3fcf3bd9e10b6141f57e2d30aeba4ef6cae82cfc
Author: Zeeshan Ali (Khattak) <zeeshanak gnome org>
Date:   Thu Aug 29 17:53:49 2013 +0300

    Switch to client-side decoration
    
    In preparation for the wayland tech demo in 3.10, all other GNOME 3 apps
    are switching to client-side window decoration so we should too.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=706414

 src/app.vala          |    7 +------
 src/display-page.vala |   29 ++++++++++++++++++++++-------
 src/properties.vala   |    9 +++++++++
 src/topbar.vala       |   34 ++++++++++++++++++++++++++++------
 4 files changed, 60 insertions(+), 19 deletions(-)
---
diff --git a/src/app.vala b/src/app.vala
index 225c79e..520cefe 100644
--- a/src/app.vala
+++ b/src/app.vala
@@ -475,7 +475,6 @@ private class Boxes.App: Boxes.UI {
 
         window = new Gtk.ApplicationWindow (application);
         window.show_menubar = false;
-        window.hide_titlebar_when_maximized = true;
 
         // restore window geometry/position
         var size = settings.get_value ("window-size");
@@ -586,11 +585,7 @@ private class Boxes.App: Boxes.UI {
 
         stage.add_child (vbox_actor);
 
-        var topbar_revealer = new Boxes.Revealer (true);
-        topbar_revealer.name = "topbar-revealer";
-        topbar_revealer.x_expand = true;
-        vbox_actor.add_child (topbar_revealer);
-        topbar_revealer.add (topbar.actor);
+        window.set_titlebar (topbar.widget);
 
         searchbar_revealer = new Boxes.Revealer (true);
         searchbar_revealer.resize = true;
diff --git a/src/display-page.vala b/src/display-page.vala
index 7bfa511..a09c017 100644
--- a/src/display-page.vala
+++ b/src/display-page.vala
@@ -4,19 +4,23 @@ using Gdk;
 
 private class Boxes.DisplayToolbar: Gtk.HeaderBar {
     private bool overlay;
+    private bool handle_drag; // Handle drag events to (un)fulscreen the main window
 
-    public DisplayToolbar (bool overlay) {
+    public DisplayToolbar (bool overlay, bool handle_drag) {
         add_events (Gdk.EventMask.POINTER_MOTION_MASK |
                     Gdk.EventMask.BUTTON_PRESS_MASK |
                     Gdk.EventMask.BUTTON_RELEASE_MASK);
 
         this.overlay = overlay;
+        this.handle_drag = handle_drag;
         if (overlay) {
             get_style_context ().add_class ("toolbar");
             get_style_context ().add_class ("osd");
             spacing = 0;
-        } else
+        } else {
             get_style_context ().add_class (Gtk.STYLE_CLASS_MENUBAR);
+            show_close_button = true;
+        }
 
         var back_icon = (get_direction () == Gtk.TextDirection.RTL)? "go-previous-rtl-symbolic" :
                                                                      "go-previous-symbolic";
@@ -61,6 +65,8 @@ private class Boxes.DisplayToolbar: Gtk.HeaderBar {
 
     public override bool button_press_event (Gdk.EventButton event) {
         var res = base.button_press_event (event);
+        if (!handle_drag)
+            return res;
 
         // With the current GdkEvent bindings this is the only way to
         // upcast a GdkEventButton to a GdkEvent (which we need for
@@ -83,6 +89,9 @@ private class Boxes.DisplayToolbar: Gtk.HeaderBar {
     }
 
     public override bool motion_notify_event (Gdk.EventMotion event) {
+        if (!handle_drag)
+            return base.motion_notify_event (event);
+
         if (button_down) {
             double dx = event.x - button_down_x;
             double dy = event.y - button_down_y;
@@ -118,6 +127,8 @@ private class Boxes.DisplayToolbar: Gtk.HeaderBar {
 private class Boxes.DisplayPage: GLib.Object {
     public Widget widget { get { return box; } }
 
+    public DisplayToolbar title_toolbar; // Toolbar used when window is not maximized
+
     private EventBox event_box;
     private Box box;
     private DisplayToolbar overlay_toolbar;
@@ -188,7 +199,7 @@ private class Boxes.DisplayPage: GLib.Object {
             return false;
         });
 
-        toolbar = new DisplayToolbar (false);
+        toolbar = new DisplayToolbar (false, true);
 
         box = new Box (Orientation.VERTICAL, 0);
         box.pack_start (toolbar, false, false, 0);
@@ -204,7 +215,7 @@ private class Boxes.DisplayPage: GLib.Object {
 
         box.pack_start (grid, true, true, 0);
 
-        overlay_toolbar = new DisplayToolbar (true);
+        overlay_toolbar = new DisplayToolbar (true, true);
         overlay_toolbar_box = new EventBox ();
         overlay_toolbar_box.add (overlay_toolbar);
         overlay_toolbar_box.valign = Gtk.Align.START;
@@ -221,8 +232,12 @@ private class Boxes.DisplayPage: GLib.Object {
 
         box.show_all ();
 
+        title_toolbar = new DisplayToolbar (false, false);
+
         toolbar.bind_property ("title", overlay_toolbar, "title", BindingFlags.SYNC_CREATE);
         toolbar.bind_property ("subtitle", overlay_toolbar, "subtitle", BindingFlags.SYNC_CREATE);
+        toolbar.bind_property ("title", title_toolbar, "title", BindingFlags.SYNC_CREATE);
+        toolbar.bind_property ("subtitle", title_toolbar, "subtitle", BindingFlags.SYNC_CREATE);
     }
 
     public void add_notification (Widget w) {
@@ -241,10 +256,10 @@ private class Boxes.DisplayPage: GLib.Object {
     }
 
      private void update_toolbar_visible() {
-         if (App.app.fullscreen && !can_grab_mouse)
-             toolbar.visible = false;
-         else
+         if (App.app.fullscreen && can_grab_mouse)
              toolbar.visible = true;
+         else
+             toolbar.visible = false;
 
          set_overlay_toolbar_visible (false);
      }
diff --git a/src/properties.vala b/src/properties.vala
index 40382e6..e1b7aa5 100644
--- a/src/properties.vala
+++ b/src/properties.vala
@@ -34,6 +34,7 @@ private class Boxes.Properties: Boxes.UI {
     private MiniGraph io;
     private MiniGraph net;
     private ulong stats_id;
+    private bool restore_fullscreen;
 
     private class PageWidget: Object {
         public Gtk.Widget widget;
@@ -314,6 +315,9 @@ private class Boxes.Properties: Boxes.UI {
         }
 
         if (ui_state == UIState.PROPERTIES) {
+            restore_fullscreen = (previous_ui_state == UIState.DISPLAY && App.app.fullscreen);
+            App.app.fullscreen = false;
+
             if (App.app.current_item is LibvirtMachine) {
                 var libvirt_machine = App.app.current_item as LibvirtMachine;
                 stats_id = libvirt_machine.stats_updated.connect (() => {
@@ -330,6 +334,11 @@ private class Boxes.Properties: Boxes.UI {
                 var page = notebook.get_data<PageWidget> (@"boxes-property-$i");
                 page.flush_changes ();
             }
+
+            if (restore_fullscreen) {
+                App.app.fullscreen = true;
+                restore_fullscreen = false;
+            }
         }
 
         fade_actor (actor, ui_state == UIState.PROPERTIES ? 255 : 0);
diff --git a/src/topbar.vala b/src/topbar.vala
index ed114c1..67d1fa1 100644
--- a/src/topbar.vala
+++ b/src/topbar.vala
@@ -6,13 +6,25 @@ public enum Boxes.TopbarPage {
     COLLECTION,
     SELECTION,
     WIZARD,
-    PROPERTIES
+    PROPERTIES,
+    DISPLAY
 }
 
 private class Boxes.Topbar: Boxes.UI {
-    public override Clutter.Actor actor { get { return gtk_actor; } }
+    // FIXME: This is really redundant now that App is using widget property
+    // instead but parent Boxes.UI currently requires an actor. Hopefully
+    // soon we can move more towards new Gtk classes and Boxes.UI requires
+    // a widget property instead.
+    public override Clutter.Actor actor {
+        get {
+            if (gtk_actor == null)
+                gtk_actor = new Clutter.Actor ();
+            return gtk_actor;
+        }
+    }
+    private Clutter.Actor gtk_actor;
 
-    private GtkClutter.Actor gtk_actor; // the topbar box
+    public Gtk.Widget widget { get { return notebook; } }
     public Notebook notebook;
 
     private Gtk.Spinner spinner;
@@ -25,11 +37,16 @@ private class Boxes.Topbar: Boxes.UI {
     private Gtk.MenuButton selection_menu_button;
     private Gtk.HeaderBar selection_toolbar;
     private Gtk.HeaderBar collection_toolbar;
+    private Gtk.HeaderBar display_toolbar;
 
     public string? _status;
     public string? status {
         get { return _status; }
-        set { _status = value; collection_toolbar.set_title (_status); }
+        set {
+            _status = value;
+            collection_toolbar.set_title (_status);
+            display_toolbar.set_title (_status);
+        }
     }
 
     public Topbar () {
@@ -42,8 +59,6 @@ private class Boxes.Topbar: Boxes.UI {
 
     private void setup_topbar () {
         notebook = new Gtk.Notebook ();
-        gtk_actor = new GtkClutter.Actor.with_contents (notebook);
-        gtk_actor.name = "topbar";
 
         /* TopbarPage.COLLECTION */
         var hbox = new Gtk.Box (Gtk.Orientation.HORIZONTAL, 0);
@@ -149,6 +164,11 @@ private class Boxes.Topbar: Boxes.UI {
         hbox = new Gtk.Box (Gtk.Orientation.HORIZONTAL, 0);
         notebook.append_page (hbox, null);
 
+        /* TopbarPage.DISPLAY */
+        hbox = new Gtk.Box (Gtk.Orientation.HORIZONTAL, 0);
+        display_toolbar = App.app.display_page.title_toolbar;
+        hbox.pack_start (display_toolbar, true, true, 0);
+        notebook.append_page (hbox, null);
 
         update_search_btn ();
         App.app.collection.item_added.connect (update_search_btn);
@@ -199,6 +219,8 @@ private class Boxes.Topbar: Boxes.UI {
             break;
 
         case UIState.DISPLAY:
+            notebook.page = TopbarPage.DISPLAY;
+            spinner.hide ();
             break;
 
         case UIState.PROPERTIES:


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]