kosmtik / kosmtik

Make maps with OpenStreetMap and Mapnik
Other
719 stars 84 forks source link

Differing renderings between serve and render #119

Open pnorman opened 8 years ago

pnorman commented 8 years ago

This originates from some chopped label debugging...

In a project with

scale: 1
metatile: 2

I have the layer

  - id: place
    geometry: point
    <<: *extents
    Datasource:
      <<: *osm2pgsql
      table: |-
        (SELECT
            way,
            class,
            rank::text,
            population,
            name
          FROM place_point
          WHERE rank = 'city' AND osm_id IN (52553466, 52556180) -- hard coded to trigger bug
          ORDER BY
            CASE class 
              WHEN 'settlement' THEN 10
              WHEN 'subregion' THEN 5
              WHEN 'locality' THEN 2 ELSE 1
            END DESC,
            place_point.rank desc,
            population DESC NULLS LAST,
            length(name) DESC,
            name
        ) AS place

paired with the MSS

Map {
  background-color: @land-color;
  buffer-size: 256;
}
#place[zoom >= 6] {
  shield-name: "[name]";
  shield-file: url("place.svg");
  shield-unlock-image: true;
  shield-size: 12;
  shield-margin: 10;
  shield-face-name: @book-fonts;
  shield-halo-fill: #fff;
  shield-halo-radius: 1.5;
  shield-text-dx: 4;
  shield-text-dy: 5;
  shield-placement-type: dummy;
  shield-repeat-distance: 2;
  shield-allow-overlap: false;
  shield-avoid-edges: false;
  shield-clip: false;
  debug-mode: collision;
}

This leads to the rendering

image

Water is there just to be able to judge placement and extents.

Capturing the SQL for the tile 6/10/22 (the one with Abbotsford) I get

SELECT ST_AsBinary("way") AS geom,"class","name","rank" FROM (SELECT
    way,
    class,
    rank::text,
    population,
    name
  FROM place_point
  WHERE rank = 'city' AND osm_id IN (52553466, 52556180)
  -- Place labels are well-known for being finicky for cut-off labels
  -- This includes terms which aren't needed directly, but are required
  -- to get consistent ordering across tile bounds.
  ORDER BY
    CASE class
      WHEN 'settlement' THEN 10
      WHEN 'subregion' THEN 5
      WHEN 'locality' THEN 2 ELSE 1
    END DESC,
    place_point.rank desc,
    population DESC NULLS LAST,
    length(name) DESC,
    name
) AS place WHERE "way" && ST_SetSRID('BOX3D(-14401959.12137977 4383204.949985144,-11897270.57853111 6887893.492833805)'::box3d, 3857)

Replacing ST_AsBinary with ST_AsText in the query I get the results

              geom              |   class    |    name    | rank
--------------------------------+------------+------------+------
 POINT(-13704980.91 6319246.22) | settlement | Vancouver  | city
 POINT(-13617620.57 6283727.06) | settlement | Abbotsford | city

I get the same results for the tile above.

At this point, I have a situation where "Abbotsford" is being rendered but shouldn't be, as its colliding with Vancouver, and both labels are within the MT boundaries, and it's in a testcase simple enough to debug.

Working around #118 by setting the bounds in the YAML

bounds: &world
  - -129.375
  - 36.5978891330702
  - -106.875
  - 52.4827802220782

I can render with node index.export ~/osm/osm-clear/project.yaml --width 1024 --height 1024 --output img.png --format png

img

This is rendering as expected, with just the higher priority label.

If I go back to serve mode and generate the meta-tile, I get tmp/osm-clear/6.5.11.meta

6 5 11 meta

This rendering is wrong, showing the lower priority label.

At this point, I'm not sure where to take my debugging

pnorman commented 8 years ago

Setting shield-allow-overlap: true; so I can see everything it attempts to place gives me image, with the Abbotsford dot entirely in the top MT and overlapping with the Vancouver text