private void renderGridCoverage( Graphics2D graphics, Envelope bounds, Dimension dimension, ReferencedEnvelope requestBBox, BufferedImage image) throws Exception { CoordinateReferenceSystem destinationCRS = getContext().getCRS(); Envelope envelope = bounds; if (envelope == null || envelope.isNull()) { // get the bounds from the context envelope = getContext().getImageBounds(); } Point upperLeft = getContext().worldToPixel(new Coordinate(envelope.getMinX(), envelope.getMinY())); Point bottomRight = getContext().worldToPixel(new Coordinate(envelope.getMaxX(), envelope.getMaxY())); Rectangle screenSize = new Rectangle(upperLeft); screenSize.add(bottomRight); GridCoverage2D coverage = convertImageToGridCoverage(requestBBox, image); AffineTransform worldToScreen = RendererUtilities.worldToScreenTransform(envelope, screenSize, destinationCRS); GridCoverageRenderer paint = new GridCoverageRenderer(destinationCRS, envelope, screenSize, worldToScreen); RasterSymbolizer symbolizer = CommonFactoryFinder.getStyleFactory(null).createRasterSymbolizer(); paint.paint(graphics, coverage, symbolizer); }
/** * Write world image extensions : TFW, PRJ, TAB * * @param request * @param file * @param in * @throws IOException */ private void writeWorldImageExt(WcsReaderRequest request, File file) throws IOException { String baseFilePath = file.getPath().substring(0, file.getPath().lastIndexOf('.')); // Compute image size and image transformed BBOX ReferencedEnvelope transformedBBox; AffineTransform transform; int width = -1; int height = -1; String ext = FileUtils.extension(file); try { final Iterator<ImageReader> readers = ImageIO.getImageReadersByFormatName(ext.substring(1)); while (readers.hasNext() && width < 0 && height < 0) { ImageInputStream stream = null; try { ImageReader reader = readers.next(); stream = ImageIO.createImageInputStream(file.getAbsoluteFile()); reader.setInput(stream, true, false); width = reader.getWidth(0); height = reader.getHeight(0); break; } catch (Exception e) { width = -1; height = -1; // try next reader; } finally { if (stream != null) { stream.close(); } } } transformedBBox = request.requestBbox.transform(request.responseCRS, true, 10); if (width < 0) { width = (int) Math.round(transformedBBox.getWidth() / request.crsResolution()); } if (height < 0) { height = (int) Math.round(transformedBBox.getHeight() / request.crsResolution()); } Rectangle imageSize = new Rectangle(width, height); transform = RendererUtilities.worldToScreenTransform(transformedBBox, imageSize); transform.invert(); } catch (Exception e) { throw new ExtractorException(e); } // Generate TFW TAB PRJ files createWorldFile(transform, ext, baseFilePath); createTABFile(transformedBBox, width, height, baseFilePath, ext); createPrjFile(request.responseCRS, baseFilePath); }
Integer findClosestZoom(GridSet gridSet, WMSMapContent map) { double reqScale = RendererUtilities.calculateOGCScale(bounds(map), gridSet.getTileWidth(), null); int i = 0; double error = Math.abs(gridSet.getGrid(i).getScaleDenominator() - reqScale); while (i < gridSet.getNumLevels() - 1) { Grid g = gridSet.getGrid(i + 1); double e = Math.abs(g.getScaleDenominator() - reqScale); if (e > error) { break; } else { error = e; } i++; } return Math.max(i, 0); }
public void testRead() throws Exception { URL url = TestData.url("shapes/pointtest.shp"); ShapefileDataStore ds = (ShapefileDataStore) new ShapefileDataStoreFactory().createDataStore(url); Envelope env = ds.getFeatureSource().getBounds(); CoordinateReferenceSystem crs = DefaultGeographicCRS.WGS84; MathTransform mt = CRS.findMathTransform(crs, DefaultGeographicCRS.WGS84); Rectangle rectangle = new Rectangle(300, 0, 300, 300); AffineTransform transform = RendererUtilities.worldToScreenTransform(env, rectangle); GeneralMatrix matrix = new GeneralMatrix(transform); MathTransform at = ReferencingFactoryFinder.getMathTransformFactory(null).createAffineTransform(matrix); mt = ReferencingFactoryFinder.getMathTransformFactory(null).createConcatenatedTransform(mt, at); ShapefileReader reader = new ShapefileReader(ShapefileRendererUtil.getShpFiles(ds), false, false); reader.setHandler( new org.geotools.renderer.shape.shapehandler.jts.PointHandler( reader.getHeader().getShapeType(), env, rectangle, mt, false)); Object shape = reader.nextRecord().shape(); assertNotNull(shape); assertTrue(shape instanceof Geometry); Coordinate[] coords = ((Geometry) shape).getCoordinates(); for (int i = 0; i < coords.length; i++) { Coordinate coordinate = coords[i]; assertNotNull(coordinate); } int i = 0; while (reader.hasNext()) { i++; shape = reader.nextRecord().shape(); assertNotNull(shape); assertTrue(shape instanceof Geometry); } assertEquals(ds.getFeatureSource().getCount(Query.ALL) - 1, i); }
/** * Takes a GetLegendGraphicRequest and produces a BufferedImage that then can be used by a * subclass to encode it to the appropriate output format. * * @param request the "parsed" request, where "parsed" means that it's values are already * validated so this method must not take care of verifying the requested layer exists and the * like. * @throws ServiceException if there are problems creating a "sample" feature instance for the * FeatureType <code>request</code> returns as the required layer (which should not occur). */ public BufferedImage buildLegendGraphic(GetLegendGraphicRequest request) throws ServiceException { // list of images to be rendered for the layers (more than one if // a layer group is given) List<RenderedImage> layersImages = new ArrayList<RenderedImage>(); List<LegendRequest> layers = request.getLegends(); // List<FeatureType> layers=request.getLayers(); // List<Style> styles=request.getStyles(); // List<String> rules=request.getRules(); boolean forceLabelsOn = false; boolean forceLabelsOff = false; if (request.getLegendOptions().get("forceLabels") instanceof String) { String forceLabelsOpt = (String) request.getLegendOptions().get("forceLabels"); if (forceLabelsOpt.equalsIgnoreCase("on")) { forceLabelsOn = true; } else if (forceLabelsOpt.equalsIgnoreCase("off")) { forceLabelsOff = true; } } boolean forceTitlesOff = false; if (request.getLegendOptions().get("forceTitles") instanceof String) { String forceTitlesOpt = (String) request.getLegendOptions().get("forceTitles"); if (forceTitlesOpt.equalsIgnoreCase("off")) { forceTitlesOff = true; } } for (LegendRequest legend : layers) { FeatureType layer = legend.getFeatureType(); // style and rule to use for the current layer Style gt2Style = legend.getStyle(); if (gt2Style == null) { throw new NullPointerException("request.getStyle()"); } // get rule corresponding to the layer index // normalize to null for NO RULE String ruleName = legend.getRule(); // was null // width and height, we might have to rescale those in case of DPI usage int w = request.getWidth(); int h = request.getHeight(); // apply dpi rescale double dpi = RendererUtilities.getDpi(request.getLegendOptions()); double standardDpi = RendererUtilities.getDpi(Collections.emptyMap()); if (dpi != standardDpi) { double scaleFactor = dpi / standardDpi; w = (int) Math.round(w * scaleFactor); h = (int) Math.round(h * scaleFactor); DpiRescaleStyleVisitor dpiVisitor = new DpiRescaleStyleVisitor(scaleFactor); dpiVisitor.visit(gt2Style); gt2Style = (Style) dpiVisitor.getCopy(); } // apply UOM rescaling if we have a scale if (request.getScale() > 0) { double pixelsPerMeters = RendererUtilities.calculatePixelsPerMeterRatio( request.getScale(), request.getLegendOptions()); UomRescaleStyleVisitor rescaleVisitor = new UomRescaleStyleVisitor(pixelsPerMeters); rescaleVisitor.visit(gt2Style); gt2Style = (Style) rescaleVisitor.getCopy(); } boolean strict = request.isStrict(); final boolean transparent = request.isTransparent(); RenderedImage titleImage = null; // if we have more than one layer, we put a title on top of each layer legend if (layers.size() > 1 && !forceTitlesOff) { titleImage = getLayerTitle(legend, w, h, transparent, request); } // Check for rendering transformation boolean hasVectorTransformation = false; boolean hasRasterTransformation = false; List<FeatureTypeStyle> ftsList = gt2Style.featureTypeStyles(); for (int i = 0; i < ftsList.size(); i++) { FeatureTypeStyle fts = ftsList.get(i); Expression exp = fts.getTransformation(); if (exp != null) { ProcessFunction processFunction = (ProcessFunction) exp; Name processName = processFunction.getProcessName(); Map<String, Parameter<?>> outputs = Processors.getResultInfo(processName, null); if (outputs.isEmpty()) { continue; } Parameter<?> output = outputs.values().iterator().next(); // we assume there is only one output if (SimpleFeatureCollection.class.isAssignableFrom(output.getType())) { hasVectorTransformation = true; break; } else if (GridCoverage2D.class.isAssignableFrom(output.getType())) { hasRasterTransformation = true; break; } } } final boolean buildRasterLegend = (!strict && layer == null && LegendUtils.checkRasterSymbolizer(gt2Style)) || (LegendUtils.checkGridLayer(layer) && !hasVectorTransformation) || hasRasterTransformation; // Just checks LegendInfo currently, should check gtStyle final boolean useProvidedLegend = layer != null && legend.getLayerInfo() != null; RenderedImage legendImage = null; if (useProvidedLegend) { legendImage = getLayerLegend(legend, w, h, transparent, request); } if (buildRasterLegend) { final RasterLayerLegendHelper rasterLegendHelper = new RasterLayerLegendHelper(request, gt2Style, ruleName); final BufferedImage image = rasterLegendHelper.getLegend(); if (image != null) { if (titleImage != null) { layersImages.add(titleImage); } layersImages.add(image); } } else if (useProvidedLegend && legendImage != null) { if (titleImage != null) { layersImages.add(titleImage); } layersImages.add(legendImage); } else { final Feature sampleFeature; if (layer == null || hasVectorTransformation) { sampleFeature = createSampleFeature(); } else { sampleFeature = createSampleFeature(layer); } final FeatureTypeStyle[] ftStyles = gt2Style.featureTypeStyles().toArray(new FeatureTypeStyle[0]); final double scaleDenominator = request.getScale(); final Rule[] applicableRules; if (ruleName != null) { Rule rule = LegendUtils.getRule(ftStyles, ruleName); if (rule == null) { throw new ServiceException( "Specified style does not contains a rule named " + ruleName); } applicableRules = new Rule[] {rule}; } else { applicableRules = LegendUtils.getApplicableRules(ftStyles, scaleDenominator); } final NumberRange<Double> scaleRange = NumberRange.create(scaleDenominator, scaleDenominator); final int ruleCount = applicableRules.length; /** * A legend graphic is produced for each applicable rule. They're being held here until the * process is done and then painted on a "stack" like legend. */ final List<RenderedImage> legendsStack = new ArrayList<RenderedImage>(ruleCount); final SLDStyleFactory styleFactory = new SLDStyleFactory(); double minimumSymbolSize = MINIMUM_SYMBOL_SIZE; // get minSymbolSize from LEGEND_OPTIONS, if defined if (request.getLegendOptions().get("minSymbolSize") instanceof String) { String minSymbolSizeOpt = (String) request.getLegendOptions().get("minSymbolSize"); try { minimumSymbolSize = Double.parseDouble(minSymbolSizeOpt); } catch (NumberFormatException e) { throw new IllegalArgumentException("Invalid minSymbolSize value: should be a number"); } } // calculate the symbols rescaling factor necessary for them to be // drawn inside the icon box double symbolScale = calcSymbolScale(w, h, layer, sampleFeature, applicableRules, minimumSymbolSize); for (int i = 0; i < ruleCount; i++) { final RenderedImage image = ImageUtils.createImage(w, h, (IndexColorModel) null, transparent); final Map<RenderingHints.Key, Object> hintsMap = new HashMap<RenderingHints.Key, Object>(); final Graphics2D graphics = ImageUtils.prepareTransparency( transparent, LegendUtils.getBackgroundColor(request), image, hintsMap); graphics.setRenderingHint( RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); Feature sample = getSampleFeatureForRule(layer, sampleFeature, applicableRules[i]); FilterFactory ff = CommonFactoryFinder.getFilterFactory(); final Symbolizer[] symbolizers = applicableRules[i].getSymbolizers(); final GraphicLegend graphic = applicableRules[i].getLegend(); // If this rule has a legend graphic defined in the SLD, use it if (graphic != null) { if (this.samplePoint == null) { Coordinate coord = new Coordinate(w / 2, h / 2); try { this.samplePoint = new LiteShape2(geomFac.createPoint(coord), null, null, false); } catch (Exception e) { this.samplePoint = null; } } shapePainter.paint(graphics, this.samplePoint, graphic, scaleDenominator, false); } else { for (int sIdx = 0; sIdx < symbolizers.length; sIdx++) { Symbolizer symbolizer = symbolizers[sIdx]; if (symbolizer instanceof RasterSymbolizer) { // skip it } else { // rescale symbols if needed if (symbolScale > 1.0 && symbolizer instanceof PointSymbolizer) { PointSymbolizer pointSymbolizer = cloneSymbolizer(symbolizer); if (pointSymbolizer.getGraphic() != null) { double size = getPointSymbolizerSize(sample, pointSymbolizer, Math.min(w, h) - 4); pointSymbolizer .getGraphic() .setSize(ff.literal(size / symbolScale + minimumSymbolSize)); symbolizer = pointSymbolizer; } } Style2D style2d = styleFactory.createStyle(sample, symbolizer, scaleRange); LiteShape2 shape = getSampleShape(symbolizer, w, h); if (style2d != null) { shapePainter.paint(graphics, shape, style2d, scaleDenominator); } } } } if (image != null && titleImage != null) { layersImages.add(titleImage); titleImage = null; } legendsStack.add(image); graphics.dispose(); } // JD: changed legend behavior, see GEOS-812 // this.legendGraphic = scaleImage(mergeLegends(legendsStack), request); BufferedImage image = mergeLegends(legendsStack, applicableRules, request, forceLabelsOn, forceLabelsOff); if (image != null) { layersImages.add(image); } } } // all legend graphics are merged if we have a layer group BufferedImage finalLegend = mergeLegends(layersImages, null, request, forceLabelsOn, forceLabelsOff); if (finalLegend == null) { throw new IllegalArgumentException("no legend passed"); } return finalLegend; }
/** * Gets the current scale of the map. The calculation happens according to OGC specification. * * @return The scale */ public Double getScale() { return RendererUtilities.calculateOGCScale(this.getDisplayArea(), this.getWidth(), null); }
public void render(Graphics2D g2d, IProgressMonitor monitor) throws RenderException { try { final IRenderContext currentContext = getContext(); currentContext.setStatus(ILayer.WAIT); CoordinateReferenceSystem destinationCRS = currentContext.getCRS(); // the bounds of the visible area in world coordinates // get the envelope and the screen extent Envelope envelope = getRenderBounds(); if (envelope == null || envelope.isNull()) { envelope = context.getImageBounds(); } Point upperLeft = currentContext.worldToPixel(new Coordinate(envelope.getMinX(), envelope.getMinY())); Point bottomRight = currentContext.worldToPixel(new Coordinate(envelope.getMaxX(), envelope.getMaxY())); Rectangle screenSize = new Rectangle(upperLeft); screenSize.add(bottomRight); final IGeoResource resource = getContext().getGeoResource(); if (resource == null || !resource.canResolve(JGrassMapGeoResource.class)) { return; } JGrassMapGeoResource grassMapGeoResource = resource.resolve(JGrassMapGeoResource.class, monitor); JGrassRegion fileWindow = new JGrassRegion(grassMapGeoResource.getFileWindow()); JGrassMapsetGeoResource parent = (JGrassMapsetGeoResource) grassMapGeoResource.parent(new NullProgressMonitor()); CoordinateReferenceSystem grassCrs = parent.getLocationCrs(); JGrassRegion screenDrawWindow = new JGrassRegion( envelope.getMinX(), envelope.getMaxX(), envelope.getMinY(), envelope.getMaxY(), fileWindow.getRows(), fileWindow.getCols()); // to intersect with the data window, we transform the screen window JGrassRegion reprojectedScreenDrawWindow = screenDrawWindow; if (!CRS.equalsIgnoreMetadata(destinationCRS, grassCrs)) { reprojectedScreenDrawWindow = screenDrawWindow.reproject(destinationCRS, grassCrs, true); } /* * if the map is not visible, do not render it */ // JGrassRegion fileWindow = grassMapGeoResource.getFileWindow(); Rectangle2D.Double fileRectDouble = fileWindow.getRectangle(); Double reprojScreenRectangle = reprojectedScreenDrawWindow.getRectangle(); if (!reprojScreenRectangle.intersects(fileRectDouble)) { getContext().setStatus(ILayer.DONE); getContext().setStatusMessage(THE_MAP_IS_OUTSIDE_OF_THE_VISIBLE_REGION); System.out.println(THE_MAP_IS_OUTSIDE_OF_THE_VISIBLE_REGION); return; } /* * we will draw only the intersection of the map in the display system = part of visible map */ Rectangle2D drawMapRectangle = reprojectedScreenDrawWindow.getRectangle().createIntersection(fileRectDouble); // Rectangle2D drawMapRectangle = fileRectDouble.getBounds2D(); // resolution is that of the file window double ewRes = fileWindow.getWEResolution(); double nsRes = fileWindow.getNSResolution(); if (fileRectDouble.getWidth() < ewRes || fileRectDouble.getHeight() < nsRes) { getContext().setStatus(ILayer.DONE); getContext().setStatusMessage(THE_MAP_IS_OUTSIDE_OF_THE_VISIBLE_REGION); System.out.println(THE_MAP_IS_OUTSIDE_OF_THE_VISIBLE_REGION); return; } MathTransform transform = CRS.findMathTransform(destinationCRS, grassCrs, true); Coordinate pixelSize = getContext().getPixelSize(); Coordinate c1 = new Coordinate(envelope.getMinX(), envelope.getMinY()); Coordinate c2 = new Coordinate(envelope.getMinX() + pixelSize.x, envelope.getMinY() + pixelSize.y); Envelope envy = new Envelope(c1, c2); Envelope envyTrans = JTS.transform(envy, transform); pixelSize = new Coordinate(envyTrans.getWidth(), envyTrans.getHeight()); /* * if the resolution is higher of that of the screen, it doesn't make much sense to draw it * all. So for visualization we just use the screen resolution to do things faster. */ if (ewRes < pixelSize.x) { ewRes = pixelSize.x; } if (nsRes < pixelSize.y) { nsRes = pixelSize.y; } fileWindow.setNSResolution(nsRes); fileWindow.setWEResolution(ewRes); nsRes = fileWindow.getNSResolution(); ewRes = fileWindow.getWEResolution(); /* * redefine the region of the map to be drawn */ /* * snap the screen to fit into the active region grid. This is mandatory for the exactness * of the query of the pixels (ex. d.what.rast). */ JGrassRegion activeWindow = grassMapGeoResource.getActiveWindow(); Coordinate minXY = JGrassRegion.snapToNextHigherInRegionResolution( drawMapRectangle.getMinX(), drawMapRectangle.getMinY(), activeWindow); Coordinate maxXY = JGrassRegion.snapToNextHigherInRegionResolution( drawMapRectangle.getMaxX(), drawMapRectangle.getMaxY(), activeWindow); JGrassRegion drawMapRegion = new JGrassRegion(minXY.x, maxXY.x, minXY.y, maxXY.y, ewRes, nsRes); // JGrassRegion drawMapRegion = new JGrassRegion(drawMapRectangle.getMinX(), // drawMapRectangle.getMaxX(), drawMapRectangle.getMinY(), drawMapRectangle // .getMaxY(), ewRes, nsRes); JGrassMapEnvironment grassMapEnvironment = grassMapGeoResource.getjGrassMapEnvironment(); GridCoverage2D coverage = JGrassCatalogUtilities.getGridcoverageFromGrassraster(grassMapEnvironment, drawMapRegion); coverage = coverage.view(ViewType.RENDERED); if (coverage != null) { // setting rendering hints RenderingHints hints = new RenderingHints(Collections.EMPTY_MAP); hints.add( new RenderingHints(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_SPEED)); hints.add( new RenderingHints(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_DISABLE)); hints.add( new RenderingHints( RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_SPEED)); hints.add( new RenderingHints( RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_SPEED)); hints.add( new RenderingHints( RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR)); hints.add( new RenderingHints( RenderingHints.KEY_STROKE_CONTROL, RenderingHints.VALUE_STROKE_PURE)); hints.add( new RenderingHints( RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_OFF)); hints.add(new RenderingHints(JAI.KEY_INTERPOLATION, new InterpolationNearest())); g2d.addRenderingHints(hints); final TileCache tempCache = JAI.createTileCache(); tempCache.setMemoryCapacity(16 * 1024 * 1024); tempCache.setMemoryThreshold(1.0f); hints.add(new RenderingHints(JAI.KEY_TILE_CACHE, tempCache)); // draw AffineTransform worldToScreen = RendererUtilities.worldToScreenTransform(envelope, screenSize, destinationCRS); final GridCoverageRenderer paint = new GridCoverageRenderer(destinationCRS, envelope, screenSize, worldToScreen, hints); RasterSymbolizer rasterSymbolizer = CommonFactoryFinder.getStyleFactory(null).createRasterSymbolizer(); paint.paint(g2d, coverage, rasterSymbolizer); tempCache.flush(); // IBlackboard blackboard = context.getMap().getBlackboard(); // String legendString = coverageReader.getLegendString(); // String name = grassMapGeoResource.getTitle(); // blackboard.putString(JGrassMapGeoResource.READERID + "#" + name, legendString); } } catch (Exception e) { e.printStackTrace(); } finally { getContext().setStatus(ILayer.DONE); getContext().setStatusMessage(null); } }
/** * @see net.refractions.udig.render.internal.wmsc.basic#renderTile(Graphics2D graphics, WMTTile * tile, CoordinateReferenceSystem crs, RasterSymbolizer style) * @param graphics * @param tile * @param style * @throws FactoryException * @throws TransformException * @throws RenderException */ private void renderTile( Graphics2D graphics, WMTTile tile, RasterSymbolizer style, WMTRenderJob renderJob) throws Exception { if (tile == null || tile.getBufferedImage() == null) { return; } // create a gridcoverage from the tile image GridCoverageFactory factory = new GridCoverageFactory(); // get the tile bounds in the CRS the tiles were drawn in ReferencedEnvelope tileBndsMercatorRef = renderJob.projectTileToTileProjectedCrs(tile.getExtent()); GridCoverage2D coverage = (GridCoverage2D) factory.create( "GridCoverage", tile.getBufferedImage(), tileBndsMercatorRef); // $NON-NLS-1$ Envelope2D coveragebounds = coverage.getEnvelope2D(); // bounds of tile ReferencedEnvelope bnds = new ReferencedEnvelope( coveragebounds.getMinX(), coveragebounds.getMaxX(), coveragebounds.getMinY(), coveragebounds.getMaxY(), renderJob.getCrsTilesProjected()); // reproject tile bounds to map CRS bnds = renderJob.projectTileProjectedToMapCrs(bnds); // determine screen coordinates of tiles Point upperLeft = getContext().worldToPixel(new Coordinate(bnds.getMinX(), bnds.getMinY())); Point bottomRight = getContext().worldToPixel(new Coordinate(bnds.getMaxX(), bnds.getMaxY())); Rectangle tileSize = new Rectangle(upperLeft); tileSize.add(bottomRight); // render try { CoordinateReferenceSystem crs = getContext().getCRS(); AffineTransform worldToScreen = RendererUtilities.worldToScreenTransform(bnds, tileSize, crs); GridCoverageRenderer paint = new GridCoverageRenderer(crs, bnds, tileSize, worldToScreen); paint.paint(graphics, coverage, style); if (TESTING) { // if(true){ /* for testing draw border around tiles */ graphics.setColor(Color.BLACK); graphics.drawLine( (int) tileSize.getMinX(), (int) tileSize.getMinY(), (int) tileSize.getMinX(), (int) tileSize.getMaxY()); graphics.drawLine( (int) tileSize.getMinX(), (int) tileSize.getMinY(), (int) tileSize.getMaxX(), (int) tileSize.getMinY()); graphics.drawLine( (int) tileSize.getMaxX(), (int) tileSize.getMinY(), (int) tileSize.getMaxX(), (int) tileSize.getMaxY()); graphics.drawLine( (int) tileSize.getMinX(), (int) tileSize.getMaxY(), (int) tileSize.getMaxX(), (int) tileSize.getMaxY()); graphics.drawString( tile.getId(), ((int) tileSize.getMaxX() - 113), ((int) tileSize.getMaxY() - 113)); } } catch (Throwable t) { WMTPlugin.log("Error Rendering tile. Painting Tile " + tile.getId(), t); // $NON-NLS-1$ } }