Hey, I noticed that QGIs is introducing slight errors when editing topology edge_data layer (with the regular edition, no pluggin ).
This is dangerous because function such a s ST_getFaceGeometry won't work afterward (in some case). SO here is a trigger designed to snap the modified edge_data onto the correct node (begin/end) (if within the "precision" set at the topology creation). Here is the code (one function, then the trigger using it). Cheers, Rémi-C PS : I'm going to put it online, but I can't now. -------------------- DROP FUNCTION IF EXISTS rc_CleanEdge_geom(toponame character varying, IN iedge_id integer, INOUT igeom GEOMETRY, IN tolerance FLOAT ); CREATE OR REPLACE FUNCTION public.rc_CleanEdge_geom(toponame character varying, IN iedge_id integer, INOUT igeom GEOMETRY, IN tolerance FLOAT DEFAULT 0.01 ) AS $BODY$ --@brief given a precision , for an edge in edge_data (we use the geom that is provided), snap the start/end point to node if it is within the correct distance DECLARE r record; q text; BEGIN --getting the end point q:= ' SELECT ed.edge_id, ed.start_node, ed.end_node, ed.geom , n1.geom AS start_node_geom, n2.geom AS end_node_geom , ST_StartPoint($2) AS start_point, ST_EndPoint($2) AS end_point ,ST_NPoints($2)-1 AS npoints FROM ' || quote_ident(toponame)||'.edge_data AS ed INNER JOIN ' || quote_ident(toponame)||'.node AS n1 ON (ed.start_node = n1.node_id) INNER JOIN ' || quote_ident(toponame)||'.node AS n2 ON (ed.end_node = n2.node_id) WHERE ed.edge_id = $1 ;'; EXECUTE q INTO r USING iedge_id, igeom; IF ST_DWithin(r.start_point ,r.start_node_geom , tolerance) THEN igeom:= ST_SetPoint(igeom, 0, r.start_node_geom); END IF; IF ST_DWithin( r.end_point ,r.end_node_geom , tolerance) THEN igeom:= ST_SetPoint(igeom, r.npoints, r.end_node_geom); END IF; RETURN ; END $BODY$ LANGUAGE plpgsql VOLATILE ; --------------- --correct topoloogy precision on edge_data trigger CREATE OR REPLACE FUNCTION rc_enforce_edge_precison_on_edge_data_geom_change( ) RETURNS trigger AS $BODY$ --this trigger is designed to update the result of street amp processing when edge_data is modified. --The directly impacted tables are result_arc, result_axis and result_intersection --the inderectly impacted tables are visualisation tables. --if the event is a deleting. Delete stuff accordingly and relaunch on previous geometry --if the eventis update or insert, juste update on modified geometry DECLARE BEGIN SELECT rc_CleanEdge_geom( TG_TABLE_SCHEMA::text , NEW.edge_id ,NEW.geom ,(SELECT precision FROM topology.topology WHERE name = TG_TABLE_SCHEMA::text) ) INTO NEW.geom FROM bdtopo_topological.edge_data WHERE edge_id = NEW.edge_id ; returN NEW; END ; $BODY$ LANGUAGE plpgsql VOLATILE; DROP TRIGGER IF EXISTS rc_enforce_edge_precison_on_edge_data_geom_change ON edge_data; CREATE TRIGGER rc_enforce_edge_precison_on_edge_data_geom_change BEFORE UPDATE ON edge_data FOR EACH ROW WHEN (ST_Equals(NEW.geom , OLD.geom)=FALSE) --only triggering that when change in geom EXECUTE PROCEDURE rc_enforce_edge_precison_on_edge_data_geom_change();
_______________________________________________ postgis-users mailing list postgis-users@lists.osgeo.org http://lists.osgeo.org/cgi-bin/mailman/listinfo/postgis-users