tammoippen / plotille

Plot in the terminal using braille dots.
MIT License
398 stars 17 forks source link

`Figure.axvline(x) coordinates are wrong` #45

Closed ntezak closed 2 years ago

ntezak commented 2 years ago

Figure.axvline(x, ...) requires 0 <= x <= 1, and it seems reasonable to assume that if the x_limits of the figure are x1, x2 the reference coordinate x is mapped to x1 + (x2 - x1) * x. In this setting x=0 corresponds to x1 and x=1 corresponds to x2.

In reality it seems that x=0 corresponds to the middle vertical (x1 + x2) / 2. So -1 would correspond to the left boundary, but negative reference coordinates are forbidden!

f = plotille.Figure()
f.width = 20
f.height = 20
f.set_x_limits(-1, 1)
f.axvline(0)  # would expect this to be at left boundary
print(f.show())
   (Y)     ^
         1 |
0.95000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.90000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.85000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.80000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.75000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.70000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.65000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.60000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.55000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.50000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.45000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.40000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.35000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.30000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.25000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.20000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.15000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.10000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
0.05000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
         0 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
-----------|-|---------|---------|-> (X)
           | -1        0         1

And likewise

In [90]: f = plotille.Figure()
    ...: f.width = 20
    ...: f.height = 20
    ...: f.set_x_limits(-2, 2)
    ...: f.axvline(0.5)  # would expect this to be in center
    ...: print(f.show())
   (Y)     ^
         1 |
0.95000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.90000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.85000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.80000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.75000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.70000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.65000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.60000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.55000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.50000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.45000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.40000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.35000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.30000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.25000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.20000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.15000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.10000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
0.05000000 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
         0 | ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡇⠀⠀⠀⠀
-----------|-|---------|---------|-> (X)
           | -2        0         2
ntezak commented 2 years ago

The following patch fixes the issue for me, but I am unsure if it breaks something else

diff --git a/plotille/_figure.py b/plotille/_figure.py
index 0fe4f9a..577194a 100644
--- a/plotille/_figure.py
+++ b/plotille/_figure.py
@@ -641,8 +641,6 @@ class Text:

 class Span:
     def __init__(self, xmin, xmax, ymin, ymax, lc):
-        assert 0 <= xmin <= xmax <= 1
-        assert 0 <= ymin <= ymax <= 1
         self._xmin = xmin
         self._xmax = xmax
         self._ymin = ymin
@@ -671,28 +669,16 @@ class Span:

     @classmethod
     def create(cls, xmin, xmax, ymin, ymax, lc=None):
-        if not (0 <= xmin <= xmax <= 1):
-            raise ValueError('xmin has to be <= xmax and both have to be within [0, 1].')
-        if not (0 <= ymin <= ymax <= 1):
-            raise ValueError('ymin has to be <= ymax and both have to be within [0, 1].')
-
         return cls(xmin, xmax, ymin, ymax, lc)

     def write(self, canvas, with_colors):
         color = self.lc if with_colors else None

-        # plot texts with color
-        xdelta = canvas.xmax_inside - canvas.xmin
-        assert xdelta > 0
-
-        ydelta = canvas.ymax_inside - canvas.ymin
-        assert ydelta > 0
-
         canvas.rect(
-            canvas.xmin + self.xmin * xdelta,
-            canvas.ymin + self.ymin * ydelta,
-            canvas.xmin + self.xmax * xdelta,
-            canvas.ymin + self.ymax * ydelta,
+            self.xmin,
+            self.ymin,
+            self.xmax,
+            self.ymax,
             color=color,
         )
tammoippen commented 2 years ago

Hi,

This is an issue with v3.8.0 . In master, the issue is already fixed, see this PR #42. It is just not published yet. Please have a try with master.

I added specific tests in 86ec904, which is part of #44 . When I finished that PR, I will publish a new version.