[gnome-boxes] Add VNC display
- From: Marc-Andre Lureau <malureau src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-boxes] Add VNC display
- Date: Tue, 25 Oct 2011 19:13:58 +0000 (UTC)
commit e95d0e6b9e3ee94583f6d739b2716ad5386ee466
Author: Marc-Andrà Lureau <marcandre lureau gmail com>
Date: Tue Oct 25 21:05:30 2011 +0200
Add VNC display
configure.ac | 10 ++++--
src/Makefile.am | 2 +
src/display-page.vala | 1 +
src/display.vala | 2 +-
src/machine.vala | 45 ++++++++++++++++------------
src/spice-display.vala | 2 +-
src/vnc-display.vala | 75 ++++++++++++++++++++++++++++++++++++++++++++++++
src/wizard.vala | 20 ++++++++++--
8 files changed, 129 insertions(+), 28 deletions(-)
---
diff --git a/configure.ac b/configure.ac
index d0005bf..2117e70 100644
--- a/configure.ac
+++ b/configure.ac
@@ -34,19 +34,21 @@ AC_PROG_LIBTOOL
GLIB_GSETTINGS
+CLUTTER_GTK_MIN_VERSION=1.0.1
GLIB_MIN_VERSION=2.29.90
-GTK_MIN_VERSION=3.1.13
GOBJECT_INTROSPECTION_MIN_VERSION=0.9.6
-CLUTTER_GTK_MIN_VERSION=1.0.1
-SPICE_GTK_MIN_VERSION=0.7
+GTK_MIN_VERSION=3.1.13
+GTK_VNC_MIN_VERSION=0.4.3
LIBVIRT_GLIB_MIN_VERSION=0.0.1
LIBXML2_MIN_VERSION=2.7.8
+SPICE_GTK_MIN_VERSION=0.7
PKG_CHECK_MODULES(BOXES, [
clutter-gtk-1.0 >= $CLUTTER_GTK_MIN_VERSION
glib-2.0 >= $GLIB_MIN_VERSION
gobject-introspection-1.0 >= $GOBJECT_INTROSPECTION_MIN_VERSION
gtk+-3.0 >= $GTK_MIN_VERSION
+ gtk-vnc-2.0 >= $GTK_VNC_MIN_VERSION
libvirt-gobject-1.0 >= $LIBVIRT_GLIB_MIN_VERSION
libxml-2.0 >= $LIBXML2_MIN_VERSION
spice-client-gtk-3.0 >= $SPICE_GTK_MIN_VERSION
@@ -57,6 +59,8 @@ VALA_CHECK_PACKAGES([
cogl-1.0
gdk-pixbuf-2.0
glib-2.0
+ gtk+-3.0
+ gtk-vnc-2.0
libvirt-gobject-1.0
libxml-2.0
posix
diff --git a/src/Makefile.am b/src/Makefile.am
index 1211a12..0da1a0d 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -19,6 +19,7 @@ AM_VALAFLAGS = \
--pkg libxml-2.0 \
--pkg posix \
--pkg spice-client-gtk-3.0 \
+ --pkg gtk-vnc-2.0 \
$(NULL)
bin_PROGRAMS = gnome-boxes
@@ -36,6 +37,7 @@ gnome_boxes_SOURCES = \
spice-display.vala \
topbar.vala \
util.vala \
+ vnc-display.vala \
wizard.vala \
$(NULL)
BUILT_SOURCES = dirs.h
diff --git a/src/display-page.vala b/src/display-page.vala
index deabcc9..55588ff 100644
--- a/src/display-page.vala
+++ b/src/display-page.vala
@@ -38,6 +38,7 @@ private class Boxes.DisplayPage: GLib.Object {
if (event_box.get_child () != null)
event_box.get_child ().event (event);
+
return false;
});
overlay = new Overlay ();
diff --git a/src/display.vala b/src/display.vala
index ad73f80..d2d8993 100644
--- a/src/display.vala
+++ b/src/display.vala
@@ -8,7 +8,7 @@ private abstract class Boxes.Display: GLib.Object {
public signal void hide (int display_id);
public signal void disconnected ();
- public abstract Gtk.Widget get_display (int n) throws Boxes.Error;
+ public abstract Gtk.Widget? get_display (int n) throws Boxes.Error;
public abstract void connect_it ();
public abstract void disconnect_it ();
diff --git a/src/machine.vala b/src/machine.vala
index 377b5c4..df36982 100644
--- a/src/machine.vala
+++ b/src/machine.vala
@@ -37,18 +37,17 @@ private abstract class Boxes.Machine: Boxes.CollectionItem {
show_id = _display.show.connect ((id) => {
app.ui_state = Boxes.UIState.DISPLAY;
- try {
- var widget = display.get_display (0);
-
- Timeout.add (Boxes.App.duration, () => {
+ Timeout.add (Boxes.App.duration, () => {
+ try {
+ var widget = display.get_display (0);
app.display_page.show_display (this, widget);
widget.grab_focus ();
+ } catch (Boxes.Error error) {
+ warning (error.message);
+ }
- return false;
- });
- } catch (Boxes.Error error) {
- warning (error.message);
- }
+ return false;
+ });
});
hide_id = _display.hide.connect ((id) => {
@@ -59,11 +58,14 @@ private abstract class Boxes.Machine: Boxes.CollectionItem {
app.ui_state = Boxes.UIState.COLLECTION;
});
- need_password_id = display.notify["need-password"].connect (() => {
+ need_password_id = _display.notify["need-password"].connect (() => {
machine_actor.set_password_needed (display.need_password);
});
- display.password = machine_actor.get_password ();
+ _display.password = machine_actor.get_password ();
+
+ if (_connect_display)
+ display.connect_it ();
}
}
@@ -292,17 +294,22 @@ private class Boxes.LibvirtMachine: Boxes.Machine {
return;
}
- if (type == "spice") {
- if (display != null)
- display.disconnect_it ();
+ if (display != null)
+ display.disconnect_it ();
+
+ switch (type) {
+ case "spice":
display = new SpiceDisplay (ghost, int.parse (gport));
- } else {
+ break;
+
+ case "vnc":
+ display = new VncDisplay (ghost, int.parse (gport));
+ break;
+
+ default:
warning ("unsupported display of type " + type);
- return;
+ break;
}
-
- if (_connect_display)
- display.connect_it ();
}
public override string get_screenshot_prefix () {
diff --git a/src/spice-display.vala b/src/spice-display.vala
index 3d12bf2..3a5d212 100644
--- a/src/spice-display.vala
+++ b/src/spice-display.vala
@@ -22,7 +22,7 @@ private class Boxes.SpiceDisplay: Boxes.Display {
session.uri = uri;
}
- public override Gtk.Widget get_display (int n) throws Boxes.Error {
+ public override Gtk.Widget? get_display (int n) throws Boxes.Error {
var display = displays.lookup (n) as Spice.Display;
if (display == null) {
diff --git a/src/vnc-display.vala b/src/vnc-display.vala
new file mode 100644
index 0000000..179c709
--- /dev/null
+++ b/src/vnc-display.vala
@@ -0,0 +1,75 @@
+// This file is part of GNOME Boxes. License: LGPLv2+
+using Gtk;
+using Vnc;
+
+private class Boxes.VncDisplay: Boxes.Display {
+ private Vnc.Display display;
+ private string host;
+ private int port;
+ private Gtk.Window window;
+
+ construct {
+ need_password = false;
+
+ display = new Vnc.Display ();
+ display.set_keyboard_grab (true);
+ display.set_pointer_grab (true);
+ display.set_force_size (false);
+ display.set_scaling (true);
+
+ // the VNC widget doesn't like not to have a realized window,
+ // so we put it into a window temporarily
+ window = new Gtk.Window ();
+ window.add (display);
+ display.realize ();
+
+ display.vnc_connected.connect (() => {
+ show (0);
+ });
+ display.vnc_disconnected.connect (() => {
+ hide (0);
+ });
+ display.vnc_initialized.connect (() => {
+ debug ("initialized");
+ });
+ display.vnc_auth_failure.connect (() => {
+ debug ("auth failure");
+ });
+ display.vnc_auth_unsupported.connect (() => {
+ debug ("auth unsupported");
+ });
+ display.vnc_auth_credential.connect (() => {
+ debug ("auth credentials");
+ });
+ }
+
+ public VncDisplay (string host, int port) {
+ this.host = host;
+ this.port = port;
+ }
+
+ public VncDisplay.with_uri (string _uri) throws Boxes.Error {
+ var uri = Xml.URI.parse (_uri);
+
+ if (uri.scheme != "vnc")
+ throw new Boxes.Error.INVALID ("the URI is not vnc://");
+
+ if (uri.server == null)
+ throw new Boxes.Error.INVALID ("the URI is missing a server");
+
+ this.host = uri.server;
+ this.port = uri.port == -1 ? 5900 : uri.port;
+ }
+
+ public override Gtk.Widget? get_display (int n) throws Boxes.Error {
+ window.remove (display);
+ return display;
+ }
+
+ public override void connect_it () {
+ display.open_host (host, port.to_string ());
+ }
+
+ public override void disconnect_it () {
+ }
+}
diff --git a/src/wizard.vala b/src/wizard.vala
index 49eef8e..acfc3c6 100644
--- a/src/wizard.vala
+++ b/src/wizard.vala
@@ -246,13 +246,25 @@ private class Boxes.Wizard: Boxes.UI {
throw new Boxes.Error.INVALID ("the URI is invalid");
if (uri.scheme == "spice" || uri.scheme == "vnc") {
- var query = new Query (uri.query_raw ?? uri.query);
-
source = new CollectionSource (uri.server, uri.scheme, text);
summary.add_property (_("Type"), uri.scheme.up ());
summary.add_property (_("Host"), uri.server.down ());
- summary.add_property (_("Port"), query.get ("port"));
- summary.add_property (_("TLS Port"), query.get ("tls-port"));
+
+ if (uri.scheme == "spice") {
+ if (uri.query_raw == null && uri.query == null)
+ throw new Boxes.Error.INVALID ("the Spice URI is incomplete");
+
+ var query = new Query (uri.query_raw ?? uri.query);
+
+ if (uri.port != -1)
+ throw new Boxes.Error.INVALID ("the Spice URI is invalid");
+
+ summary.add_property (_("Port"), query.get ("port"));
+ summary.add_property (_("TLS Port"), query.get ("tls-port"));
+ } else {
+ if (uri.port != -1)
+ summary.add_property (_("Port"), uri.port.to_string ());
+ }
} else
throw new Boxes.Error.INVALID ("Unsupported protocol");
} else {
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]