Why doesn't carto render labels for places mapped as closed ways?

As mentioned in the title, carto doesn’t render the names of polygons like neighbourhoods. Is it just a renderer doing renderer stuff that should be ignored or is there a legitimate reason for this and an alternate Mapping method that should be used instead ?

Hi,
See: Rendering of name labels on place=suburb/quarter/neighbourhood polygons · Issue #4986 · openstreetmap-carto/openstreetmap-carto · GitHub

So, it’s a Design decision.

1 Like

Render place names on areas the same way as on nodes · Issue #103 · openstreetmap-carto/openstreetmap-carto · GitHub is the issue that discusses it in general. I tried to get consensus on one option in Render place names from both points and polygons by pnorman · Pull Request #2816 · openstreetmap-carto/openstreetmap-carto · GitHub but there wasn’t general agreement.

Some more recent discussion outside of OSM Carto was Place on nodes and relation · Issue #86 · shortbread-tiles/shortbread-docs · GitHub but it died out.

In general the number of people interested in an issue like this far exceeds those willing and able to write a solution. When I was an OSM Carto maintainer I decided that given the unhelpful comments I wouldn’t participate in the discussion there on the issue except for PR reviews.

3 Likes

If that makes sense, you can always create or use a relation with the polygon as outerand your node as label as seen here, see discussion mentioned by @pnorman for details.

2 Likes

This is an example of the problem as there are two Le Prat objects in the database: node 6818224679 and relation 10060749.

The node is part of the relation.

They’re still separate objects, just like way 731167673 is a part of the relation but still is its own object.

Membership in a relation doesn’t make the object that is a member disappear. It hasn’t done that since we got rid of old-style multipolygons several years ago.

Currently the Le Prat example is a clean one, but a month ago the node and relation had different values for name:fr. Cases like that are where we start to run into problems.

3 Likes

The issue was that name:fr was wildly added in France, an automated edit (made without asking the community). It should have been reverted, not added where it was “missing”.
Yes, duplicating names makes maintenance harder.
Having the role label should be sufficient to derivate the name and the place from the relation.

they are connected objects, the node is with the role label in the relation, both have the same name and same place tag.

that’s up to the data consumer to decide. IMHO it looks better if it does.

3 Likes

How? Have a look here. The “Dublin” on the left is the centroid of this relation; the one on the right this node. They are both tagged place=city. If you look here (the same vector tiles, but a style with debug enabled) you can see that in the case of the Shortbread vector tiles, there’s actually no difference between the two Dublins (apart from the population, which is oddly different) - there is no way for a data consumer to tell the difference.

It would be possible for the thing that creates the database for raster tiles or the vector tiles themselves for vector ones to “only look at nodes and ignore relations”, but that is what prompted the question in the first place. It is much harder to say “only render a city from its way or relation if there is no corresponding node to show instead”.

If you can solve the problem, then please head over here and present your solution!

The relation’s primary feature tag is type=boundary boundary=administrative. There is a redundant place=city tag, so the redundant label is unfortunate but unsurprising. The relation doesn’t need place=city. In case it matters, Nominatim can cope by looking for the place=city on the label member node. As long as it’s present on the relation for whatever reason, it could be treated as a secondary attribute.

This is a bit different than the original question, which pertains to place=* areas (closed ways). A redundant label can only occur if the feature is mapped redundantly as an area and a standalone node within it. I don’t think users would be surprised to see that two separate features have resulted in two separate labels. That said, it’s probably better to map a boundary=place relation, so that mappers don’t have to potentially work around a very large, complex area.

1 Like

iirc I do exactly this, skip centroids where there is a label node in the relation, not difficult to do, I just used functionality that was already there.

3 Likes

I agree with Christoph and Paul that “label” is an awkward name for this, as it seems to indicate rendering instructions rather than explicitly state on the data level that this node is the centre of this area. I would have preferred to call the role “centre”, but when I looked at it, “label” was what was used in the data, so I “accepted” it.

1 Like

How? Can you point to some code that does it in all 3 of these cases:

  • Where a pgsql database is used for raster rendering (either in the lua script at database update or in the SQL used for display)
  • Where vector tiles are used (e.g. Tilemaker / MapLibre - either in the initial processing (lua with limited spatial awareness in the case of Tilemaker, and/or using only selections that can be added to MapLibre)
  • Where something like osm-tag-transform is used and there is no spatial awareness.

We’re quickly getting into “don’t map for the renderer” territory with this line of questioning. For what it’s worth, the technology exists. I think the more interesting discussion would be about the edge cases discussed in the Shortbread issue – which of them this community considers to be valid or invalid tagging. For example, can the place=* tag only occur on the relation or only on the label node? As long as the tagging scheme is reasonably clear, the software you mention can be adapted to work with it so that ultimately style authors shouldn’t need to fuss over these details unless they want to.

2 Likes

you are emphasizing the spatial awareness, but for a cheaper solution you can simply trust the relations without checking whether the role label point is actually inside the area.

As a good test case, Hawaii’s label member lies just outside any of the boundary relation’s rings. Though I think this is an unfortunate case of label as a rendering hint. I don’t think a boundary of this type should require a label member at all, since the state is an administrative area (political geography) but not a populated place (human geography).

So you’re suggesting “just render places from relations and ignore place nodes”?

How would that work for places that are mapped as nodes but not relations?

Worst in this case, Relation: ‪Hawaii‬ (‪3403603‬) | OpenStreetMap, the state shares the name of one island of the arphipelago.
Back to the Dublin/Dublin case, I would simply as suggested by @SomeoneElse remove the label node and use an admin_centre node.

Well, ish. If you’ve got a database that you can query then yes, you can query a database. Some tools (e.g. Tilemaker) support “what relation is this a member of” on the fly, but in some cases neither approach is available - unless you chuck everything into a database, do some processing and read it out again.

That’s why I’ve been pushing back against flippant answers above that said just “it should be easy” without thinking about the actual data in OSM, where the place node may be something other role than label, or may be a different place value to the relation, etc.

There’s quite a bit of code behind https://map.atownsend.org.uk/maps/map/map.html to suppress place values in several circumstances (e.g. looking at whether something has other tags, is a townland, etc. etc.). Unfortunately, (as the Shortbread discussion showed) the OSM tagging really needs to sort itself out a bit here - if duplicate place objects are necessary then they should be predictable.

1 Like