From af6dc684efa05f3eebd3d9a206566d4635c036c6 Mon Sep 17 00:00:00 2001 From: Brian Sperlongano Date: Thu, 21 Mar 2024 03:08:56 -0400 Subject: [PATCH] Reduce transportation_name segmentation (#1643) This PR reduces transportation_name layer fragmentation by ensuring the short brunnel segments are merged rather than dropped from view. --------- Co-authored-by: Tomas Pohanka --- .../update_transportation_merge.sql | 17 +++++ .../transportation_name.sql | 4 +- .../update_transportation_name.sql | 65 +++++++++++-------- 3 files changed, 57 insertions(+), 29 deletions(-) diff --git a/layers/transportation/update_transportation_merge.sql b/layers/transportation/update_transportation_merge.sql index 6d50e406..7ad9194d 100644 --- a/layers/transportation/update_transportation_merge.sql +++ b/layers/transportation/update_transportation_merge.sql @@ -42,6 +42,23 @@ SELECT $$ LANGUAGE SQL IMMUTABLE PARALLEL SAFE; +-- Determine whether a segment is long enough to have an attribute +CREATE OR REPLACE FUNCTION visible_text(g geometry, attr text, zoom_level integer) + RETURNS text AS +$$ +SELECT + CASE WHEN + -- Width of a tile in meters (111,842 is the length of one degree of latitude at the equator in meters) + -- 111,842 * 180 / 2^zoom_level + -- = 20131560 / POW(2, zoom_level) + -- Drop brunnel if length of way < 2% of tile width (less than 3 pixels) + ST_Length(g) * + COS(RADIANS(ST_Y(ST_Centroid(ST_Transform(g, 4326))))) * + POW(2, zoom_level) / 20131560 > 0.02 + THEN attr END +$$ LANGUAGE SQL IMMUTABLE + PARALLEL SAFE; + -- Instead of using relations to find out the road names we -- stitch together the touching ways with the same name -- to allow for nice label rendering diff --git a/layers/transportation_name/transportation_name.sql b/layers/transportation_name/transportation_name.sql index 798aa4da..2458df04 100644 --- a/layers/transportation_name/transportation_name.sql +++ b/layers/transportation_name/transportation_name.sql @@ -204,7 +204,7 @@ FROM ( indoor FROM osm_transportation_name_linestring WHERE zoom_level = 12 - AND LineLabel(zoom_level, COALESCE(tags->'name', ref), geometry) + AND LineLabel(zoom_level, COALESCE(ref, tags->'name'), geometry) AND NOT highway_is_link(highway) AND CASE WHEN highway_class(highway, NULL::text, NULL::text) NOT IN ('path', 'minor') THEN TRUE @@ -228,7 +228,7 @@ FROM ( indoor FROM osm_transportation_name_linestring WHERE zoom_level = 13 - AND LineLabel(zoom_level, COALESCE(tags->'name', ref), geometry) + AND LineLabel(zoom_level, COALESCE(ref, tags->'name'), geometry) AND CASE WHEN highway <> 'path' THEN TRUE WHEN highway = 'path' AND ( diff --git a/layers/transportation_name/update_transportation_name.sql b/layers/transportation_name/update_transportation_name.sql index 40375266..213051e1 100644 --- a/layers/transportation_name/update_transportation_name.sql +++ b/layers/transportation_name/update_transportation_name.sql @@ -426,17 +426,17 @@ BEGIN -- etldoc: osm_transportation_name_linestring -> osm_transportation_name_linestring_gen1 INSERT INTO osm_transportation_name_linestring_gen1 (id, geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order) + route_1, route_2, route_3, route_4, route_5, route_6) SELECT MIN(id) as id, ST_Simplify(ST_LineMerge(ST_Collect(geometry)), 50) AS geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order + route_1, route_2, route_3, route_4, route_5, route_6 FROM ( SELECT id, geometry, tags, ref, highway, subclass, - CASE WHEN ST_Length(geometry) > 8000 THEN brunnel ELSE '' END AS brunnel, - network, route_1, route_2, route_3, route_4, route_5, route_6, z_order + visible_text(geometry, brunnel, 9) AS brunnel, + network, route_1, route_2, route_3, route_4, route_5, route_6 FROM osm_transportation_name_linestring ) osm_transportation_name_linestring_gen1_pre_merge WHERE ( @@ -449,12 +449,12 @@ BEGIN ) AND ( (highway IN ('motorway', 'trunk') OR highway = 'construction' AND subclass IN ('motorway', 'trunk')) ) - GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6, z_order + GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6 ON CONFLICT (id) DO UPDATE SET geometry = excluded.geometry, tags = excluded.tags, ref = excluded.ref, highway = excluded.highway, subclass = excluded.subclass, brunnel = excluded.brunnel, network = excluded.network, route_1 = excluded.route_1, route_2 = excluded.route_2, route_3 = excluded.route_3, route_4 = excluded.route_4, - route_5 = excluded.route_5, route_6 = excluded.route_6, z_order = excluded.z_order; + route_5 = excluded.route_5, route_6 = excluded.route_6; -- Analyze source table ANALYZE osm_transportation_name_linestring_gen1; @@ -469,17 +469,17 @@ BEGIN -- etldoc: osm_transportation_name_linestring_gen1 -> osm_transportation_name_linestring_gen2 INSERT INTO osm_transportation_name_linestring_gen2 (id, geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order) + route_1, route_2, route_3, route_4, route_5, route_6) SELECT MIN(id) as id, ST_Simplify(ST_LineMerge(ST_Collect(geometry)), 120) AS geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order + route_1, route_2, route_3, route_4, route_5, route_6 FROM ( SELECT id, (ST_Dump(geometry)).geom AS geometry, tags, ref, highway, subclass, - CASE WHEN ST_Length(geometry) > 14000 THEN brunnel ELSE '' END AS brunnel, - network, route_1, route_2, route_3, route_4, route_5, route_6, z_order + visible_text(geometry, brunnel, 8) AS brunnel, + network, route_1, route_2, route_3, route_4, route_5, route_6 FROM osm_transportation_name_linestring_gen1 ) osm_transportation_name_linestring_gen2_pre_merge WHERE ( @@ -492,12 +492,12 @@ BEGIN ) AND ( (highway IN ('motorway', 'trunk') OR highway = 'construction' AND subclass IN ('motorway', 'trunk')) ) - GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6, z_order + GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6 ON CONFLICT (id) DO UPDATE SET geometry = excluded.geometry, tags = excluded.tags, ref = excluded.ref, highway = excluded.highway, subclass = excluded.subclass, brunnel = excluded.brunnel, network = excluded.network, route_1 = excluded.route_1, route_2 = excluded.route_2, route_3 = excluded.route_3, route_4 = excluded.route_4, - route_5 = excluded.route_5, route_6 = excluded.route_6, z_order = excluded.z_order; + route_5 = excluded.route_5, route_6 = excluded.route_6; -- Analyze source table ANALYZE osm_transportation_name_linestring_gen2; @@ -512,17 +512,17 @@ BEGIN -- etldoc: osm_transportation_name_linestring_gen2 -> osm_transportation_name_linestring_gen3 INSERT INTO osm_transportation_name_linestring_gen3 (id, geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order) + route_1, route_2, route_3, route_4, route_5, route_6) SELECT MIN(id) as id, ST_Simplify(ST_LineMerge(ST_Collect(geometry)), 200) AS geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order + route_1, route_2, route_3, route_4, route_5, route_6 FROM ( SELECT id, (ST_Dump(geometry)).geom AS geometry, tags, ref, highway, subclass, - CASE WHEN ST_Length(geometry) > 20000 THEN brunnel ELSE '' END AS brunnel, - network, route_1, route_2, route_3, route_4, route_5, route_6, z_order + visible_text(geometry, brunnel, 7) AS brunnel, + network, route_1, route_2, route_3, route_4, route_5, route_6 FROM osm_transportation_name_linestring_gen2 ) osm_transportation_name_linestring_gen3_pre_merge WHERE ( @@ -535,12 +535,12 @@ BEGIN ) AND ( (highway = 'motorway' OR highway = 'construction' AND subclass = 'motorway') ) - GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6, z_order + GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6 ON CONFLICT (id) DO UPDATE SET geometry = excluded.geometry, tags = excluded.tags, ref = excluded.ref, highway = excluded.highway, subclass = excluded.subclass, brunnel = excluded.brunnel, network = excluded.network, route_1 = excluded.route_1, route_2 = excluded.route_2, route_3 = excluded.route_3, route_4 = excluded.route_4, - route_5 = excluded.route_5, route_6 = excluded.route_6, z_order = excluded.z_order; + route_5 = excluded.route_5, route_6 = excluded.route_6; -- Analyze source table ANALYZE osm_transportation_name_linestring_gen3; @@ -555,25 +555,36 @@ BEGIN -- etldoc: osm_transportation_name_linestring_gen3 -> osm_transportation_name_linestring_gen4 INSERT INTO osm_transportation_name_linestring_gen4 (id, geometry, tags, ref, highway, subclass, brunnel, network, - route_1, route_2, route_3, route_4, route_5, route_6, z_order) - SELECT id, ST_Simplify(geometry, 500) AS geometry, tags, ref, highway, subclass, brunnel, network, route_1, route_2, - route_3, route_4, route_5, route_6, z_order - FROM osm_transportation_name_linestring_gen3 + route_1, route_2, route_3, route_4, route_5, route_6) + SELECT MIN(id) as id, + ST_Simplify(ST_LineMerge(ST_Collect(geometry)), 500) AS geometry, + tags, ref, highway, subclass, brunnel, network, + route_1, route_2, route_3, route_4, route_5, route_6 + FROM ( + SELECT id, + (ST_Dump(geometry)).geom AS geometry, + tags, ref, highway, subclass, + visible_text(geometry, brunnel, 6) AS brunnel, + network, route_1, route_2, route_3, route_4, route_5, route_6 + FROM osm_transportation_name_linestring_gen3 + ) osm_transportation_name_linestring_gen4_pre_merge WHERE ( full_update IS TRUE OR EXISTS ( SELECT NULL FROM transportation_name.name_changes_gen WHERE transportation_name.name_changes_gen.is_old IS FALSE AND - transportation_name.name_changes_gen.id = osm_transportation_name_linestring_gen3.id + transportation_name.name_changes_gen.id = osm_transportation_name_linestring_gen4_pre_merge.id ) ) AND ( - (highway = 'motorway' OR highway = 'construction' AND subclass = 'motorway') AND - ST_Length(geometry) > 20000 - ) ON CONFLICT (id) DO UPDATE SET geometry = excluded.geometry, tags = excluded.tags, ref = excluded.ref, + ST_Length(geometry) > 20000 AND + (highway = 'motorway' OR highway = 'construction' AND subclass = 'motorway') + ) + GROUP BY tags, ref, highway, subclass, brunnel, network, route_1, route_2, route_3, route_4, route_5, route_6 + ON CONFLICT (id) DO UPDATE SET geometry = excluded.geometry, tags = excluded.tags, ref = excluded.ref, highway = excluded.highway, subclass = excluded.subclass, brunnel = excluded.brunnel, network = excluded.network, route_1 = excluded.route_1, route_2 = excluded.route_2, route_3 = excluded.route_3, route_4 = excluded.route_4, - route_5 = excluded.route_5, route_6 = excluded.route_6, z_order = excluded.z_order; + route_5 = excluded.route_5, route_6 = excluded.route_6; -- noinspection SqlWithoutWhere DELETE FROM transportation_name.name_changes_gen;