Statistics
| Revision:

root / trunk / libraries / libRaster / src / org / gvsig / raster / dataset / io / EcwDriver.java @ 12383

History | View | Annotate | Download (27.7 KB)

1
/* gvSIG. Sistema de Informaci?n Geogr?fica de la Generalitat Valenciana
2
 *
3
 * Copyright (C) 2007 IVER T.I. and Generalitat Valenciana.
4
 *
5
 * This program is free software; you can redistribute it and/or
6
 * modify it under the terms of the GNU General Public License
7
 * as published by the Free Software Foundation; either version 2
8
 * of the License, or (at your option) any later version.
9
 *
10
 * This program is distributed in the hope that it will be useful,
11
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 * GNU General Public License for more details.
14
 *
15
 * You should have received a copy of the GNU General Public License
16
 * along with this program; if not, write to the Free Software
17
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307,USA.
18
 */
19
package org.gvsig.raster.dataset.io;
20

    
21
import java.awt.geom.NoninvertibleTransformException;
22
import java.awt.geom.Point2D;
23
import java.io.File;
24
import java.util.Vector;
25

    
26
import org.cresques.cts.ICoordTrans;
27
import org.cresques.cts.IProjection;
28
import org.gvsig.raster.dataset.BandList;
29
import org.gvsig.raster.dataset.FileNotOpenException;
30
import org.gvsig.raster.dataset.GeoInfo;
31
import org.gvsig.raster.dataset.IBuffer;
32
import org.gvsig.raster.dataset.InvalidSetViewException;
33
import org.gvsig.raster.dataset.NotSupportedExtensionException;
34
import org.gvsig.raster.dataset.RasterDataset;
35
import org.gvsig.raster.dataset.RasterDriverException;
36
import org.gvsig.raster.dataset.io.rmf.ParsingException;
37
import org.gvsig.raster.datastruct.Extent;
38
import org.gvsig.raster.datastruct.Transparency;
39
import org.gvsig.raster.util.RasterUtilities;
40
import org.gvsig.raster.util.extensionPoints.ExtensionPoints;
41
import org.gvsig.raster.util.extensionPoints.ExtensionPointsSingleton;
42

    
43
import com.ermapper.ecw.JNCSException;
44
import com.ermapper.ecw.JNCSFile;
45
import com.ermapper.ecw.JNCSFileNotOpenException;
46
import com.ermapper.ecw.JNCSInvalidSetViewException;
47
import com.ermapper.ecw.JNCSProgressiveUpdate;
48

    
49

    
50
/**
51
 * Driver de Ecw
52
 * 
53
 * @author Nacho Brodin (nachobrodin@gmail.com)
54
 */
55
public class EcwDriver extends RasterDataset implements JNCSProgressiveUpdate {
56
    
57
        private JNCSFile                                 file = null;
58
        private int                                         currentFullWidth = -1;
59
        private int                                         currentFullHeight = -1;
60
        /**
61
         * Contorno en coordenadas geogr?ficas sin rotaci?n aplicada. Esto es util para poder
62
         * calcular los pixeles necesarios que se van a leer del raster.
63
         */
64
        public Contour                                        bBoxWithoutRot = new Contour();
65
        /**
66
         * Estado de transparencia del raster.
67
         */
68
        protected Transparency                  fileTransparency = null;
69
        
70
        /**
71
         * Extent de la ventana seleccionada
72
         */
73
    private Extent                                        viewRequest = null;
74
        private boolean                                 readCancel = false;
75
    
76
        public static void register() {
77
                ExtensionPoints extensionPoints = ExtensionPointsSingleton.getInstance();
78
                extensionPoints.add("RasterReader", "ecw", EcwDriver.class);
79
                extensionPoints.add("RasterReader", "jp2", EcwDriver.class);
80
        }
81
                
82
        class Contour extends Vector {
83
                final private static long serialVersionUID = 0;
84
                public double minX = Double.MAX_VALUE, minY = Double.MAX_VALUE;
85
                public double maxX = -Double.MAX_VALUE, maxY = -Double.MAX_VALUE;
86
                public Contour() {
87
                        super();
88
                }
89
                public void add(Point2D pt) {
90
                        super.add(pt);
91
                        if (pt.getX() > maxX) maxX = pt.getX();
92
                        if (pt.getX() < minX) minX = pt.getX();
93
                        if (pt.getY() > maxY) maxY = pt.getY();
94
                        if (pt.getY() < minY) minY = pt.getY();
95
                }
96
        }
97
        
98
        /**
99
         * Constructor. Abre el dataset.
100
         * @param proj Proyecci?n
101
         * @param fName Nombre del fichero ecw
102
         * @throws NotSupportedExtensionException
103
         */
104
        public EcwDriver(IProjection proj, Object param)throws NotSupportedExtensionException {
105
                 super(proj, ((String)param));
106
                 setParam(param);
107
             extent = new Extent();
108
             try {
109

    
110
                     if (!new File(((String)param)).exists() && !((String)param).startsWith("ecwp:"))
111
                             throw new NotSupportedExtensionException("Extension not supported");
112

    
113
                     file = new JNCSFile(((String)param), false);
114
                     load();
115
                     //readGeoInfo(fName);
116
                     bandCount = file.numBands;
117
                     getTransparencyDatasetStatus();
118
                     setDataType(IBuffer.TYPE_BYTE);
119
                     
120
                     super.init();
121
                     
122
                     try {
123
                             loadFromRmf(getRmfBlocksManager());
124
                     } catch (ParsingException e) {
125
                             //No lee desde rmf
126
                     }        
127
                         
128
             } catch (Exception e) {
129
                     throw new NotSupportedExtensionException("Extension not supported");
130
             }
131
    }
132

    
133
        /**
134
     * Carga un ECW.
135
     * @param fname
136
     */
137
    public GeoInfo load() {
138
        double minX;
139
        double minY;
140
        double maxX;
141
        double maxY;
142

    
143
        if(file.cellIncrementY > 0)
144
                file.cellIncrementY = -file.cellIncrementY;
145
        
146
        minX = file.originX;
147
        maxY = file.originY;
148
        maxX = file.originX +
149
               ((double) (file.width) * file.cellIncrementX);
150
        minY = file.originY +
151
               ((double) (file.height) * file.cellIncrementY);
152
        
153
        currentFullWidth = file.width;
154
        currentFullHeight = file.height;
155
        boundingBoxWithoutRotation();
156
        
157
        extent = new Extent(minX, minY, maxX, maxY);
158
        requestExtent = extent;
159
        return this;
160
    }
161
    
162
    /**
163
         * Calcula la bounding box en la que est? metido el raster teniendo en cuenta
164
         * el tama?o de pixel y la rotaci?n. 
165
         */
166
        private void boundingBoxWithoutRotation() {
167
                double ox = file.originX;
168
                double oy = file.originY;
169
                double resx = file.cellIncrementX;
170
                double resy = file.cellIncrementY;
171
                                
172
                bBoxWithoutRot.add(new Point2D.Double(ox, oy));
173
                bBoxWithoutRot.add(new Point2D.Double(ox + resx * (file.width), oy));
174
                bBoxWithoutRot.add(new Point2D.Double(ox, oy + resy * (file.height)));
175
                bBoxWithoutRot.add(new Point2D.Double(ox + resx * (file.width), oy + resy * (file.height)));
176
        }
177

    
178
    /**
179
     * Cierra el fichero ECW
180
     */
181
    public void close() {
182
            if(file != null){
183
                    file.close(true);
184
                    file = null;
185
            }
186
    }
187
    
188
    /**
189
         * Obtiene el objeto que contiene el estado de la transparencia
190
         */
191
        public Transparency getTransparencyDatasetStatus() {
192
                if(fileTransparency == null)
193
                        fileTransparency = new Transparency();
194
                return fileTransparency;
195
        }
196
        
197
    /**
198
     * Devuelve el ancho de la imagen
199
     */
200
    public int getWidth() {
201
        return file.width;
202
    }
203

    
204
    /**
205
     * Devuelve el alto de la imagen
206
     */
207
    public int getHeight() {
208
        return file.height;
209
    }
210
    
211
    /**
212
         * Obtiene el extent de la ?ltima ventana seleccionada.
213
         * @return Extent
214
         */
215
        public Extent getView() {
216
        return viewRequest;
217
    }
218
        
219
        /*
220
         * (non-Javadoc)
221
         * @see org.gvsig.fmap.driver.RasterDataset#setView(org.gvsig.fmap.raster.Extent)
222
         */
223
        public void setView(Extent e) {
224
                if(rmfExists) {
225
                        Point2D.Double petInit = null, petEnd = null;
226
                        try {
227
                                petInit = new Point2D.Double(e.minX(), e.maxY());
228
                                petEnd = new Point2D.Double(e.maxX(), e.minY());
229
                                transformRMF.inverseTransform(petInit, petInit);
230
                                transformRMF.inverseTransform(petEnd, petEnd);
231
                                transformTFW.transform(petInit, petInit);
232
                                transformTFW.transform(petEnd, petEnd);
233
                        } catch(NoninvertibleTransformException ex) {
234
                                
235
                        }
236
                        viewRequest = new Extent(petInit.getX(), petInit.getY(), petEnd.getX(), petEnd.getY());
237
                } else
238
                        viewRequest = new Extent(e);
239
    }
240
        
241
        /**
242
         * Cuando se hace una petici?n de carga de buffer la extensi?n pedida puede estar ajustada a la extensi?n del raster
243
         * o no estarlo. En caso de no estarlo los pixeles del buffer que caen fuera de la extensi?n del raster tendr?n valor
244
         * de NoData. Esta funci?n calcula en que pixel del buffer hay que empezar a escribir en caso de que este sea mayor
245
         * que los datos a leer.
246
         * @param dWorldTLX Posici?n X superior izquierda en coord reales
247
         * @param dWorldTLY Posici?n Y superior izquierda en coord reales
248
         * @param dWorldBRX Posici?n X inferior derecha en coord reales
249
         * @param dWorldBRY Posici?n Y inferior derecha en coord reales
250
         * @param nWidth Ancho en pixeles del buffer
251
         * @param nHeight Alto en pixeles del buffer
252
         * @return desplazamiento dentro del buffer en X e Y
253
         */ 
254
        private int[] calcStepBuffer(Extent dataExtent, int nWidth, int nHeight, int[] stpBuffer) {
255
            Extent imageExtent = new Extent(bBoxWithoutRot.minX, bBoxWithoutRot.minY, bBoxWithoutRot.maxX, bBoxWithoutRot.maxY);
256
            Extent ajustDataExtent = RasterUtilities.calculateAdjustedView(dataExtent, imageExtent);
257
            if(!RasterUtilities.compareExtents(dataExtent, ajustDataExtent)) {
258
                    Point2D p1 = worldToRaster(new Point2D.Double(ajustDataExtent.minX(), ajustDataExtent.maxY()));
259
                    Point2D p2 = worldToRaster(new Point2D.Double(ajustDataExtent.maxX(), ajustDataExtent.minY()));
260
                    Point2D p3 = worldToRaster(new Point2D.Double(dataExtent.minX(), dataExtent.maxY()));
261
                    Point2D p4 = worldToRaster(new Point2D.Double(dataExtent.maxX(), dataExtent.minY()));
262
                    //Ese es el ancho y alto q tendr?a el buffer en caso de haberse ajustado
263
                    int w = (int)Math.abs(Math.ceil(p2.getX()) - Math.floor(p1.getX())); 
264
                    int h = (int)Math.abs(Math.floor(p1.getY()) - Math.ceil(p2.getY()));
265
                    
266
                    stpBuffer[0] = (int)(p1.getX() + (-p3.getX()));
267
                    stpBuffer[1] = (int)(p1.getY() + (-p3.getY()));
268
                    stpBuffer[2] = stpBuffer[0] + w; 
269
                    stpBuffer[3] = stpBuffer[1] + h;
270
                    return new int[]{w, h};
271
            }
272
            return new int[]{nWidth, nHeight};
273
        }
274
        
275
        /*
276
         * (non-Javadoc)
277
         * @see org.gvsig.fmap.driver.RasterDataset#worldToRaster(java.awt.geom.Point2D)
278
         */
279
        public Point2D worldToRaster(Point2D pt) {
280
                double x = ((pt.getX() - bBoxWithoutRot.minX) * ((double) currentFullWidth)) / (double)(bBoxWithoutRot.maxX - bBoxWithoutRot.minX);
281
                double y = ((bBoxWithoutRot.maxY - pt.getY()) * ((double) currentFullHeight)) / (double)(bBoxWithoutRot.maxY - bBoxWithoutRot.minY);
282
                Point2D ptRes = new Point2D.Double(x, y);
283
                return ptRes;
284
        }
285
        
286
        /*
287
         * (non-Javadoc)
288
         * @see org.gvsig.fmap.driver.RasterDataset#rasterToWorld(java.awt.geom.Point2D)
289
         */
290
        public Point2D rasterToWorld(Point2D pt) {
291
                double x = bBoxWithoutRot.minX + ((pt.getX() * (bBoxWithoutRot.maxX - bBoxWithoutRot.minX)) / currentFullWidth);
292
                double y = bBoxWithoutRot.maxY - ((pt.getY() * (bBoxWithoutRot.maxY - bBoxWithoutRot.minY)) / currentFullHeight);
293
                Point2D ptRes = new Point2D.Double(x, y);
294
                return ptRes;
295
        }
296
        
297
        /*
298
         * (non-Javadoc)
299
         * @see org.gvsig.fmap.driver.RasterDataset#getWindowRaster(double, double, double, double, org.gvsig.fmap.driver.BandList, org.gvsig.fmap.driver.IBuffer, boolean)
300
         */
301
        public IBuffer getWindowRaster(double x, double y, double w, double h, BandList bandList, IBuffer rasterBuf, boolean adjustToExtent) {
302
                
303
                //Si cojemos pixeles completos hemos de calcular las coordenadas reales de esos pixeles completos para hacer la petici?n.
304
                //Este el calculo que se hizo en RasterMultiDataset para calcular pixeles completos, convertir a pixel, redondear el primero
305
                //por abajo y el ultimo por arriba
306
                Point2D p1 = worldToRaster(new Point2D.Double(x, y));
307
                Point2D p2 = worldToRaster(new Point2D.Double(x + w, y - h));
308
                Point2D a = rasterToWorld(new Point2D.Double(Math.floor(p1.getX()), Math.floor(p1.getY())));
309
                Point2D b = rasterToWorld(new Point2D.Double(Math.ceil(p2.getX()), Math.ceil(p2.getY())));
310

    
311
                //Extent selectedExtent = new Extent(x, y, x + w, y - h);
312
                Extent selectedExtent = new Extent(a.getX(), a.getY(), b.getX(), b.getY());
313
                setView(selectedExtent);
314
                int wPx = rasterBuf.getWidth();
315
                int hPx = rasterBuf.getHeight();
316
                int[] stpBuffer = new int[]{0, 0 , wPx, hPx};
317
                
318
                //TODO: FUNCIONALIDAD: Implementar adjustToExtent = false
319
                /*if(!adjustToExtent){
320
                       int[] wh = calcStepBuffer(selectedExtent, wPx, hPx, stpBuffer);
321
                       if(x < 0)
322
                               x  = 0;
323
                       if(y < 0)
324
                               y  = 0;
325
                       readData(buf, bandList, x, y, wh[0], wh[1], wh[0], wh[1], 0, 0, stpBuffer);
326
                       return;
327
            }*/
328
                 
329
                loadBuffer(viewRequest, wPx, hPx, rasterBuf, bandList, stpBuffer);
330
                
331
                return rasterBuf;
332
        }
333

    
334
        /*
335
         * (non-Javadoc)
336
         * @see org.gvsig.fmap.driver.RasterDataset#getWindowRaster(int, int, int, int, org.gvsig.fmap.driver.BandList, org.gvsig.fmap.driver.IBuffer)
337
         */
338
        public IBuffer getWindowRaster(int x, int y, int w, int h, BandList bandList, IBuffer rasterBuf) {
339
                Point2D init = this.rasterToWorld(new Point2D.Double(x, y));
340
                Point2D end = this.rasterToWorld(new Point2D.Double(x + w, y + h));
341
                Extent selectedExtent = new Extent(init.getX(), init.getY(), end.getX(), end.getY());
342
                setView(selectedExtent);
343
                int[] stpBuffer = new int[]{0, 0 , w, h};
344
                
345
                loadBuffer(viewRequest, w, h, rasterBuf, bandList, stpBuffer);
346
                return rasterBuf;
347
        }
348
        
349
        /*
350
         * (non-Javadoc)
351
         * @see org.gvsig.fmap.driver.RasterDataset#getWindowRaster(double, double, double, double, int, int, org.gvsig.fmap.driver.BandList, org.gvsig.fmap.driver.IBuffer, boolean)
352
         */
353
        public IBuffer getWindowRaster(double minX, double minY, double maxX, double maxY, int bufWidth, int bufHeight, BandList bandList, IBuffer rasterBuf, boolean adjustToExtent) {
354
                Extent selectedExtent = new Extent(minX, maxY, maxX, minY);
355
                setView(selectedExtent);
356
                int[] stpBuffer = new int[]{0, 0 , bufWidth, bufHeight};
357
                
358
                //TODO: FUNCIONALIDAD: Implementar adjustToExtent = false
359
                
360
                loadBuffer(viewRequest, bufWidth, bufHeight, rasterBuf, bandList, stpBuffer);
361
                return rasterBuf;
362
        }
363

    
364
        /*
365
         * (non-Javadoc)
366
         * @see org.gvsig.fmap.driver.RasterDataset#getWindowRaster(int, int, int, int, int, int, org.gvsig.fmap.driver.BandList, org.gvsig.fmap.driver.IBuffer)
367
         */
368
        public IBuffer getWindowRaster(int x, int y, int w, int h, int bufWidth, int bufHeight, BandList bandList, IBuffer rasterBuf) {
369
                Point2D init = this.rasterToWorld(new Point2D.Double(x, y));
370
                Point2D end = this.rasterToWorld(new Point2D.Double(x + w, y + h));
371
                Extent selectedExtent = new Extent(init.getX(), init.getY(), end.getX(), end.getY());
372
                setView(selectedExtent);
373
                int[] stpBuffer = new int[]{0, 0 , bufWidth, bufHeight};
374
                
375
                loadBuffer(viewRequest, bufWidth, bufHeight, rasterBuf, bandList, stpBuffer);
376
                return rasterBuf;
377
        }
378

    
379
        /**
380
         * Carga el buffer con las bandas RGB del raster con los par?metros especificados de extensi?n
381
         * y tama?o de buffer. El problema de ecw es que solo podemos leer 3 bandas de una vez ya que solo disponemos
382
         * de una llamada readLineRGBA. Para leer m?s bandas tendremos que hacer multiples llamadas a setView para leer
383
         * 3 cada vez.
384
         * 
385
         * Si por ejemplo tenemos un ecw de 6 bandas [0, 1, 2, 3, 4, 5] y queremos cargar un buffer con el siguiente orden
386
         * [0, -, 2, -, 4, -] La variable readBandsFromECW har? la llamada a setView con los valores [0, 2, 4, 0, 0, 0]. La
387
         * funci?n drawRGB ser? la encargada de hacer el switch para obtener [0, -, 2, -, 4, -].
388
         * 
389
         * Bug#1: Si se dispone de un ecw de m?s de tres bandas podemos llamar a setView con readBandsFromECW con el orden
390
         * que queramos, por ejemplo [3, 2, 5, 1, 0] pero para ecw de 3 bandas la llamada con las bandas cambiadas no
391
         * hace caso. El caso de readBandsFromECW = [2, 0, 1] ser? tomado siempre como [0, 1, 2]. 
392
         * 
393
         * @param selectedExtent Extensi?n seleccionada
394
         * @param bufWidth Ancho de buffer
395
         * @param bufHeight Alto de buffer
396
         * @param rasterBuf Buffer de datos
397
         */
398
        private void loadBuffer(Extent selectedExtent, int bufWidth, int bufHeight, IBuffer rasterBuf, BandList bandList, int[] stpBuffer){
399
                try{
400
                        //Leemos el raster desde la librer?a 
401
                
402
                        int[] readBandsFromECW = new int[file.numBands];
403
                        int[] readBands = new int[file.numBands];
404
                        
405
                        
406
                        for(int i = 0; i < readBandsFromECW.length; i ++)
407
                                readBands[i] = -1;
408
                        int cont = 0;
409
                        for(int i = 0; i < file.numBands; i++) {
410
                                int[] bandsToDraw = bandList.getBand(i).getBufferBandListToDraw();
411
                                if(bandsToDraw != null) {
412
                                        for(int j = 0; j < bandsToDraw.length; j++){
413
                                                readBandsFromECW[cont] = i;
414
                                                readBands[cont] = i;
415
                                                cont ++;
416
                                        }
417
                                }
418

    
419
                        }
420
                        
421
                        if(readCancel) {
422
                                readCancel = false;
423
                                return;
424
                        }
425
                                                
426
                        file.setView(file.numBands, readBandsFromECW, selectedExtent.minX(), selectedExtent.maxY(), selectedExtent.maxX(), selectedExtent.minY(), bufWidth, bufHeight);
427
                        
428
                        //Escribimos el raster sobre un IBuffer
429
                        int[] pRGBArray = new int[bufWidth];
430
                        drawRGB(rasterBuf, pRGBArray, readBands, bandList);
431
                                                                                                        
432
                }catch(JNCSInvalidSetViewException exc){
433
                        exc.printStackTrace();
434
                }catch (JNCSFileNotOpenException e) {
435
                        e.printStackTrace();
436
                }catch (JNCSException ex) {
437
                        ex.printStackTrace();
438
                }
439
                
440
        }
441
        
442
        
443
        private void drawRGB(IBuffer rasterBuf, int[] pRGBArray, int[] readBands, BandList bandList)throws JNCSException{
444
                int bandR = readBands[0];
445
                int bandG = (readBands.length > 1) ? readBands[1] : -1;
446
                int bandB = (readBands.length > 2) ? readBands[2] : -1;
447
        
448
                //********* caso especial que resuelve Bug#1 **********************
449
                if(file.numBands == 3 && bandList.getDrawableBandsCount() < 3) {  
450
                        for(int i = 0; i < 3; i ++){
451
                                int[] b = bandList.getBand(i).getBufferBandListToDraw();
452
                                if(b != null){
453
                                        bandG = 1; bandR = 0; bandB = 2;
454
                                }
455
                        }
456
                }
457
                if(file.numBands == 3 && bandR == bandG && bandG == bandB) { //caso especial que resuelve Bug#1
458
                        for(int i = 0; i < 3; i ++) {
459
                                int[] b = bandList.getBand(i).getBufferBandListToDraw();
460
                                if(b != null){
461
                                        if(i == 0){
462
                                                for (int line = 0; line < rasterBuf.getHeight(); line++) {
463
                                            file.readLineRGBA(pRGBArray);
464
                                            for(int col = 0; col < pRGBArray.length; col ++){
465
                                                    rasterBuf.setElem(line, col, bandR, (byte)((pRGBArray[col] & 0x00ff0000) >> 16));
466
                                                    rasterBuf.setElem(line, col, bandG, (byte)((pRGBArray[col] & 0x00ff0000) >> 16));
467
                                                    rasterBuf.setElem(line, col, bandB, (byte)((pRGBArray[col] & 0x00ff0000) >> 16));
468
                                            }
469
                                        }
470
                                                return;
471
                                        }
472
                                        if(i == 1) {
473
                                                for (int line = 0; line < rasterBuf.getHeight(); line++) {
474
                                            file.readLineRGBA(pRGBArray);
475
                                            for(int col = 0; col < pRGBArray.length; col ++){
476
                                                    rasterBuf.setElem(line, col, bandR, (byte)((pRGBArray[col] & 0x0000ff00) >> 8));
477
                                                    rasterBuf.setElem(line, col, bandG, (byte)((pRGBArray[col] & 0x0000ff00) >> 8));
478
                                                    rasterBuf.setElem(line, col, bandB, (byte)((pRGBArray[col] & 0x0000ff00) >> 8));
479
                                            }
480
                                        }
481
                                                return;
482
                                        }
483
                                        if(i == 2) {
484
                                                for (int line = 0; line < rasterBuf.getHeight(); line++) {
485
                                            file.readLineRGBA(pRGBArray);
486
                                            for(int col = 0; col < pRGBArray.length; col ++){
487
                                                    rasterBuf.setElem(line, col, bandR, (byte)(pRGBArray[col] & 0x000000ff));
488
                                                    rasterBuf.setElem(line, col, bandG, (byte)(pRGBArray[col] & 0x000000ff));
489
                                                    rasterBuf.setElem(line, col, bandB, (byte)(pRGBArray[col] & 0x000000ff));
490
                                            }
491
                                        }
492
                                                return;
493
                                        }
494
                                }
495
                                if(readCancel) {
496
                                        readCancel = false;
497
                                        return;
498
                                }
499
                        }
500

    
501
                }
502
                //********* END caso especial que resuelve Bug#1 **********************
503
                
504
                if(bandR >= 0 && bandG >= 0 && bandB >= 0) {
505
                        for (int line = 0; line < rasterBuf.getHeight(); line++) {
506
                    file.readLineRGBA(pRGBArray);
507
                    for(int col = 0; col < pRGBArray.length; col ++){
508
                            rasterBuf.setElem(line, col, bandR, (byte)((pRGBArray[col] & 0x00ff0000) >> 16));
509
                            rasterBuf.setElem(line, col, bandG, (byte)((pRGBArray[col] & 0x0000ff00) >> 8));
510
                            rasterBuf.setElem(line, col, bandB, (byte)(pRGBArray[col] & 0x000000ff));
511
                    }
512
                }
513
                        return;
514
                }
515
                
516
                if(readCancel) {
517
                        readCancel = false;
518
                        return;
519
                }
520
                
521
                if(bandR >= 0 && bandG >= 0) {
522
                        for (int line = 0; line < rasterBuf.getHeight(); line++) {
523
                    file.readLineRGBA(pRGBArray);
524
                    for(int col = 0; col < pRGBArray.length; col ++){
525
                            rasterBuf.setElem(line, col, bandR, (byte)((pRGBArray[col] & 0x00ff0000) >> 16));
526
                            rasterBuf.setElem(line, col, bandG, (byte)((pRGBArray[col] & 0x0000ff00) >> 8));
527
                    }
528
                }
529
                        return;
530
                }
531
                
532
                if(readCancel) {
533
                        readCancel = false;
534
                        return;
535
                }
536
                                
537
                if(bandR >= 0){
538
                        for (int line = 0; line < rasterBuf.getHeight(); line++) {
539
                    file.readLineRGBA(pRGBArray);
540
                    for(int col = 0; col < pRGBArray.length; col ++)
541
                            rasterBuf.setElem(line, col, bandR, (byte)((pRGBArray[col] & 0x00ff0000) >> 16));
542
                }
543
                        return;
544
                }
545
                
546
                if(readCancel) {
547
                        readCancel = false;
548
                        return;
549
                }
550

    
551
        }
552
        
553
        public void reProject(ICoordTrans rp) {
554
        }
555

    
556
         /**
557
         * Calcula la transformaci?n que se produce sobre la vista cuando la imagen tiene un fichero .rmf
558
         * asociado. En Gdal el origen de coordenadas en Y es el valor m?nimo y crece hasta el m?ximo. De la
559
         * misma forma calcula la matriz de transformaci?n de la cabecera del fichero o del world file asociado
560
         * @param originX Origen de la imagen en la coordenada X
561
         * @param originY Origen de la imagen en la coordenada Y
562
         */
563
        public void setExtentTransform(double originX, double originY, double psX, double psY) {                
564
                transformRMF.setToTranslation(originX, originY);
565
                transformRMF.scale(psX, psY);
566
                
567
                transformTFW.setToTranslation(file.originX, file.originY);
568
                transformTFW.scale(file.cellIncrementX, file.cellIncrementY);
569
        }
570

    
571
        /*
572
         * (non-Javadoc)
573
         * @see org.gvsig.raster.dataset.RasterDataset#getBlockSize()
574
         */
575
        public int getBlockSize() {
576
                return 0;
577
        }
578

    
579
        /*
580
         * (non-Javadoc)
581
         * @see org.gvsig.raster.driver.RasterDataset#readCompletetLine(int, int)
582
         */
583
        public Object readCompleteLine(int line, int band) throws InvalidSetViewException, FileNotOpenException, RasterDriverException {
584
                if(line < 0 || line >= file.height || band < 0 || band >= getBandCount())
585
                        throw new InvalidSetViewException("Request out of grid");
586
                
587
                Point2D begin = rasterToWorld(new Point2D.Double(0, line));
588
                Point2D end = rasterToWorld(new Point2D.Double(file.width, line + 1));
589
                int[] readBandsFromECW = new int[file.numBands];
590
                if(file.numBands <= 3) {
591
                        for(int i = 0; i < file.numBands; i++)
592
                                readBandsFromECW[i] = i;
593
                }else {
594
                        readBandsFromECW[0] = band;
595
                }
596
                
597
                Extent e = new Extent(begin.getX(), begin.getY(), end.getX(), end.getY());
598
                
599
                try {
600
                        int[] value = new int[file.width];
601
                        file.setView(file.numBands, readBandsFromECW, e.minX(), e.maxY(), e.maxX(), e.minY(), file.width, 1);
602
                        file.readLineRGBA(value);
603
                        
604
                        if(file.numBands <= 3) {
605
                                switch(getDataType()) {
606
                                case IBuffer.TYPE_BYTE: byte[] b = new byte[file.width];
607
                                                                                switch(band) {
608
                                                                                case 0: for(int i = 0; i < file.width; i ++)
609
                                                                                                        b[i] = (byte)(((value[i] & 0x00ff0000) >> 16) & 0xff);
610
                                                                                                break;
611
                                                                                case 1: for(int i = 0; i < file.width; i ++)
612
                                                                                                        b[i] = (byte)(((value[i] & 0x0000ff00) >> 8) & 0xff);
613
                                                                                                break;
614
                                                                                case 2: for(int i = 0; i < file.width; i ++)
615
                                                                                                        b[i] = (byte)((value[i] & 0x000000ff) & 0xff);
616
                                                                                                break;
617
                                                                                }
618
                                                                                return b;
619
                                }
620
                        }else {
621
                                switch(getDataType()) {
622
                                case IBuffer.TYPE_BYTE: byte[] b = new byte[file.width];
623
                                                                                for(int i = 0; i < file.width; i ++)
624
                                                                                        b[i] = (byte)(((value[i] & 0x00ff0000) >> 16) & 0xff);
625
                                                                                break;
626
                                }
627
                        }
628
                        //TODO: FUNCIONALIDAD: Ecw con otro tipo de dato != Byte
629
                } catch (JNCSFileNotOpenException e1) {
630
                        throw new FileNotOpenException("Error en jecw: JNCSFileNotOpenException");
631
                } catch (JNCSInvalidSetViewException e1) {
632
                        throw new FileNotOpenException("Error en jecw: JNCSInvalidSetViewException");
633
                } catch (JNCSException e1) {
634
                        throw new RasterDriverException("Error la lectura de datos ecw");
635
                }
636
                
637
                return null;
638
        }
639
        
640
        /*
641
         *  (non-Javadoc)
642
         * @see org.gvsig.raster.dataset.RasterDataset#readBlock(int, int, int)
643
         */
644
        public Object readBlock(int pos, int blockHeight) throws InvalidSetViewException, FileNotOpenException, RasterDriverException {
645
                if(pos < 0)
646
                        throw new InvalidSetViewException("Request out of grid");
647
                
648
                if((pos + blockHeight) > file.height)
649
                        blockHeight = Math.abs(file.height - pos);
650
                
651
                Point2D begin = rasterToWorld(new Point2D.Double(0, pos));
652
                Point2D end = rasterToWorld(new Point2D.Double(file.width, pos + blockHeight));
653
                int[] readBandsFromECW = new int[file.numBands];
654
                
655
                for(int i = 0; i < file.numBands; i++)
656
                        readBandsFromECW[i] = i;
657
                
658
                byte[][][] buf = new byte[file.numBands][blockHeight][file.width];
659
                Extent e = new Extent(begin.getX(), begin.getY(), end.getX(), end.getY());
660
                e = RasterUtilities.calculateAdjustedView(getExtent(), e);
661
                
662
                try {
663
                        int[] value = new int[file.width];
664
                        file.setView(file.numBands, readBandsFromECW, e.minX(), e.maxY(), e.maxX(), e.minY(), file.width, blockHeight);
665
                        
666
                        if(file.numBands <= 3) {
667
                                for (int row = 0; row < blockHeight; row++) {
668
                                        file.readLineRGBA(value);
669
                                        switch(getDataType()) {
670
                                        case IBuffer.TYPE_BYTE: 
671
                                                for(int col = 0; col < file.width; col ++) {
672
                                                        buf[0][row][col] = (byte)(((value[col] & 0x00ff0000) >> 16) & 0xff);
673
                                                        buf[1][row][col] = (byte)(((value[col] & 0x0000ff00) >> 8) & 0xff);
674
                                                        buf[2][row][col] = (byte)((value[col] & 0x000000ff) & 0xff);
675
                                                }
676
                                                break;
677
                                        }
678
                                }
679
                                
680
                                if(readCancel) {
681
                                        readCancel = false;
682
                                        return null;
683
                                }
684
                                
685
                        } else {
686
                                //TODO: FUNCIONALIDAD: file.numBands > 3
687
                        }
688

    
689
                        //TODO: FUNCIONALIDAD: Ecw con otro tipo de dato != Byte
690
                } catch (JNCSFileNotOpenException e1) {
691
                        throw new FileNotOpenException("Error en jecw: JNCSFileNotOpenException");
692
                } catch (JNCSInvalidSetViewException e1) {
693
                        throw new FileNotOpenException("Error en jecw: JNCSInvalidSetViewException");
694
                } catch (JNCSException e1) {
695
                        throw new RasterDriverException("Error la lectura de datos ecw");
696
                }
697
                
698
                return buf;
699
        }
700
        
701
        /*
702
         * (non-Javadoc)
703
         * @see org.gvsig.raster.driver.RasterDataset#getData(int, int, int)
704
         */
705
        public Object getData(int x, int y, int band)throws InvalidSetViewException, FileNotOpenException, RasterDriverException {
706
                if(x < 0 || y < 0 || x >= file.width || y >= file.height)
707
                        throw new InvalidSetViewException("Request out of grid");
708
                
709
                Point2D begin = rasterToWorld(new Point2D.Double(x, y));
710
                Point2D end = rasterToWorld(new Point2D.Double(x + 1, y + 1));
711
                int[] readBandsFromECW = new int[file.numBands];
712
                if(file.numBands <= 3){
713
                        for(int i = 0; i < file.numBands; i++)
714
                                readBandsFromECW[i] = i;
715
                }else{
716
                        readBandsFromECW[0] = band;
717
                }
718
                
719
                Extent e = new Extent(begin.getX(), begin.getY(), end.getX(), end.getY());                
720
                try {
721
                        int[] value = new int[1];
722
                        file.setView(file.numBands, readBandsFromECW, e.minX(), e.maxY(), e.maxX(), e.minY(), 1, 1);
723
                        file.readLineRGBA(value);
724
                        if(file.numBands <= 3){
725
                                switch(band){
726
                                case 0: return new Integer((((value[0] & 0x00ff0000) >> 16) & 0xffffffff));
727
                                case 1: return new Integer((((value[0] & 0x0000ff00) >> 8) & 0xffffffff));
728
                                case 2: return new Integer((((value[0] & 0x000000ff)) & 0xffffffff));
729
                                }
730
                        }
731
                        return new Integer((((value[0] & 0x00ff0000) >> 16) & 0xffffffff));
732
                } catch (JNCSFileNotOpenException e1) {
733
                        throw new FileNotOpenException("Error en jecw: JNCSFileNotOpenException");
734
                } catch (JNCSInvalidSetViewException e1) {
735
                        throw new FileNotOpenException("Error en jecw: JNCSInvalidSetViewException");
736
                } catch (JNCSException e1) {
737
                        throw new RasterDriverException("Error reading ecw data");
738
                }
739
        }
740
        
741
        public void refreshUpdate(int arg0, int arg1, double arg2, double arg3, double arg4, double arg5) {
742
        }
743

    
744
        public void refreshUpdate(int arg0, int arg1, int arg2, int arg3, int arg4, int arg5) {
745
        }
746
        
747
        /*
748
         * (non-Javadoc)
749
         * @see org.gvsig.raster.driver.GeoData#getStringProjection()
750
         */
751
        public String getStringProjection() throws RasterDriverException{
752
                return file.projection;
753
        }
754
        
755
        /*
756
         *  (non-Javadoc)
757
         * @see org.gvsig.raster.dataset.RasterDataset#setCanceled(boolean, int)
758
         */
759
        public void setCanceled(boolean value, int process) {
760
                super.setCanceled(value, process);
761
                
762
                if(process == CANCEL_READ || process == 0)
763
                        readCancel = value;
764
        }
765

    
766
        /*
767
         *  (non-Javadoc)
768
         * @see org.gvsig.raster.dataset.RasterDataset#isCanceled(int)
769
         */
770
        public boolean isCanceled(int process) {
771
                if(process == CANCEL_READ) {
772
                        return readCancel;
773
                } else
774
                        return super.isCanceled(process);
775
        }
776
}
777

    
778

    
779