I'm generating images from various sources and the projections are not necessarily known ahead of time. The images are subject to interpolation and other alterations while being rendered, but I can generate 2D arrays of latitude and longitude points that correspond to pixels in the rendered image.

I need to be able to draw geo-political boundaries on top of the images using the latitude/longitude arrays as a reference. I don't normally work with GIS type problems, but I've done some research and I think what I want to do is take in a shape file with lat/lon points defining line segments making up geo-political boundaries and interpolate the closest locations for the edges of those line segments on my image.

Although I have an idea for a general approach, is there a preferred way to do this in Java, or a library providing the functionality? I found GeoTools which would do what I want if the projection was known ahead of time, but I need to be able to generate overlays on the fly. In addition I need the following features:

  • Must work with varying resolution, boundaries should still be legible when zoomed in heavily. That is, when a pixel in the source image is being represented by multiple pixels at the display, boundaries should be drawn gracefully.
  • Must be able to render maps in real time, or at least with reasonable latency. Although the projections are not all necessarily known ahead of time, they will not change often. If some amount of automated preprocessing can be done ahead of time to improve performance, that is an option.
  • An open source (but commercial friendly) solution is preferred, but I can go with a closed source solution if necessary.

What you want is called "warping" in GIS. It is mostly applied to images, rather than shapefiles, but the procedure for shapefiles is not hard. Let's take a look.

The white dots on the first image below represent an array of (lat, lon) grid points drawn in their correct locations on the image. The array does not appear perfectly regular due to distortions in the image (including distortions due to its projection). Let's call these the "target" points. You intend to keep this image as-is: your purpose is to draw a feature over the image in the visually correct locations.

Target image

Target image

The shapefile features themselves are given as sequences of points. Each point is specified with a pair of coordinates, latitude and longitude. To illustrate, consider the following linear feature (thick gray line segments with light red vertices). Let's call these the "source" vertices. They are shown superimposed on the same set of (lat, lon) reference points seen in the image, but now these reference points are drawn in a standard Cartesian coordinate system, where they will be regularly spaced.

Source feature

Source feature

The one-to-one matching of the source grid vertices with the target grid vertices can be thought of in several useful ways. One is to think of each source vertex getting displaced toward its target counterpart:

Vector displacements

Vector displacements

These are the same dark red dots shown in the previous figure. Their target points, in blue, are the same as the white dots shown in the first image.

We need to carry out this same "warping" on the shapefile feature. This requires interpolating the vector displacements. Bilinear interpolation usually works fine. It's quick and easy, because all you have to do to displace each feature vertex is

  1. Find the source grid cell in which it lies.

  2. Fetch the coordinates of the targets of the four vertices of that source grid cell.

  3. Separately and independently, interpolate the coordinates. This will be the target coordinates of the source vertex.

The separate interpolation in step 3 is nothing more than looking up values in two coarse grids: one is the grid of x coordinates of the targets (shown next) and the other is a grid of y coordinates of the targets (immediately following).

X Grid

X grid

Y Grid

Y Grid

When you draw the feature on the image, using the warped coordinates, it will display where it is intended to be:


(For the warping to be accurate, the shape's vertices need to be enclosed within the array of reference points. Otherwise you need to extrapolate, which rapidly becomes uncertain.)

There may exist some GIS software to perform this operation (and perhaps some kind and informed reader will be able to supply a link). As you would expect from this description, its input will consist of:

(a) A grid of source points. (There are often called "ground control points," or GCPs, because a standard application is to convert coordinates obtained in the field to standard geographic coordinates.) Some solutions will more generally process a triangulated network of source points.

(b) A corresponding grid of target points.

(c) A layer of vector shapes, like those found in a shapefile. An example of this is Kenneth McVay's ShapeWarp script for ArcView 3.


One option you have is to implement an architecture like the following:

  1. load the political boundaries on a WMS server of your choice. Both Geoserver and Mapserver are excellent open source choices with Geoserver being an all Java solution and easier to setup. Mapserver should give better performance

  2. modify your image rendering code so that at the time in which you need to draw the boundaries it computes a bounding box for the covered area (in lat/lon), an image size (in pixels) and the projection of your data (since you said the projection is not known ahead of time and thus can vary depending on the data you're processing)

  3. issue a WMS getMap request (it sounds complicated, but it really is a plain HTTP GET request with standard params) to the WMS server set up at step 1 using the bounding box, projection and image size computed at step 2. The WMS server will take care of converting the source data to the requested projection. You can use httpclient to handle the request.

  4. merge the image returned by the WMS server into your own image using Java imaging libraries

The benefits of this solution are that WMS is a standard and therefore you can swap Geoserver for any other WMS server at any time.

The WMS rendering can be done on an entirely different server or cluster of servers, offloading the local machine.

You can swap the political boundaries and/or add layers or imagery at any time with a dead-simple customization of the WMS request and configuration on the WMS side.

  • I don't have a reference projection. – Jordan Bentley Nov 7 '11 at 13:00
  • probably my statement was not clear (I edited the answer): by reference projection I mean the projection in which is the data you're currently processing. The WMS server will then translate from the original boundary projection into this projection. – unicoletti Nov 7 '11 at 15:19
  • 1
    I'm looking through the Geoserver and Mapserver documentation but I don't see anything about passing in an array of lat/lon coordinates. They both refer to specifying a prebuilt projection which doesn't help me. Is there some terminology that I'm missing? Also setting up a web service seems like overkill, can this not be done locally? – Jordan Bentley Nov 7 '11 at 16:09
  • @JordanBentley frankly after reading your last question I don't think I understand what you want to do anymore. Please clarify your answer or take some time to study my answer a little bit more. – unicoletti Nov 7 '11 at 16:24
  • By time the data gets to my application, I have no information about the projection other than a grid of lat/lon values which correspond to pixels in my image. I can't reverse engineer the projection from the data, for all I know it could be Mercator, equi-rectangular, or some custom projection that I don't have a definition of. I need to be able to draw political boundaries from that information. – Jordan Bentley Nov 7 '11 at 16:35

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.