Statistics
| Revision:

root / trunk / libraries / libCresques / src / org / cresques / io / GdalFile.java @ 13173

History | View | Annotate | Download (41.9 KB)

1 13128 bsanchez
/*
2
 * Cresques Mapping Suite. Graphic Library for constructing mapping applications.
3
 *
4 13130 bsanchez
 * Copyright (C) 2004-5.
5
 *
6 13128 bsanchez
 * 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., 59 Temple Place - Suite 330, Boston, MA  02111-1307,USA.
19
 *
20
 * For more information, contact:
21 13130 bsanchez
 *
22 13128 bsanchez
 * cresques@gmail.com
23
 */
24
package org.cresques.io;
25
26
import java.awt.Image;
27
import java.awt.Point;
28
import java.awt.geom.NoninvertibleTransformException;
29
import java.awt.geom.Point2D;
30
import java.awt.image.BufferedImage;
31
import java.awt.image.DataBuffer;
32
import java.io.IOException;
33
import java.util.Vector;
34
35
import org.cresques.cts.ICoordTrans;
36
import org.cresques.cts.IProjection;
37
import org.cresques.filter.RasterBuf;
38
import org.cresques.io.data.Metadata;
39
import org.cresques.px.Extent;
40
41
import es.gva.cit.jgdal.Gdal;
42
import es.gva.cit.jgdal.GdalBuffer;
43
import es.gva.cit.jgdal.GdalException;
44
import es.gva.cit.jgdal.GdalRasterBand;
45
import es.gva.cit.jgdal.GeoTransform;
46
/**
47
 * Soporte 'nativo' para ficheros desde GDAL.
48
 * Este conjunto de funcionalidades est? tomado de manera casi literal
49
 * del soporte para ECW de ermapper.<br>
50
 * Probablemente esto deber?a formar parte del JNI que recubre a la
51
 * librer?a en C extraida de gdal.<br>
52
 * Lo pongo aqu? a manera de ejemplo de como atacar un formato binario
53 13130 bsanchez
 * desde Java.<br><br>
54 13128 bsanchez
 * @author Luis W. Sevilla.
55
 */
56
57
class GdalNative extends Gdal {
58
        static boolean                                 WITH_OVERVIEWS = true;
59
        private String                                 ext = "";
60
        public         GeoTransform                 trans = null;
61
        /**
62
         * Contorno en coordenadas geogr?ficas. (y Extent del raster).
63
         */
64
        public Contour                                 bBoxRot = new Contour();
65
        /**
66
         * Contorno en coordenadas geogr?ficas sin rotaci?n aplicada. Esto es util para poder
67 13130 bsanchez
         * calcular los pixeles necesarios que se van a leer del raster. Cuando el raster no tiene
68
         * rotaci?n coincide con esq.
69 13128 bsanchez
         */
70
        public Contour                                bBoxWithoutRot = new Contour();
71
        public int                                         width = 0, height = 0;
72
        public double                                 originX = 0D, originY = 0D;
73
        public String                                 version = "";
74
        private int                                 alpha = 0;
75
        protected int                                 rBandNr = 1, gBandNr = 2, bBandNr = 3, aBandNr = 4;
76
        private int                                 dataType = GDT_Byte;
77
        /**
78
         * Metadatos leidos de la imagen
79
         */
80
        private Metadata                        metadata = null;
81
        private boolean                         georeferenced = true;
82
83 13130 bsanchez
84 13128 bsanchez
        // Polilinea con extent
85
        public class Contour extends Vector {
86
                final private static long serialVersionUID = -3370601314380922368L;
87
                public double minX = Double.MAX_VALUE, minY = Double.MAX_VALUE;
88
                public double maxX = -Double.MAX_VALUE, maxY = -Double.MAX_VALUE;
89
                public Contour() {
90
                        super();
91
                }
92
                public void add(Point2D pt) {
93
                        super.add(pt);
94
                        if (pt.getX() > maxX) maxX = pt.getX();
95
                        if (pt.getX() < minX) minX = pt.getX();
96
                        if (pt.getY() > maxY) maxY = pt.getY();
97
                        if (pt.getY() < minY) minY = pt.getY();
98
                }
99
        }
100 13130 bsanchez
101 13128 bsanchez
        public GdalNative(String fName) throws GdalException, IOException {
102
                super();
103
                init(fName);
104
        }
105 13130 bsanchez
106 13128 bsanchez
        /**
107
         * <P>
108
         * Calcula la bounding box en la que est? metido el raster teniendo en cuenta
109 13130 bsanchez
         * el tama?o de pixel y la rotaci?n. Esto lo hace con los valores de transformaci?n
110 13128 bsanchez
         * leidos por gdal en el vector de 6 elementos adfGeoTransform donde cada elemento
111
         * del vector represnta los siguientes valores
112
         * </P>
113
         * <UL>
114
         * <LI>0-origen X</LI>
115
         * <LI>1-tama?o de pixel X</LI>
116
         * <LI>2-shear en X</LI>
117
         * <LI>3-origen Y</LI>
118
         * <LI>4-shear en Y</LI>
119
         * <LI>5-Tama?o de pixel Y</LI>
120
         * </UL>
121
         * <P>
122
         * Para el calculo de una esquina aplicamos la formula siguiente:<BR>
123
         * PtoX = originX + pixelSizeX * x + shearX * y;<BR>
124
         * PtoY = originY + shearY * x + pixelSizeY * y;<BR>
125
         * Aplicandolo a las cuatro esquinas sustituimos en cada una de ellas por.
126
         * </P>
127 13130 bsanchez
         * <UL>
128 13128 bsanchez
         * <LI>Esquina superior izquierda: x = 0; y = 0;</LI>
129
         * <LI>Esquina superior derecha: x = MaxX; y = 0;</LI>
130
         * <LI>Esquina inferior izquierda: x = 0; y = MaxY;</LI>
131
         * <LI>Esquina inferior derecha: x = MaxX; y = MaxY;</LI>
132 13130 bsanchez
         * </UL>
133 13128 bsanchez
         * <P>
134
         * quedandonos en los cuatro casos:
135
         * </P>
136 13130 bsanchez
         * <UL>
137 13128 bsanchez
         * <LI>Esquina superior izquierda: originX; originY;</LI>
138
         * <LI>Esquina superior derecha: PtoX = originX + pixelSizeX * x; PtoY = originY + shearY * x;</LI>
139
         * <LI>Esquina inferior izquierda:  PtoX = originX + shearX * y; PtoY = originY + pixelSizeY * y;</LI>
140
         * <LI>Esquina inferior derecha: PtoX = originX + pixelSizeX * x + shearX * y; PtoY = originY + shearY * x + pixelSizeY * y;</LI>
141
         * </UL>
142 13130 bsanchez
         *
143 13128 bsanchez
         */
144
        private void boundingBoxFromGeoTransform(){
145
                double geoX = 0D, geoY = 0D;
146
147
                //Upper left corner
148
                bBoxRot.add(new Point2D.Double(trans.adfgeotransform[0], trans.adfgeotransform[3]));
149
150
                //Lower left corner
151
                geoX = trans.adfgeotransform[0] +  trans.adfgeotransform[2] * height;
152
                geoY = trans.adfgeotransform[3] +  trans.adfgeotransform[5] * height;
153
                bBoxRot.add(new Point2D.Double(geoX, geoY));
154 13130 bsanchez
155 13128 bsanchez
                //Upper right corner
156
                geoX = trans.adfgeotransform[0] + trans.adfgeotransform[1] * width;
157
                geoY = trans.adfgeotransform[3] + trans.adfgeotransform[4] * width;
158
                bBoxRot.add(new Point2D.Double(geoX, geoY));
159 13130 bsanchez
160 13128 bsanchez
                //Lower right corner
161
                geoX = trans.adfgeotransform[0] + trans.adfgeotransform[1] * width + trans.adfgeotransform[2] * height;
162
                geoY = trans.adfgeotransform[3] + trans.adfgeotransform[4] * width + trans.adfgeotransform[5] * height;
163
                bBoxRot.add(new Point2D.Double(geoX, geoY));
164 13130 bsanchez
165 13128 bsanchez
                //TODO: ?OJO! con coordenadas geogr?ficas
166
        }
167 13130 bsanchez
168 13128 bsanchez
        /**
169
         * Calcula la bounding box en la que est? metido el raster teniendo en cuenta
170 13130 bsanchez
         * el tama?o de pixel y la rotaci?n.
171 13128 bsanchez
         */
172
        private void boundingBoxWithoutRotation(){
173
                double ox = trans.adfgeotransform[0];
174
                double oy = trans.adfgeotransform[3];
175
                double resx = trans.adfgeotransform[1];
176
                double resy = trans.adfgeotransform[5];
177 13130 bsanchez
178 13128 bsanchez
                bBoxWithoutRot.add(new Point2D.Double(ox, oy));
179
                bBoxWithoutRot.add(new Point2D.Double(ox + resx * width, oy));
180
                bBoxWithoutRot.add(new Point2D.Double(ox, oy + resy * height));
181
                bBoxWithoutRot.add(new Point2D.Double(ox + resx * width, oy + resy * height));
182
183
                //TODO: ?OJO! con coordenadas geogr?ficas
184
        }
185 13130 bsanchez
186 13128 bsanchez
        private void init(String fName) throws GdalException, IOException {
187
                open(fName,GA_ReadOnly);
188
                ext = fName.toLowerCase().substring(fName.lastIndexOf('.')+1);
189
                if (ext.compareTo("tif") == 0)
190
                        WITH_OVERVIEWS = false;
191
                width = getRasterXSize();
192
                height = getRasterYSize();
193
                setDataType(this.getRasterBand(1).getRasterDataType());
194
                metadata = new Metadata(getMetadata());
195 13130 bsanchez
196 13128 bsanchez
                //Asignamos la interpretaci?n de color leida por gdal a cada banda. Esto nos sirve
197
                //para saber que banda de la imagen va asignada a cada banda de visualizaci?n (ARGB)
198
                metadata.initColorInterpretation(getRasterCount());
199
                metadata.initNoDataByBand(getRasterCount());
200 13130 bsanchez
                        for(int i = 0; i < getRasterCount(); i++){
201
                                GdalRasterBand rb = getRasterBand(i + 1);
202
                                String colorInt = getColorInterpretationName(rb.getRasterColorInterpretation());
203
                                metadata.setNoDataValue(i, rb.getRasterNoDataValue());
204
                                metadata.setColorInterpValue(i, colorInt);
205
                                if(colorInt.equals("Red"))
206
                                        rBandNr = i + 1;
207
                                if(colorInt.equals("Green"))
208
                                        gBandNr = i + 1;
209
                                if(colorInt.equals("Blue"))
210
                                        bBandNr = i + 1;
211
                                if(colorInt.equals("Alpha"))
212
                                        aBandNr = i + 1;
213
                        }
214
215 13128 bsanchez
                try{
216
                        trans = getGeoTransform();
217 13130 bsanchez
218 13128 bsanchez
                        boundingBoxWithoutRotation();
219
                        boundingBoxFromGeoTransform();
220 13130 bsanchez
221 13128 bsanchez
                        this.georeferenced = true;
222
                }catch(GdalException exc){
223
                        bBoxRot.add(new Point2D.Double(0, 0));
224
                        bBoxRot.add(new Point2D.Double(width, 0));
225
                        bBoxRot.add(new Point2D.Double(0, height));
226
                        bBoxRot.add(new Point2D.Double(width, height));
227
                        bBoxWithoutRot = bBoxRot;
228
                        this.georeferenced = false;
229
                }
230
        }
231 13130 bsanchez
232 13128 bsanchez
        public void setAlpha(int a) { alpha = a; }
233 13130 bsanchez
234 13128 bsanchez
        public void setDataType(int dt) { dataType = dt; }
235
        public int getDataType() { return dataType; }
236 13130 bsanchez
237 13128 bsanchez
        double lastReadLine = -1;
238
        int currentFullWidth = -1;
239
        int currentFullHeight = -1;
240
        int currentViewWidth = -1;
241
        int currentViewHeight = -1;
242
        double currentViewX = 0D;
243
        double currentViewY = 0D;
244
        double viewportScaleX = 0D;
245
        double viewportScaleY = 0D;
246
        double wcWidth = 0D;
247
        double stepX = 0D;
248
        double stepY = 0D;
249
        int currentOverview = -1;
250 13130 bsanchez
251 13128 bsanchez
        protected GdalRasterBand bandR = null, bandG = null, bandB = null, bandA = null;
252 13130 bsanchez
253 13128 bsanchez
        private boolean[] orientation;
254 13130 bsanchez
255 13128 bsanchez
        /**
256
         * Devuelve la banda actualmente en uso para el color especificado.
257
         * @param color 0=Rojo, 1=Green, 2=Blue.
258
         * @return
259
         */
260
        public GdalRasterBand getCurrentBand(int color) {
261 13130 bsanchez
                if (color == 0)
262 13128 bsanchez
                        return bandR;
263 13130 bsanchez
                else if (color == 1)
264 13128 bsanchez
                        return bandG;
265
                return bandB;
266
        }
267 13130 bsanchez
268 13128 bsanchez
        //Supone rasters no girados
269
        public Point2D worldToRaster(Point2D pt) {
270
                double x = (((double) currentFullWidth) / (bBoxWithoutRot.maxX - bBoxWithoutRot.minX)) * (pt.getX() - bBoxWithoutRot.minX);
271
                double y = (((double) currentFullHeight) / (bBoxWithoutRot.maxY - bBoxWithoutRot.minY)) * (bBoxWithoutRot.maxY - pt.getY());
272
                Point2D ptRes = new Point2D.Double(x, y);
273
                return ptRes;
274
        }
275 13130 bsanchez
276 13128 bsanchez
        /**
277
         * Si el tama?o de pixel en X es menor que 0 entonces la imagen se orienta al contrario en X por lo que en los zooms
278 13130 bsanchez
         * habr? que invertir la petici?n de la parte derecha a la izquierda y viceversa. Esto lo detectamos con la
279
         * variable orientation , si orientation[0] es false entonces el punto inicial del zoom lo invertimos de la
280 13128 bsanchez
         * siguiente forma:
281
         * Nuevo_punto_inicialX = (Ancho_total_raster - punto_inicial_del_zoomX) - Ancho_de_petici?n
282
         *
283 13130 bsanchez
         * Si el tama?o de pixel en Y es mayor que 0 entonces la imagen se orienta al contrario en Y por
284
         * lo que en los zooms habr? que invertir la petici?n de abajo a arriba y viceversa. Esto lo detectamos con la
285
         * variable orientation , si orientation[1] es true entonces el punto inicial del zoom lo invertimos de la
286 13128 bsanchez
         * siguiente forma:
287
         * Nuevo_punto_inicialY = (Alto_total_raster - punto_inicial_del_zoomY) - Alto_de_petici?n
288 13130 bsanchez
         *
289 13128 bsanchez
         * @param dWorldTLX
290
         * @param dWorldTLY
291
         * @param dWorldBRX
292
         * @param dWorldBRY
293
         * @param nWidth
294
         * @param nHeight
295
         * @param orientation array de dos elementos que representa la orientaci?n de la petici?n en
296
         * X e Y. El primer elemento representa el signo de pixelSize en X, true si es positivo y false
297
         * si es negativo. El segundo elemento representa el signo de pixelSize en Y
298
         * @return
299
         */
300
        public int setView(double dWorldTLX, double dWorldTLY,
301 13130 bsanchez
                                                double dWorldBRX, double dWorldBRY,
302
                                                int nWidth, int nHeight, boolean[] orientation) {
303 13128 bsanchez
                int err = 0;
304
                this.orientation = orientation;
305
                currentFullWidth = width;
306
                currentFullHeight = height;
307
                Point2D tl = worldToRaster(new Point2D.Double(dWorldTLX, dWorldTLY));
308
                Point2D br = worldToRaster(new Point2D.Double(dWorldBRX, dWorldBRY));
309
                // Calcula cual es la primera l?nea a leer;
310
                currentViewWidth = nWidth;
311
                currentViewHeight = nHeight;
312
                wcWidth = Math.abs(br.getX() - tl.getX());
313 13130 bsanchez
314 13128 bsanchez
                if(!orientation[0]) //Invierte la orientaci?n en X
315
                        currentViewX = (width - tl.getX()) - (br.getX()-tl.getX());
316
                else
317
                        currentViewX = tl.getX();
318 13130 bsanchez
319 13128 bsanchez
                viewportScaleX = (double) currentViewWidth/(br.getX()-tl.getX());
320
                viewportScaleY = (double) currentViewHeight/(br.getY()-tl.getY());
321
                stepX = 1D/viewportScaleX;
322
                stepY = 1D/viewportScaleY;
323
324
                if(orientation[1])//Invierte la orientaci?n en Y
325
                        lastReadLine = (height - tl.getY()) - (br.getY()-tl.getY());
326
                else
327
                        lastReadLine = tl.getY();
328 13130 bsanchez
329 13128 bsanchez
                try {
330
                        // calcula el overview a usar
331
                        bandR = getRasterBand(1);
332
                        currentOverview = -1;
333
                        if (WITH_OVERVIEWS && bandR.getOverviewCount() > 0) {
334
                                GdalRasterBand ovb = null;
335 13130 bsanchez
                                for (int i=bandR.getOverviewCount()-1; i>0; i--) {
336 13128 bsanchez
                                        ovb = bandR.getOverview(i);
337
                                        if (ovb.getRasterBandXSize()>getRasterXSize()*viewportScaleX) {
338
                                                currentOverview = i;
339 13130 bsanchez
                                                                        viewportScaleX *= ((double) width/(double) ovb.getRasterBandXSize());
340
                                                                        viewportScaleY *= ((double) height/(double) ovb.getRasterBandYSize());
341
                                                                        stepX = 1D/viewportScaleX;
342
                                                                        stepY = 1D/viewportScaleY;
343
                                                                        currentFullWidth = ovb.getRasterBandXSize();
344
                                                                        currentFullHeight = ovb.getRasterBandYSize();
345
                                                                        tl = worldToRaster(new Point2D.Double(dWorldTLX, dWorldTLY));
346
                                                                        if(!orientation[0])//Invierte la orientaci?n en X
347
                                                                                currentViewX = (width - tl.getX()) - (br.getX()-tl.getX());
348
                                                                        else
349
                                                                                currentViewX = tl.getX();
350
                                                                        if(orientation[1])//Invierte la orientaci?n en Y
351
                                                                                lastReadLine = (height - tl.getY()) - (br.getY()-tl.getY());
352
                                                                        else
353
                                                                                lastReadLine = tl.getY();
354
                                                                        break;
355 13128 bsanchez
                                        }
356
                                }
357
                        }
358 13130 bsanchez
359 13128 bsanchez
                        // Selecciona las bandas y los overviews necesarios
360
                        bandR = getRasterBand(rBandNr);
361
                        setDataType(bandR.getRasterDataType());
362 13130 bsanchez
363 13128 bsanchez
                        if (this.getRasterCount() > 1) {
364
                                bandG = getRasterBand(gBandNr);
365 13130 bsanchez
                                bandB = getRasterBand(bBandNr);
366 13128 bsanchez
                                if(metadata.isAlphaBand())
367 13130 bsanchez
                                        bandA = getRasterBand(aBandNr);
368 13128 bsanchez
                        }
369
                        if (currentOverview > 0) {
370
                                bandR = bandR.getOverview(currentOverview);
371 13130 bsanchez
                                        if (this.getRasterCount() > 1) {
372 13128 bsanchez
                                        bandG = bandG.getOverview(currentOverview);
373
                                        bandB = bandB.getOverview(currentOverview);
374
                                        if(metadata.isAlphaBand())
375
                                                bandA = bandA.getOverview(currentOverview);
376
                                }
377
                        }
378
379
                } catch (GdalException e) {
380
                        e.printStackTrace();
381
                }
382
                return err;
383
        }
384 13130 bsanchez
385 13128 bsanchez
        int lastY = -1;
386 13130 bsanchez
387 13128 bsanchez
        public void readLine(int[][] line) throws GdalException {
388 13130 bsanchez
                                int w = (int) (Math.ceil(((double)currentViewWidth)*stepX) + 1);
389
                                int x = (int) Math.ceil(currentViewX);
390
                                int y = (int) Math.ceil(lastReadLine);
391
                                GdalBuffer r = null, g = null, b = null, p = null;
392
                                GdalBuffer a = new GdalBuffer();
393
394
                                //if (alpha > 0) a = alpha << 24;
395
                                if (x+w > bandR.getRasterBandXSize())
396
                                        w = bandR.getRasterBandXSize()-x;
397
398
                                if(bandR.getRasterColorTable() != null){
399
                                        p = bandR.readRasterWithPalette(x, y, w, 1, w, 1, dataType);
400
                                        a.buffByte = p.buffAPalette;
401
                                        r = new GdalBuffer();
402
                                        r.buffByte = p.buffRPalette;
403
                                        g = new GdalBuffer();
404
                                        g.buffByte = p.buffGPalette;
405
                                        b = new GdalBuffer();
406
                                        b.buffByte = p.buffBPalette;
407
                                }else{
408
                                        a.buffByte = new byte[w];
409 13128 bsanchez
                        r = bandR.readRaster(x, y, w, 1, w, 1, dataType);
410
                        if (bandG != null)
411 13130 bsanchez
                                        g = bandG.readRaster(x, y, w, 1, w, 1, dataType);
412 13128 bsanchez
                        if (bandB != null)
413 13130 bsanchez
                                        b = bandB.readRaster(x, y, w, 1, w, 1, dataType);
414
                                }
415
416 13128 bsanchez
                lastReadLine += stepY;
417 13130 bsanchez
418
                        int i=0;
419
                        double j = 0D;
420
                        double initOffset =  Math.abs(currentViewX - ((int)currentViewX));
421
422
                        if (dataType == GDT_CInt16 || dataType == GDT_Int16  || dataType == GDT_UInt16){
423
                                if (g == null){ // Sibgle Band (Typical DEM)
424
                                        for (int k=0; k<4; k++){
425
                                                for (i=0, j = initOffset; i<currentViewWidth && j<r.getSize(); i++, j+=stepX) {
426
                                                        if(k<3)
427
                                                                line[i][k] = (r.buffShort[(int) j] & 0xffff);
428
                                                        else
429
                                                                line[i][3] = 0xff;
430
                                                }
431
                                                }
432
                                }else { // Multiband
433
                                        //System.err.println("readLine(): Raster 16bits multibanda");
434
                                        GdalBuffer [] bands = {r,g,b};
435
                                        for (int k=0; k<4; k++){
436
                                                        for (i=0, j = initOffset; i<currentViewWidth && j<r.getSize(); i++, j+=stepX){
437
                                                                if(k<3)
438
                                                                        line[i][k] = (bands[k].buffShort[(int) j] & 0xffff);
439
                                                                else
440
                                                                        line[i][3] = 0xff;
441
                                                        }
442
                                        }
443
                                }
444
                        }else if(dataType == GDT_Float32){
445
                                GdalBuffer [] bands = {r,g,b};
446 13128 bsanchez
                        for (int k=0; k<4; k++){
447 13130 bsanchez
                                                for (i=0, j = initOffset; i<currentViewWidth && j<r.getSize(); i++, j+=stepX){
448
                                                        if(k < 3)
449
                                                                line[i][k] = (int)bands[0].buffFloat[(int) j];
450
                                                        else
451
                                                                line[i][3] = 0xff;
452
                                                }
453 13128 bsanchez
                        }
454 13130 bsanchez
                        }
455
456 13128 bsanchez
                return;
457
        }
458 13130 bsanchez
459 13128 bsanchez
        //int liney = 0;
460
        int readLineRGBA(int [] line) throws GdalException {
461
                int err = 0;
462 13130 bsanchez
463
                                int w = (int) (Math.ceil(((double)currentViewWidth)*stepX) + 1);
464
                                int x = (int) currentViewX;
465
                                int y = (int) lastReadLine;
466
                                GdalBuffer r = null, g = null, b = null, p = null;
467
                                GdalBuffer a = new GdalBuffer();
468
469
                                while(y >= bandR.getRasterBandYSize())
470
                                        y--;
471
472
                                //if (alpha > 0) a = alpha << 24;
473
                                if (x+w > bandR.getRasterBandXSize())
474
                                        w = bandR.getRasterBandXSize()-x;
475
476
                                if(bandR.getRasterColorTable() != null){
477
                                        p = bandR.readRasterWithPalette(x, y, w, 1, w, 1, dataType);
478
                                        a.buffByte = p.buffAPalette;
479
                                        r = new GdalBuffer();
480
                                        r.buffByte = p.buffRPalette;
481
                                        g = new GdalBuffer();
482
                                        g.buffByte = p.buffGPalette;
483
                                        b = new GdalBuffer();
484
                                        b.buffByte = p.buffBPalette;
485
                                }else{
486
                                        r = bandR.readRaster(x, y, w, 1, w, 1, dataType);
487 13128 bsanchez
                        if (bandG != null)
488 13130 bsanchez
                                        g = bandG.readRaster(x, y, w, 1, w, 1, dataType);
489 13128 bsanchez
                        if (bandB != null)
490 13130 bsanchez
                                        b = bandB.readRaster(x, y, w, 1, w, 1, dataType);
491
492
                                        if(metadata.isAlphaBand()){
493
                                        //if(getRasterCount() == 4 && shortName.equals("PNG")){
494
                                                a = bandA.readRaster(x, y, w, 1, w, 1, GDT_Byte);
495
                                        }else{
496
                                        a.buffByte = new byte[w];
497
                                        for (int i = 0;i < w;i++)
498
                                                a.buffByte[i] = (byte)255;
499
                                        }
500
                                }
501
502
                                lastReadLine += stepY;
503
504
                        int i=0;
505
                        double j =  Math.abs(currentViewX - ((int)currentViewX));
506 13128 bsanchez
                int alpha = (this.alpha & 0xff) << 24;
507
508
                if(orientation[0]){ //Pixel size en X positivo
509 13130 bsanchez
                                if (dataType == GDT_Byte){
510
                                        if (g != null)
511
                                                        for (i=0; i<currentViewWidth && j<r.getSize(); i++, j+=stepX) {
512
                                                                int jInt = (int)(j);
513
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) + ((r.buffByte[jInt] & 0xff) << 16) + ((g.buffByte[jInt] & 0xff) << 8) + (b.buffByte[jInt] & 0xff);
514
                                                        }
515
                                                else
516
                                                        for (i=0; i<currentViewWidth && j<r.getSize(); i++, j+=stepX) {
517
                                                                int jInt = (int)(j);
518
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) + ((r.buffByte[jInt] & 0xff) << 16) + ((r.buffByte[jInt] & 0xff) << 8) + (r.buffByte[jInt] & 0xff);
519
                                                        }
520
                                }else if (dataType == GDT_CInt16 || dataType == GDT_Int16  || dataType == GDT_UInt16){
521
                                        if (g == null) // Sibgle Band (Typical DEM)
522
                                                        for (i=0; i<currentViewWidth && j<r.getSize(); i++, j+=stepX) {
523
                                                                int jInt = (int)(j);
524
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) + r.buffShort[jInt];
525
                                                        }
526
                                        else { // Multiband - Raster 16bits multibanda
527
                                                        for (i=0; i<currentViewWidth && j<r.getSize(); i++, j+=stepX) {
528
                                                                int jInt = (int)(j);
529
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) | (((r.buffShort[jInt] & 0xfff0) << 12) & 0xff0000 ) |
530
                                                                                                                                         (((g.buffShort[jInt] & 0xfff0) << 4 ) & 0xff00 ) |
531
                                                                                                                                         (((b.buffShort[jInt] & 0xfff0) >> 4 ) & 0xff );
532
                                                        }
533
                                        }
534
                                }
535 13128 bsanchez
                }else{ //Pixel size en X negativo
536
                        if (dataType == GDT_Byte){
537 13130 bsanchez
                                        if (g != null)
538
                                                        for (i=currentViewWidth - 1; i>=0 && j<r.getSize(); i--, j+=stepX) {
539
                                                                int jInt = (int)(j);
540
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) + ((r.buffByte[jInt] & 0xff) << 16) + ((g.buffByte[jInt] & 0xff) << 8) + (b.buffByte[jInt] & 0xff);
541
                                                        }
542
                                                else
543
                                                        for (i=currentViewWidth - 1; i>=0 && j<r.getSize(); i--, j+=stepX) {
544
                                                                int jInt = (int)(j);
545
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) + ((r.buffByte[jInt] & 0xff) << 16) + ((r.buffByte[jInt] & 0xff) << 8) + (r.buffByte[jInt] & 0xff);
546
                                                        }
547
                                }else if (dataType == GDT_CInt16 || dataType == GDT_Int16  || dataType == GDT_UInt16){
548
                                        if (g == null) // Sibgle Band (Typical DEM)
549
                                                for (i=currentViewWidth - 1; i>=0 && j<r.getSize(); i--, j+=stepX) {
550
                                                                int jInt = (int)(j);
551
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) + r.buffShort[jInt];
552
                                                        }
553
                                        else { // Multiband - Raster 16bits multibanda;
554
                                                for (i=currentViewWidth - 1; i>=0 && j<r.getSize(); i--, j+=stepX) {
555
                                                                int jInt = (int)(j);
556
                                                                line[i] = (alpha & ((a.buffByte[jInt])& 0xff) << 24) | (((r.buffShort[jInt] & 0xfff0) << 12) & 0xff0000 ) |
557
                                                                                                                                         (((g.buffShort[jInt] & 0xfff0) << 4 ) & 0xff00 ) |
558
                                                                                                                                         (((b.buffShort[jInt] & 0xfff0) >> 4 ) & 0xff );
559
                                                        }
560
                                        }
561
                                }
562
563 13128 bsanchez
                }
564
565
                return err;
566
        }
567 13130 bsanchez
568 13128 bsanchez
        /**
569
         * Lee una franja de la imagen.
570
         * @param bandH Altura de la franja
571
         * @param bufH        Altura del buffer
572
         * @param buf        Buffer con la franja (retorno)
573
         * @return
574
         * @throws GdalException
575
         */
576
        public int readBandRGBA(int bandH, int bufH, int [] buf) throws GdalException {
577
                int err = 0;
578 13130 bsanchez
                                int w = (int)(((double)currentViewWidth)*stepX);
579
                                int x = (int)(((double)currentViewX)*stepX);
580
                                int y = (int) lastReadLine;
581
                                int h = (int) (((double)bandH)*stepX);
582
                                System.out.println("Leyendo "+y);
583
                                GdalBuffer r = null, g = null, b = null, p = null;
584
                                GdalBuffer a = new GdalBuffer();
585
586
                                if (x+w > bandR.getRasterBandXSize())
587
                                        w = bandR.getRasterBandXSize()-x;
588
589
                                if(bandR.getRasterColorTable() != null){
590
                                        p = bandR.readRasterWithPalette(x, y, w, h, w, h, GDT_Byte);
591
                                        a.buffByte = p.buffAPalette;
592
                                        r = new GdalBuffer();
593
                                        r.buffByte = p.buffRPalette;
594
                                        g = new GdalBuffer();
595
                                        g.buffByte = p.buffGPalette;
596
                                        b = new GdalBuffer();
597
                                        b.buffByte = p.buffBPalette;
598
                                }else{
599
                                        r = bandR.readRaster(x, y, w, h, w, h, dataType);
600 13128 bsanchez
                        if (bandG != null)
601 13130 bsanchez
                                        g = bandG.readRaster(x, y, w, h, w, h, dataType);
602 13128 bsanchez
                        if (bandB != null)
603 13130 bsanchez
                                        b = bandB.readRaster(x, y, w, h, w, h, dataType);
604
605
                                        if(metadata.isAlphaBand()){
606
                                        //if(getRasterCount() == 4 && shortName.equals("PNG")){
607
                                                a = bandA.readRaster(x, y, w, h, w, h, GDT_Byte);
608
                                        }else{
609
                                        a.buffByte = new byte[w];
610
                                        for (int i = 0;i < w*h;i++)
611
                                                a.buffByte[i] = (byte)255;
612
                                        }
613
                                }
614
615
                                lastReadLine += ((double)bandH)*stepY;
616
617
                        // TODO Acabar de implementarlo
618
                        float k=0F;
619 13128 bsanchez
                int alpha = (this.alpha & 0xff) << 24;
620 13130 bsanchez
                        for (int j=0, t=0; j<bandH; j++) {
621
                                k = j*w; t=j*currentViewWidth;
622
                                for (int i=0; i<currentViewWidth && k<r.getSize(); i++, k+=stepX) {
623
                                        buf[t+i] = (alpha & ((a.buffByte[(int)j])& 0xff) << 24) + ((r.buffByte[(int) k]) << 16) + ((g.buffByte[(int) k]) << 8) + b.buffByte[(int) k];
624
                                }
625
                        }
626
627 13128 bsanchez
                return err;
628 13130 bsanchez
629 13128 bsanchez
        }
630
631
        /* (non-Javadoc)
632
         * @see org.cresques.io.GeoRasterFile#getData(int, int, int)
633
         */
634
        public Object[] getData(int x, int y) {
635
                try {
636
                        Object[] data = new Object[getRasterCount()];
637
                        for(int i = 0; i < getRasterCount(); i++){
638
                                GdalRasterBand rb = getRasterBand(i + 1);
639
                                GdalBuffer r = rb.readRaster(x, y, 1, 1, 1, 1, dataType);
640
                                switch(dataType){
641
                                case 0:        break;                                                                        //Sin tipo
642
                                case 1:        data[i] = new Integer(r.buffByte[0]);         //Buffer byte (8)
643
                                                break;
644
                                case 2:                                                                                        //Buffer short (16)
645
                                case 3:        data[i] = new Integer(r.buffShort[0]);        //Buffer short (16)
646
                                                break;
647
                                case 4:                                                                                        //Buffer int (32)
648
                                case 5: data[i] = new Integer(r.buffInt[0]);        //Buffer int (32)
649
                                                break;
650
                                case 6:        data[i] = new Float(r.buffFloat[0]);        //Buffer float (32)
651
                                                break;
652
                                case 7:        data[i] = new Double(r.buffDouble[0]);        //Buffer double (64)
653
                                                break;
654
                                }
655
                        }
656
                        return data;
657
                } catch (GdalException e) {
658
                        return null;
659
                }
660
        }
661 13130 bsanchez
662 13128 bsanchez
        void pintaInfo() {
663
                try {
664
                        //System.out.println("Origin = "+originX+","+originY);
665
                        //System.out.println("Origin = "+this.);
666
                        System.out.println("GeoTransform:");
667
                        GeoTransform trans = getGeoTransform();
668
                        for (int i=0; i<6; i++)
669
                                System.out.println("  param["+i+"]="+trans.adfgeotransform[i]);
670
                        System.out.println("Metadata:");
671
                        String [] metadata = getMetadata();
672
                        for (int i=0; i<metadata.length; i++) {
673
                                System.out.println(metadata[i]);
674
                        }
675
                } catch (GdalException e) {
676 13130 bsanchez
677 13128 bsanchez
                }
678 13130 bsanchez
679 13128 bsanchez
        }
680 13130 bsanchez
681 13128 bsanchez
        void pintaPaleta() {
682
        }
683 13130 bsanchez
684 13128 bsanchez
        public int getBlockSize(){
685
                return this.getBlockSize();
686
        }
687
688
        /**
689
         * Obtiene el objeto que contiene los metadatos
690
         */
691
        public Metadata getMetadataJavaObject() {
692
                return metadata;
693
        }
694
695
        /**
696
         * Obtiene el flag que dice si la imagen est? o no georreferenciada
697
         * @return true si est? georreferenciada y false si no lo est?.
698
         */
699
        public boolean isGeoreferenced() {
700
                return georeferenced;
701
        }
702
}
703
704
/**
705
 * @author Luis W. Sevilla
706
 */
707
public class GdalFile extends GeoRasterFile {
708
        public final static int         BAND_HEIGHT = 64;
709
        protected GdalNative                 file = null;
710
711
        private Extent v = null;
712 13130 bsanchez
713 13128 bsanchez
        public GdalFile(IProjection proj, String fName){
714
                super(proj, fName);
715
                extent = new Extent();
716
                try {
717
                        file = new GdalNative(fName);
718
                        load();
719
                        readGeoInfo(fName);
720 13130 bsanchez
                        bandCount = file.getRasterCount();
721 13128 bsanchez
                        if ( bandCount > 2) {
722
                                setBand(RED_BAND,   0);
723
                                setBand(GREEN_BAND, 1);
724
                                setBand(BLUE_BAND,  2);
725
                        } else
726
                                setBand(RED_BAND|GREEN_BAND|BLUE_BAND, 0);
727
                } catch(Exception e){
728 13130 bsanchez
                                System.out.println("Error en GdalOpen");
729
                                e.printStackTrace();
730
                                file = null;
731 13128 bsanchez
                }
732 13130 bsanchez
733 13128 bsanchez
                switch(file.getDataType()){
734 13130 bsanchez
                case 1:setDataType(DataBuffer.TYPE_BYTE);break;//GDT_BYTE
735
                case 2://GDT_UInt16
736
                case 3:setDataType(DataBuffer.TYPE_SHORT);break;//GDT_Int16
737 13128 bsanchez
                case 4://GDT_UInt32
738
                case 5:setDataType(DataBuffer.TYPE_INT);break;//GDT_Int32
739
                case 6:setDataType(DataBuffer.TYPE_FLOAT);break;//GDT_Float32
740
                case 7:setDataType(DataBuffer.TYPE_DOUBLE);break;//GDT_Float64
741
                case 8:setDataType(DataBuffer.TYPE_UNDEFINED);break;//GDT_CInt16
742
                case 9:setDataType(DataBuffer.TYPE_UNDEFINED);break;//GDT_CInt32
743
                case 10:setDataType(DataBuffer.TYPE_UNDEFINED);break;//GDT_CFloat32
744
                case 11:setDataType(DataBuffer.TYPE_UNDEFINED);break;//GDT_CFloat64
745
                }
746 13130 bsanchez
747 13128 bsanchez
        }
748 13130 bsanchez
749 13128 bsanchez
        /**
750
         * Obtenemos o calculamos el extent de la imagen.
751
         */
752 13173 bsanchez
        public GeoFileSE load() {
753 13128 bsanchez
                extent = new Extent(file.bBoxRot.minX, file.bBoxRot.minY, file.bBoxRot.maxX, file.bBoxRot.maxY);
754
                requestExtent = new Extent(file.bBoxWithoutRot.minX, file.bBoxWithoutRot.minY, file.bBoxWithoutRot.maxX, file.bBoxWithoutRot.maxY);
755
                return this;
756
        }
757 13130 bsanchez
758 13128 bsanchez
        /**
759
         * Cierra el fichero de imagen
760
         */
761
        public void close() {
762
                try {
763
                        if(file != null){
764
                                file.close();
765
                                file = null;
766
                        }
767
                } catch (GdalException e) {
768
                        // TODO Auto-generated catch block
769
                        e.printStackTrace();
770
                }
771
        }
772 13130 bsanchez
773 13128 bsanchez
        /**
774
         * Asigna a cada banda R,G o B una banda de la imagen
775
         */
776
        public void setBand(int flag, int bandNr) {
777
                super.setBand(flag, bandNr);
778
                if ((flag & GeoRasterFile.RED_BAND) == GeoRasterFile.RED_BAND) file.rBandNr = bandNr+1;
779
                if ((flag & GeoRasterFile.GREEN_BAND) == GeoRasterFile.GREEN_BAND) file.gBandNr = bandNr+1;
780
                if ((flag & GeoRasterFile.BLUE_BAND) == GeoRasterFile.BLUE_BAND) file.bBandNr = bandNr+1;
781
        }
782 13130 bsanchez
783 13128 bsanchez
        /**
784
         * Asigna el extent de la vista actual. existe un fichero .rmf debemos hacer una transformaci?n
785
         * de la vista asignada ya que la petici?n viene en coordenadas del fichero .rmf y la vista (v)
786
         * ha de estar en coordenadas del fichero.
787
         */
788 13130 bsanchez
        public void setView(Extent e) {
789 13128 bsanchez
                if(rmfExists){
790 13130 bsanchez
791 13128 bsanchez
                        Point2D.Double petInit = null, petEnd = null;
792
                        try{
793
                                petInit = new Point2D.Double(e.minX(),  e.maxY());
794
                                petEnd = new Point2D.Double(e.maxX(), e.minY());
795
                                transformRMF.inverseTransform(petInit, petInit);
796
                                transformRMF.inverseTransform(petEnd, petEnd);
797
                                transformTFW.transform(petInit, petInit);
798
                                transformTFW.transform(petEnd, petEnd);
799
                        }catch(NoninvertibleTransformException ex){}
800
                        double h = file.bBoxWithoutRot.maxY - file.bBoxWithoutRot.minY;
801
                        if(!file.isGeoreferenced())
802 13130 bsanchez
                                v = new Extent(        petInit.getX(), h - petInit.getY(), petEnd.getX(), h - petEnd.getY());
803 13128 bsanchez
                        else
804
                                v = new Extent(        petInit.getX(), petInit.getY(), petEnd.getX(), petEnd.getY());
805 13130 bsanchez
806 13128 bsanchez
                }else
807 13130 bsanchez
                        v = new Extent(e.minX(), e.minY(), e.maxX(), e.maxY());
808 13128 bsanchez
        }
809 13130 bsanchez
810 13128 bsanchez
         /**
811
         * Calcula la transformaci?n que se produce sobre la vista cuando la imagen tiene un fichero .rmf
812
         * asociado. En Gdal el origen de coordenadas en Y es el valor m?nimo y crece hasta el m?ximo. De la
813
         * misma forma calcula la matriz de transformaci?n de la cabecera del fichero o del world file asociado
814
         * @param originX Origen de la imagen en la coordenada X
815
         * @param originY Origen de la imagen en la coordenada Y
816
         */
817 13130 bsanchez
        public void setExtentTransform(double originX, double originY, double psX, double psY) {
818 13128 bsanchez
                transformRMF.setToTranslation(originX, originY);
819
                transformRMF.scale(psX, psY);
820 13130 bsanchez
821
                if(file.trans != null){
822 13128 bsanchez
                        transformTFW.setToTranslation(file.trans.adfgeotransform[0], file.trans.adfgeotransform[3]);
823
                        transformTFW.scale(file.trans.adfgeotransform[1], file.trans.adfgeotransform[5]);
824
                }
825
        }
826 13130 bsanchez
827 13128 bsanchez
        /**
828
         * Obtiene extent de la vista actual
829
         */
830 13130 bsanchez
        public Extent getView() {
831
                return v;
832 13128 bsanchez
        }
833 13130 bsanchez
834 13128 bsanchez
        /**
835
         * Obtiene la anchura del fichero
836
         */
837 13130 bsanchez
        public int getWidth() {
838
                return file.width;
839 13128 bsanchez
        }
840 13130 bsanchez
841 13128 bsanchez
        /**
842
         * Obtiene la altura del fichero
843
         */
844 13130 bsanchez
        public int getHeight() {
845 13128 bsanchez
                return file.height;
846
        }
847
848
        /* (non-Javadoc)
849
         * @see org.cresques.io.GeoRasterFile#reProject(org.cresques.cts.ICoordTrans)
850
         */
851
        public void reProject(ICoordTrans rp) {
852
                // TODO Auto-generated method stub
853
        }
854 13130 bsanchez
855 13128 bsanchez
        /**
856
         * Obtiene la orientaci?n de la imagen a partir del signo del tama?o de pixel para poder
857 13130 bsanchez
         * asignarlo en el setView. Esto es util para poder conocer como debe leerse la image,
858
         * de abajo a arriba, de arriba a abajo, de izquierda a derecha o de derecha a izquierda.
859
         * La posici?n habitual es la que el pixel size en X es positivo y en Y negativo leyendose
860 13128 bsanchez
         * en este caso las X de menor a mayor y las Y de mayor a menor. Los casos posibles son:
861
         * <UL>
862
         * <LI><B>X > 0; Y < 0;</B> {true, false}</LI>
863
         * <LI><B>X > 0; Y > 0;</B> {true, true}</LI>
864
         * <LI><B>X < 0; Y > 0;</B> {false, true}</LI>
865
         * <LI><B>X < 0; Y < 0;</B> {false, false}</LI>
866
         * </UL>
867 13130 bsanchez
         *
868 13128 bsanchez
         * @return
869
         */
870
        private boolean[] getOrientation(){
871
                boolean[] orientation = {true, false};
872
                if(!rmfExists){
873
                        if(file.trans != null && file.trans.adfgeotransform != null && file.trans.adfgeotransform[5] > 0)
874
                                orientation[1] = true;
875
                        if(file.trans != null && file.trans.adfgeotransform != null && file.trans.adfgeotransform[1] < 0)
876
                                orientation[0] = false;
877
                }else{
878
                        if(rmfTransform.getScaleY() > 0)
879
                                orientation[1] = true;
880
                        if(rmfTransform.getScaleX() < 0)
881
                                orientation[0] = false;
882
                }
883
                return orientation;
884
        }
885 13130 bsanchez
886 13128 bsanchez
        /* (non-Javadoc)
887
         * @see org.cresques.io.GeoRasterFile#updateImage(int, int, org.cresques.cts.ICoordTrans)
888
         */
889
        public Image updateImage(int width, int height, ICoordTrans rp) {
890
                int line, pRGBArray[] = null;
891
                Image image = null;
892 13130 bsanchez
893 13128 bsanchez
                if (mustVerifySize()) {
894
                        // Work out the correct aspect for the setView call.
895
                        double dFileAspect = (double)v.width()/(double)v.height();
896
                        double dWindowAspect = (double)width /(double)height;
897 13130 bsanchez
898 13128 bsanchez
                        if (dFileAspect > dWindowAspect) {
899 13130 bsanchez
                                height =(int)((double)width/dFileAspect);
900 13128 bsanchez
                        } else {
901 13130 bsanchez
                                width = (int)((double)height*dFileAspect);
902 13128 bsanchez
                        }
903
                }
904 13130 bsanchez
905
                // Set the view
906 13128 bsanchez
                file.setView(v.minX(), v.maxY(), v.maxX(), v.minY(),
907
                        width, height, getOrientation());
908 13130 bsanchez
909 13128 bsanchez
                if(width<=0)width=1;
910
                if(height<=0)height=1;
911 13130 bsanchez
912 13128 bsanchez
                image = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
913
                //image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
914
                pRGBArray = new int[width/**BAND_HEIGHT*/];
915
                try {
916
                        //int nLin = height % BAND_HEIGHT;
917
                        file.setAlpha(getAlpha());
918
                        setBand(RED_BAND,   rBandNr);
919
                        setBand(GREEN_BAND, gBandNr);
920
                        setBand(BLUE_BAND,  bBandNr);
921
                        for (line=0; line < height; line++) { //+=BAND_HEIGHT) {
922
                                //int bandH = Math.min(BAND_HEIGHT, height-line);
923
                                //file.readBandRGBA(bandH, BAND_HEIGHT, pRGBArray);
924
                                file.readLineRGBA(pRGBArray);
925
                                setRGBLine((BufferedImage) image, 0, line, width, 1/*bandH*/, pRGBArray, 0, width);
926
                        }
927
                } catch (Exception e) {
928
                        // TODO Auto-generated catch block
929
                        e.printStackTrace();
930
                }
931 13130 bsanchez
932 13128 bsanchez
                return image;
933
        }
934 13130 bsanchez
935 13128 bsanchez
        public RasterBuf getRaster(int width, int height, ICoordTrans rp) {
936
                int line;
937
                RasterBuf raster = null;
938 13130 bsanchez
939 13128 bsanchez
                if(mustVerifySize()){
940
                        // Work out the correct aspect for the setView call.
941
                        double dFileAspect = (double)v.width()/(double)v.height();
942
                        double dWindowAspect = (double)width /(double)height;
943 13130 bsanchez
944 13128 bsanchez
                        if (dFileAspect > dWindowAspect) {
945 13130 bsanchez
                                height =(int)((double)width/dFileAspect);
946 13128 bsanchez
                        } else {
947 13130 bsanchez
                                width = (int)((double)height*dFileAspect);
948 13128 bsanchez
                        }
949
                }
950 13130 bsanchez
951 13128 bsanchez
                // Set the view
952
                boolean[] orientation = getOrientation();
953
                file.setView(v.minX(), v.maxY(), v.maxX(), v.minY(),
954
                        width, height, orientation);
955 13130 bsanchez
956 13128 bsanchez
                raster = new RasterBuf(DataBuffer.TYPE_INT, width, height, 4, new Point(0,0));
957
                try {
958
959
                        file.setAlpha(getAlpha());
960
                        setBand(RED_BAND,   rBandNr);
961
                        setBand(GREEN_BAND, gBandNr);
962
                        setBand(BLUE_BAND,  bBandNr);
963
                        for (line=0; line < height; line++) { //+=BAND_HEIGHT) {
964
                                file.readLine(raster.getLineInt(line));
965
                        }
966
                } catch (Exception e) {
967
                        e.printStackTrace();
968
                }
969 13130 bsanchez
970 13128 bsanchez
                return raster;
971
        }
972 13130 bsanchez
973 13128 bsanchez
        /**
974 13130 bsanchez
         * Asigna al objeto Image los valores con los dato de la imagen contenidos en el
975 13128 bsanchez
         * vector de enteros.
976
         * @param image        imagen con los datos actuales
977
         * @param startX        inicio de la posici?n en X dentro de la imagen
978
         * @param startY        inicio de la posici?n en X dentro de la imagen
979
         * @param w        Ancho de la imagen
980
         * @param h        Alto de la imagen
981
         * @param rgbArray        vector que contiene la banda que se va a sustituir
982
         * @param offset        desplazamiento
983
         * @param scansize        tama?o de imagen recorrida por cada p
984
         */
985 13130 bsanchez
        protected void setRGBLine(BufferedImage image, int startX, int startY, int w, int h, int[] rgbArray,
986 13128 bsanchez
                         int offset, int scansize) {
987
                image.setRGB(startX, startY, w, h, rgbArray, offset, scansize);
988
        }
989 13130 bsanchez
990 13128 bsanchez
        /**
991 13130 bsanchez
         * Asigna al objeto Image la mezcla entre los valores que ya tiene y los valores
992 13128 bsanchez
         * con los dato de la imagen contenidos en el vector de enteros. De los valores RGB
993
         * que ya contiene se mantienen las bandas que no coinciden con el valor de flags. La
994
         * banda correspondiente a flags es sustituida por los datos del vector.
995
         * @param image        imagen con los datos actuales
996
         * @param startX        inicio de la posici?n en X dentro de la imagen
997
         * @param startY        inicio de la posici?n en X dentro de la imagen
998
         * @param w        Ancho de la imagen
999
         * @param h        Alto de la imagen
1000
         * @param rgbArray        vector que contiene la banda que se va a sustituir
1001
         * @param offset        desplazamiento
1002
         * @param scansize        tama?o de imagen recorrida por cada paso
1003
         * @param flags        banda que se va a sustituir (Ctes de GeoRasterFile)
1004
         */
1005 13130 bsanchez
        protected void setRGBLine(BufferedImage image, int startX, int startY, int w, int h, int[] rgbArray,
1006 13128 bsanchez
                         int offset, int scansize, int flags) {
1007 13130 bsanchez
                int [] line = new int[rgbArray.length];
1008 13128 bsanchez
                image.getRGB(startX, startY, w, h, line, offset, scansize);
1009
                if (flags == GeoRasterFile.RED_BAND)
1010
                        for (int i=0; i<line.length; i++)
1011
                                line[i] = (line[i] & 0x0000ffff) | (rgbArray[i] & 0xffff0000);
1012
                else if (flags == GeoRasterFile.GREEN_BAND)
1013
                        for (int i=0; i<line.length; i++)
1014
                                line[i] = (line[i] & 0x00ff00ff) | (rgbArray[i] & 0xff00ff00);
1015
                else if (flags == GeoRasterFile.BLUE_BAND)
1016
                        for (int i=0; i<line.length; i++)
1017
                                line[i] = (line[i] & 0x00ffff00) | (rgbArray[i] & 0xff0000ff);
1018
                image.setRGB(startX, startY, w, h, line, offset, scansize);
1019
        }
1020 13130 bsanchez
1021 13128 bsanchez
        /**
1022 13130 bsanchez
         * Asigna al objeto Image la mezcla entre los valores que ya tiene y los valores
1023 13128 bsanchez
         * con los dato de la imagen contenidos en el vector de enteros. De los valores RGB
1024
         * que ya contiene se mantienen las bandas que no coinciden con el valor de flags. La
1025
         * banda correspondiente a flags es sustituida por los datos del vector.
1026
         * @param image        imagen con los datos actuales
1027
         * @param startX        inicio de la posici?n en X dentro de la imagen
1028
         * @param startY        inicio de la posici?n en X dentro de la imagen
1029
         * @param w        Ancho de la imagen
1030
         * @param h        Alto de la imagen
1031
         * @param rgbArray        vector que contiene la banda que se va a sustituir
1032
         * @param offset        desplazamiento
1033
         * @param scansize        tama?o de imagen recorrida por cada paso
1034
         * @param origBand        Banda origen del GeoRasterFile
1035
         * @param destBandFlag        banda que se va a sustituir (Ctes de GeoRasterFile)
1036
         */
1037 13130 bsanchez
        protected void setRGBLine(BufferedImage image, int startX, int startY, int w, int h, int[] rgbArray,
1038 13128 bsanchez
                         int offset, int scansize, int origBand, int destBandFlag) {
1039 13130 bsanchez
                int [] line = new int[rgbArray.length];
1040 13128 bsanchez
                image.getRGB(startX, startY, w, h, line, offset, scansize);
1041
                if (origBand == 0 && destBandFlag == GeoRasterFile.RED_BAND)
1042
                        for (int i=0; i<line.length; i++)
1043
                                line[i] = (line[i] & 0x0000ffff) | (rgbArray[i] & 0xffff0000);
1044
                else if (origBand == 1 && destBandFlag == GeoRasterFile.GREEN_BAND)
1045
                        for (int i=0; i<line.length; i++)
1046
                                line[i] = (line[i] & 0x00ff00ff) | (rgbArray[i] & 0xff00ff00);
1047
                else if (origBand == 2 && destBandFlag == GeoRasterFile.BLUE_BAND)
1048
                        for (int i=0; i<line.length; i++)
1049
                                line[i] = (line[i] & 0x00ffff00) | (rgbArray[i] & 0xff0000ff);
1050 13130 bsanchez
1051 13128 bsanchez
                else if (origBand == 0 && destBandFlag == GeoRasterFile.GREEN_BAND)
1052
                        for (int i=0; i<line.length; i++)
1053
                                line[i] = (line[i] & 0xffff00ff) | ((rgbArray[i] & 0x00ff0000) >> 8) ;
1054
                else if (origBand == 0 && destBandFlag == GeoRasterFile.BLUE_BAND)
1055
                        for (int i=0; i<line.length; i++)
1056
                                line[i] = (line[i] & 0xffffff00) | ((rgbArray[i] & 0x00ff0000) >> 16);
1057
                else if (origBand == 1 && destBandFlag == GeoRasterFile.RED_BAND)
1058
                        for (int i=0; i<line.length; i++)
1059
                                line[i] = (line[i] & 0xff00ffff) | ((rgbArray[i] & 0x0000ff00) << 8);
1060 13130 bsanchez
1061 13128 bsanchez
                else if (origBand == 1 && destBandFlag == GeoRasterFile.BLUE_BAND)
1062
                        for (int i=0; i<line.length; i++)
1063
                                line[i] = (line[i] & 0xffffff00) | ((rgbArray[i] & 0x0000ff00) >> 8);
1064
                else if (origBand == 2 && destBandFlag == GeoRasterFile.RED_BAND)
1065
                        for (int i=0; i<line.length; i++)
1066
                                line[i] = (line[i] & 0xff00ffff) | ((rgbArray[i] & 0x000000ff) << 16);
1067
                else if (origBand == 2 && destBandFlag == GeoRasterFile.GREEN_BAND)
1068
                        for (int i=0; i<line.length; i++)
1069
                                line[i] = (line[i] & 0xffff00ff) | ((rgbArray[i] & 0x000000ff) << 8);
1070
                image.setRGB(startX, startY, w, h, line, offset, scansize);
1071
        }
1072 13130 bsanchez
1073
        /*
1074 13128 bsanchez
        private void showOnOpen() {
1075 13130 bsanchez
                        // Report en la apertura (quitar)
1076
                        System.out.println("Fichero GDAL '"+getName()+"' abierto.");
1077
                        System.out.println("Version = "+file.version);
1078
                        System.out.println("   Size = ("+file.width+","+file.height+")");
1079
                        try {
1080 13128 bsanchez
                        System.out.println("   NumBands = ("+file.getRasterCount()+")");
1081
                } catch (GdalException e) {
1082
                        // TODO Auto-generated catch block
1083
                        e.printStackTrace();
1084
                }
1085 13130 bsanchez
                        //file.pintaInfo();
1086
                        file.pintaPaleta();
1087 13128 bsanchez

1088
        }
1089 13130 bsanchez
        */
1090 13128 bsanchez
1091
        /* (non-Javadoc)
1092
         * @see org.cresques.io.GeoRasterFile#updateImage(int, int, org.cresques.cts.ICoordTrans, java.awt.Image, int, int)
1093
         */
1094
        public Image updateImage(int width, int height, ICoordTrans rp, Image img, int origBand, int destBandFlag)throws SupersamplingNotSupportedException{
1095
                int line, pRGBArray[] = null;
1096 13130 bsanchez
1097 13128 bsanchez
                if(mustVerifySize()){
1098
                        // Work out the correct aspect for the setView call.
1099
                        double dFileAspect = (double)v.width()/(double)v.height();
1100
                        double dWindowAspect = (double)width /(double)height;
1101 13130 bsanchez
1102 13128 bsanchez
                        if (dFileAspect > dWindowAspect) {
1103 13130 bsanchez
                                height =(int)((double)width/dFileAspect);
1104 13128 bsanchez
                        } else {
1105 13130 bsanchez
                                width = (int)((double)height*dFileAspect);
1106 13128 bsanchez
                        }
1107
                }
1108 13130 bsanchez
1109 13128 bsanchez
                // Set the view
1110
                boolean[] orientation = getOrientation();
1111
                file.setView(v.minX(), v.maxY(), v.maxX(), v.minY(),
1112
                        width, height, orientation);
1113 13130 bsanchez
1114 13128 bsanchez
                if(width<=0)width=1;
1115
                if(height<=0)height=1;
1116 13130 bsanchez
1117 13128 bsanchez
                pRGBArray = new int[width];
1118
                try {
1119
                        setBand(RED_BAND,   rBandNr);
1120
                        setBand(GREEN_BAND, gBandNr);
1121
                        setBand(BLUE_BAND,  bBandNr);
1122
                        file.setAlpha(getAlpha());
1123
                        if(img!=null){
1124
                                if(orientation[1]){
1125
                                        for (line=0; line < height; line++) {
1126
                                                file.readLineRGBA(pRGBArray);
1127
                                                setRGBLine((BufferedImage) img, 0, height - 1 - line, width, 1, pRGBArray, 0, width, origBand, destBandFlag);
1128 13130 bsanchez
                                        }
1129 13128 bsanchez
                                }else{
1130
                                        for (line=0; line < height; line++) {
1131
                                                file.readLineRGBA(pRGBArray);
1132
                                                setRGBLine((BufferedImage) img, 0, line, width, 1, pRGBArray, 0, width, origBand, destBandFlag);
1133
                                        }
1134
                                }
1135
                                return img;
1136
                        }else{
1137
                                Image image = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
1138
                                if(orientation[1]){
1139
                                        for (line=0; line < height; line++) {
1140
                                                file.readLineRGBA(pRGBArray);
1141
                                                setRGBLine((BufferedImage) image, 0, height - 1 - line, width, 1, pRGBArray, 0, width);
1142 13130 bsanchez
                                        }
1143 13128 bsanchez
                                }else{
1144
                                        for (line=0; line < height; line++) {
1145
                                                file.readLineRGBA(pRGBArray);
1146
                                                setRGBLine((BufferedImage) image, 0, line, width, 1, pRGBArray, 0, width);
1147
                                        }
1148
                                }
1149
                                return image;
1150
                        }
1151
                } catch (Exception e) {
1152
                        // TODO Auto-generated catch block
1153
                        e.printStackTrace();
1154
                }
1155 13130 bsanchez
1156 13128 bsanchez
                return img;
1157
        }
1158 13130 bsanchez
1159 13128 bsanchez
        /* (non-Javadoc)
1160
         * @see org.cresques.io.GeoRasterFile#getData(int, int, int)
1161
         */
1162
        public Object getData(int x, int y, int band) {
1163
                if(file != null){
1164
                        Object[] data = file.getData(x, y);
1165
                        return data[band];
1166
                }
1167
                return null;
1168
        }
1169 13130 bsanchez
1170 13128 bsanchez
        /**
1171
         * Devuelve los datos de una ventana solicitada
1172
         * @param ulX        coordenada X superior izda.
1173
         * @param ulY        coordenada Y superior derecha.
1174
         * @param sizeX        tama?o en X de la ventana.
1175
         * @param sizeY tama?o en Y de la ventana.
1176
         * @param band        Banda solicitada.
1177
         */
1178
        public byte[] getWindow(int ulX, int ulY, int sizeX, int sizeY, int band){
1179 13130 bsanchez
1180 13128 bsanchez
                return null;
1181
        }
1182 13130 bsanchez
1183 13128 bsanchez
        /**
1184
         * Obtiene la zona (Norte / Sur)
1185
         * @return true si la zona es norte y false si es sur
1186
         */
1187 13130 bsanchez
1188 13128 bsanchez
        public boolean getZone(){
1189 13130 bsanchez
1190 13128 bsanchez
                return false;
1191
        }
1192 13130 bsanchez
1193 13128 bsanchez
        /**
1194
         *Devuelve el n?mero de zona UTM
1195 13130 bsanchez
         *@return N?mero de zona
1196 13128 bsanchez
         */
1197 13130 bsanchez
1198 13128 bsanchez
        public int getUTM(){
1199 13130 bsanchez
1200
                return 0;
1201 13128 bsanchez
        }
1202 13130 bsanchez
1203 13128 bsanchez
        /**
1204
         * Obtiene el sistema de coordenadas geograficas
1205
         * @return Sistema de coordenadas geogr?ficas
1206
         */
1207
        public String getGeogCS(){
1208 13130 bsanchez
1209
                return new String("");
1210 13128 bsanchez
        }
1211 13130 bsanchez
1212 13128 bsanchez
        /**
1213
         * Devuelve el tama?o de bloque
1214
         * @return Tama?o de bloque
1215
         */
1216
        public int getBlockSize(){
1217 13130 bsanchez
                return file.getBlockSize();
1218 13128 bsanchez
        }
1219 13130 bsanchez
1220 13128 bsanchez
        /**
1221
         * Obtiene el objeto que contiene los metadatos
1222
         */
1223
        public Metadata getMetadata() {
1224
                if(file != null)
1225
                        return file.getMetadataJavaObject();
1226 13130 bsanchez
                else
1227 13128 bsanchez
                        return null;
1228
        }
1229 13130 bsanchez
1230 13128 bsanchez
        /**
1231
         * Obtiene el flag que dice si la imagen est? o no georreferenciada
1232
         * @return true si est? georreferenciada y false si no lo est?.
1233
         */
1234
        public boolean isGeoreferenced() {
1235
                return file.isGeoreferenced();
1236
        }
1237 13130 bsanchez
1238 13128 bsanchez
        /**
1239
         * Obtiene los par?metros de la transformaci?n af?n que corresponde con los elementos de
1240
         * un fichero tfw.
1241 13130 bsanchez
         * <UL>
1242 13128 bsanchez
         * <LI>[1]tama?o de pixel en X</LI>
1243
         * <LI>[2]rotaci?n en X</LI>
1244
         * <LI>[4]rotaci?n en Y</LI>
1245
         * <LI>[5]tama?o de pixel en Y</LI>
1246
         * <LI>[0]origen en X</LI>
1247
         * <LI>[3]origen en Y</LI>
1248
         * </UL>
1249
         * Este m?todo debe ser reimplementado por el driver si tiene esta informaci?n. En principio
1250
         * Gdal es capaz de proporcionarla de esta forma.
1251 13130 bsanchez
         *
1252 13128 bsanchez
         * En caso de que exista fichero .rmf asociado al raster pasaremos de la informaci?n de georreferenciaci?n
1253
         * del .tfw y devolveremos la que est? asociada al rmf
1254
         * @return vector de double con los elementos de la transformaci?n af?n.
1255
         */
1256
        public double[] getTransform(){
1257
                if(file != null && file.trans != null && !this.rmfExists())
1258
                        return file.trans.adfgeotransform;
1259
                else{
1260
                        if(this.rmfExists){
1261 13130 bsanchez
                                double[] rmfGeoref = {        rmfTransform.getTranslateX(),
1262 13128 bsanchez
                                                                                rmfTransform.getScaleX(),
1263 13130 bsanchez
                                                                                rmfTransform.getShearX(),
1264 13128 bsanchez
                                                                                rmfTransform.getTranslateY(),
1265
                                                                                rmfTransform.getShearY(),
1266
                                                                                rmfTransform.getScaleY()};
1267
                                return rmfGeoref;
1268
                        }
1269
                        return null;
1270
                }
1271 13130 bsanchez
1272 13128 bsanchez
        }
1273
}
1274