Leaflet – Using CRS.Simple Transformation for Real-Life Measurements

coordinate systemleafletscale

I am trying to set-up a CRS.Simple Coordinate Reference System with a custom transformation.
I got a real world construction plan with

  • scale of 1:500
  • width 11112px
  • height 10432px
  • density 288

I tiled it using sharp/libvips with a tilesize of 256. I get the folder output with zoom levels 0 to 6 and a density of 96

Here is my approach I tried, somewhat unsucessfully, the measurement is some meters off and I cant figure out which values to change

  const heigth = 10432;
  const width = 11112;
  const density = 288;
  const tileSize = 256;
  const scaleFactor = 500;

  const mapMinZoom = 0;
  const mapMaxZoom = 7;
  const mapMaxResolution = 1;
  const mapMinResolution = Math.pow(2, mapMaxZoom) * mapMaxResolution;

  const crs = L.CRS.Simple;

  const dpiX = (tileSize / width * Math.pow(2, mapMaxZoom)) * density;
  const dpiY = (tileSize / heigth * Math.pow(2, mapMaxZoom)) * density;

  const factorX = 1 / (1 / dpiX * 2.54 * scaleFactor / 100);
  const factorY = 1 / (1 / dpiY * 2.54 * scaleFactor / 100);

  // @ts-ignore
  crs.transformation = new L.Transformation(factorX, 0, factorY, 0);
  crs.scale = function (zoom) {
    return Math.pow(2, zoom) / mapMinResolution;
  };
  crs.zoom = function (scale) {
    return Math.log(scale * mapMinResolution) / Math.LN2;
  };

  this.map = L.map('map', {
    crs: crs,
  });

  L.tileLayer('http://localhost:3000/{z}/{y}/{x}.jpg', {
    tileSize: 256,
    minZoom: mapMinZoom, maxZoom: mapMaxZoom,
    noWrap: true,
    tms: false
  }).addTo(this.map);

Best Answer

I found the solution

// dpi = dpi of original image
const factor = 1 / (1 / dpi * 2.54 * scaleFactor / 100);
crs.transformation = new L.Transformation(factor , 0, factor , 0);

enter image description here

Related Question