Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Loading…

Gtk3 integration with ipython works. #1588

Merged
merged 7 commits into from

3 participants

@thomir

This branch adds support for interactive Gtk3 UI support.

The older Gtk2 bindings (pygtk) are being deprecated in the wild, in favor of the newer gi bindings. This allows users to use new features in Gtk3. This is a very simple branch, that follows the same pattern as the 'gtk' UI support feature, but for Gtk3.

@fperez
Owner

Do you have any tests we can use to see this functionality at work? It could be an interactive example that goes into docs/examples/lib if it's hard to unittest this...

Also, since this adds a 'gtk3' target for the %gui magic, the docstring for magic_gui needs to be updated to show that gtk3 is also a valid value.

@thomir

Hi,

Thanks for looking at this. Both changes have been made now. I added a docstring to the %gui magic function. I notice that the UI types weren't listed alphabetically, so I put the docstring for 'gtk3' right below the docstring or 'gtk'. As far as testing is concerned, I've followed the pattern for the 'gtk' Gui integration.

IPython/core/magic.py
@@ -94,7 +94,7 @@ def needs_local_scope(func):
func.needs_local_scope = True
return func
-
+
@takluyver Owner

For future reference: please try to avoid whitespace changes in functional pull requests, because it makes it hard to see what's really changed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
docs/examples/lib/gui-gtk3.py
@@ -0,0 +1,37 @@
+#!/usr/bin/env python
+"""Simple Gtk example to manually test event loop integration.
+
+This is meant to run tests manually in ipython as:
+
+In [1]: %gui gtk3
+
+In [2]: %run gui-gtk3.py
+"""
+
+from gi.repository import Gtk
+
+
+def hello_world(wigdet, data=None):
+ print "Hello World"
@takluyver Owner

Can you change this to print("Hello World") so it's easy to test from Python 3 (I've just done it locally, and it does work). The brackets are valid in Python 2 for a single argument.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@fperez
Owner

@thomir, it seems that (in addition to the small fix suggested by @takluyver), this PR now has a conflict with master, likelye something small that's colliding with other recently merged code. We'll have to ask you to rebase it before we can merge it, unfortunately.

Let us know if you need help with that and we'll give you a hand. Once you rebase and make that small fix I'll take care of merging it quickly so this doesn't happen again.

@takluyver
Owner

It may well be the whitespace changes conflicting with a change in nearby lines.

@fperez
Owner

Yes, very likely, though I haven't confirmed yet by looking at the conflicts.

@thomir

Hi,

Sorry about the whitespace changes - my editor automatically strips trailing whitespace, so I didn't even notice I had done this.

I've merged trunk, and fixed the conflicts. I think I've done this correctly, although I'm using the git backend to bzr, so there's a chance it's not correct.

Thanks again for looking at this.

IPython/core/magic.py
((13 lines not shown))
contents = openpy.read_py_file(arg_s, skip_encoding_cookie=True)
self.set_next_input(contents)
+>>>>>>> MERGE-SOURCE
@takluyver Owner

Nope, this merge didn't quite go right.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@takluyver
Owner

The docstring change for the %gui magic seems to have gone missing after the latest merge.

@thomir

OK, I figured out how to use rebase properly :)

@thomir

whitespace-only changes reverted.

@takluyver takluyver merged commit 9096723 into ipython:master
@takluyver
Owner

@fperez already OKed the changes, so I've merged this.

@fperez
Owner

Many thanks to all!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
This page is out of date. Refresh to see the latest.
View
1  IPython/core/magic.py
@@ -3420,6 +3420,7 @@ def magic_gui(self, parameter_s=''):
%gui wx # enable wxPython event loop integration
%gui qt4|qt # enable PyQt4 event loop integration
%gui gtk # enable PyGTK event loop integration
+ %gui gtk3 # enable Gtk3 event loop integration
%gui tk # enable Tk event loop integration
%gui OSX # enable Cocoa event loop integration
# (requires %matplotlib 1.1)
View
1  IPython/lib/__init__.py
@@ -21,6 +21,7 @@
enable_tk, disable_tk,
enable_glut, disable_glut,
enable_pyglet, disable_pyglet,
+ enable_gtk3, disable_gtk3,
set_inputhook, clear_inputhook,
current_gui
)
View
31 IPython/lib/inputhook.py
@@ -36,6 +36,7 @@
GUI_OSX = 'osx'
GUI_GLUT = 'glut'
GUI_PYGLET = 'pyglet'
+GUI_GTK3 = 'gtk3'
GUI_NONE = 'none' # i.e. disable
#-----------------------------------------------------------------------------
@@ -421,6 +422,33 @@ def disable_pyglet(self):
"""
self.clear_inputhook()
+ def enable_gtk3(self, app=None):
+ """Enable event loop integration with Gtk3 (gir bindings).
+
+ Parameters
+ ----------
+ app : ignored
+ Ignored, it's only a placeholder to keep the call signature of all
+ gui activation methods consistent, which simplifies the logic of
+ supporting magics.
+
+ Notes
+ -----
+ This methods sets the PyOS_InputHook for Gtk3, which allows
+ the Gtk3 to integrate with terminal based applications like
+ IPython.
+ """
+ from IPython.lib.inputhookgtk3 import inputhook_gtk3
+ self.set_inputhook(inputhook_gtk3)
+ self._current_gui = GUI_GTK
+
+ def disable_gtk3(self):
+ """Disable event loop integration with PyGTK.
+
+ This merely sets PyOS_InputHook to NULL.
+ """
+ self.clear_inputhook()
+
def current_gui(self):
"""Return a string indicating the currently active GUI or None."""
return self._current_gui
@@ -439,6 +467,8 @@ def current_gui(self):
disable_glut = inputhook_manager.disable_glut
enable_pyglet = inputhook_manager.enable_pyglet
disable_pyglet = inputhook_manager.disable_pyglet
+enable_gtk3 = inputhook_manager.enable_gtk3
+disable_gtk3 = inputhook_manager.disable_gtk3
clear_inputhook = inputhook_manager.clear_inputhook
set_inputhook = inputhook_manager.set_inputhook
current_gui = inputhook_manager.current_gui
@@ -480,6 +510,7 @@ def enable_gui(gui=None, app=None):
GUI_QT4: enable_qt4,
GUI_GLUT: enable_glut,
GUI_PYGLET: enable_pyglet,
+ GUI_GTK3: enable_gtk3,
}
try:
gui_hook = guis[gui]
View
34 IPython/lib/inputhookgtk3.py
@@ -0,0 +1,34 @@
+# encoding: utf-8
+"""
+Enable Gtk3 to be used interacive by IPython.
+
+Authors: Thomi Richards
+"""
+#-----------------------------------------------------------------------------
+# Copyright (c) 2012, the IPython Development Team.
+#
+# Distributed under the terms of the Modified BSD License.
+#
+# The full license is in the file COPYING.txt, distributed with this software.
+#-----------------------------------------------------------------------------
+
+#-----------------------------------------------------------------------------
+# Imports
+#-----------------------------------------------------------------------------
+
+import sys
+from gi.repository import Gtk, GLib
+
+#-----------------------------------------------------------------------------
+# Code
+#-----------------------------------------------------------------------------
+
+def _main_quit(*args, **kwargs):
+ Gtk.main_quit()
+ return False
+
+
+def inputhook_gtk3():
+ GLib.io_add_watch(sys.stdin, GLib.IO_IN, _main_quit)
+ Gtk.main()
+ return 0
View
37 docs/examples/lib/gui-gtk3.py
@@ -0,0 +1,37 @@
+#!/usr/bin/env python
+"""Simple Gtk example to manually test event loop integration.
+
+This is meant to run tests manually in ipython as:
+
+In [1]: %gui gtk3
+
+In [2]: %run gui-gtk3.py
+"""
+
+from gi.repository import Gtk
+
+
+def hello_world(wigdet, data=None):
+ print("Hello World")
+
+def delete_event(widget, event, data=None):
+ return False
+
+def destroy(widget, data=None):
+ Gtk.main_quit()
+
+window = Gtk.Window(Gtk.WindowType.TOPLEVEL)
+window.connect("delete_event", delete_event)
+window.connect("destroy", destroy)
+button = Gtk.Button("Hello World")
+button.connect("clicked", hello_world, None)
+
+window.add(button)
+button.show()
+window.show()
+
+try:
+ from IPython.lib.inputhook import enable_gtk3
+ enable_gtk3()
+except ImportError:
+ Gtk.main()
Something went wrong with that request. Please try again.