scalageotools

GridGeometry2D's world to grid function translating wrong


Using geotools version 11.2

import java.awt.Rectangle


import com.vividsolutions.jts.geom.Envelope
import org.geotools.coverage.grid.{GeneralGridEnvelope, GridGeometry2D}
import org.geotools.geometry.jts.ReferencedEnvelope
import org.geotools.referencing.crs.DefaultGeographicCRS.WGS84

val minX = -78.523
val minY = 38.010
val maxX = -78.451
val maxY = 38.069
val width = 400
val height = 300

val bounds = new ReferencedEnvelope(new Envelope(minX, maxX, minY, maxY), WGS84)
val rect = new Rectangle(0, 0, width, height)
val ggEnvelope = new GeneralGridEnvelope(rect, bounds.getDimension)
val gm = new GridGeometry2D(ggEnvelope, bounds)
////////////////// This should be [0, 299] but is [-1, 299]//////////////////////////////
gm.worldToGrid(bounds.getLowerCorner)

Solution

  • Ended up using this function. You can see something similar for maxX and minY in the source code for GridGeometry2D.java worldToGrid function

      val TOL = 1.0E-6
      val values = Array(0.0)
    
      def safeWorldAccess(grid: GridCoverage2D, point: DirectPosition2D): Double = {
        val trPoint = point.clone()
        val gridGeom = grid.getGridGeometry
        if (Math.abs(trPoint.getX - gridGeom.getEnvelope2D.getMinX) <= TOL) {
          trPoint.setLocation(trPoint.getX + TOL, trPoint.getY)
        }
    
        if (Math.abs(trPoint.getY - gridGeom.getEnvelope2D.getMaxY) <= TOL) {
         trPoint.setLocation(trPoint.getX, trPoint.getY - TOL)
        }
        val gc: GridCoordinates2D = gridGeom.worldToGrid(trPoint)
        grid.evaluate(gc, values).head
      }