程序是用Java Web实现, struts2文件标签和简单Js调用。
实现核心代码
1.TileUtils.java
复制代码
1 package com.xiefei.core;
2
3 import java.awt.Graphics2D;
4 import java.awt.Image;
5 import java.awt.Toolkit;
6 import java.awt.Transparency;
7 import java.awt.image.BufferedImage;
8 import java.awt.image.CropImageFilter;
9 import java.awt.image.FilteredImageSource;
10 import java.awt.image.ImageFilter;
11 import java.io.File;
12
13 import javax.imageio.ImageIO;
14
15 public class TileUtils {
16 private int minLevel;
17 private int maxLevel;
18 private int picLevel;
19 private double mercatorX;
20 private double mercatorY;
21 private String pic;
22 private String savePath;
//代码效果参考:http://www.zidongmutanji.com/bxxx/216116.html
24 public TileUtils(String pic, double mercatorX, double mercatorY,
25 String savePath) {
26 this.pic = pic;
27 this.mercatorX = mercatorX;
28 this.mercatorY = mercatorY;
29 this.savePath = savePath;
30 }
31
32 public TileUtils(String pic, int minLevel, int maxLevel, int picLevel, double mercatorX,
33 double mercatorY, String savePath) {
34 this.pic = pic;
35 this.minLevel = minLevel;
36 this.maxLevel = maxLevel;
37 this.mercatorX = mercatorX;
38 this.mercatorY = mercatorY;
39 this.savePath = savePath;
40 this.picLevel = picLevel;
41 }
42
43 public void cutterAll() throws Exception {
44 for (int i = minLevel; i <= maxLevel; i++) {
45 cutterOne(i);
46 }
47 }
48
49 public void cutterOne(int level) throws Exception {
50 //图片中心的像素坐标(pixelX,pixelY),图片中心的平面坐标即魔卡托坐标(mercatorX, mercatorY)
51 //像素坐标 = 平面坐标 Math.pow(2, level - 18)
52 double pixelX = mercatorX Math.pow(2, level - 18);
53 double pixelY = mercatorY Math.pow(2, level - 18);
54 System.out.println("pixelX : " + pixelX);
55 System.out.println("pixelY : " + pixelY);
56 BufferedImage bi = ImageIO.read(new File(pic));
57 int width = bi.getWidth();
58 int height = bi.getHeight();
59 //图片遵循原则:当前图片所属级别picLevel不缩放即像素级别相等。
60 //按照公式缩放:当前级别图片长度 = 原图片长度 Math.pow(2, level - picLevel)
61 //minX: 图片左下角X坐标
62 //minY: 图片左下角Y坐标
63 //maxX: 图片右上角X坐标
64 //maxY: 图片右上角Y坐标
65 double minX = pixelX - width Math.pow(2, level - picLevel) / 2;
66 double minY = pixelY - height Math.pow(2, level - picLevel) / 2;
67 double maxX = pixelX + width Math.pow(2, level - picLevel) / 2;
68 double maxY = pixelY + height Math.pow(2, level - picLevel) / 2;
69 System.out.println("(minX,minY) = (" + minX + ", " + minY + ")" );
70 System.out.println("(maxX,maxY) = (" + maxX + ", " + maxY + ")" );
71 int neatMinX = (int) minX / 256;
72 int remMinX = (int) minX % 256;
73 int neatMinY = (int) minY / 256;
74 int remMinY = (int) minY % 256 ;
75
76 int neatMaxX = (int) maxX / 256;
77 int remMaxX = 256 - (int) maxX % 256;
78 int neatMaxY = (int) maxY / 256;
79 int remMaxY = 256 - (int) maxY % 256;
80 //(neatMinX,neatMinY)为图片左下角最近的整数图块坐标,neatMinX到neatMaxX即当前级别下切割图块的图块坐标x
81 //(neatMaxX,neatMaxY)为图片右上角最近的整数图块坐标,neatMinY到neatMaxY即当前级别下切割图块的图块坐标y
82 System.out.println("neatMinX: " + neatMinX);
83 System.out.println("neatMaxX: " + neatMaxX);
84 System.out.println("neatMinY: " + neatMinY);
85 System.out.println("neatMaxY: " + neatMaxY);
86 System.out.println("remMinX width remMaxX : " + remMinX + " "+ width + " "+ remMaxX );
87 System.out.println("remMinY height remMaxY : " + remMinY + " " + height +" " + remMaxY );
88
89 // 扩充原图片为width height --- > (remMinX + width + remMaxX ) (remMinY +
90 // height +remMaxY)
91 int extendWidth = (neatMaxX - neatMinX + 1 ) 256;
92 int extendHeight = (neatMaxY - neatMinY + 1 ) 256;
93 System.out.println("extendWidth: " + extendWidth);
94 System.out.println("extendHeight: " + extendHeight);
95
96 BufferedImage outputImage = null;
97 Graphics2D g = bi.createGraphics();
98 BufferedImage extend = g.getDeviceConfiguration().createCompatibleImage(extendWidth, extendHeight, Transparency.TRANSLUCENT);
99 g.dispose();
100 g = extend.createGraphics();
101 g.drawImage(extend, 0, 0, extendWidth, extendHeight, null);
102 g.drawImage(bi, remMinX, remMaxY, (int) (width Math.pow(2, level - picLevel)), (int)(height Math.pow(2, level - picLevel)), null);
103 outputImage = extend;
104
105 //切割图片,共( neatMaxX - neatMinX + 1) (neatMaxY - neatMinY + 1)份 256256图片
106 String dirName = savePath.substring(0, savePath.lastIndexOf("\")) + "\tiles\" + level;
107 System.out.println("dirName : " + dirName);
//代码效果参考:http://www.zidongmutanji.com/bxxx/22470.html
109
110 File dir = new File(dirName);
111 Image image = extend.getScaledInstance(extendWidth, extendHeight, Image.SCALE_DEFAULT);
112 if(dir.exists()) {
113 System.out.println("创建目录失败!, 目录已存在!");
114 } else {
115 if(dir.mkdirs()) {
116 ImageIO.write(extend, "png", new File(dirName + savePath.substring(savePath.lastIndexOf("\"))));
117 System.out.println("savePath : " + dirName + savePath.substring(savePath.lastIndexOf("\")));
118 System.out.println("Extend success!");
119 int w = neatMaxX - neatMinX + 1;
120 int h = neatMaxY - neatMinY + 1;
121 for(int i = 0; i < w; i++) {
122 for(int j = 1; j <= h; j++) {
123 ImageFilter cropFilter = new CropImageFilter(256 i, 256 (h - j), 256, 256);
124 Image img = Toolkit.getDefaultToolkit().createImage(new FilteredImageSource(image.getSource(),cropFilter));
125 BufferedImage tag = new BufferedImage(256, 256 , BufferedImage.TYPE_INTBGR);
126 Graphics2D gs = tag.createGraphics();
127 tag = gs.getDeviceConfiguration().createCompatibleImage(256, 256, Transparency.TRANSLUCENT);
128 gs.dispose();
129 gs = tag.createGraphics();
130 gs.drawImage(img, 0, 0, null);
131 g.dispose();
132 String cropPicName = dirName + "\tile" + (neatMinX + i) + "" + (neatMinY + j - 1) + ".png";
133 ImageIO.write(tag, "png", new File(cropPicName));
134 }
135 }
136 System.out.println("切割图片成功!");
137 } else {
138 System.out.println("创建目录失败!");
139 }
140 }
141 }
142
143 }
代码的核心思想是将原图片外围拓展成256整数倍长度(最小包围),即源代码中的extendWidth extendHeight图片长度,然后再横竖切割成多个256256的瓦片图块。
2.index.jsp(切割图片主页)
1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
2 <%
3 String path = request.getContextPath();
4 String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
5 %>
6 <%@ taglib prefix="s" uri="/struts-tags" %>
7 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
8
9
10
11
12
13
14
15
16
17
18
19
45
46
47
48
51
52
53 请选择需要切图的图片来源
54 图片中心的经度坐标
55 图片中心的纬度坐标
56
57
58 最小级别
59
60 16
61 17
62 18
63 19
64
65 最大级别
66
67 16
68 17
69 18
70 19
71
72 图片所在级别
73
74 16
75 17
76 18
77 19
78
79 请选择输出目录
80
81
82
83