diff --git a/example/grid_example.py b/example/grid_example.py index 4afa3035..46e29dcc 100644 --- a/example/grid_example.py +++ b/example/grid_example.py @@ -141,7 +141,9 @@ def grid_mutil_yaxis() -> Grid: ) bar.overlap(line) - return Grid().add(bar, opts.GridOpts(pos_left="5%", pos_right="20%")) + return Grid().add( + bar, opts.GridOpts(pos_left="5%", pos_right="20%"), is_control_axis_index=True + ) Page().add(*[fn() for fn, _ in C.charts]).render() diff --git a/example/line_example.py b/example/line_example.py index f556c800..abdfad51 100644 --- a/example/line_example.py +++ b/example/line_example.py @@ -29,6 +29,45 @@ def line_smooth() -> Line: return c +@C.funcs +def line_areastyle() -> Line: + c = ( + Line() + .add_xaxis(Faker.choose()) + .add_yaxis( + "商家A", Faker.values(), areastyle_opts=opts.AreaStyleOpts(opacity=0.5) + ) + .add_yaxis( + "商家B", Faker.values(), areastyle_opts=opts.AreaStyleOpts(opacity=0.5) + ) + .set_global_opts(title_opts=opts.TitleOpts(title="Line-面积图")) + ) + return c + + +@C.funcs +def line_areastyle_boundary_gap() -> Line: + c = ( + Line() + .add_xaxis(Faker.choose()) + .add_yaxis("商家A", Faker.values(), is_smooth=True) + .add_yaxis("商家B", Faker.values(), is_smooth=True) + .set_series_opts( + areastyle_opts=opts.AreaStyleOpts(opacity=0.5), + label_opts=opts.LabelOpts(is_show=False), + ) + .set_global_opts( + title_opts=opts.TitleOpts(title="Line-面积图(紧贴 Y 轴)"), + xaxis_opts=opts.AxisOpts( + axistick_opts=opts.AxisTickOpts(is_align_with_label=True), + is_scale=False, + boundary_gap=False, + ), + ) + ) + return c + + @C.funcs def line_yaxis_log() -> Line: c = ( diff --git a/pyecharts/charts/composite_charts/grid.py b/pyecharts/charts/composite_charts/grid.py index 6d3119a7..a90f9f0e 100644 --- a/pyecharts/charts/composite_charts/grid.py +++ b/pyecharts/charts/composite_charts/grid.py @@ -23,7 +23,9 @@ class Grid(Base): self, chart: RectChart, grid_opts: Union[opts.GridOpts, dict], + *, grid_index: int = 0, + is_control_axis_index: bool = False, ): if self.options is None: self.options = copy.deepcopy(chart.options) @@ -31,8 +33,10 @@ class Grid(Base): self.options.update(grid=[], title=[]) if self.theme != ThemeType.WHITE: self.options.update(color=[]) - for s in self.options.get("series"): - s.update(xAxisIndex=self._axis_index, yAxisIndex=self._axis_index) + + if not is_control_axis_index: + for s in self.options.get("series"): + s.update(xAxisIndex=self._axis_index, yAxisIndex=self._axis_index) title = chart.options.get("title", opts.TitleOpts().opts) if isinstance(title, opts.TitleOpts): @@ -41,26 +45,29 @@ class Grid(Base): title = (title,) self.options.get("title").extend(title) - for s in chart.options.get("series"): - s.update(xAxisIndex=self._axis_index, yAxisIndex=self._axis_index) + if not is_control_axis_index: + for s in chart.options.get("series"): + s.update(xAxisIndex=self._axis_index, yAxisIndex=self._axis_index) for dep in chart.js_dependencies.items: self.js_dependencies.add(dep) - if grid_index == 0: - grid_index = self._grow_grid_index + if isinstance(chart, RectChart): + if grid_index == 0: + grid_index = self._grow_grid_index - for x in chart.options.get("xAxis"): - x.update(gridIndex=grid_index) - for y in chart.options.get("yAxis"): - y.update(gridIndex=grid_index) - self._grow_grid_index += 1 + for x in chart.options.get("xAxis"): + x.update(gridIndex=grid_index) + for y in chart.options.get("yAxis"): + y.update(gridIndex=grid_index) + self._grow_grid_index += 1 if self._axis_index > 0: self.options.get("series").extend(chart.options.get("series")) self.options.get("legend").extend(chart.options.get("legend")) - self.options.get("xAxis").extend(chart.options.get("xAxis")) - self.options.get("yAxis").extend(chart.options.get("yAxis")) + if isinstance(chart, RectChart): + self.options.get("xAxis").extend(chart.options.get("xAxis")) + self.options.get("yAxis").extend(chart.options.get("yAxis")) self.options.get("grid").append(grid_opts) self._axis_index += 1 diff --git a/test/test_display.py b/test/test_display.py new file mode 100644 index 00000000..fbe95e7b --- /dev/null +++ b/test/test_display.py @@ -0,0 +1,17 @@ +from nose.tools import eq_ + +from pyecharts.render.display import HTML, Javascript + + +def test_display_html(): + html_content = "
hello world
" + obj = HTML(html_content) + eq_(obj.data, html_content) + eq_(obj.__html__(), html_content) + + +def test_display_javascript(): + js_content = "console.log('hello world')" + obj = Javascript(js_content) + eq_(obj.data, js_content) + eq_(obj._repr_javascript_(), js_content) diff --git a/test/test_grid.py b/test/test_grid.py new file mode 100644 index 00000000..27f2e07e --- /dev/null +++ b/test/test_grid.py @@ -0,0 +1,71 @@ +from nose.tools import eq_ + +from pyecharts import options as opts +from pyecharts.charts import Bar, Grid, Line + + +def _chart_for_grid() -> Bar: + x_data = ["{}月".format(i) for i in range(1, 13)] + bar = ( + Bar() + .add_xaxis(x_data) + .add_yaxis( + "蒸发量", + [2.0, 4.9, 7.0, 23.2, 25.6, 76.7, 135.6, 162.2, 32.6, 20.0, 6.4, 3.3], + yaxis_index=0, + ) + .add_yaxis( + "降水量", + [2.6, 5.9, 9.0, 26.4, 28.7, 70.7, 175.6, 182.2, 48.7, 18.8, 6.0, 2.3], + yaxis_index=1, + ) + .extend_axis( + yaxis=opts.AxisOpts( + name="蒸发量", type_="value", min_=0, max_=250, position="right" + ) + ) + .extend_axis( + yaxis=opts.AxisOpts( + type_="value", name="温度", min_=0, max_=25, position="left" + ) + ) + .set_global_opts( + yaxis_opts=opts.AxisOpts( + name="降水量", min_=0, max_=250, position="right", offset=80 + ), + tooltip_opts=opts.TooltipOpts(trigger="axis", axis_pointer_type="cross"), + ) + ) + + line = ( + Line() + .add_xaxis(x_data) + .add_yaxis( + "平均温度", + [2.0, 2.2, 3.3, 4.5, 6.3, 10.2, 20.3, 23.4, 23.0, 16.5, 12.0, 6.2], + yaxis_index=2, + color="#675bba", + label_opts=opts.LabelOpts(is_show=False), + ) + ) + + bar.overlap(line) + return bar + + +def test_grid_control_axis_index(): + bar = _chart_for_grid() + gc = Grid().add( + bar, opts.GridOpts(pos_left="5%", pos_right="20%"), is_control_axis_index=True + ) + expected_idx = (0, 1, 2) + for idx, series in enumerate(gc.options.get("series")): + eq_(series.get("yAxisIndex"), expected_idx[idx]) + + +def test_grid_do_not_control_axis_index(): + bar = _chart_for_grid() + gc = Grid().add(bar, opts.GridOpts(pos_left="5%", pos_right="20%")) + expected_idx = (0, 0, 0) + for idx, series in enumerate(gc.options.get("series")): + eq_(series.get("yAxisIndex"), expected_idx[idx])