[IPython-dev] Qt api selection re. ipython and matplotlib

Eric Firing efiring at hawaii.edu
Wed Jul 6 04:15:41 EDT 2011


On 07/05/2011 08:06 PM, MinRK wrote:
> On Jul 5, 2011, at 18:32, Darren Dale<dsdale24 at gmail.com>  wrote:
>
>> On Tue, Jul 5, 2011 at 8:39 PM, MinRK<benjaminrk at gmail.com>  wrote:
>>> On Tue, Jul 5, 2011 at 09:45, Eric Firing<efiring at hawaii.edu>  wrote:
>>>> On 07/05/2011 01:36 AM, Darren Dale wrote:
>>>>>
>>>>> On Tue, Jul 5, 2011 at 2:22 AM, Eric Firing<efiring at hawaii.edu>   wrote:
>>>>>>
>>>>>> On 07/04/2011 06:51 PM, MinRK wrote:
>>>>>>>
>>>>>>> On Mon, Jul 4, 2011 at 20:57, Eric Firing<efiring at hawaii.edu>     wrote:
>>>>>>>>
>>>>>>>> If I remove the version-setting from qt.py, then ipython still works
>>>>>>>> with mpl and PyQt4 via "ipython pylab=qt", but it does not work with
>>>>>>>> qtconsole or with PySide.
>>>>>>>
>>>>>>> I don't think we are going to rewrite the whole qtconsole to support
>>>>>>> version 1 for 0.11 this week.  What we can do is change the default
>>>>>>> behavior in qt_for_kernel,
>>>>>>>
>>>>>>>
>>>>>>> (https://github.com/ipython/ipython/blob/master/IPython/external/qt_for_kernel.py)
>>>>>>> which is where code that interacts with other applications gets
>>>>>>> imported.  Currently, we use our v2 import unless matplotlib<= 1.0.1
>>>>>>> is detected.  However, we can change that default to be more
>>>>>>> conservative.  User code (e.g. matplotlib code, integration with other
>>>>>>> apps) is not in the same process as the QtConsole, so we can have v1
>>>>>>> code in the kernel with v2 in the frontend.
>>>>>
>>>>> Good point.
>>>>>
>>>>>> If ipython and mpl have to be synchronized, and if we want to be able to
>>>>>> choose to use pyside or pyqt4, then I think we need more than a change in
>>>>>> the ipython default.  It looks like this calls for yet another pesky
>>>>>> rcParams entry in mpl.  Then that can be used for figuring out what to
>>>>>> import in both matplotlib and ipython.  The default, if there is no
>>>>>> rcParams
>>>>>> entry, would be PyQt4 with the platform default API version.
>>>>>>
>>>>>> Darren, does this sound like a solution that would work for you?
>>>>>
>>>>> If ipython changes its qt_for_kernel to not set the api level, then it
>>>>> seems to me that either the environment variable approach or the
>>>>> rcParams approach will work for pylab/pyplot. The rcParams approach is
>>>>> a little awkward for folks using the OO interface, but it looks like
>>>>> it would work. You mentioned that it does not work with the ipython
>>>>> console and pyside though, what doesn't work?
>>>>
>>>> No figure is displayed after plotting, and then there is an error upon
>>>> exiting ipython if the figure (which was never displayed) is not closed.
>>>>
>>>> Eric
>>>>
>>>>
>>>
>>> I think the logic should be something along the lines of:
>>>
>>> if matplotlib:
>>>     if matplotlib<= 1.0.1:
>>>          use PyQt+v1 # old matplotlib can't support v2, if I
>>> understand correctly
>>>     else:
>>>          ask matplotlib
>>> if no answer or no matplotlib:
>>>     if QT_API defined:
>>>         if QT_API=pyqt:
>>>                 use PyQt+v2 #because this is an ETS env variable, and
>>> ETS requires v2
>>>         elif QT_API=pyside:
>>>            use pyside
>>>     else:
>>>         try pyqt+v1
>>>         if no pyqt:
>>>              try pyside
>>>
>>> gist: QT_API should be respected if set, and use v2 unless matplotlib
>>> is too old to allow it.  If nothing is specified, the default is
>>> pyqt+v1, the safest option, but PySide should still be chosen if it's
>>> the only Qt installed.
>>>
>>> Does this make sense?
>>
>> You won't be able to tell what PyQt API to use from matplotlib. I
>> think the default api (version 1) would be the appropriate choice
>> unless QT_API is set, since as you say this is an ETS environment
>> variable and ETS is the only python2 library I am aware of that
>> actually requires PyQt4's v2 API. It would be useful to document this
>> somewhere, perhaps at
>> http://ipython.org/ipython-doc/dev/interactive/reference.html#gui-event-loop-support-support
>
> I didn't mean that it would ask matplotlib what PyQt API to use, only
> whether to use PyQt or PySide.  Eric issues a PR that suggested such
> an option was incoming.
>
> I've issued another pull request based on Eric's that handles various
> cases, and also tries to explain some of this mess in the docs as you
> suggested.
>
> PyQt4 unmolested will happen most of the time, but PySide when
> requested will still be used, and PySide will be a fallback for
> ``gui=qt`` if PyQt isn't installed.
>
> The *only* way PyQt4 will be using v2 is if the ETS env variable is
> set as QT_API=pyqt, *and* matplotlib had nothing to say about PyQt vs
> PySide (matplotlib being<= 1.0.1 also prevents PyQt with v2).  If we
> gathered from matplotlib that we should use PyQt, it will not be
> patched to v2.
>
> This places matplotlib / PyQt v1 code at the highest priority, but
> also allows ETS, and code that uses modern interfaces, to work via
> QT_API.

Darren et al.,

Is all this good from your mpl/qt standpoint?  We could make mpl pay 
attention to the ETS QT_API environment variable, if present, while 
retaining the rcParam.  For example, QT_API could simply override the 
rcParam, with the additional effect of forcing v2 in the PyQt4 case.  In 
other words, if QT_API is defined, we would follow the original ETS 
strategy; otherwise the rcParams strategy as in my last mpl pull 
request.  I think that although this is a bit more complicated, and 
would require one more iteration on the ipython side as well as on the 
mpl side, it might last longer as a way to handle just about all 
situations, including mpl mixed with ETS things.

Regarding PySide: I actually can't get it to work in interactive mode 
(that is, display a plot) even from the straight python prompt; it is 
working in interactive mode at present only in the ipython qtconsole. 
As of April, PySide apparently did not use the input hook:

http://lists.pyside.org/pipermail/pyside/2011-April/002362.html

Google didn't turn up anything more recent.  So how is it that pylab 
with PySide is working in qtconsole?

Eric




>
>>
>> By the way, I find the new ipython's new argument parsing really
>> non-intuitive. It took me 5 attempts to figure out how to do "ipython
>> gui=qt", even after skimming the output of "ipython -h". What's wrong
>> with "ipython --gui=qt"? Does ipython really need to put its own
>> unique spin on argument parsing?
>
> The reason for Brian's design here is that now the command line args
> are coupled with the config system.  Specifying a value on the command
> line is now identical to specifying it in a config file, so it looks
> like a Python assignment (because it is).  It also means that 100% of
> IPython is configurable from the command-line.
>
>
> -MinRK




More information about the IPython-dev mailing list