Statistics
| Revision:

gvsig-raster / org.gvsig.raster.cache / trunk / org.gvsig.raster.cache / org.gvsig.raster.cache.lib.impl / src / main / java / org / gvsig / raster / cache / tile / impl / layer / TiledLayerImpl.java @ 980

History | View | Annotate | Download (8.48 KB)

1
/* gvSIG. Geographic Information System of the Valencian Government
2
 *
3
 * Copyright (C) 2007-2008 Infrastructures and Transports Department
4
 * of the Valencian Government (CIT)
5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 2
9
 * of the License, or (at your option) any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
20
 *
21
 */
22
package org.gvsig.raster.cache.tile.impl.layer;
23

    
24
import java.io.File;
25
import java.security.MessageDigest;
26
import java.security.NoSuchAlgorithmException;
27
import java.util.ArrayList;
28

    
29
import org.gvsig.raster.cache.tile.Tile;
30
import org.gvsig.raster.cache.tile.disk.ITileFileSystemStrategy;
31
import org.gvsig.raster.cache.tile.exception.TileGettingException;
32
import org.gvsig.raster.cache.tile.impl.TileCacheImpl;
33
import org.gvsig.raster.cache.tile.impl.TileImpl;
34
import org.gvsig.raster.cache.tile.impl.memory.LRUTileCache;
35
import org.gvsig.raster.cache.tile.impl.pool.ThreadPool;
36
import org.gvsig.raster.cache.tile.layer.TiledLayer;
37
import org.gvsig.raster.cache.tile.provider.CacheStruct;
38
import org.gvsig.raster.cache.tile.provider.TileListener;
39
import org.gvsig.raster.cache.tile.provider.TileServer;
40

    
41
/**
42
 * Main implementation for the tile cache
43
 *
44
 * @author Nacho Brodin (nachobrodin@gmail.com)
45
 */
46
public class TiledLayerImpl implements TiledLayer {
47
        private TileServer                  provider          = null;
48
        private TileCacheImpl               tileCache         = null;
49
        private String                      basePath          = null;
50
        private String                      pathToDirLayer    = null;
51
        private String                      idLayer           = null;
52
        //private LRUTileCache                memoryCache = null;
53
        private ThreadPool                  pool              = null;
54
        private ITileFileSystemStrategy     strategy          = null;
55
        
56
        public TiledLayerImpl(TileCacheImpl tileCache, 
57
                        TileServer provider, 
58
                        ITileFileSystemStrategy strategy, 
59
                        LRUTileCache memCache) {
60
                this.tileCache = tileCache;
61
                this.provider = provider;
62
                this.basePath = tileCache.getBaseDirectory();
63
                //this.memoryCache = memCache;
64
                this.strategy = strategy;
65
        }
66
        
67
        public ThreadPool getThreadPool() {
68
                if(pool == null)
69
                        pool = new ThreadPool(false);
70
                return pool;
71
        }
72
        
73
        /**
74
         * Updates the string with the base directory
75
         * @param dir
76
         */
77
        public void updateBaseDirectory(String dir) {
78
                this.basePath = dir;
79
                this.pathToDirLayer = null;
80
        }
81
        
82
        public Tile getTile(Tile tile) throws TileGettingException {
83
                assignPathTile(tile);
84
                
85
                //Busca en memoria
86
                /*if(memoryCache != null) {
87
                        buf = memoryCache.get(tile.getId());
88
                        if(buf != null)
89
                                return buf;
90
                }*/
91
                
92
                //Busca en disco
93
                provider.getDownloader().readTileFromDisk(tile);
94
                if(tile.dataIsLoaded()) {
95
                        if(!tile.isCorrupt())
96
                                return tile;
97
                        return 
98
                                null;
99
                }
100
                
101
                
102
                //Lo obtiene y lo carga desde disco
103
                provider.getDownloader().downloadTile(tile);
104
                tileCache.updateSize(tile.getFile().length());
105
                tileCache.saveSize();
106
                if(!tile.isCorrupt())
107
                        return tile;
108
                return 
109
                        null;
110
        }
111
        
112
        /*
113
         * (non-Javadoc)
114
         * @see org.gvsig.raster.cache.tile.layer.TiledLayer#getTiles(java.util.ArrayList, org.gvsig.raster.cache.tile.provider.TileListener)
115
         */
116
        public void getTiles(ArrayList<Tile> tiles, TileListener listener) throws TileGettingException {
117
                org.gvsig.raster.cache.tile.impl.pool.TilePipe pipe = new org.gvsig.raster.cache.tile.impl.pool.TilePipe();
118

    
119
                //If a tile is in memory or in disk then this will be returned 
120
                //else this will be gotten from the provider
121

    
122
                int nTilesToDownload = 0;
123
                for (int i = 0; i < tiles.size(); i++) {
124
                        Tile tile = tiles.get(i);
125
                        assignPathTile(tile);
126
                        
127
                        /*if(memoryCache != null) { //Busca en memoria
128
                                buf = memoryCache.get(tile.getId());
129
                                if(buf != null) {
130
                                        tile.setData(new Object[]{buf});
131
                                        listener.tileReady(tile);
132
                                        continue;
133
                                }
134
                        }*/
135
                        
136
                        provider.getDownloader().readTileFromDisk(tile);
137
                        if(tile.dataIsLoaded()) {
138
                                listener.tileReady(tile);
139
                                continue;
140
                        }
141
                        
142
                        //Lo obtiene desde el proveedor
143
                        ((TileImpl)tile).setSharedPipe(pipe);
144
                        ((TileImpl)tile).setDownloader(provider.getDownloader());
145
                        getThreadPool().addTask(tile);
146
                        nTilesToDownload ++;
147
                }
148

    
149
                for (int i = 0; i < nTilesToDownload; i++) {
150
                        Tile tile = pipe.getTile();
151
                        tileCache.updateSize(tile.getFile().length());
152
                        listener.tileReady(tile);
153
                }
154

    
155
                tileCache.saveSize();
156
        }
157

    
158
        /*
159
         * (non-Javadoc)
160
         * @see org.gvsig.raster.cache.tile.layer.TiledLayer#getBaseLayerDirectory()
161
         */
162
        public String getBaseLayerDirectory() {
163
                CacheStruct struct = provider.getStruct();
164
                int maxLevel = struct.getNumberOfLevels() - 1;
165
                if(pathToDirLayer == null) {
166
                        try {
167
                                MessageDigest md = java.security.MessageDigest.getInstance("MD5");
168
                                md.update(new String(struct.getServerURL() + 
169
                                                struct.getLayerName() + 
170
                                                struct.getFileSuffix() +
171
                                                struct.getWorldWidthOfTileMatrixByLevel(maxLevel) + 
172
                                                struct.getWorldHeightOfTileMatrixByLevel(maxLevel) + 
173
                                                struct.getTileSizeByLevel(maxLevel)[0] +
174
                                                struct.getTileSizeByLevel(maxLevel)[1] +
175
                                                struct.getNumberOfLevels() + 
176
                                                struct.getEPSG() + 
177
                                                struct.getFileSize()).getBytes());
178
                                idLayer = convertToHex(md.digest());
179
                        } catch (NoSuchAlgorithmException e) {
180
                                idLayer = new String(struct.getServerURL() + 
181
                                                struct.getLayerName() +
182
                                                struct.getFileSuffix() +
183
                                                struct.getWorldWidthOfTileMatrixByLevel(maxLevel) + 
184
                                                struct.getWorldHeightOfTileMatrixByLevel(maxLevel) + 
185
                                                struct.getTileSizeByLevel(maxLevel)[0] +
186
                                                struct.getTileSizeByLevel(maxLevel)[1] +
187
                                                struct.getNumberOfLevels() + 
188
                                                struct.getEPSG() +
189
                                                struct.getFileSize());
190
                        }
191
                        int begin = struct.getLayerName().lastIndexOf(File.separator) + 1;
192
                        int end = struct.getLayerName().lastIndexOf(".");
193
                        end = end < 0 ? struct.getLayerName().length() : end;
194
                        String name = struct.getLayerName().substring(begin, end);
195
                        idLayer = idLayer + "-" + name;
196
                        pathToDirLayer = basePath + File.separator + idLayer;
197
                }
198
                return pathToDirLayer;
199
        }
200
        
201
        /*
202
         * (non-Javadoc)
203
         * @see org.gvsig.raster.cache.tile.layer.TiledLayer#getID()
204
         */
205
        public String getID() {
206
                if(idLayer == null)
207
                        getBaseLayerDirectory();
208
                return idLayer;
209
        }
210
        
211
        /*
212
         * (non-Javadoc)
213
         * @see org.gvsig.raster.cache.tile.layer.TiledLayer#delete()
214
         */
215
        public long delete() {
216
                File f = new File(getBaseLayerDirectory());
217
                if(f.exists() && f.isDirectory()) {
218
                        return deleteDirectory(f);
219
                }
220
                return 0;
221
        }
222
        
223
        /**
224
         * Deletes a directory removing first files inside.
225
         * @param f
226
         */
227
        private long deleteDirectory(File f) {
228
                long size = 0;
229
                File[] files = f.listFiles();
230
                for (int i = 0; i < files.length; i++) {
231
                        if (files[i].isDirectory()) {
232
                                size += deleteDirectory(files[i]);
233
                        } else {
234
                                size += files[i].length();
235
                        }
236
                        files[i].delete();
237
                }
238
                return size;
239
        }
240
        
241
        /**
242
         * Assigns the path to a tile
243
         * @param tile
244
         * @return
245
         */
246
        public String assignPathTile(Tile tile) {
247
                String file = getBaseLayerDirectory() + 
248
                                          File.separator + 
249
                                          strategy.getRelativeToLayerDirTilePath(tile.getRow(), 
250
                                                          tile.getCol(), 
251
                                                          tile.getLevel(),
252
                                                          tile.getVariable(),
253
                                                          tile.getZ(),
254
                                                          tile.getTimeInstant()
255
                                                          ) +
256
                      "." + provider.getFileSuffix();
257
                String path = file.substring(0, file.lastIndexOf(File.separator));
258
                File f = new File(path);
259
                if(!f.exists())
260
                        f.mkdirs();
261
                tile.setFile(new File(file));
262
                return file;
263
        }
264
        
265
        /**
266
         * Converts an array of bytes to hexadecimal string
267
         * @param data
268
         * @return
269
         */
270
        private String convertToHex(byte[] data) { 
271
        StringBuffer buf = new StringBuffer();
272
        for (int i = 0; i < data.length; i++) { 
273
            int halfbyte = (data[i] >>> 4) & 0x0F;
274
            int two_halfs = 0;
275
            do { 
276
                if ((0 <= halfbyte) && (halfbyte <= 9)) 
277
                    buf.append((char) ('0' + halfbyte));
278
                else 
279
                    buf.append((char) ('a' + (halfbyte - 10)));
280
                halfbyte = data[i] & 0x0F;
281
            } while(two_halfs++ < 1);
282
        } 
283
        return buf.toString();
284
    }
285

    
286
}