Areas should replace three data types currently used in OpenStreetMap:
- closed ways (problems: self-intersections, tags can be related to area and line)
- multipolygons (problems: easily breakable, tags can go on ways and relations)
- coastline, multi-multipolygons (problems: quite a lot of ways — tens of thousands, — tags can go on everything)
I propose to create a new data type, area:
<area id="..." ...> <tag k="..." v="..." /> <ring> <nd ref="1" /> <nd ref="2" /> </ring> <ring> <nd ref="3" /> <nd ref="4" /> </ring> </area>
As you can see, areas are built of rings. This would allow to store Simple Features multipolygons, with inner and outer rings. Points are ordered counter clockwise for outer and clockwise for inner rings, like Simple Features model defines.
It is mostly the same as The Future of Areas/Areas on Nodes, but instead of specifying inner/outer rings, we rely on node order. This would benefit editors and renderers, since:
- having node coordinates, it is obvious which rings are inner and which are outer;
- building a Simple Features polygon is trivial;
- partially downloaded area still can be rendered.
Each node should come up at most once. All rings are closed, so the first node should not be repeated at the end.
- Closed ways easily translate into areas (sans tag conflicts) and won't require extra objects.
- There can be a lot of nodes in an area, and all of those would be downloaded at once.
Then, I propose to add area reference to ways:
<way id="..." ...> <tag k="..." v="..." /> <nd ref="5" /> <nd ref="6" /> <arearef id="1000" reverse="false" /> </way>
A way can have many arearefs. The direction of ways is the same as for nodes in an area: counter clockwise for outer rings, clockwise for inner. Tags on ways apply only to those ways, and not to areas.
- References do not increase version number, so it is possible to edit an area simultaneously.
- Coastlines and objects like the border of France are easy to draw (just make an empty area with tags and reference it).
- Due to direction constraint, it is possible to edit or render a part of an area with no trouble.
- You cannot be sure you have downloaded all rings of an area.
- Areas for forests or plains that cover whole countries can appear.
- Consistence check at the server side would be hard to implement.
- Reversing ways would be much harder, since it can break areas.
<area id="1"> <tag k="landuse" v="residential" /> <!-- two outer rings: list nodes counter clockwise --> <ring> <nd ref="8" /> <nd ref="9" /> <nd ref="10" /> <nd ref="11" /> </ring> <ring> <nd ref="3" /> <nd ref="2" /> <nd ref="4" /> </ring> </area> <way> <nd ref="1" /> ... <nd ref="1" /> <!-- the way has nodes clockwise: for representing an outer ring, we need it reversed --> <arearef id="1" reverse="true" /> </way> <!-- next three ways go in correct directions, so just mark them as parts of the area --> <way> <nd ref="7" /> ... <nd ref="5" /> <arearef id="1" reverse="false" /> </way> <way> <nd ref="5" /> ... <nd ref="7" /> <arearef id="1" reverse="false" /> </way> <way> <nd ref="6" /> ... <nd ref="6" /> <arearef id="1" reverse="false" /> </way>
There should be a number of checks for correctness, which were not possible for multipolygons. Of course, geometry checks are still impossible in our database, but at least we can check for duplicate nodes.
Areas on nodes
Rings should not touch or have self-intersections: check that there are no duplicate nodes; every node should be referenced only once in all the rings.
Process all ways after they have been uploaded; for every uploaded way there should be a way (better — only one way) with the same area ref starting or ending (better — depends on reverse flag) on both end nodes. No need to check nodes and their coordinates.
Ways having area ref should not have self-intersections, but can be closed.
No touching of rings
Ways that form rings of an area (and nodes in that area) should not have common nodes, except for start and end nodes. This check can strain the database, so it is optional.
Requesting number of ways
Before downloading a complete area (/area/:id/full), one would want to know number of ways it has: it would be quite unfortunate having to download the complete coastline, for example. There should be an "info" request that gives exactly that. Alternatively, we can have "number of references" field in the database, which gets updated every time a way gains or looses area reference.
Or we can just make /full request fail if number of ways is greater that 1000, for example.