Merge pull request #60 from openmaptiles/feature/transportation

Implementation of Transport Layer
pull/89/head
Lukas Martinelli 2016-12-01 11:02:13 +01:00 zatwierdzone przez GitHub
commit 9d37d1f4ba
20 zmienionych plików z 685 dodań i 537 usunięć

Wyświetl plik

@ -1,85 +0,0 @@
CREATE OR REPLACE FUNCTION highway_is_link(highway TEXT) RETURNS BOOLEAN AS $$
SELECT highway LIKE '%_link';
$$ LANGUAGE SQL IMMUTABLE STRICT;
-- etldoc: layer_highway[shape=record fillcolor=lightpink, style="rounded,filled",
-- etldoc: label="<sql> layer_highway |<z4z7> z4-z7 |<z8> z8 |<z9> z9 |<z10> z10 |<z11> z11 |<z12> z12|<z13> z13|<z14_> z14_" ] ;
CREATE OR REPLACE FUNCTION layer_highway(bbox geometry, zoom_level int)
RETURNS TABLE(osm_id bigint, geometry geometry, class highway_class, subclass text, properties highway_properties) AS $$
SELECT
osm_id, geometry,
to_highway_class(highway) AS class, highway AS subclass,
to_highway_properties(is_bridge, is_tunnel, is_ford, is_ramp, is_oneway) AS properties
FROM (
-- etldoc: ne_10m_global_roads -> layer_highway:z4z7
SELECT
NULL::bigint AS osm_id, geometry, highway,
FALSE AS is_bridge, FALSE AS is_tunnel, FALSE AS is_ford, FALSE AS is_ramp, FALSE AS is_oneway,
0 AS z_order
FROM ne_10m_global_roads
WHERE zoom_level BETWEEN 4 AND 7 AND scalerank <= 1 + zoom_level
UNION ALL
-- etldoc: osm_highway_linestring_gen4 -> layer_highway:z8
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring_gen4
WHERE zoom_level = 8
UNION ALL
-- etldoc: osm_highway_linestring_gen3 -> layer_highway:z9
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring_gen3
WHERE zoom_level = 9
UNION ALL
-- etldoc: osm_highway_linestring_gen2 -> layer_highway:z10
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring_gen2
WHERE zoom_level = 10
UNION ALL
-- etldoc: osm_highway_linestring_gen1 -> layer_highway:z11
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring_gen1
WHERE zoom_level = 11
UNION ALL
-- etldoc: osm_highway_linestring -> layer_highway:z12
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring
WHERE zoom_level = 12
AND (to_highway_class(highway) < 'minor_road'::highway_class OR highway IN ('unclassified', 'residential'))
AND NOT highway_is_link(highway)
AND NOT is_area
UNION ALL
-- etldoc: osm_highway_linestring -> layer_highway:z13
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring
WHERE zoom_level = 13
AND to_highway_class(highway) < 'path'::highway_class
AND NOT is_area
UNION ALL
-- etldoc: osm_highway_linestring -> layer_highway:z14_
SELECT osm_id, geometry, highway, is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring
WHERE zoom_level >= 14 AND NOT is_area
UNION ALL
-- NOTE: We limit the selection of polys because we need to be careful to net get false positives here because
-- it is possible that closed linestrings appear both as highway linestrings and as polygon
-- etldoc: osm_highway_polygon -> layer_highway:z13
-- etldoc: osm_highway_polygon -> layer_highway:z14_
SELECT osm_id, geometry, highway, FALSE AS is_bridge, FALSE AS is_tunnel, FALSE AS is_ford, FALSE AS is_ramp, FALSE AS is_oneway, z_order
FROM osm_highway_polygon
-- We do not want underground pedestrian areas for now
WHERE zoom_level >= 13 AND is_area AND COALESCE(layer, 0) >= 0
) AS zoom_levels
WHERE geometry && bbox
ORDER BY z_order ASC;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -1,39 +0,0 @@
layer:
id: "highway"
description: |
Roads or [`highway`](http://wiki.openstreetmap.org/wiki/Key:highway) in OpenStreetMap lingo.
This layer is directly derived from the OSM road hierarchy which is why it is called `highway`. Only
at zoom level 4 to 7 some major highways from Natural Earth are used otherwise it is only OSM data.
It contains all roads from motorways to primary, secondary and tertiary roads to residential roads and
foot paths. Styling the roads is the most essential part of the map. If you can put enough effort into it
makes sense to carefully style each `subclass`. For more comfortable styling you can also just style the roads
by `class`. Roads can have different properties, a road can have `oneway=yes` and `bridge=yes` at the same time.
These properties are reflected in the field `properties`.
This layer is not meant for labelling the roads (the purpose of the layer `highway_name`).
The `highway` layer also contains polygons for things like plazas.
buffer_size: 4
srs: +proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over
fields:
class: |
Either `motorway`, `major_road` (containing `trunk`, `primary`, `secondary` and `tertiary` roads) and `minor_road` (less important roads in the hierarchy like `residential` or `service`) or `path` for
non vehicle paths (such as `cycleway` or `footpath`).
subclass: |
Original value of the [`highway`](http://wiki.openstreetmap.org/wiki/Key:highway) tag. Use this to do more
precise styling.
properties: |
Additional properties describing the nature of road.
The properties `bridge` and `tunnel` can be combined with `oneway` as well. So to style all bridges the same you
should style both the properties `bridge` and `bridge:oneway`.
Properties can be one of `bridge:oneway`, `tunnel:oneway`, `ramp`, `ford`, `bridge`, `tunnel` or`oneway`.
datasource:
geometry_field: geometry
srid: 900913
query: (SELECT geometry, class::text, subclass, properties::text FROM layer_highway(!bbox!, z(!scale_denominator!))) AS t
schema:
- ./types.sql
- ./ne_global_roads.sql
- ./highway.sql
datasources:
- type: imposm3
mapping_file: ./mapping.yaml

Wyświetl plik

@ -1,121 +0,0 @@
generalized_tables:
# etldoc: imposm3 -> osm_highway_linestring_gen4
highway_linestring_gen4:
source: highway_linestring_gen3
sql_filter: highway IN ('motorway','trunk') AND NOT is_area
tolerance: 200.0
# etldoc: imposm3 -> osm_highway_linestring_gen3
highway_linestring_gen3:
source: highway_linestring_gen2
sql_filter: highway IN ('motorway','trunk', 'primary') AND NOT is_area
tolerance: 120.0
# etldoc: imposm3 -> osm_highway_linestring_gen2
highway_linestring_gen2:
source: highway_linestring_gen1
sql_filter: highway IN ('motorway','trunk', 'primary', 'secondary') AND NOT is_area
tolerance: 50.0
# etldoc: imposm3 -> osm_highway_linestring_gen1
highway_linestring_gen1:
source: highway_linestring
sql_filter: highway IN ('motorway','trunk', 'primary', 'secondary', 'tertiary') AND NOT is_area
tolerance: 20.0
tables:
# etldoc: imposm3 -> osm_highway_linestring
highway_linestring:
type: linestring
fields:
- name: osm_id
type: id
- name: geometry
type: geometry
- name: highway
key: highway
type: string
- key: ref
name: ref
type: string
- name: z_order
type: wayzorder
- name: layer
key: layer
type: integer
- key: tunnel
name: is_tunnel
type: bool
- key: bridge
name: is_bridge
type: bool
- key: ramp
name: is_ramp
type: bool
- key: ford
name: is_ford
type: bool
- key: oneway
name: is_oneway
type: bool
- key: name
name: name
type: string
- name: name_en
key: name:en
type: string
- name: is_area
key: area
type: bool
mapping:
highway:
- motorway
- motorway_link
- trunk
- trunk_link
- primary
- primary_link
- secondary
- secondary_link
- tertiary
- tertiary_link
- unclassified
- residential
- road
- living_street
- raceway
- construction
- track
- service
- path
- cycleway
- bridleway
- footway
- corridor
- crossing
- pedestrian
# etldoc: imposm3 -> osm_highway_polygon
highway_polygon:
type: polygon
fields:
- name: osm_id
type: id
- name: geometry
type: geometry
- name: highway
key: highway
type: string
- name: z_order
type: wayzorder
- name: layer
key: layer
type: integer
- name: is_area
key: area
type: bool
mapping:
highway:
- pedestrian

Wyświetl plik

@ -1,44 +0,0 @@
DO $$
BEGIN
IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'highway_class') THEN
CREATE TYPE highway_class AS ENUM ('motorway', 'major_road', 'minor_road', 'path');
END IF;
END
$$;
DO $$
BEGIN
IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'highway_properties') THEN
CREATE TYPE highway_properties AS ENUM ('bridge:oneway', 'tunnel:oneway', 'ramp', 'ford', 'bridge', 'tunnel', 'oneway');
END IF;
END
$$;
CREATE OR REPLACE FUNCTION to_highway_class(highway TEXT) RETURNS highway_class AS $$
SELECT CASE
WHEN highway IN ('motorway', 'motorway_link') THEN 'motorway'::highway_class
-- A major class is helpful in styling - one can still differentiate on a finer level using the subclass
WHEN highway IN ('trunk', 'trunk_link',
'primary', 'primary_link',
'secondary', 'secondary_link',
'tertiary', 'tertiary_link') THEN 'major_road'::highway_class
WHEN highway IN ('unclassified', 'residential', 'living_street', 'road', 'track', 'service') THEN 'minor_road'::highway_class
WHEN highway IN ('pedestrian', 'path', 'footway', 'cycleway', 'steps') THEN 'path'::highway_class
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE STRICT;
CREATE OR REPLACE FUNCTION to_highway_properties(is_bridge boolean, is_tunnel boolean, is_ford boolean, is_ramp boolean, is_oneway boolean) RETURNS highway_properties AS $$
SELECT CASE
WHEN is_bridge AND is_oneway THEN 'bridge:oneway'::highway_properties
WHEN is_tunnel AND is_oneway THEN 'tunnel:oneway'::highway_properties
WHEN is_ramp THEN 'ramp'::highway_properties
WHEN is_ford THEN 'ford'::highway_properties
WHEN is_bridge THEN 'bridge'::highway_properties
WHEN is_tunnel THEN 'tunnel'::highway_properties
WHEN is_oneway THEN 'oneway'::highway_properties
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -1,29 +0,0 @@
layer:
id: "highway_name"
description: |
This is the layer for labelling the highways. Only highways that are named `name=*` and are long enough
to place text upon appear. The OSM roads are stitched together if they contain the same name
to have better label placement than having many small linestrings.
For motorways you should use the `ref` field to label them while for other roads you should use `name`.
buffer_size: 8
srs: +proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over
fields:
name: The OSM [`name`](http://wiki.openstreetmap.org/wiki/Highways#Names_and_references) value of the highway.
ref: The OSM [`ref`](http://wiki.openstreetmap.org/wiki/Key:ref) tag of the motorway or road.
ref_length: Length of the `ref` field. Useful for having a shield icon as background for labeling motorways.
class: |
Either `motorway`, `major_road` (containing `trunk`, `primary`, `secondary` and `tertiary` roads) and `minor_road` (less important roads in the hierarchy like `residential` or `service`) or `path` for
non vehicle paths (such as `cycleway` or `footpath`).
subclass: |
Original value of the [`highway`](http://wiki.openstreetmap.org/wiki/Key:highway) tag. Use this to do more
precise styling.
datasource:
geometry_field: geometry
srid: 900913
query: (SELECT geometry, name, ref, ref_length, class::text, subclass FROM layer_highway_name(!bbox!, z(!scale_denominator!))) AS t
schema:
- ./merge_highways.sql
- ./layer.sql
datasources:
- type: imposm3
mapping_file: ../highway/mapping.yaml

Wyświetl plik

@ -1,50 +0,0 @@
-- etldoc: layer_highway_name[shape=record fillcolor=lightpink, style="rounded,filled",
-- etldoc: label="layer_highway_name | <z8> z8 |<z9> z9 |<z10> z10 |<z11> z11 |<z12> z12|<z13> z13|<z14_> z14_" ] ;
CREATE OR REPLACE FUNCTION layer_highway_name(bbox geometry, zoom_level integer)
RETURNS TABLE(osm_id bigint, geometry geometry, name text, ref text, ref_length int, class highway_class, subclass text) AS $$
SELECT osm_id, geometry, name,
NULLIF(ref, ''), NULLIF(LENGTH(ref), 0) AS ref_length,
to_highway_class(highway) AS class, highway AS subclass
FROM (
-- etldoc: osm_highway_name_linestring_gen3 -> layer_highway_name:z8
SELECT * FROM osm_highway_name_linestring_gen3
WHERE zoom_level = 8
UNION ALL
-- etldoc: osm_highway_name_linestring_gen2 -> layer_highway_name:z9
SELECT * FROM osm_highway_name_linestring_gen2
WHERE zoom_level = 9
UNION ALL
-- etldoc: osm_highway_name_linestring_gen1 -> layer_highway_name:z10
-- etldoc: osm_highway_name_linestring_gen1 -> layer_highway_name:z11
SELECT * FROM osm_highway_name_linestring_gen1
WHERE zoom_level BETWEEN 10 AND 11
UNION ALL
-- etldoc: osm_highway_name_linestring -> layer_highway_name:z12
SELECT * FROM osm_highway_name_linestring
WHERE zoom_level = 12
AND LineLabel(zoom_level, COALESCE(NULLIF(name, ''), ref), geometry)
AND to_highway_class(highway) < 'minor_road'::highway_class
AND NOT highway_is_link(highway)
UNION ALL
-- etldoc: osm_highway_name_linestring -> layer_highway_name:z13
SELECT * FROM osm_highway_name_linestring
WHERE zoom_level = 13
AND LineLabel(zoom_level, COALESCE(NULLIF(name, ''), ref), geometry)
AND to_highway_class(highway) < 'path'::highway_class
UNION ALL
-- etldoc: osm_highway_name_linestring -> layer_highway_name:z14_
SELECT * FROM osm_highway_name_linestring
WHERE zoom_level >= 14
) AS zoom_levels
WHERE geometry && bbox
ORDER BY z_order ASC;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -1,57 +0,0 @@
-- 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
-- Because this works well for roads that do not have relations as well
-- etldoc: osm_highway_linestring -> osm_highway_name_linestring
CREATE TABLE IF NOT EXISTS osm_highway_name_linestring AS (
SELECT
(ST_Dump(geometry)).geom AS geometry,
-- NOTE: The osm_id is no longer the original one which can make it difficult
-- to lookup road names by OSM ID
member_osm_ids[0] AS osm_id,
member_osm_ids,
name,
ref,
highway,
z_order
FROM (
SELECT
ST_LineMerge(ST_Union(geometry)) AS geometry,
name,
ref,
highway,
min(z_order) AS z_order,
array_agg(DISTINCT osm_id) AS member_osm_ids
FROM osm_highway_linestring
-- We only care about roads for labelling
WHERE name <> '' OR ref <> ''
GROUP BY name, highway, ref
) AS highway_union
);
CREATE INDEX IF NOT EXISTS osm_highway_name_linestring_geometry_idx ON osm_highway_name_linestring USING gist(geometry);
-- etldoc: osm_highway_name_linestring -> osm_highway_name_linestring_gen1
CREATE TABLE IF NOT EXISTS osm_highway_name_linestring_gen1 AS (
SELECT ST_Simplify(geometry, 50) AS geometry, osm_id, member_osm_ids, name, ref, highway, z_order
FROM osm_highway_name_linestring
WHERE highway IN ('motorway','trunk') AND ST_Length(geometry) > 8000
);
CREATE INDEX IF NOT EXISTS osm_highway_name_linestring_gen1_geometry_idx ON osm_highway_name_linestring_gen1 USING gist(geometry);
-- etldoc: osm_highway_name_linestring_gen1 -> osm_highway_name_linestring_gen2
CREATE TABLE IF NOT EXISTS osm_highway_name_linestring_gen2 AS (
SELECT ST_Simplify(geometry, 120) AS geometry, osm_id, member_osm_ids, name, ref, highway, z_order
FROM osm_highway_name_linestring_gen1
WHERE highway IN ('motorway','trunk') AND ST_Length(geometry) > 14000
);
CREATE INDEX IF NOT EXISTS osm_highway_name_linestring_gen2_geometry_idx ON osm_highway_name_linestring_gen2 USING gist(geometry);
-- etldoc: osm_highway_name_linestring_gen2 -> osm_highway_name_linestring_gen3
CREATE TABLE IF NOT EXISTS osm_highway_name_linestring_gen3 AS (
SELECT ST_Simplify(geometry, 120) AS geometry, osm_id, member_osm_ids, name, ref, highway, z_order
FROM osm_highway_name_linestring_gen2
WHERE highway = 'motorway' AND ST_Length(geometry) > 20000
);
CREATE INDEX IF NOT EXISTS osm_highway_name_linestring_gen3_geometry_idx ON osm_highway_name_linestring_gen3 USING gist(geometry);

Wyświetl plik

@ -1,34 +0,0 @@
tables:
# etldoc: imposm3 -> osm_railway_linestring
railway_linestring:
type: linestring
fields:
- name: osm_id
type: id
- name: geometry
type: geometry
- key: railway
name: railway
type: string
- name: z_order
type: wayzorder
- key: tunnel
name: is_tunnel
type: bool
- key: bridge
name: is_bridge
type: bool
- key: service
name: service
type: string
- key: usage
name: usage
type: string
mapping:
railway:
- rail
- light_rail
- subway
- narrow_gauge
- preserved
- tram

Wyświetl plik

@ -1,35 +0,0 @@
CREATE OR REPLACE FUNCTION railway_class(railway text, service text) RETURNS TEXT AS $$
SELECT CASE
WHEN railway='rail' AND service='' THEN 'rail'
ELSE 'minor_rail'
END;
$$ LANGUAGE SQL IMMUTABLE;
CREATE OR REPLACE FUNCTION railway_brunnel(is_bridge boolean, is_tunnel boolean) RETURNS TEXT AS $$
SELECT CASE
WHEN is_bridge THEN 'bridge'
WHEN is_tunnel THEN 'tunnel'
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE;
-- etldoc: layer_railway[shape=record fillcolor=lightpink, style="rounded,filled",
-- etldoc: label="layer_railway | <z13> z13 | <z14_> z14_" ] ;
CREATE OR REPLACE FUNCTION layer_railway(bbox geometry, zoom_level int)
RETURNS TABLE(osm_id bigint, geometry geometry, class text, subclass text, properties railway_properties) AS $$
SELECT osm_id, geometry,
railway_class(railway, service) AS class,
railway AS subclass,
to_railway_properties(is_bridge, is_tunnel) AS properties
FROM (
-- etldoc: osm_railway_linestring -> layer_railway :z13
SELECT * FROM osm_railway_linestring
WHERE zoom_level = 13 AND railway = 'rail' AND service=''
UNION ALL
-- etldoc: osm_railway_linestring -> layer_railway :z14_
SELECT * FROM osm_railway_linestring WHERE zoom_level >= 14
) AS zoom_levels
WHERE geometry && bbox
ORDER BY z_order ASC;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -1,25 +0,0 @@
layer:
id: "railway"
description: |
The `railway` layer contains linestrings marking tracks from [OSM Railways](http://wiki.openstreetmap.org/wiki/Railways).
It contains tracks for [passenger and freight trains]() and smaller tracks for [Trams](http://wiki.openstreetmap.org/wiki/Tag:railway%3Dtram) or [similar](http://wiki.openstreetmap.org/wiki/Tag:railway%3Dlight_rail) vehicles. But also tracks for [subways](http://wiki.openstreetmap.org/wiki/Tag:railway%3Dsubway), [narrow-gauge trains](http://wiki.openstreetmap.org/wiki/Tag:railway%3Dnarrow_gauge) or [historic trains](http://wiki.openstreetmap.org/wiki/Tag:railway%3Dpreserved).
Non mainline tracks (marked with class `minor_rail`) used for [storage of trains](http://wiki.openstreetmap.org/wiki/Tag:service%3Dyard) and [maintenance](http://wiki.openstreetmap.org/wiki/Tag:service%3Dsiding) are contained in the highest zoom levels and should be styled more subtle than the mainline tracks with class `rail`.
fields:
class: |
Divides the track into mainline tracks (class `rail`) and less important tracks
used for maintenance (class `minor_rail`).
subclass: |
Original value of the [`railway`](http://wiki.openstreetmap.org/wiki/Key:railway) can be one of
`rail`, `light_rail`, `subway`, `narrow_gauge`, `preserved`, `tram`.
properties: |
Additional properties describing the nature of tracks. Can be either `bridge` or `tunnel`.
buffer_size: 4
datasource:
geometry_field: geometry
query: (SELECT geometry, class, subclass, properties::text FROM layer_railway(!bbox!, z(!scale_denominator!))) AS t
schema:
- ./types.sql
- ./railway.sql
datasources:
- type: imposm3
mapping_file: ./mapping.yaml

Wyświetl plik

@ -1,15 +0,0 @@
DO $$
BEGIN
IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'railway_properties') THEN
CREATE TYPE railway_properties AS ENUM ('bridge', 'tunnel');
END IF;
END
$$;
CREATE OR REPLACE FUNCTION to_railway_properties(is_bridge boolean, is_tunnel boolean) RETURNS railway_properties AS $$
SELECT CASE
WHEN is_bridge THEN 'bridge'::railway_properties
WHEN is_tunnel THEN 'tunnel'::railway_properties
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -0,0 +1,43 @@
CREATE OR REPLACE FUNCTION brunnel(is_bridge BOOL, is_tunnel BOOL, is_ford BOOL) RETURNS TEXT AS $$
SELECT CASE
WHEN is_bridge THEN 'bridge'
WHEN is_tunnel THEN 'tunnel'
WHEN is_ford THEN 'ford'
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE STRICT;
-- The classes for highways are derived from the classes used in ClearTables
-- https://github.com/ClearTables/ClearTables/blob/master/transportation.lua
CREATE OR REPLACE FUNCTION highway_class(highway TEXT) RETURNS TEXT AS $$
SELECT CASE
WHEN highway IN ('motorway', 'motorway_link') THEN 'motorway'
WHEN highway IN ('trunk', 'trunk_link') THEN 'trunk'
WHEN highway IN ('primary', 'primary_link') THEN 'primary'
WHEN highway IN ('secondary', 'secondary_link') THEN 'secondary'
WHEN highway IN ('tertiary', 'tertiary_link') THEN 'tertiary'
WHEN highway IN ('unclassified', 'residential', 'living_street', 'road') THEN 'minor'
WHEN highway IN ('service', 'track') THEN highway
WHEN highway IN ('pedestrian', 'path', 'footway', 'cycleway', 'steps') THEN 'path'
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE STRICT;
-- The classes for railways are derived from the classes used in ClearTables
-- https://github.com/ClearTables/ClearTables/blob/master/transportation.lua
CREATE OR REPLACE FUNCTION railway_class(railway TEXT) RETURNS TEXT AS $$
SELECT CASE
WHEN railway IN ('rail', 'narrow_gauge', 'preserved', 'funicular') THEN 'rail'
WHEN railway IN ('subway', 'light_rail', 'monorail', 'tram') THEN 'transit'
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE STRICT;
-- Limit service to only the most important values to ensure
-- we always know the values of service
CREATE OR REPLACE FUNCTION service_value(service TEXT) RETURNS TEXT AS $$
SELECT CASE
WHEN service IN ('spur', 'yard', 'siding', 'crossover', 'driveway', 'alley', 'parking_aisle') THEN service
ELSE NULL
END;
$$ LANGUAGE SQL IMMUTABLE STRICT;

Wyświetl plik

@ -0,0 +1,125 @@
CREATE OR REPLACE FUNCTION highway_is_link(highway TEXT) RETURNS BOOLEAN AS $$
SELECT highway LIKE '%_link';
$$ LANGUAGE SQL IMMUTABLE STRICT;
-- etldoc: layer_transportation[shape=record fillcolor=lightpink, style="rounded,filled",
-- etldoc: label="<sql> layer_transportation |<z4z6> z4-z6 |<z7z8> z7-z8 |<z9> z9 |<z10> z10 |<z11> z11 |<z12> z12|<z13> z13|<z14_> z14+" ] ;
CREATE OR REPLACE FUNCTION layer_transportation(bbox geometry, zoom_level int)
RETURNS TABLE(osm_id bigint, geometry geometry, class text, subclass text, ramp int, oneway int, brunnel TEXT, service TEXT) AS $$
SELECT
osm_id, geometry,
CASE
WHEN highway IS NOT NULL THEN highway_class(highway)
WHEN railway IS NOT NULL THEN railway_class(railway)
END AS class,
COALESCE(NULLIF(highway,''), NULLIF(railway, '')) AS subclass,
-- All links are considered as ramps as well
CASE WHEN highway_is_link(highway) THEN 1 ELSE is_ramp::int END AS ramp,
is_oneway::int AS oneway,
brunnel(is_bridge, is_tunnel, is_ford) AS brunnel,
NULLIF(service, '') AS service
FROM (
-- etldoc: ne_10m_global_roads -> layer_transportation:z4z6
SELECT
NULL::bigint AS osm_id, geometry,
highway, NULL AS railway, NULL AS service,
NULL::boolean AS is_bridge, NULL::boolean AS is_tunnel,
NULL::boolean AS is_ford,
NULL::boolean AS is_ramp, NULL::boolean AS is_oneway,
0 AS z_order
FROM ne_10m_global_roads
WHERE zoom_level BETWEEN 4 AND 6 AND scalerank <= 1 + zoom_level
UNION ALL
-- etldoc: osm_highway_linestring_gen4 -> layer_transportation:z7z8
SELECT
osm_id, geometry, highway, NULL AS railway, NULL AS service,
NULL::boolean AS is_bridge, NULL::boolean AS is_tunnel,
NULL::boolean AS is_ford,
NULL::boolean AS is_ramp, NULL::boolean AS is_oneway,
z_order
FROM osm_highway_linestring_gen4
WHERE zoom_level BETWEEN 7 AND 8
UNION ALL
-- etldoc: osm_highway_linestring_gen3 -> layer_transportation:z9
SELECT
osm_id, geometry, highway, NULL AS railway, NULL AS service,
NULL::boolean AS is_bridge, NULL::boolean AS is_tunnel,
NULL::boolean AS is_ford,
NULL::boolean AS is_ramp, NULL::boolean AS is_oneway,
z_order
FROM osm_highway_linestring_gen3
WHERE zoom_level = 9
UNION ALL
-- etldoc: osm_highway_linestring_gen2 -> layer_transportation:z10
SELECT
osm_id, geometry, highway, NULL AS railway, NULL AS service,
NULL::boolean AS is_bridge, NULL::boolean AS is_tunnel,
NULL::boolean AS is_ford,
NULL::boolean AS is_ramp, NULL::boolean AS is_oneway,
z_order
FROM osm_highway_linestring_gen2
WHERE zoom_level = 10
UNION ALL
-- etldoc: osm_highway_linestring_gen1 -> layer_transportation:z11
SELECT
osm_id, geometry, highway, NULL AS railway, NULL AS service,
NULL::boolean AS is_bridge, NULL::boolean AS is_tunnel,
NULL::boolean AS is_ford,
NULL::boolean AS is_ramp, NULL::boolean AS is_oneway,
z_order
FROM osm_highway_linestring_gen1
WHERE zoom_level = 11
UNION ALL
-- etldoc: osm_highway_linestring -> layer_transportation:z12
-- etldoc: osm_highway_linestring -> layer_transportation:z13
-- etldoc: osm_highway_linestring -> layer_transportation:z14_
SELECT
osm_id, geometry, highway, NULL AS railway,
service_value(service) AS service,
is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_highway_linestring
WHERE NOT is_area AND (
zoom_level = 12 AND (
highway_class(highway) NOT IN ('track', 'path', 'minor')
OR highway IN ('unclassified', 'residential')
)
OR zoom_level = 13 AND highway_class(highway) NOT IN ('track', 'path')
OR zoom_level >= 14
)
UNION ALL
-- etldoc: osm_railway_linestring -> layer_transportation:z13
-- etldoc: osm_railway_linestring -> layer_transportation:z14
SELECT
osm_id, geometry, NULL AS highway, railway,
service_value(service) AS service,
is_bridge, is_tunnel, is_ford, is_ramp, is_oneway, z_order
FROM osm_railway_linestring
WHERE zoom_level = 13 AND (railway='rail' AND service = '')
OR zoom_Level >= 14
UNION ALL
-- NOTE: We limit the selection of polys because we need to be
-- careful to net get false positives here because
-- it is possible that closed linestrings appear both as
-- highway linestrings and as polygon
-- etldoc: osm_highway_polygon -> layer_transportation:z13
-- etldoc: osm_highway_polygon -> layer_transportation:z14_
SELECT
osm_id, geometry,
highway, NULL AS railway, NULL AS service,
FALSE AS is_bridge, FALSE AS is_tunnel, FALSE AS is_ford,
FALSE AS is_ramp, FALSE AS is_oneway, z_order
FROM osm_highway_polygon
-- We do not want underground pedestrian areas for now
WHERE zoom_level >= 13 AND is_area AND COALESCE(layer, 0) >= 0
) AS zoom_levels
WHERE geometry && bbox
ORDER BY z_order ASC;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -0,0 +1,220 @@
generalized_tables:
# etldoc: imposm3 -> osm_highway_linestring_gen4
highway_linestring_gen4:
source: highway_linestring_gen3
sql_filter: highway IN ('motorway','trunk') AND NOT is_area
tolerance: 200.0
# etldoc: imposm3 -> osm_highway_linestring_gen3
highway_linestring_gen3:
source: highway_linestring_gen2
sql_filter: highway IN ('motorway','trunk', 'primary') AND NOT is_area
tolerance: 120.0
# etldoc: imposm3 -> osm_highway_linestring_gen2
highway_linestring_gen2:
source: highway_linestring_gen1
sql_filter: highway IN ('motorway','trunk', 'primary', 'secondary') AND NOT is_area
tolerance: 50.0
# etldoc: imposm3 -> osm_highway_linestring_gen1
highway_linestring_gen1:
source: highway_linestring
sql_filter: highway IN ('motorway','trunk', 'primary', 'secondary', 'tertiary') AND NOT is_area
tolerance: 20.0
name_field: &name
name: name
key: name
type: string
name_en_field: &name_en
name: name_en
key: name:en
type: string
short_name_field: &short_name
key: short_name
name: short_name
type: string
tunnel_field: &tunnel
key: tunnel
name: is_tunnel
type: bool
bridge_field: &bridge
key: bridge
name: is_bridge
type: bool
ramp_field: &ramp
key: ramp
name: is_ramp
type: bool
ford_field: &ford
key: ford
name: is_ford
type: bool
oneway_field: &oneway
key: oneway
name: is_oneway
type: bool
area_field: &area
name: is_area
key: area
type: bool
service_field: &service
key: service
name: service
type: string
usage_field: &usage
key: usage
name: usage
type: string
ref_field: &ref
key: ref
name: ref
type: string
network_field: &network
key: network
name: network
type: string
layer_field: &layer
key: layer
name: layer
type: integer
z_order_field: &z_order
name: z_order
type: wayzorder
tables:
# etldoc: imposm3 -> osm_highway_linestring
highway_linestring:
type: linestring
fields:
- name: osm_id
type: id
- name: geometry
type: geometry
- name: highway
key: highway
type: string
- *ref
- *network
- *z_order
- *layer
- *name
- *name_en
- *short_name
- *tunnel
- *bridge
- *ramp
- *ford
- *oneway
- *area
- *service
- *usage
mapping:
highway:
- motorway
- motorway_link
- trunk
- trunk_link
- primary
- primary_link
- secondary
- secondary_link
- tertiary
- tertiary_link
- unclassified
- residential
- road
- living_street
- raceway
- construction
- track
- service
- path
- cycleway
- bridleway
- footway
- corridor
- crossing
- pedestrian
# etldoc: imposm3 -> osm_railway_linestring
railway_linestring:
type: linestring
fields:
- name: osm_id
type: id
- name: geometry
type: geometry
- key: railway
name: railway
type: string
- *ref
- *network
- *z_order
- *layer
- *name
- *name_en
- *short_name
- *tunnel
- *bridge
- *ramp
- *ford
- *oneway
- *area
- *service
- *usage
mapping:
railway:
- rail
- narrow_gauge
- preserved
- funicular
- subway
- light_rail
- monorail
- tram
# etldoc: imposm3 -> osm_highway_polygon
highway_polygon:
type: polygon
fields:
- name: osm_id
type: id
- name: geometry
type: geometry
- name: highway
key: highway
type: string
- name: z_order
type: wayzorder
- name: layer
key: layer
type: integer
- name: is_area
key: area
type: bool
mapping:
highway:
- pedestrian
# TODO: Future table for joining networks
# etldoc: imposm3 -> osm_route_member
route_member:
type: relation_member
columns:
- name: osm_id
type: id
- name: member
type: member_id
- name: role
type: member_role
- name: type
type: member_type
- *ref
- *network
mapping:
route:
- road

Wyświetl plik

@ -0,0 +1,109 @@
layer:
id: "transportation"
description: |
**transportation** containsrRoads and railways.
This layer is directly derived from the OSM road hierarchy which is why it is called `highway`. Only
at zoom level 4 to 7 some major highways from Natural Earth are used otherwise it is only OSM data.
It contains all roads from motorways to primary, secondary and tertiary roads to residential roads and
foot paths. Styling the roads is the most essential part of the map. If you can put enough effort into it
makes sense to carefully style each `subclass`. For more comfortable styling you can also just style the roads
by `class`. Roads can have different properties, a road can have `oneway=yes` and `bridge=yes` at the same time.
These properties are reflected in the field `properties`.
This layer is not meant for labelling the roads (the purpose of the layer `highway_name`).
The `highway` layer also contains polygons for things like plazas.
buffer_size: 4
srs: +proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over
fields:
class:
description: |
Distinguish between more and less important roads.
values:
- motorway
- trunk
- primary
- secondary
- tertiary
- minor
- track
- service
- path
subclass:
description: |
Use **subclass** to do more precise styling.
Original value of the
[`highway`](http://wiki.openstreetmap.org/wiki/Key:highway) or
[`railway`](http://wiki.openstreetmap.org/wiki/Key:railway) tag.
values:
- motorway
- motorway_link
- trunk
- trunk_link
- primary
- primary_link
- secondary
- secondary_link
- tertiary
- tertiary_link
- unclassified
- residential
- road
- living_street
- raceway
- construction
- track
- service
- path
- cycleway
- bridleway
- footway
- corridor
- crossing
- pedestrian
- rail
- narrow_gauge
- preserved
- funicular
- subway
- light_rail
- monorail
- tram
brunnel:
description: |
Mark whether way is a tunnel or bridge.
values:
- bridge
- tunnel
- ford
oneway:
description: |
Mark with `1` whether way is a oneway (in the direction of the way)
or not with `0`.
values: [0, 1]
ramp:
description: |
Mark with `1` whether way is a ramp (link or steps)
or not with `0`.
values: [0, 1]
service:
description: |
Original value of the [`service`](http://wiki.openstreetmap.org/wiki/Key:service) tag.
values:
- spur
- yard
- siding
- crossover
- driveway
- alley
- parking_aisle
datasource:
geometry_field: geometry
srid: 900913
query: (SELECT geometry, class, subclass, oneway, ramp, brunnel, service FROM layer_transportation(!bbox!, z(!scale_denominator!))) AS t
schema:
- ./class.sql
- ./ne_global_roads.sql
- ./layer.sql
datasources:
- type: imposm3
mapping_file: ./mapping.yaml

Wyświetl plik

@ -0,0 +1,52 @@
-- etldoc: layer_transportation_name[shape=record fillcolor=lightpink, style="rounded,filled",
-- etldoc: label="layer_transportation_name | <z8> z8 |<z9> z9 |<z10> z10 |<z11> z11 |<z12> z12|<z13> z13|<z14_> z14_" ] ;
CREATE OR REPLACE FUNCTION layer_transportation_name(bbox geometry, zoom_level integer)
RETURNS TABLE(osm_id bigint, geometry geometry, name text, ref text, ref_length int, network text, class text, subclass text) AS $$
SELECT osm_id, geometry, name,
NULLIF(ref, ''), NULLIF(LENGTH(ref), 0) AS ref_length,
--TODO: The road network of the road is not yet implemented
NULL::text AS network,
highway_class(highway) AS class, highway AS subclass
FROM (
-- etldoc: osm_transportation_name_linestring_gen3 -> layer_transportation_name:z8
SELECT * FROM osm_transportation_name_linestring_gen3
WHERE zoom_level = 8
UNION ALL
-- etldoc: osm_transportation_name_linestring_gen2 -> layer_transportation_name:z9
SELECT * FROM osm_transportation_name_linestring_gen2
WHERE zoom_level = 9
UNION ALL
-- etldoc: osm_transportation_name_linestring_gen1 -> layer_transportation_name:z10
-- etldoc: osm_transportation_name_linestring_gen1 -> layer_transportation_name:z11
SELECT * FROM osm_transportation_name_linestring_gen1
WHERE zoom_level BETWEEN 10 AND 11
UNION ALL
-- etldoc: osm_transportation_name_linestring -> layer_transportation_name:z12
SELECT * FROM osm_transportation_name_linestring
WHERE zoom_level = 12
AND LineLabel(zoom_level, COALESCE(NULLIF(name, ''), ref), geometry)
AND highway_class(highway) NOT IN ('minor', 'track', 'path')
AND NOT highway_is_link(highway)
UNION ALL
-- etldoc: osm_transportation_name_linestring -> layer_transportation_name:z13
SELECT * FROM osm_transportation_name_linestring
WHERE zoom_level = 13
AND LineLabel(zoom_level, COALESCE(NULLIF(name, ''), ref), geometry)
AND highway_class(highway) NOT IN ('track', 'path')
UNION ALL
-- etldoc: osm_transportation_name_linestring -> layer_transportation_name:z14_
SELECT * FROM osm_transportation_name_linestring
WHERE zoom_level >= 14
) AS zoom_levels
WHERE geometry && bbox
ORDER BY z_order ASC;
$$ LANGUAGE SQL IMMUTABLE;

Wyświetl plik

@ -0,0 +1,57 @@
-- 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
-- Because this works well for roads that do not have relations as well
-- etldoc: osm_transportation_linestring -> osm_transportation_name_linestring
CREATE TABLE IF NOT EXISTS osm_transportation_name_linestring AS (
SELECT
(ST_Dump(geometry)).geom AS geometry,
-- NOTE: The osm_id is no longer the original one which can make it difficult
-- to lookup road names by OSM ID
member_osm_ids[0] AS osm_id,
member_osm_ids,
name,
ref,
highway,
z_order
FROM (
SELECT
ST_LineMerge(ST_Union(geometry)) AS geometry,
name,
ref,
highway,
min(z_order) AS z_order,
array_agg(DISTINCT osm_id) AS member_osm_ids
FROM osm_highway_linestring
-- We only care about highways (not railways) for labeling
WHERE (name <> '' OR ref <> '') AND NULLIF(highway, '') IS NOT NULL
GROUP BY name, highway, ref
) AS highway_union
);
CREATE INDEX IF NOT EXISTS osm_transportation_name_linestring_geometry_idx ON osm_transportation_name_linestring USING gist(geometry);
-- etldoc: osm_transportation_name_linestring -> osm_transportation_name_linestring_gen1
CREATE TABLE IF NOT EXISTS osm_transportation_name_linestring_gen1 AS (
SELECT ST_Simplify(geometry, 50) AS geometry, osm_id, member_osm_ids, name, ref, highway, z_order
FROM osm_transportation_name_linestring
WHERE highway IN ('motorway','trunk') AND ST_Length(geometry) > 8000
);
CREATE INDEX IF NOT EXISTS osm_transportation_name_linestring_gen1_geometry_idx ON osm_transportation_name_linestring_gen1 USING gist(geometry);
-- etldoc: osm_transportation_name_linestring_gen1 -> osm_transportation_name_linestring_gen2
CREATE TABLE IF NOT EXISTS osm_transportation_name_linestring_gen2 AS (
SELECT ST_Simplify(geometry, 120) AS geometry, osm_id, member_osm_ids, name, ref, highway, z_order
FROM osm_transportation_name_linestring_gen1
WHERE highway IN ('motorway','trunk') AND ST_Length(geometry) > 14000
);
CREATE INDEX IF NOT EXISTS osm_transportation_name_linestring_gen2_geometry_idx ON osm_transportation_name_linestring_gen2 USING gist(geometry);
-- etldoc: osm_transportation_name_linestring_gen2 -> osm_transportation_name_linestring_gen3
CREATE TABLE IF NOT EXISTS osm_transportation_name_linestring_gen3 AS (
SELECT ST_Simplify(geometry, 120) AS geometry, osm_id, member_osm_ids, name, ref, highway, z_order
FROM osm_transportation_name_linestring_gen2
WHERE highway = 'motorway' AND ST_Length(geometry) > 20000
);
CREATE INDEX IF NOT EXISTS osm_transportation_name_linestring_gen3_geometry_idx ON osm_transportation_name_linestring_gen3 USING gist(geometry);

Wyświetl plik

@ -0,0 +1,77 @@
layer:
id: "transportation_name"
description: |
This is the layer for labelling the highways. Only highways that are named `name=*` and are long enough
to place text upon appear. The OSM roads are stitched together if they contain the same name
to have better label placement than having many small linestrings.
For motorways you should use the `ref` field to label them while for other roads you should use `name`.
buffer_size: 8
srs: +proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over
fields:
name: The OSM [`name`](http://wiki.openstreetmap.org/wiki/Highways#Names_and_references) value of the highway.
ref: The OSM [`ref`](http://wiki.openstreetmap.org/wiki/Key:ref) tag of the motorway or road.
ref_length: Length of the `ref` field. Useful for having a shield icon as background for labeling motorways.
network: The OSM [`network`](http://wiki.openstreetmap.org/wiki/Key:network) tag of the road.
class:
description: |
Distinguish between more and less important roads.
values:
- motorway
- trunk
- primary
- secondary
- tertiary
- minor
- track
- service
- path
subclass:
description: |
Use **subclass** to do more precise styling.
Original value of the
[`highway`](http://wiki.openstreetmap.org/wiki/Key:highway) or
[`railway`](http://wiki.openstreetmap.org/wiki/Key:railway) tag.
values:
- motorway
- motorway_link
- trunk
- trunk_link
- primary
- primary_link
- secondary
- secondary_link
- tertiary
- tertiary_link
- unclassified
- residential
- road
- living_street
- raceway
- construction
- track
- service
- path
- cycleway
- bridleway
- footway
- corridor
- crossing
- pedestrian
- rail
- narrow_gauge
- preserved
- funicular
- subway
- light_rail
- monorail
- tram
datasource:
geometry_field: geometry
srid: 900913
query: (SELECT geometry, name, ref, ref_length, class::text, subclass FROM layer_transportation_name(!bbox!, z(!scale_denominator!))) AS t
schema:
- ./merge_highways.sql
- ./layer.sql
datasources:
- type: imposm3
mapping_file: ../transportation/mapping.yaml

Wyświetl plik

@ -1,13 +1,12 @@
tileset:
layers:
- layers/boundary/boundary.yaml
- layers/highway/highway.yaml
- layers/highway_name/highway_name.yaml
- layers/transportation/transportation.yaml
- layers/transportation_name/transportation_name.yaml
- layers/building/building.yaml
- layers/housenumber/housenumber.yaml
- layers/place/place.yaml
- layers/poi/poi.yaml
- layers/railway/railway.yaml
- layers/water_name/water_name.yaml
- layers/water/water.yaml
- layers/waterway/waterway.yaml