1# -*- coding: utf-8 -*-
2# This file is part of pygal
3#
4# A python svg graph plotting library
5# Copyright © 2012-2016 Kozea
6#
7# This library is free software: you can redistribute it and/or modify it under
8# the terms of the GNU Lesser General Public License as published by the Free
9# Software Foundation, either version 3 of the License, or (at your option) any
10# later version.
11#
12# This library is distributed in the hope that it will be useful, but WITHOUT
13# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14# FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more
15# details.
16#
17# You should have received a copy of the GNU Lesser General Public License
18# along with pygal. If not, see <http://www.gnu.org/licenses/>.
19
20"""Dual chart base. Dual means a chart with 2 scaled axis like xy"""
21
22from pygal._compat import is_str
23from pygal.graph.graph import Graph
24from pygal.util import compute_scale, cut
25
26
27class Dual(Graph):
28    _dual = True
29
30    def _value_format(self, value):
31        """
32        Format value for dual value display.
33        """
34        return '%s: %s' % (
35            self._x_format(value[0]),
36            self._y_format(value[1]))
37
38    def _compute_x_labels(self):
39        x_pos = compute_scale(
40            self._box.xmin, self._box.xmax, self.logarithmic,
41            self.order_min, self.min_scale, self.max_scale
42        )
43        if self.x_labels:
44            self._x_labels = []
45            for i, x_label in enumerate(self.x_labels):
46                if isinstance(x_label, dict):
47                    pos = self._x_adapt(x_label.get('value'))
48                    title = x_label.get('label', self._x_format(pos))
49                elif is_str(x_label):
50                    pos = self._x_adapt(x_pos[i % len(x_pos)])
51                    title = x_label
52                else:
53                    pos = self._x_adapt(x_label)
54                    title = self._x_format(pos)
55
56                self._x_labels.append((title, pos))
57            self._box.xmin = min(self._box.xmin, min(cut(self._x_labels, 1)))
58            self._box.xmax = max(self._box.xmax, max(cut(self._x_labels, 1)))
59
60        else:
61            self._x_labels = list(zip(map(self._x_format, x_pos), x_pos))
62
63    def _compute_x_labels_major(self):
64        # In case of dual, x labels must adapters and so majors too
65        self.x_labels_major = self.x_labels_major and list(
66            map(self._x_adapt, self.x_labels_major))
67        super(Dual, self)._compute_x_labels_major()
68
69    def _get_x_label(self, i):
70        """Convenience function to get the x_label of a value index"""
71        return
72