What is the default GUI backend for Matplotlib? - python

I have made the following script, let's call it test-matplotlib-printbackend.py:
#!/usr/bin/env python
import matplotlib as mpl
import matplotlib.pyplot as plt
xx = range(100)
yy = [i*2+5 for i in xx]
fig, ax = plt.subplots()
ax.plot(xx, yy)
print("Matplotlib plt backend: {}".format(plt.get_backend()))
plt.show()
For Python3 under MINGW64 on Windows 10, as well as Python3 under Anaconda on Windows 10, I get the printout:
Matplotlib plt backend: Qt5Agg
However, for Python3 on Rasbian (Raspberry Pi's Debian OS), I get the printout:
Matplotlib plt backend: TkAgg
This kind of puzzles me, because I sort of expected TkAgg would be the default GUI backend for matplotlib on all platforms !?
So, I just wanted to know - is the default GUI backend for Matplotlib for different platforms documented anywhere?

The backend selection logic is not very transparent and not well documented.
In modern matplotlib there is no "default backend", i.e. the rcParams['backend'] is set to a "sentinel".
Upon importing matplotlib the first working backend from a candidate list ["macosx", "qt5agg", "qt4agg", "gtk3agg", "tkagg", "wxagg"] is chosen.
In order to avoid this automatic selection, you can set the backend manually via the rcParams['backend'] parameter or the MPLBACKEND environment variable. That part is documented

The default backend is defined in the mpl.rcParams['backend']. On Linux_x64 this is set to 'Qt5Agg'. The _get_running_interactive_framework function in the matplotlib.backends.__init__ checks for available backends. PyQt5 is highest in the priority list. The pyplot.switch_backend function uses _get_running_interactive_framework to select the effectively used backend on import. Search for the line switch_backend(rcParams["backend"]) here: https://matplotlib.org/3.1.1/_modules/matplotlib/pyplot.html
You could check whether PyQt5 is available on Rasbian and what the rcParams entry is.

Related

Matplotlib styles not being applied

I'm using Spyder v5 within Anaconda and having issues with any styles being applied on charts. Basic chart below (deliberately commented out the sns import to see if it makes any difference -it doesn't)
Basic code below - gives a normal plot as expected
import matplotlib.pyplot as plt
#import seaborn as sns
x_values = [0,1,2,3,4,5,6,7,8,9,10]
x_squared = [x ** 2 for x in x_values]
plt.plot(x_values,x_squared, label = "X-Squared")
plt.plot(x_values,x_cubed, label = "X-Cubed")
plt.show()
If i then try
plt.style.use("seaborn-deep")
plt.plot(x_values,x_squared, label = "X-Squared")
plt.plot(x_values,x_cubed, label = "X-Cubed")
plt.show()
Nothing changes? The style is avaialble (from plt.styles.available) and there is no error when applying the style so something is amiss here.
If i import seaborn then nothing changes
If i try any or all of the following from other solutions in various places in my plt code then nothing much changes (all of the below lines of code work with no errors
%matplotlib inline
plt.rcParams.update(plt.rcParamsDefault)
sns.set()
One time somehow this did seem to force it to change to a seaborn-paper style but that's then the only one i can use and i can't use any other seaborn or other styles at all?? Not sure what forced it to change, think it was sns.set() so I suspect the one it then shows is the default seaborn style, but then why won't it let me use any other styles?
As i'm using SPyder in anaconda the packages are installed to do this plot
I do have Python installed on my base desktop as well... but documentation insists this won't cause a problem and i've not had this problem on any other code ever of having another installation
any tips?

Edit curves lines and axes parameter option in Spyder [duplicate]

I'm using Python 2.6 and PyQt4. The matplotlib backend is set to "Qt4Agg".
The plot shows up, but the option to edit the curve parameters (the one that looks like a green ticked box) is not showing up.
Any ideas?
Edit:
Here is the checkbox that I am NOT seeing:
Sample code:
import matplotlib
matplotlib.use('Qt4Agg')
import matplotlib.pyplot as plt
matplotlib.rcParams['interactive'] = True
plt.ion()
x=[1,2,3]
plt.plot(x,x)
inp = input('Press enter to exit ')
Edit 2:
I've found a clue, but I still don't know what the problem is. I tried importing the NavigationToolbar by
from matplotlib.backends.backend_qt4 import NavigationToolbar2QT
and then accessed the documentation with
print(help(NavigationToolbar2QT))
On Windows where I am using the latest version of Pyzo, a method called "edit_parameters(self)" is present. When I do the same for Python 2.6 on the Linux machine, that method is missing altogether. What could be wrong?
Problem identified as an old version of matplotlib.

Edit curves lines and axes parameter option not showing in matplotlib

I'm using Python 2.6 and PyQt4. The matplotlib backend is set to "Qt4Agg".
The plot shows up, but the option to edit the curve parameters (the one that looks like a green ticked box) is not showing up.
Any ideas?
Edit:
Here is the checkbox that I am NOT seeing:
Sample code:
import matplotlib
matplotlib.use('Qt4Agg')
import matplotlib.pyplot as plt
matplotlib.rcParams['interactive'] = True
plt.ion()
x=[1,2,3]
plt.plot(x,x)
inp = input('Press enter to exit ')
Edit 2:
I've found a clue, but I still don't know what the problem is. I tried importing the NavigationToolbar by
from matplotlib.backends.backend_qt4 import NavigationToolbar2QT
and then accessed the documentation with
print(help(NavigationToolbar2QT))
On Windows where I am using the latest version of Pyzo, a method called "edit_parameters(self)" is present. When I do the same for Python 2.6 on the Linux machine, that method is missing altogether. What could be wrong?
Problem identified as an old version of matplotlib.

Resizing matplotlib figure with set_fig(width/height) doesn't work

For some reason this code creates a figure that is only the standard size: it doesn't change the height or width (I chose widths and heights that are ludicrous to clearly illustrate the problem):
import matplotlib.pyplot as plt
fig = plt.figure()
fig.set_figwidth(30)
fig.set_figheight(1)
print('Width: {}'.format(fig.get_figwidth()))
plt.show()
I'm running on OSX 10.10.4, Python 3.4.3, Matplotlib 1.4.3. (Installed via Macports.) Any ideas? What am I missing?
The optional parameter forward propagates changes to the canvas in a GUI window that already exists.
Documentation here:
optional kwarg forward=True will cause the canvas size to be automatically updated; e.g., you can resize the figure window from the shell
Using Figure(figsize=(w,h)) also works.
For Matplotlib 2.2.0 and newer
forward=True is the default for all three of set_figheight, set_figwidth, and set_size_inches (set_size_inches changes both height and width simultaneously).
For Matplotlib 1.5.0
forward=True must be specified explicitly as it is False by default. (In Matplotlib 2.0.0, the default is changed to True only for set_size_inches).
For Matplotlib 1.4.3 and older
forward is only supported by set_size_inches.
set_figheight and set_figwidth do not support this argument, so it is a bit difficult to only change a single dimension of a pre-created GUI.
I'm not certain why those documented functions don't work, but they have been fixed for the next matplotlib release (>v1.4.3). As a workaround until the next release, replacing set_figwidth and set_figheight solves this problem.
import matplotlib.pyplot as plt
fig = plt.figure()
# Instead of set_figwidth(30)
fig.set_size_inches(30, fig.get_figheight(), forward=True)
plt.show()

make matplotlib plotting window pop up as the active one

I'm working with python and matplotlib on mac os x.
When I'm working on many different windows and I have to run a script which produces a plot, the plot window always open behind the active window and is very frustration having to switch between windows for looking at the image.
Is it any why to decide the location of the plot window, and/or pop up it as foreground window?
thanks
For me (OSX 10.10.2, Matplotlib 1.4.3), what works is changing the matplotlib backend to TkAgg. Before importing pyplot or anything, go:
import matplotlib
matplotlib.use('TkAgg')
Plot windows now pop-up, and can be Command-Tab'ed to.
I was bothered by exactly the same problem. I found finally a solution (in pylab mode, with qt4agg backend):
get_current_fig_manager().window.raise_()
or
fig = gcf()
fig.canvas.manager.window.raise_()
Regards,
Markus
I found this solution was so often needed (e.g. when using Spyder IDE), I wrapped it into a function.
def show_plot(figure_id=None):
if figure_id is None:
fig = plt.gcf()
else:
# do this even if figure_id == 0
fig = plt.figure(num=figure_id)
plt.show()
plt.pause(1e-9)
fig.canvas.manager.window.activateWindow()
fig.canvas.manager.window.raise_()
I found a good answer on this thread:
How to make a Tkinter window jump to the front?
Basically, the idea is to use window attributes - set the '-topmost' attribute to True (1) to make the window come to the foreground, and then set it to False (0) so that it later allows other windows to appear in front of it. Here's code that worked for me:
import matplotlib.pyplot as plt
wm = plt.get_current_fig_manager()
wm.window.attributes('-topmost', 1)
wm.window.attributes('-topmost', 0)
For MacOS Sierra and python 3.6, Matplotlib 2.0.0
import matplotlib.pyplot as plt
plt.get_current_fig_manager().show()
the above line does the job no need of anything else.
This worked for me!!
(Tested on Mac OS X 10.11, Spyder 2.3.5.2 - Python 3.4)
Go to Preferences > IPython console > Graphics and set a backend to Qt (after that you need to restart the kernel).
Make a file that contains:
def raise_window(figname=None):
if figname: plt.figure(figname)
cfm = plt.get_current_fig_manager()
cfm.window.activateWindow()
cfm.window.raise_()
and import it at startup (Preferences > IPython console > Startup > Run a file). Now, just call function raise_window() below your code.
Example:
import numpy as np
import matplotlib.pyplot as plt
X = np.linspace(-np.pi, np.pi, 256)
C, S = np.cos(X), np.sin(X)
plt.figure()
plt.plot(X, C)
plt.plot(X, S)
raise_window()
For me only the following works (with TkAgg backend):
plt.gcf().canvas.get_tk_widget().focus_force()
As of matplotlib 1.5.1 on MacOSX 10.11.6, if you start an iPython (5.0.0, Python: 3.5.2) shell and use %matplotlib you can bring a matplotlib plot to the front using:
>>> %matplotlib
Using matplotlib backend: MacOSX
>>> import matplotlib.pyplot as plt
>>> plt.plot([1,3,2,4])
>>> plt.show()
** Edit: Advice seems to be not to use %pylab as it pollutes the global name space **
.. shell and use %pylab you can bring a matplotlib plot to the front using:
>>> %pylab
Using matplotlib backend: MacOSX
Populating the interactive namespace from numpy and matplotlib
>>> plot([1,3,2,4])
>>> show()
You can set
backend : MacOSX
in your matplotlibrc file for a permanent solution.
It works for me on macos mojave, with matplotlib 2.1.2. However, other users have complained that it does not work for them, so it might be affected by other settings
The following worked on Jupyter notebook with Qt5 backend on Windows. I tested it with Python 3.7, matplotlib 3.2.1.
%matplotlib qt5
import matplotlib.pyplot as plt
import numpy as np
from PyQt5 import QtCore
plt.plot(np.linspace(0,1))
window = plt.get_current_fig_manager().window
window.setWindowFlags(window.windowFlags() | QtCore.Qt.WindowStaysOnTopHint)
plt.show()
window.setWindowFlags(window.windowFlags() & ~QtCore.Qt.WindowStaysOnTopHint)
plt.show()

Categories

Resources