Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit dbb34b1

Browse files
committed
Interactive setting of savefig rcParams (Qt only).
An additional window pops after selecting the filename to allow setting of savefig-related rcParams. For simplicity and consistency, the "ps.usedistiller" rcParam is now normalized to `None` when not set.
1 parent eb6e422 commit dbb34b1

File tree

3 files changed

+110
-19
lines changed

3 files changed

+110
-19
lines changed

lib/matplotlib/backends/backend_qt5.py

Lines changed: 102 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,8 @@
2525

2626
from .qt_compat import (QtCore, QtGui, QtWidgets, _getSaveFileName,
2727
__version__, is_pyqt5)
28-
from matplotlib.backends.qt_editor.formsubplottool import UiSubplotTool
28+
from .qt_editor import formlayout
29+
from .qt_editor.formsubplottool import UiSubplotTool
2930

3031
backend_version = __version__
3132

@@ -745,19 +746,19 @@ def save_figure(self, *args):
745746
startpath = matplotlib.rcParams.get('savefig.directory', '')
746747
startpath = os.path.expanduser(startpath)
747748
start = os.path.join(startpath, self.canvas.get_default_filename())
749+
748750
filters = []
749-
selectedFilter = None
751+
selected_filter = None
750752
for name, exts in sorted_filetypes:
751-
exts_list = " ".join(['*.%s' % ext for ext in exts])
752-
filter = '%s (%s)' % (name, exts_list)
753+
filters.append(
754+
'{} ({})'.format(name, ' '.join(map('*.{}'.format, exts))))
753755
if default_filetype in exts:
754-
selectedFilter = filter
755-
filters.append(filter)
756+
selected_filter = filters[-1]
756757
filters = ';;'.join(filters)
757758

758-
fname, filter = _getSaveFileName(self.parent,
759-
"Choose a filename to save to",
760-
start, filters, selectedFilter)
759+
fname, selected_filter = _getSaveFileName(
760+
self.parent, "Choose a filename to save to",
761+
start, filters, selected_filter)
761762
if fname:
762763
if startpath == '':
763764
# explicitly missing key or empty str signals to use cwd
@@ -766,6 +767,25 @@ def save_figure(self, *args):
766767
# save dir for next time
767768
savefig_dir = os.path.dirname(six.text_type(fname))
768769
matplotlib.rcParams['savefig.directory'] = savefig_dir
770+
options = _default_savefig_options
771+
try:
772+
options = (options
773+
+ [None]
774+
+ _extra_savefig_options[
775+
os.path.splitext(fname)[1].lower()])
776+
except KeyError:
777+
pass
778+
fedit_arg = []
779+
for option in options:
780+
if option is None:
781+
fedit_arg.append((None, None))
782+
else:
783+
fedit_arg.append(option.make_fedit_entry())
784+
fedit_res = formlayout.fedit(fedit_arg, "Options")
785+
if not fedit_res:
786+
return
787+
for option, res in zip(filter(None, options), fedit_res):
788+
option.setter(res)
769789
try:
770790
self.canvas.print_figure(six.text_type(fname))
771791
except Exception as e:
@@ -774,6 +794,79 @@ def save_figure(self, *args):
774794
QtWidgets.QMessageBox.Ok, QtWidgets.QMessageBox.NoButton)
775795

776796

797+
class _Option(object):
798+
799+
def __init__(self, name, rc_key=None, getter=None, setter=None):
800+
if rc_key and not (getter or setter):
801+
def make_fedit_entry():
802+
return (name, matplotlib.rcParams[rc_key])
803+
804+
def setter(val):
805+
matplotlib.rcParams[rc_key] = val
806+
807+
elif getter and setter and not rc_key:
808+
def make_fedit_entry():
809+
return (name, getter())
810+
811+
else:
812+
raise ValueError("Invalid entry")
813+
814+
self.name = name
815+
self.make_fedit_entry = make_fedit_entry
816+
self.setter = setter
817+
818+
819+
_default_savefig_options = [
820+
_Option("DPI", "savefig.dpi"),
821+
_Option("Face color", "savefig.facecolor"),
822+
_Option("Edge color", "savefig.edgecolor"),
823+
_Option("Tight bounding box",
824+
getter=lambda: matplotlib.rcParams["savefig.bbox"] == "tight",
825+
setter=lambda val: matplotlib.rcParams.__setitem__(
826+
"savefig.bbox", "tight" if val else "standard")),
827+
_Option("Tight bounding box padding", "savefig.pad_inches"),
828+
_Option("Transparent background", "savefig.transparent")]
829+
830+
831+
_extra_savefig_options = {
832+
".jpg": [
833+
_Option("JPEG quality", "savefig.jpeg_quality")],
834+
".jpeg": [
835+
_Option("JPEG quality", "savefig.jpeg_quality")],
836+
".pdf": [
837+
_Option("PDF compression", "pdf.compression"),
838+
_Option("PDF font type",
839+
getter=lambda:
840+
[str(matplotlib.rcParams["pdf.fonttype"]),
841+
"3", "42"],
842+
setter=lambda val:
843+
matplotlib.rcParams.__setitem__("pdf.fonttype", val))],
844+
".ps": [
845+
_Option("PS paper size",
846+
getter=lambda:
847+
[matplotlib.rcParams["ps.papersize"]]
848+
+ ["auto", "letter", "legal", "ledger"]
849+
+ ["A{}".format(i) for i in range(11)]
850+
+ ["B{}".format(i) for i in range(11)],
851+
setter=lambda val:
852+
matplotlib.rcParams.__setitem__("ps.papersize", val)),
853+
_Option("PS use AFM font", "ps.useafm"),
854+
_Option("PS distiller",
855+
getter=lambda:
856+
[str(matplotlib.rcParams["ps.usedistiller"])]
857+
+ ["None", "ghostscript", "xpdf"],
858+
setter=lambda val:
859+
matplotlib.rcParams.__setitem__("ps.usedistiller", val)),
860+
_Option("PS distiller resolution", "ps.distiller.res"),
861+
_Option("PS font type",
862+
getter=lambda:
863+
[str(matplotlib.rcParams["ps.fonttype"]),
864+
"3", "42"],
865+
setter=lambda val:
866+
matplotlib.rcParams.__setitem__("ps.fonttype", val))]
867+
}
868+
869+
777870
class SubplotToolQt(UiSubplotTool):
778871
def __init__(self, targetfig, parent):
779872
UiSubplotTool.__init__(self, None)

lib/matplotlib/rcsetup.py

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -519,10 +519,8 @@ def update_savefig_format(value):
519519
def validate_ps_distiller(s):
520520
if isinstance(s, six.string_types):
521521
s = s.lower()
522-
if s in ('none', None):
522+
if s in ('none', None, 'false', False):
523523
return None
524-
elif s in ('false', False):
525-
return False
526524
elif s in ('ghostscript', 'xpdf'):
527525
return s
528526
else:
@@ -1349,7 +1347,7 @@ def _validate_linestyle(ls):
13491347
'ps.papersize': ['letter', validate_ps_papersize],
13501348
'ps.useafm': [False, validate_bool], # Set PYTHONINSPECT
13511349
# use ghostscript or xpdf to distill ps output
1352-
'ps.usedistiller': [False, validate_ps_distiller],
1350+
'ps.usedistiller': [None, validate_ps_distiller],
13531351
'ps.distiller.res': [6000, validate_int], # dpi
13541352
'ps.fonttype': [3, validate_fonttype], # 3 (Type3) or 42 (Truetype)
13551353
# compression level from 0 to 9; 0 to disable

matplotlibrc.template

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -542,12 +542,12 @@ backend : $TEMPLATE_BACKEND
542542
# ps backend params
543543
#ps.papersize : letter # auto, letter, legal, ledger, A0-A10, B0-B10
544544
#ps.useafm : False # use of afm fonts, results in small files
545-
#ps.usedistiller : False # can be: None, ghostscript or xpdf
546-
# Experimental: may produce smaller files.
547-
# xpdf intended for production of publication quality files,
548-
# but requires ghostscript, xpdf and ps2eps
549-
#ps.distiller.res : 6000 # dpi
550-
#ps.fonttype : 3 # Output Type 3 (Type3) or Type 42 (TrueType)
545+
#ps.usedistiller : None # can be: None, ghostscript or xpdf
546+
# Experimental: may produce smaller files.
547+
# xpdf intended for production of publication quality files,
548+
# but requires ghostscript, xpdf and ps2eps
549+
#ps.distiller.res : 6000 # dpi
550+
#ps.fonttype : 3 # Output Type 3 (Type3) or Type 42 (TrueType)
551551

552552
# pdf backend params
553553
#pdf.compression : 6 # integer from 0 to 9

0 commit comments

Comments
 (0)