Repository: fabanc/pyvoronoi (language: python)

Issue:
Bug. Vertex Positions are not corretly rounded.

Bug: Position is not rounded but truncated when added to Points. This leads to deviation of positions, when floating errors occur.


Discussion / hints:
Thank you @jnthnw! I will try to reproduce and fix. I am letting C++ handle the conversion automatically. Have you noticed the issue for:

- Points passed to the pyvoronoi API?
- Point created as part of the Voronoi diagram output?
- Both?

Fix patch:
diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml
index a36debc..0ce29b4 100644
--- a/.github/workflows/build.yml
+++ b/.github/workflows/build.yml
@@ -15,11 +15,8 @@ jobs:
             matrix:
                 os: [
                   ubuntu-22.04,
-                  # ubuntu-20.04, 
                   windows-2022, 
-                  # windows-2019,
-                  macos-13,
-                  macos-14
+                  macos-13
                 ]
     
         steps:
@@ -32,11 +29,12 @@ jobs:
 
             # Calling cibuildwheel. Most of the options are the default, but explicit is better than implicit.
             - name: Build wheels
-              uses: pypa/cibuildwheel@v2.19.1
+              uses: pypa/cibuildwheel@v2.21.3
               env:
                 CIBW_BEFORE_BUILD: python -m pip install Cython
                 CIBW_BUILD_VERBOSITY: 3
                 CIBW_DEBUG_TRACEBACK: TRUE
+                CIBW_SKIP: "pp3*"
               with:
                 package-dir: .
                 output-dir: dist
diff --git a/pyvoronoi/pyvoronoi.pyx b/pyvoronoi/pyvoronoi.pyx
index bb5373b..894df89 100644
--- a/pyvoronoi/pyvoronoi.pyx
+++ b/pyvoronoi/pyvoronoi.pyx
@@ -513,7 +513,7 @@ cdef class Pyvoronoi:
         return Point(self._to_voronoi_int(py_point[0]), self._to_voronoi_int(py_point[1]))
 
     cdef int _to_voronoi_int(self, val):
-        return val * self.SCALING_FACTOR
+        return round(val * self.SCALING_FACTOR)
 
     cdef double _to_voronoi_double(self, val):
         return val * <double>self.SCALING_FACTOR
diff --git a/setup.py b/setup.py
index b0d66ca..d356fb1 100644
--- a/setup.py
+++ b/setup.py
@@ -2,10 +2,9 @@
 import os
 from setuptools import setup
 from setuptools.extension import Extension
-from setuptools.command.test import test as TestCommand
 from pathlib import Path
 
-version = '1.1.4'
+version = '1.1.5'
 
 """
 Note on using the setup.py:
@@ -42,28 +41,6 @@
                 )
 
 
-# This command has been borrowed from
-# http://pytest.org/latest/goodpractises.html
-class PyTest(TestCommand):
-    user_options = [('pytest-args=', 'a', "Arguments to pass to py.test")]
-
-    def initialize_options(self):
-        TestCommand.initialize_options(self)
-        self.pytest_args = []
-
-    def finalize_options(self):
-        TestCommand.finalize_options(self)
-        self.test_args = []
-        self.test_suite = True
-
-    def run_tests(self):
-        # import here, cause outside the eggs aren't loaded
-        import pytest
-
-        errno = pytest.main(self.pytest_args)
-        sys.exit(errno)
-
-
 # This command has been borrowed from
 # http://www.pydanny.com/python-dot-py-tricks.html
 
@@ -117,10 +94,7 @@ def build_extensions(self):
         "Topic :: Software Development :: Libraries :: Python Modules"
     ],
     ext_modules=[ext],
-    tests_require=['pytest'],
     cmdclass={
-        'test': PyTest,
         'build_ext': build_ext_subclass
-    },
-        
+    },   
 )


Test patch:
diff --git a/tests/test_pyvoronoi.py b/tests/test_pyvoronoi.py
index dd24776..27083fa 100644
--- a/tests/test_pyvoronoi.py
+++ b/tests/test_pyvoronoi.py
@@ -52,6 +52,19 @@ def test_add_point_after_construct(self):
         pv.Construct()
         self.assertRaises(pyvoronoi.VoronoiException, pv.AddPoint, [0, 0])
 
+    def test_add_segment_rounding(self):
+        factor = 10
+        segment = [[0.59, 1.09], [0, 2]]
+        pv = pyvoronoi.Pyvoronoi(factor)
+        pv.AddSegment(segment)
+        segments = pv.GetSegments()
+        print(segments)
+        self.assertTrue(len(segments) == 1)
+        self.assertTrue(segments[0] == [
+            [round(segment[0][0] * factor), round(segment[0][1] * factor)],
+            [segment[1][0] * factor, segment[1][1] * factor],
+        ])
+
 class TestPyvoronoiConstruct(TestCase):
     def test_square(self):
         pv = pyvoronoi.Pyvoronoi(1)