/** Get an image based on index numbers */ public BufferedImage getIndexedImage( int x, int y, int zoom, int cacheZoom, GMapListener listener) { if (listener != null) { if (!getGDataSource().isCached(x, y, zoom)) { listener.updateGMapPainting(); listener.updateGMapMessage(GMap.MESSAGE_DOWNLOADING); } else { listener.updateGMapMessage(GMap.MESSAGE_PAINTING); } } BufferedImage thumbImage = getGDataSource().getImage(x, y, zoom, true); if (thumbImage == null) return defaultImage; // if we dont have to paint cache, return here if (cacheZoom == (GPhysicalPoint.MIN_ZOOM - 1) || cacheZoom >= zoom) return thumbImage; BufferedImage paintedImage = new BufferedImage( GDataSource.sourceSize.width, GDataSource.sourceSize.height, BufferedImage.TYPE_INT_ARGB); Graphics2D graphics2D = paintedImage.createGraphics(); graphics2D.drawImage( thumbImage, 0, 0, GDataSource.sourceSize.width, GDataSource.sourceSize.height, null); // now lets move to painting the cache double imageNum = Math.pow(2, zoom - cacheZoom); // draw cache lines int startX = (int) (imageNum * x); int startY = (int) (imageNum * y); // get composite to restore later, set new transparent composite Composite originalComposite = graphics2D.getComposite(); graphics2D.setComposite(opacity40); // draw grid for (int i = 0; i < imageNum; i++) { for (int j = 0; j < imageNum; j++) { // points Point upperLeft = new Point( (int) (GDataSource.sourceSize.width / imageNum) * i, (int) (GDataSource.sourceSize.height / imageNum) * j); Dimension size = new Dimension( (int) (GDataSource.sourceSize.width / imageNum), (int) (GDataSource.sourceSize.height / imageNum)); // draw lines graphics2D.setColor(new Color(100, 100, 100)); graphics2D.drawLine(upperLeft.x, upperLeft.y, upperLeft.x + size.width, upperLeft.y); graphics2D.drawLine(upperLeft.x, upperLeft.y, upperLeft.x, upperLeft.y + size.height); // check if file exists if (getGDataSource().isCached(startX + i, startY + j, cacheZoom)) graphics2D.setColor(Color.RED); else graphics2D.setColor(new Color(155, 155, 155)); // shade rectangle graphics2D.fillRect(upperLeft.x, upperLeft.y, size.width, size.height); } } // restore composite graphics2D.setComposite(originalComposite); return paintedImage; }
/** Main method used to build the image based on a large number of tiles. */ public void buildImage( BufferedImage toReturn, int x, int y, int w, int h, int zoom, int cachedZoom, GMapListener listener) { // validate // if(x < 0 || y < 0 || w <= 0 || h <= 0) return getDefaultImage(w,h); // if(toReturn != null) Graphics2D g = toReturn.createGraphics(); // find index of point int xIndex = x / GDataSource.sourceSize.width; int yIndex = y / GDataSource.sourceSize.height; // find coord of our starting point int xCoord = x % GDataSource.sourceSize.width; int yCoord = y % GDataSource.sourceSize.height; // Checks for invalid xCoord and yCoord if (xCoord < 0) { xCoord = 0; } if (yCoord < 0) { yCoord = 0; } // load this index BufferedImage image = getIndexedImage(xIndex, yIndex, zoom, cachedZoom, listener); // get info about the image // Dimension imageSize = new Dimension(image.getWidth(),image.getHeight()); // Holds number of row and column images needed int rowImages; int colImages; // find the width of what we CAN paint int paintWidth = GDataSource.sourceSize.width - xCoord; int paintHeight = GDataSource.sourceSize.height - yCoord; // Calculate number of row images if ((h - paintHeight) % 256 == 0) { rowImages = 1 + (h - paintHeight) / 256; } else { rowImages = 2 + (h - paintHeight) / 256; } // Calculate number of column images if ((w - paintWidth) % 256 == 0) { colImages = 1 + (w - paintWidth) / 256; } else { colImages = 2 + (w - paintWidth) / 256; } // Overal Image coordinates int xImage = 0; int yImage = 0; // DEBUG // System.out.println(x + " " + y + " " + w + " " + h + " " + rowImages + " " + colImages); // System.out.println(); // set listener if (listener != null) listener.updateGMapTaskSize(rowImages * colImages); // a counter for the listener int completed = 0; // Iteratively loops through all CACHED images and paints them for (int row = 0; row < rowImages; row++) { for (int col = 0; col < colImages; col++) { int thisXIndex = x / GDataSource.sourceSize.width + col; int thisYIndex = y / GDataSource.sourceSize.height + row; getSpecificImage(x, y, w, h, col, row, toReturn, zoom, cachedZoom, listener, true); if (getGDataSource().isCached(thisXIndex, thisYIndex, zoom)) { if (listener != null) { listener.updateGMapCompleted(completed); completed++; } } if (listener.asynchronousGMapStopFlag()) return; } } // do the UNCACHED IMAGES NEXT for (int row = 0; row < rowImages; row++) { for (int col = 0; col < colImages; col++) { int thisXIndex = x / GDataSource.sourceSize.width + col; int thisYIndex = y / GDataSource.sourceSize.height + row; if (!getGDataSource().isCached(thisXIndex, thisYIndex, zoom)) { getSpecificImage(x, y, w, h, col, row, toReturn, zoom, cachedZoom, listener, false); if (listener != null) { listener.updateGMapCompleted(completed); completed++; if (listener.asynchronousGMapStopFlag()) return; } } } } // the dispatch to GDraw object gDraw.draw(toReturn, new GPhysicalPoint(x, y, zoom), zoom); }