Commit 1716b937 authored by Yori Fournier's avatar Yori Fournier

Merge branch '106-ready-tomerge' into 'dev'

Resolve "FEATURE: add FormatterDictToLines in mpl_toolbox"

Closes #106

See merge request !79
parents e4ab4896 883e0840
Pipeline #732 canceled with stage
...@@ -22,6 +22,7 @@ from .formatter import Formatter ...@@ -22,6 +22,7 @@ from .formatter import Formatter
from .formatter import FormatterListToLine from .formatter import FormatterListToLine
from .formatter import FormatterArrayToLines from .formatter import FormatterArrayToLines
from .formatter import FormatterAppendToLines from .formatter import FormatterAppendToLines
from .formatter import FormatterDictToLines
from .mpl_weighted_grid import WeightedGrid from .mpl_weighted_grid import WeightedGrid
from .mpl_weighted_grid import VerticalWeightedGrid from .mpl_weighted_grid import VerticalWeightedGrid
......
...@@ -29,6 +29,10 @@ D_LEGEND_POS = None ...@@ -29,6 +29,10 @@ D_LEGEND_POS = None
# Class Ax2dPlots overwriting MyAxes # Class Ax2dPlots overwriting MyAxes
class Ax2dPlots(MplAxes): class Ax2dPlots(MplAxes):
def __init__(self, *args, **kwargs):
MplAxes.__init__(self, *args, **kwargs)
self.formatter = None
# DECLARE KEYWORDS -------------------------------------------------- # DECLARE KEYWORDS --------------------------------------------------
def declare_keywords(self): def declare_keywords(self):
...@@ -55,9 +59,11 @@ class Ax2dPlots(MplAxes): ...@@ -55,9 +59,11 @@ class Ax2dPlots(MplAxes):
# DEFAULT FORMAT RAWDAT ... to be overwritten ------------------------ # DEFAULT FORMAT RAWDAT ... to be overwritten ------------------------
def format_rawdata(self, rawdata): def format_rawdata(self, rawdata):
formatter = self.keywords.get('formatter', FormatterListToLine()) if self.formatter != self.keywords.get('formatter', None):
formatter.set_axes(self) self.formatter = self.keywords.get('formatter', FormatterListToLine())
self.data = formatter.shape(rawdata) self.formatter.set_axes(self)
self.data = self.formatter.shape(rawdata)
return(True) return(True)
...@@ -170,7 +176,7 @@ class Ax2dPlots(MplAxes): ...@@ -170,7 +176,7 @@ class Ax2dPlots(MplAxes):
elif legend_pos == 'bl': elif legend_pos == 'bl':
self.legend(bbox_to_anchor=(0.03, 0.03), loc=3, borderpad=0.5, prop={'size': 14}) self.legend(bbox_to_anchor=(0.03, 0.03), loc=3, borderpad=0.5, prop={'size': 14})
else: else:
print(WARN + "I could not understand the legen positioning (legend_pos) should be ['ur', 'ul', 'br', 'bl']. I set it to 'ul'") print(WARN + "I could not understand the legend positioning (legend_pos) should be ['ur', 'ul', 'br', 'bl']. I set it to 'ul'")
self.legend(bbox_to_anchor=(0.03, 0.97), loc=2, borderpad=0.5, prop={'size': 14}) self.legend(bbox_to_anchor=(0.03, 0.97), loc=2, borderpad=0.5, prop={'size': 14})
return(True) return(True)
...@@ -5,11 +5,15 @@ class Formatter(object): ...@@ -5,11 +5,15 @@ class Formatter(object):
def __init__(self): def __init__(self):
self.axes = None self.axes = None
def init(self):
pass
def shape(self, rawdata): def shape(self, rawdata):
pass pass
def set_axes(self, axes): def set_axes(self, axes):
self.axes = axes self.axes = axes
self.init()
class FormatterListToLine(Formatter): class FormatterListToLine(Formatter):
...@@ -23,13 +27,12 @@ class FormatterListToLine(Formatter): ...@@ -23,13 +27,12 @@ class FormatterListToLine(Formatter):
def shape(self, rawdata): def shape(self, rawdata):
ydata = rawdata ydata = rawdata
xdata = list(range(0, len(ydata))) xdata = range(0, len(ydata))
data = {'ydatas': [ydata], data = {'ydatas': [ydata],
'xdata': xdata, 'xdata': xdata,
'xlabel': self.xlabel, 'xlabel': self.xlabel,
'ylabel': self.ylabel, 'ylabel': self.ylabel}
}
return(data) return(data)
...@@ -50,19 +53,21 @@ class FormatterArrayToLines(Formatter): ...@@ -50,19 +53,21 @@ class FormatterArrayToLines(Formatter):
xdata = ydatas.pop(self.xdata_index) xdata = ydatas.pop(self.xdata_index)
else: else:
ydatas = rawdata ydatas = rawdata
xdata = list(range(0, len(ydatas[0]))) # generic xdata xdata = range(0, len(ydatas[0])) # generic xdata
data = {'ydatas': ydatas, data = {'ydatas': ydatas,
'xdata': xdata, 'xdata': xdata,
'xlabel': self.xlabel, 'xlabel': self.xlabel,
'ylabel': self.ylabel, 'ylabel': self.ylabel}
}
return(data) return(data)
class FormatterAppendToLines(Formatter): class FormatterAppendToLines(Formatter):
def __init__(self, xdata_index=None, xlabel=None, ylabel=None, with_label=False): def __init__(self, xdata_index=None, xlabel=None, ylabel=None, with_label=False):
Formatter.__init__(self)
self.xlabel = xlabel self.xlabel = xlabel
self.ylabel = ylabel self.ylabel = ylabel
self.xdata_index = xdata_index self.xdata_index = xdata_index
...@@ -98,16 +103,89 @@ class FormatterAppendToLines(Formatter): ...@@ -98,16 +103,89 @@ class FormatterAppendToLines(Formatter):
else: else:
labels = repeat(None) labels = repeat(None)
else: else:
xdata = list(range(0, len(ydatas[0]))) # generic xdata xdata = range(0, len(ydatas[0])) # generic xdata
data = {'ydatas': ydatas, data = {'ydatas': ydatas,
'xdata': xdata, 'xdata': xdata,
'xlabel': self.xlabel, 'xlabel': self.xlabel,
'ylabel': self.ylabel, 'ylabel': self.ylabel,
'labels': labels, 'labels': labels}
}
return(data) return(data)
class FormatterDictToLines(Formatter): class FormatterDictToLines(Formatter):
pass
def __init__(self, xvar=None, yvars=None, xlabel=None, ylabel=None, with_label=False):
Formatter.__init__(self)
self.xlabel = xlabel
self.ylabel = ylabel
self.with_label = with_label
self.xvar = xvar # key of xdata
self.yvars = yvars # keys of ydatas
def init(self): # called only when formatter is set to an axes
self.axes.keywords.update({'xvar': self.xvar})
self.axes.keywords.update({'yvars': self.yvars})
def shape(self, rawdata):
# Init
xdata = None
ydatas = []
tmp_labels = []
labels = []
# YDATAS
if self.axes.keywords['yvars'] is not None:
for var_name in self.axes.keywords['yvars']:
try:
# DATA AND LABEL
ydatas.append(rawdata[var_name])
tmp_labels.append(var_name)
except KeyError:
print(WARN + "The key {0} does not exist in the data. IGNORED.".format(var_name))
if ydatas == []:
print(SEVR + "There were no data corresponding to yvars in data.")
else:
print(SEVR + "The keyword yvars should not be None! Set it either in the Formatter constructor or modifiy the axes's keywords directly")
# XDATA
if self.axes.keywords['xvar'] is not None:
try:
# JUST DATA
xdata = rawdata[self.axes.keywords['xvar']]
except KeyError:
print(SEVR + "The requested xvar {0} does not exist in the data!".format(self.axes.keywords['xvar']))
else:
print(SEVR + "The keyword xvar should not be None! Set it either in the Formatter constructor or modifiy the axes's keywords directly")
if self.with_label:
if self.xlabel is None:
self.xlabel = self.axes.keywords['xvar']
labels = tmp_labels
data = {'ydatas': ydatas,
'xdata': xdata,
'xlabel': self.xlabel,
'ylabel': self.ylabel,
'labels': labels}
return(data)
...@@ -34,7 +34,7 @@ from .. import INFO, SEVR, WARN, SPCE ...@@ -34,7 +34,7 @@ from .. import INFO, SEVR, WARN, SPCE
from .. import ion, ioff, is_interactive from .. import ion, ioff, is_interactive
from .. import MyWin from .. import MplWin
from .. import np from .. import np
......
...@@ -21,7 +21,7 @@ class FormatterListToLineTestCase(unittest.TestCase): ...@@ -21,7 +21,7 @@ class FormatterListToLineTestCase(unittest.TestCase):
self.assertIsNone(formatter.ylabel) self.assertIsNone(formatter.ylabel)
correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.,]], correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.,]],
'xdata': [0., 1., 2., 3., 4., 5.,], 'xdata': range(0, 6),
'xlabel': None, 'xlabel': None,
'ylabel': None, 'ylabel': None,
} }
...@@ -36,7 +36,7 @@ class FormatterListToLineTestCase(unittest.TestCase): ...@@ -36,7 +36,7 @@ class FormatterListToLineTestCase(unittest.TestCase):
self.assertEqual(formatter.ylabel, r'y-axis') self.assertEqual(formatter.ylabel, r'y-axis')
correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.]], correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.]],
'xdata': [0., 1., 2., 3., 4., 5.], 'xdata': range(0, 6),
'xlabel': r'x-axis', 'xlabel': r'x-axis',
'ylabel': r'y-axis', 'ylabel': r'y-axis',
} }
...@@ -62,9 +62,9 @@ class FormatterArrayToLinesTestCase(unittest.TestCase): ...@@ -62,9 +62,9 @@ class FormatterArrayToLinesTestCase(unittest.TestCase):
correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.], correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.],
[0., 2., 4., 6., 8., 10.], [0., 2., 4., 6., 8., 10.],
[0., 3., 6., 9., 12., 15.]], [0., 3., 6., 9., 12., 15.]],
'xdata': [0., 1., 2., 3., 4., 5.], 'xdata': range(0, 6),
'xlabel': None, 'xlabel': None,
'ylabel': None, 'ylabel': None,
} }
self.assertEqual(data, correct_data) self.assertEqual(data, correct_data)
...@@ -117,7 +117,7 @@ class FormatterAppendToLinesTestCase(unittest.TestCase): ...@@ -117,7 +117,7 @@ class FormatterAppendToLinesTestCase(unittest.TestCase):
correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.,], correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.,],
[0., 2., 4., 6., 8., 10.], [0., 2., 4., 6., 8., 10.],
[0., 3., 6., 9., 12., 15.]], [0., 3., 6., 9., 12., 15.]],
'xdata': [0., 1., 2., 3., 4., 5.], 'xdata': range(0, 6),
'xlabel': None, 'xlabel': None,
'ylabel': None, 'ylabel': None,
'labels': [], 'labels': [],
...@@ -173,7 +173,7 @@ class FormatterAppendToLinesTestCase(unittest.TestCase): ...@@ -173,7 +173,7 @@ class FormatterAppendToLinesTestCase(unittest.TestCase):
correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.], correct_data = {'ydatas': [[0., 1., 2., 3., 4., 5.],
[0., 2., 4., 6., 8., 10.], [0., 2., 4., 6., 8., 10.],
[0., 3., 6., 9., 12., 15.]], [0., 3., 6., 9., 12., 15.]],
'xdata': [0., 1., 2., 3., 4., 5.], 'xdata': range(0, 6),
'xlabel': r'x-axis', 'xlabel': r'x-axis',
'ylabel': r'y-axis', 'ylabel': r'y-axis',
'labels': ['y0', 'y1', 'y2'], 'labels': ['y0', 'y1', 'y2'],
......
...@@ -8,6 +8,7 @@ from .tuto002 import script as sc002 ...@@ -8,6 +8,7 @@ from .tuto002 import script as sc002
from .tuto003 import script as sc003 from .tuto003 import script as sc003
from .tuto004 import script as sc004 from .tuto004 import script as sc004
from .tuto005 import script as sc005 from .tuto005 import script as sc005
from .tuto006 import script as sc006
class TutorialsTestCase(unittest.TestCase): class TutorialsTestCase(unittest.TestCase):
...@@ -89,7 +90,11 @@ class TutorialsTestCase(unittest.TestCase): ...@@ -89,7 +90,11 @@ class TutorialsTestCase(unittest.TestCase):
def test_tuto_005(self): def test_tuto_005(self):
fig = sc005() fig = sc005()
fig.plot() fig.plot()
def test_tuto_006(self):
fig = sc006()
fig.plot()
if __name__ == '__main__': if __name__ == '__main__':
unittest.main() unittest.main()
#!/usr/bin/env python
def script(with_print=False):
import sys
sys.path.append('../../')
from myplotlib.mpl_toolbox import Ax2dPlots, FormatterDictToLines
from myplotlib import EmptyFig, VerticalGrid, HorizontalGrid
# rawdata set
rawdata = {'time': [0.1, 0.3, 1.0, 3.0, 10., 30., 100., 300., 1000.],
'kinetic energy': [0.1, 0.2, 0.4, 0.6, 1.0, 0.9, 1.2, 1.3, 1.2],
'magnetic energy': [0.12, 0.22, 0.44, 0.65, 1.05, 0.96, 1.27, 1.34, 1.28],
'thermal energy': [0.1, 0.21, 0.41, 0.59, 1.01, 0.88, 1.17, 1.31, 1.22]}
# Create an empty figure
fig = EmptyFig(figsize=(8., 6.))
# Add a grid with margin and padding for the titles
vgrid = VerticalGrid(margin=0.17, padding=0.0)
fig.set_grid(vgrid)
# Create a formatter for the rawdata set (set the second list as x-axis)
formatter = FormatterDictToLines(xvar='time',
yvars=('kinetic energy',
'magnetic energy',
'thermal energy'),
with_label=True)
# Create 5 axes
ax1 = Ax2dPlots(fig, formatter=formatter, legend=True, legend_pos='br')
# Add the axes into the grid
vgrid.append_axes(ax1, 'ax1', rawdata)
# Layout the grid
fig.layout()
if with_print:
# save as file
fig.print_to_file('./tuto006.png')
return(fig)
if __name__ == '__main__':
script(True)
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment