From d0c663d90e8d47abfa26a3be4d70559da7c50373 Mon Sep 17 00:00:00 2001 From: Jochen Topf Date: Thu, 3 Jul 2025 15:01:18 +0200 Subject: [PATCH] Add core/extract topic using the new locator feature of osm2pgsql This allows filtering all data by bounding box or polygon. --- themes/core/README.md | 33 +++++++++++++++++ themes/core/topics/extract.lua | 66 ++++++++++++++++++++++++++++++++++ 2 files changed, 99 insertions(+) create mode 100644 themes/core/topics/extract.lua diff --git a/themes/core/README.md b/themes/core/README.md index 0f8811c..ec94c53 100644 --- a/themes/core/README.md +++ b/themes/core/README.md @@ -54,6 +54,39 @@ If a valid elevation tag is found, the attributes `core.ele_m` and `core.ele_ft` are added and contain the elevation in meters and feet, respectively, as a number, rounded to the nearest integer. +## Topic 'extract' + +### Description + +Restrict imported data to a bounding box or polygon using the Locator feature +of osm2pgsql. Use this topic *before* any other topics you want to restrict. +Objects intersecting the locator area are kept, all others are discarded. For +closed ways the area of the polygon is used for intersection, for unclosed ways +the linestring. For relations that can be turned into multipolygons, the +multipolygon is used, otherwise all node and way members of the polygon are +checked as point and linestring features, respectively. + +Geometries are *not* clipped to the locator area. + +This only works in osm2pgsql version 2.2.0 and above. + +### Tables + +This topic doesn't add any output tables. + +### Configuration + +* `locator`: Set to an existing osm2pgsql.Locator (optional, if not set, a new + locator will be created). +* `bbox`: A table with the bounding box to be added to the locator. The table + must contain four elements, in that order: min lon, min lat, max lon, max + lat. + +### Attributes + +No attributes are added. + + ## Topic 'layer' ### Description diff --git a/themes/core/topics/extract.lua b/themes/core/topics/extract.lua new file mode 100644 index 0000000..a3a3ec8 --- /dev/null +++ b/themes/core/topics/extract.lua @@ -0,0 +1,66 @@ +-- --------------------------------------------------------------------------- +-- +-- Theme: core +-- Topic: extract +-- +-- --------------------------------------------------------------------------- + +local themepark, theme, cfg = ... + +-- --------------------------------------------------------------------------- + +local locator + +if cfg.locator == nil then + locator = osm2pgsql.define_locator({ + name = 'themepark-core-extract-' .. math.random(100000000) + }) +else + locator = cfg.locator +end + +if cfg.bbox ~= nil then + local b = cfg.bbox + locator:add_bbox('inside', b[1], b[2], b[3], b[4]) +end + +-- --------------------------------------------------------------------------- + +themepark:add_proc('node', function(object) + if not locator:first_intersecting(object:as_point()) then + return 'stop' + end +end) + +themepark:add_proc('way', function(object) + local geom + if object.is_closed then + geom = object:as_polygon() + end + + if geom == nil or geom:is_null() then + geom = object:as_linestring() + end + + if not locator:first_intersecting(geom) then + return 'stop' + end +end) + +themepark:add_proc('relation', function(object) + local geom = object:as_multipolygon() + + if geom:is_null() then + geom = object:as_geometrycollection() + end + + if geom:is_null() then + return 'stop' + end + + if not locator:first_intersecting(geom) then + return 'stop' + end +end) + +-- ---------------------------------------------------------------------------