Sandro Santilli wrote >> Except face 0, which is the "universe" face, all the others >> should be "gaps" in your topology. You can zoom to the face's >> bounding box ("mbr" field) to take a closer look (do you have qgis >> set up by now?). > > Ok. I had already looked at some of them but as face-derived geometries > (using ST_GetFaceGeometry) and not as real faces. As geometries, to me > they look like polygons and I didn't realize they were in fact holes. See > this example in QGIS for face_id 2418 turned into a polygon: > https://dl.dropboxusercontent.com/u/5196336/geomFromFace_id_2418.bmp. Now, > look at its mbr representation: > https://dl.dropboxusercontent.com/u/5196336/mbrFace_id_2418.bmp. How do > you tell it's a hole and not just a regular face? > >> What you could do programmatically is for each face to fetch the list >> of edges bounding it and pick the face on the other side as a candidate; >> then for each candidate face you find TopoGeometry objects containing >> it in their definition and pick one to assign that orphaned face >> (you could use smaller TopoGeometry, or larger, or whatever). > > Let's try this or face_id 2418 (which is, btw, a meaningful unit and not > an error...): / > SELECT f.face_id, e.edge_id, e.left_face, e.right_face > FROM de_20k_topo.face f JOIN > de_20k_topo.edge_data e ON (f.face_id = e.left_face OR > f.face_id = e.right_face) > WHERE face_id = 2418; / > * > face_id, edge_id, left_face, right_face * > 2418;2663;2418;950 > 2418;6986;2418;340 > 2418;2672;2418;951 > 2418;2665;2418;344 > 2418;6989;2418;2417 > > I pick the first edge (2663) and take it's right_face, 950, as a > candidate: / > SELECT topogeo_id > FROM de_20k_topo.relation > WHERE element_id = 950; / > * > topogeo_id * > 814 > > Only TopoGeom 814 has face_id 950 as one of its elements. Will assign > face_id 2418 > to this TopoGeom: / > INSERT INTO de_20k_topo.relation > VALUES (814, 1, 2418, 3); / > > Then what? Is that it? Does that mean that that big hole 2418 is now > unioned with face_id 950 (in which case it isn't what I want as it's a > meaningful ecological unit)? > > >> It might be better first to deal with the faces that are associated >> with multiple TopoGeometry, just to avoid assigning an orphaned face >> to a TopoGeometry based on it's containing a face which will later >> be removed from the definition because duplicated. > > Good point. > >> Eh, that part is a still a bit weak in documantation, maybe. >> A TopoGeometry is a Geometry defined by its components. > >> In your case (areal TopoGeometry objects) it is a (multi)Polygon >> defined by a set of faces. Note that QGIS is also able to >> show you the TopoGeometry objects, and lets you edit them "spatially" >> (less robust than editing them by adding/removing components but with >> some care easier to use). > >>> In this case, the light grey line is where a single edge should be. Blue >>> edges 6381 >>> and 6341 should not be there. The light grey line should start from the >>> node >>> at the bottom right and connect at its other end somewhere in the middle >>> of >>> edge 6340: > >> Uhm, edge identifiers are missing from that dump. >> I take it 6381 is the lower blue and 6341 the upper blue. > > You're correct here. > >> I suggest you load the TopoGeometry layer with qgis and see for yourself. > > When you say load the TopoGeometry layer, I assume you mean the topogeom > column I populated with: / > UPDATE syshiera.de_20k SET topogeom = toTopoGeom(geom_32198, > 'de_20k_topo', 1, 2.0) / > > Right? > > When I load it in QGIS using the PostGIS table loader, I can visualize it > and see there are holes. E.g. > https://dl.dropboxusercontent.com/u/5196336/holeInTopogeometry.bmp > >> Unfortunately (that'd be useful to add in qgis) it won't be easy to >> find TopoGeometry 1546 as extracting the id of a TopoGeometry requires >> running an expression on the database: id(topogeom). > > I can either / > SELECT * > FROM syshiera.de_20k > WHERE id(topogeom) = 1546; / > > or, as I mentioned before, I can superimpose my 'faces' layer, which I > derived from de_20k_topo.face > using ST_GetFaceGeometry, to 'topogeom' to get the topogeo_id. No? > >> You could create a view selecting just that topoGeometry, or a subset >> of them, or you could just load them all, hoping it won't be too >> expensive >> (another spot where qgis support for postgis topology could be improved). > > I agree, just loading the TopoViewer freezes QGIS for a while and I don't > lack ressources on my machine. > >> Chances are it would be enough to assign face 2227 to the TopoGeometry >> with id 1546 (likely the one not-assigned). But as face 2227 was not >> in your initial set (unassigned faces) I guess there's another >> TopoGeometry >> which does have 2227 in his definition, but not the one on the right. >> In that case you have to pick which of the two contending TopoGeometry >> objects should get face 2227 assigned, before you drop it. Basically, >> which >> TopoGeometry will get assigned the space occupied by that face. > > TopoGeometry 1551 has 2227. More explanation about this in my previous > post and below > >> Given QGIS editing support for TopoGeometry objects you should be able >> to see all of this by loading the layer and setting 50% transparency. >> Enabling topological editing and editing those two TopoGeometry objects >> should help you with manual resolution of this issue. > > Will try this, thanks > >>> Edge 2227 is missing from TopoGeom 1546: Where is it? > >> You meant _face_ 2227. >> Right, it's not assigned to TopoGeometry 1546, >> but to another one. > > That's what I meant yes. > >>> So edges 2225 and 2227 are associated with TopoGeom 1551. Will change >>> that: > >> Again, you mean faces (last number is element_type, 3==face). >> So TopoGeometry objects 1546 and 1551 overlap, and their intersection >> is the union of faces 2225 and 2227. > >>> UPDATE de_20k_topo.relation SET topogeo_id = 1546 >>> WHERE topogeo_id = 1551 AND element_id = 2227; > >> There's already a record associating face 2227 with TopoGeometry 1546 >> so you don't need another record, just drop the one associating it >> with TopoGeometry 1551: > > Ok, now I see where you're going.. > >> DELETE FROM de_20k_topo.relation >> WHERE topogeo_id = 1551 AND element_id = 2227; > >>> And then again: >>> >>> /SELECT ST_RemEdgeModFace('de_20k_topo', 6346); / >>> >>> ERROR: TopoGeom 1551 in layer 1 (syshiera.de_20k.topogeom) cannot be >>> represented healing faces 2225 and 2227 > >> Right, you only resolved the overlap of face 2227, but there's still >> the overlap of face 2225 :) > >> DELETE FROM de_20k_topo.relation >> WHERE topogeo_id = 1551 AND element_id = 2225; > > Now it's clearer in my head what I need to do, thanks to you! > >> It looks like you're on the right track so far. > > Will keep trying and I will win. Again, thanks so much for your help.
-- View this message in context: http://postgis.17.x6.nabble.com/Topology-cannot-delete-slivers-or-gaps-tp5007250p5007278.html Sent from the PostGIS - User mailing list archive at Nabble.com. _______________________________________________ postgis-users mailing list postgis-users@lists.osgeo.org http://lists.osgeo.org/cgi-bin/mailman/listinfo/postgis-users