Skip to content

Commit

Permalink
viewer app vectordb layer with name attribute labels; vectordb wms us…
Browse files Browse the repository at this point in the history
…ing jts rasterizer and labels; vectordb wms with reprojection
  • Loading branch information
swoellauer committed Mar 7, 2024
1 parent 3dec35f commit e074cf5
Show file tree
Hide file tree
Showing 11 changed files with 224 additions and 69 deletions.
25 changes: 7 additions & 18 deletions src/postgis/style/StyleJtsGeometryRasterizer.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import org.locationtech.jts.geom.Polygon;

import util.collections.vec.Vec;
import vectordb.style.ImgLabel;
import vectordb.style.Style;

public class StyleJtsGeometryRasterizer implements StyleJtsGeometryConsumer {
Expand All @@ -19,19 +20,7 @@ public class StyleJtsGeometryRasterizer implements StyleJtsGeometryConsumer {

public final Graphics2D gc;

private static class Label {
public final String text;
public final int x;
public final int y;

public Label(String text, int x, int y) {
this.text = text;
this.x = x;
this.y = y;
}
}

private final Vec<Label> labelBuffer = new Vec<Label>();
private final Vec<ImgLabel> labelBuffer = new Vec<ImgLabel>();

public StyleJtsGeometryRasterizer(double xoff, double yoff, double xscale, double yscale, Graphics2D gc) {
this.xoff = xoff;
Expand All @@ -55,7 +44,7 @@ public void acceptPolygon(Style style, Polygon polygon, String text) {
xs[i] = (int) ((c.x + xoff) * xscale);
ys[i] = (int) ((yoff - c.y) * yscale);
}
style.drawPolygon(gc, xs, ys, len);
style.drawImgPolygon(gc, xs, ys, len);
} else {
float[][] rings = new float[interiorRings + 1][];
{
Expand All @@ -69,7 +58,7 @@ public void acceptPolygon(Style style, Polygon polygon, String text) {
Coordinate[] cs = ring.getCoordinateSequence().toCoordinateArray();
rings[r + 1] = convert(cs);
}
style.drawPolygonWithHoles(gc, rings);
style.drawImgPolygonWithHoles(gc, rings);
}

if(text != null) {
Expand All @@ -80,16 +69,16 @@ public void acceptPolygon(Style style, Polygon polygon, String text) {
if(!ptext.isEmpty()) {
int xtext = (int) ((ptext.getX() + xoff) * xscale);
int ytext = (int) ((yoff - ptext.getY()) * yscale);
Label label = new Label(text, xtext, ytext);
ImgLabel label = new ImgLabel(text, xtext, ytext);
labelBuffer.add(label);
}
}
}
}

public void drawLabels(Style style) {
for (Label label : labelBuffer) {
style.drawText(gc, label.x, label.y, label.text);
for (ImgLabel label : labelBuffer) {
style.drawImgText(gc, label.x, label.y, label.text);
}
labelBuffer.clear();
}
Expand Down
1 change: 0 additions & 1 deletion src/server/api/postgis/PostgisHandler_image_png.java
Original file line number Diff line number Diff line change
Expand Up @@ -157,7 +157,6 @@ public static ImageBufferARGB render(PostgisLayer postgisLayer, int renderEPSG,
}

gc.dispose();

return image;
}
}
4 changes: 2 additions & 2 deletions src/server/api/postgis/PostgisHandler_wms.java
Original file line number Diff line number Diff line change
Expand Up @@ -427,7 +427,7 @@ private ImageBufferARGB createLegend(PostgisLayer postgisLayer, boolean crop, St
int y = vPos[0] - 20;
//Logger.info("field value: " + value);
Style style = styleProvider.getStyleByValue(value);
style.drawPolygon(gc, new int[] {5, 40, 40, 5}, new int[] {y + 10, y + 10, y + 20, y + 20}, 4);
style.drawImgPolygon(gc, new int[] {5, 40, 40, 5}, new int[] {y + 10, y + 10, y + 20, y + 20}, 4);
gc.setColor(Color.BLACK);
gc.drawString(""+value, 52 - fontMetrics.stringWidth(""+value), vPos[0]);
if(style.hasTitle()) {
Expand All @@ -439,7 +439,7 @@ private ImageBufferARGB createLegend(PostgisLayer postgisLayer, boolean crop, St
gc.drawString("Uniform style", 0, 20);
Style style = styleProvider.getStyle();
int y = 20;
style.drawPolygon(gc, new int[] {20, 160, 160, 20}, new int[] {y + 10, y + 10, y + 20, y + 20}, 4);
style.drawImgPolygon(gc, new int[] {20, 160, 160, 20}, new int[] {y + 10, y + 10, y + 20, y + 20}, 4);
}

gc.dispose();
Expand Down
81 changes: 81 additions & 0 deletions src/server/api/vectordbs/ConverterRenderer.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
package server.api.vectordbs;

import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.RenderingHints;

import org.gdal.ogr.DataSource;
import org.gdal.ogr.Feature;
import org.gdal.ogr.Geometry;
import org.gdal.ogr.Layer;
import org.locationtech.jts.io.WKBReader;
import org.tinylog.Logger;

import pointcloud.Rect2d;
import postgis.style.StyleJtsGeometryRasterizer;
import util.GeoUtil.Transformer;
import util.image.ImageBufferARGB;
import vectordb.style.Style;

public class ConverterRenderer {

public static ImageBufferARGB render(DataSource datasource, Object sync, Rect2d renderRect, int width, int height, String labelField, Style style, Transformer layerRenderTransformer) {
ImageBufferARGB image = new ImageBufferARGB(width, height);
Graphics2D gc = image.bufferedImage.createGraphics();
gc.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
gc.setColor(Color.DARK_GRAY);

double xlen = renderRect.width();
double ylen = renderRect.height();
double xscale = (width - 4) / xlen;
double yscale = (height - 4) / ylen;
double xoff = - renderRect.xmin + 2 * (1 / xscale);
double yoff = renderRect.ymax + 2 * (1 / yscale);

StyleJtsGeometryRasterizer styleJtsGeometryRasterizer = new StyleJtsGeometryRasterizer(xoff, yoff, xscale, yscale, gc);

WKBReader wkbReader = new WKBReader();
int layerCount = datasource.GetLayerCount();
for(int layerIndex=0; layerIndex<layerCount; layerIndex++) {
Layer layer = datasource.GetLayerByIndex(layerIndex);
synchronized (sync) {
layer.SetSpatialFilter(null); // clear filter
layer.ResetReading(); // reset iterator
Feature feature = layer.GetNextFeature();
while(feature != null) {
try {
Geometry geometry = feature.GetGeometryRef();
if(geometry != null) {
if(layerRenderTransformer != null) {
geometry.Transform(layerRenderTransformer.coordinateTransformation);
}
byte[] wkb = geometry.ExportToWkb();
if(wkb != null) {
org.locationtech.jts.geom.Geometry jtsGeometry = wkbReader.read(wkb);
String label = null;
if(labelField != null) {
label = feature.GetFieldAsString(labelField);
if(label != null && label.isBlank()) {
label = null;
}
}
//Logger.info(jtsGeometry.getClass() + " " + label);
styleJtsGeometryRasterizer.acceptGeometry(style, jtsGeometry, label);
}
} else {
Logger.warn("missing geometry");
}
} catch(Exception e) {
Logger.warn(e);
}
feature = layer.GetNextFeature();
}
}
}
styleJtsGeometryRasterizer.drawLabels(style);

gc.dispose();
return image;
}

}
52 changes: 30 additions & 22 deletions src/server/api/vectordbs/VectordbHandler_wms.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@

import java.io.IOException;
import java.io.PrintWriter;
import java.util.Arrays;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
Expand All @@ -14,15 +13,13 @@
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;


import org.tinylog.Logger;
import org.eclipse.jetty.io.EofException;
import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.server.Response;
import org.eclipse.jetty.server.UserIdentity;
import org.gdal.ogr.DataSource;
import org.gdal.osr.CoordinateTransformation;
import org.gdal.osr.SpatialReference;
import org.tinylog.Logger;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
Expand All @@ -37,6 +34,7 @@
import util.image.ImageBufferARGB;
import vectordb.Renderer;
import vectordb.VectorDB;
import vectordb.style.Style;

public class VectordbHandler_wms extends VectordbHandler {

Expand Down Expand Up @@ -85,33 +83,43 @@ public void handle_GetMap(VectorDB vectordb, Request request, Response response,
int width = Web.getInt(request, "WIDTH");
int height = Web.getInt(request, "HEIGHT");
String crs = Web.getString(request, "CRS");
util.GeoUtil.Transformer transformer = null;

SpatialReference srcSr = vectordb.getSpatialReference();
if(srcSr != null && crs != null && crs.startsWith("EPSG:")) {
SpatialReference dstSr = null;
int epsg = Integer.parseInt(crs.substring(5));
if(epsg > 0) {
if(epsg == GeoUtil.EPSG_WEB_MERCATOR) {
dstSr = GeoUtil.WEB_MERCATOR_SPATIAL_REFERENCE;
util.GeoUtil.Transformer layerWmsTransformer = null;

SpatialReference layerSr = vectordb.getSpatialReference();
if(layerSr != null && crs != null && crs.startsWith("EPSG:")) {
SpatialReference wmsSr = null;
int wmsEPSG = Integer.parseInt(crs.substring(5));
if(wmsEPSG > 0) {
if(wmsEPSG == GeoUtil.EPSG_WEB_MERCATOR) {
wmsSr = GeoUtil.WEB_MERCATOR_SPATIAL_REFERENCE;
} else {
dstSr = GeoUtil.getSpatialReferenceFromEPSG(epsg);
wmsSr = GeoUtil.getSpatialReferenceFromEPSG(wmsEPSG);
}
}
if(dstSr != null) {
if(dstSr.IsSame(srcSr) == 0) {
if(wmsSr != null) {
if(wmsSr.IsSame(layerSr) == 0) {
Logger.info("transform");
transformer = new GeoUtil.Transformer(srcSr, dstSr);
layerWmsTransformer = new GeoUtil.Transformer(layerSr, wmsSr);
}
}
}

String labelField = vectordb.hasNameAttribute() ? vectordb.getNameAttribute() : null;

String[] bbox = request.getParameter("BBOX").split(",");
Rect2d wmsRect = Rect2d.parse(bbox[0], bbox[1], bbox[2], bbox[3]);
Rect2d wmsRect = Rect2d.parse(bbox[0], bbox[1], bbox[2], bbox[3]);

ImageBufferARGB image = null;
DataSource datasource = vectordb.getDataSource();
try {
image = Renderer.render(datasource, vectordb, wmsRect, width, height, transformer, vectordb.getStyle());
//image = Renderer.render(datasource, vectordb, wmsRect, width, height, layerWmsTransformer, vectordb.getStyle(), labelField);
{
Style style = vectordb.getStyle();
if(style == null) {
style = Renderer.STYLE_DEFAULT;
}
image = ConverterRenderer.render(datasource, vectordb, wmsRect, width, height, labelField, style, layerWmsTransformer);
}
} finally {
VectorDB.closeDataSource(datasource);
}
Expand Down Expand Up @@ -258,15 +266,15 @@ public void handle_GetFeatureInfo(VectorDB vectordb, Request request, Response r
throw new RuntimeException("unknown CRS");
}
}

int layerEPSG = 0;
try {
layerEPSG = Integer.parseInt(vectordb.getDetails().epsg);
} catch(Exception e) {
Logger.warn(e);
}
boolean reproject = wmsEPSG > 0 && layerEPSG > 0 && wmsEPSG != layerEPSG;

String bboxParam = request.getParameter("BBOX");
Rect2d wmsRect2d = null;
if(bboxParam != null) {
Expand All @@ -286,7 +294,7 @@ public void handle_GetFeatureInfo(VectorDB vectordb, Request request, Response r
Logger.info(reqWidth + " " + reqHeight + " " + reqX + " " + reqY);
Logger.info(wmsRect2d);
Logger.info(wmsPixelRect2d);

Rect2d layerPixelRect2d = wmsPixelRect2d;
if(reproject) {
SpatialReference wmsSr = GeoUtil.getSpatialReferenceFromEPSG(wmsEPSG);
Expand Down
Loading

0 comments on commit e074cf5

Please sign in to comment.