2

I am trying to use the spatialite ST_VoronojDiagram function on a table containing four 4 points that are almost aligned: (1.01 2.02, 2.02 3.03, 10.01 10.02, 11.01 11.02). I wrote the following script in Python:

import sqlite3

#connexion to databse
conn = sqlite3.connect("D:\\my_path\\test.sqlite")
conn.enable_load_extension(True)
conn.execute("SELECT load_extension('mod_spatialite')")
cur = conn.cursor()
conn.text_factory = str


#creating points table
cur.execute("CREATE TABLE test_geom (id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT)")
cur.execute("SELECT AddGeometryColumn('test_geom', 'geometry', 4326, 'POINT', 'XY')")
conn.commit()


#inserting points
cur.execute("INSERT INTO test_geom VALUES (NULL, ST_GeomFromText('POINT(1.01 2.02)'))")
cur.execute("INSERT INTO test_geom VALUES (NULL, ST_GeomFromText('POINT(2.02 3.03)'))")
cur.execute("INSERT INTO test_geom VALUES (NULL, ST_GeomFromText ('POINT(10.01 10.02)'))")
cur.execute("INSERT INTO test_geom VALUES (NULL, ST_GeomFromText('POINT(11.01 11.02)'))")
conn.commit()


#creating voronoi polygons table
cur.execute("""DROP TABLE IF EXISTS 'test_vor'""")
cur.execute("""CREATE TABLE test_vor (id INTEGER NOT NULL PRIMARY KEY)""")
cur.execute("""SELECT AddGeometryColumn('test_vor', 'geometry', 4326, 'MULTIPOLYGON', 'XY')""")
conn.commit()


#inserting polygons
cur.execute("""
    INSERT INTO test_vor
    SELECT NULL, CastToMultiPolygon(ST_VoronojDiagram(ST_Collect(geometry),0,0.5))
    FROM test_geom
    """)
conn.commit()


#getting voronoi polygons geometry as text
cur.execute("""SELECT AsText(CastToMultiPolygon(ST_VoronojDiagram(ST_Collect(geometry))))FROM test_geom""")
conn.commit()
diag = cur.fetchall()
print diag

I get [(None,)] as a result.

When I add a random fifth point (18 -4):

cur.execute("INSERT INTO test_geom VALUES (NULL, ST_GeomFromText('POINT(18 -4)'))")

I get this (which is the form of result I want with the four first points):

[('MULTIPOLYGON(((8.334226 -4.294226, 10.725264 1.140878, 16.562488 4.467512, 21 .932716 6.966707, 21.932716 -8.226943, 6.940762 -8.226943, 8.334226 -4.294226)), ((10.725264 1.140878, 8.334226 -4.294226, -57.262816 61.302816, -57.262816 78.2 92816, -56.825362 78.292816, -53.3301 74.3601, 10.725264 1.140878)), ((8.334226 -4.294226, 6.940762 -8.226943, -57.262816 -8.226943, -57.262816 61.302816, 8.334 226 -4.294226)), ((16.562488 4.467512, 10.725264 1.140878, -53.3301 74.3601, 16. 562488 4.467512)), ((16.562488 4.467512, -53.3301 74.3601, -56.825362 78.292816, 21.932716 78.292816, 21.932716 6.966707, 16.562488 4.467512)))',)]

I tried creating the Voronoi polygons in QGIS using the toolbox and I get this: voronoi left: first 4 points; right: 5 points

blue: created with QGIS toolbox Voronoi polygons; purple: created with my python script

QGIS manages to create those polygons even for almost aligned points, so there must be a way to do it with a python script.

Is there any option/configuration/function that I'm missing?

  • There may be a bug in Spatialite. You can use this SQL for testing directly with spatialite-gui select voronojdiagram(st_geomfromtext('MULTIPOINT (( 1.01 2.02 ), ( 2.02 3.03 ), ( 10.01 10.02 ), ( 11.01 11.02 ),POINT(18 -4))'),1,100,0.01) I used the extra parameters for edges_only, frame_extra_size, and tolerance but without luck. – user30184 Apr 26 '16 at 10:38
  • @user30184 Too bad... Would it by any chance work better with PostGIS? – EliseB Apr 26 '16 at 10:55
  • Seems to require PostGIS 2.3.0 postgis.net/docs/manual-dev/ST_Voronoi.html. I don't have such high version and could not test. The SQL to use for testing is probably select st_voronoj( st_geomfromtext('MULTIPOINT (( 1.01 2.02 ), ( 2.02 3.03 ), ( 10.01 10.02 ), ( 11.01 11.02 ))')). And I had typo in my Spatialite SQL but I did test with correct one select voronojdiagram(st_geomfromtext('MULTIPOINT (( 1.01 2.02 ), ( 2.02 3.03 ), ( 10.01 10.02 ), ( 11.01 11.02 ))'),1,100,0.01) yields NULL. – user30184 Apr 26 '16 at 13:19

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.