Statistics
| Revision:

root / trunk / libraries / libCq CMS for java.old / src / org / cresques / io / MrSidFile.java @ 4974

History | View | Annotate | Download (31 KB)

1
/*
2
 * Cresques Mapping Suite. Graphic Library for constructing mapping applications.
3
 *
4
 * Copyright (C) 2004-5.
5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 2
9
 * of the License, or (at your option) any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307,USA.
19
 *
20
 * For more information, contact:
21
 *
22
 * cresques@gmail.com
23
 */
24
package org.cresques.io;
25

    
26
import java.awt.Image;
27
import java.awt.geom.Point2D;
28
import java.awt.image.BufferedImage;
29
import java.io.IOException;
30
import java.util.Vector;
31

    
32
import org.cresques.cts.ICoordTrans;
33
import org.cresques.cts.IProjection;
34
import org.cresques.io.MrSidNative.Contour;
35
import org.cresques.px.Extent;
36

    
37
import es.gva.cit.jmrsid.LTIColorSpace;
38
import es.gva.cit.jmrsid.LTIDataType;
39
import es.gva.cit.jmrsid.LTIGeoCoord;
40
import es.gva.cit.jmrsid.LTIImageStage;
41
import es.gva.cit.jmrsid.LTIMetadataDatabase;
42
import es.gva.cit.jmrsid.LTIMetadataRecord;
43
import es.gva.cit.jmrsid.LTIPixel;
44
import es.gva.cit.jmrsid.LTIScene;
45
import es.gva.cit.jmrsid.LTISceneBuffer;
46
import es.gva.cit.jmrsid.LTIUtils;
47
import es.gva.cit.jmrsid.MrSIDException;
48
import es.gva.cit.jmrsid.MrSIDImageReader;
49

    
50

    
51
/**
52
 * Soporte para los fichero MrSID de Lizardtech
53
 * @author Nacho Brodin (brodin_ign@gva.es)
54
 */
55
class MrSidNative extends MrSIDImageReader {
56
    static boolean WITH_OVERVIEWS = true;
57

    
58
    /**
59
     * Contorno en coordenadas geogr?ficas. (y Extent del raster).
60
     */
61
    public Contour esq = new Contour();
62
    public int width = 0;
63
    public int height = 0;
64
    public double originX = 0D;
65
    public double originY = 0D;
66
    public String version = "";
67
    public LTIMetadataDatabase metadata;
68
    public LTIPixel pixel = null;
69
    private int alpha = 0;
70
    protected int rBandNr = 1;
71
    protected int gBandNr = 2;
72
    protected int bBandNr = 3;
73
    protected byte[] bandR;
74
    protected byte[] bandG;
75
    protected byte[] bandB;
76
    private int dataType = LTIDataType.LTI_DATATYPE_UINT8;
77

    
78
    //View
79
    double currentViewY = -1;
80
    int currentFullWidth = -1;
81
    int currentFullHeight = -1;
82
    int currentViewWidth = -1;
83
    int currentViewHeight = -1;
84
    double currentViewX = 0D;
85
    double viewportScale = 0D;
86
    double step = 0D;
87
    int currentOverview = -1;
88
    private double zoomoverview = 0.0;
89
    int eColorSpace;
90
    int eSampleType;
91
    public int nbands;
92
    int noverviews;
93
    public int xini;
94
    public int yini;
95
    public int anchoOver;
96
    public int altoOver;
97
    public int blocksize = 1;
98

    
99
    /**
100
     * Constructor
101
     * @param fName
102
     * @throws MrSIDException
103
     * @throws IOException
104
     */
105
    public MrSidNative(String fName) throws MrSIDException, IOException {
106
        super(fName);
107
        init(fName);
108
    }
109
    
110
    /**
111
     * Inicializa las variables de instancia con los valores de la imagen
112
     * @param fName
113
     * @throws MrSIDException
114
     * @throws IOException
115
     */
116
    private void init(String fName) throws MrSIDException, IOException {
117
        this.initialize();
118

    
119
        String ext = fName.toLowerCase().substring(fName.lastIndexOf('.') + 1);
120

    
121
        width = this.getWidth();
122
        height = this.getHeight();
123
        eSampleType = this.getDataType();
124
        nbands = this.getNumBands();
125
        eColorSpace = this.getColorSpace();
126
        noverviews = this.getNumLevels();
127

    
128
        metadata = this.getMetadata();
129

    
130
        double ox = 0D;
131
        double oy = 0D;
132
        double resx = 0D;
133
        double resy = 0D;
134

    
135
        LTIGeoCoord geoc = this.getGeoCoord();
136

    
137
        ox = geoc.getX();
138
        oy = geoc.getY();
139
        resx = geoc.getXRes();
140
        resy = geoc.getYRes();
141

    
142
        System.out.println("Origin = (" + ox + "," + oy + ")");
143
        System.out.println("Pixel Size = (" + resx + "," + resy + ")");
144
        esq.add(new Point2D.Double(ox, oy));
145
        esq.add(new Point2D.Double(ox + (resx * width), oy));
146
        esq.add(new Point2D.Double(ox, oy + (resy * height)));
147
        esq.add(new Point2D.Double(ox + (resx * width), oy + (resy * height)));
148

    
149
        blocksize = this.getStripHeight();
150
        System.out.println("StripHeight = (" + blocksize + ")");
151
    }
152

    
153
    /**
154
     * Asigna el valor de Alpha
155
     * @param a        alpha
156
     */
157
    public void setAlpha(int a) {
158
        alpha = a;
159
    }
160

    
161
    /**
162
     * Asigna el tipo de datos
163
     * @param dt        tipo de datos
164
     */
165
    public void setDataType(int dt) {
166
        dataType = dt;
167
    }
168

    
169
    /**
170
     * Obtiene un punto 2D con las coordenadas del raster a partir de uno en coordenadas
171
     * del punto real.
172
     * @param pt        punto en coordenadas del punto real
173
     * @return        punto en coordenadas del raster
174
     */
175
    public Point2D worldToRaster(Point2D pt) {
176
        double x = (((double) currentFullWidth) / (esq.maxX - esq.minX)) * (pt.getX() -
177
                   esq.minX);
178
        double y = (((double) currentFullHeight) / (esq.maxY - esq.minY)) * (esq.maxY -
179
                   pt.getY());
180
        Point2D ptRes = new Point2D.Double(x, y);
181

    
182
        return ptRes;
183
    }
184

    
185
    /**
186
     * Calcula el overview a usar de la imagen y el viewport a partir del ancho, alto y
187
     * coordenadas del mundo real
188
     * @param dWorldTLX        Coordenada X superior izquierda
189
     * @param dWorldTLY        Coordenada Y superior izquierda
190
     * @param dWorldBRX        Coordenada X inferior derecha
191
     * @param dWorldBRY        Coordenada Y inferior derecha
192
     * @param nWidth        ancho
193
     * @param nHeight        alto
194
     */
195
    public void setView(double dWorldTLX, double dWorldTLY, double dWorldBRX,
196
                        double dWorldBRY, int nWidth, int nHeight) {
197
        //Ancho y alto de la im?gen en pixeles (pixeles de la overview)
198
        currentFullWidth = width;
199
        currentFullHeight = height;
200

    
201
        //Ventana de la imagen. (en tama?o completo)
202
        //tl->esq sup izda en pixeles
203
        //br->esq inf der en pixeles
204
        Point2D tl = worldToRaster(new Point2D.Double(dWorldTLX, dWorldTLY));
205
        Point2D br = worldToRaster(new Point2D.Double(dWorldBRX, dWorldBRY));
206

    
207
        //Ancho y alto de la im?gen (pixeles en pantalla)
208
        currentViewWidth = nWidth;
209
        currentViewHeight = nHeight;
210

    
211
        currentViewX = tl.getX();
212
        currentViewY = tl.getY();
213

    
214
        viewportScale = (double) currentViewWidth / (br.getX() - tl.getX());
215
        currentViewY = tl.getY();
216

    
217
        try {
218
            // calcula el overview a usar
219
            int[] dims = null;
220
            double zoom = 1.0;
221
            zoomoverview = 1.0;
222
            currentOverview = -1;
223

    
224
            if (WITH_OVERVIEWS && ((noverviews - 1) > 0)) {
225
                for (int i = (noverviews - 1); i > 0; i--) {
226
                    zoom = LTIUtils.levelToMag(i);
227
                    dims = this.getDimsAtMag(zoom);
228

    
229
                    if (dims[0] > (this.getWidth() * viewportScale)) {
230
                        currentOverview = i;
231
                        zoomoverview = zoom;
232
                        viewportScale /= zoomoverview;
233
                        currentFullWidth = dims[0];
234
                        currentFullHeight = dims[1];
235
                        tl = worldToRaster(new Point2D.Double(dWorldTLX,
236
                                                              dWorldTLY));
237
                        currentViewX = tl.getX();
238
                        currentViewY = tl.getY();
239

    
240
                        break;
241
                    }
242
                }
243
            }
244

    
245
            setDataType(eSampleType);
246
        } catch (MrSIDException e) {
247
            e.printStackTrace();
248
        }
249
    }
250

    
251
    /**
252
     * Muestra alguna informaci?n para la depuraci?n
253
     */
254
    void pintaInfo() {
255
        try {
256
            System.out.println("GeoTransform:");
257

    
258
            LTIGeoCoord geoc = this.getGeoCoord();
259

    
260
            System.out.println("  param[0]=" + geoc.getX());
261
            System.out.println("  param[0]=" + geoc.getY());
262
            System.out.println("  param[0]=" + geoc.getXRes());
263
            System.out.println("  param[0]=" + geoc.getYRes());
264
            System.out.println("  param[0]=" + geoc.getXRot());
265
            System.out.println("  param[0]=" + geoc.getYRot());
266
            System.out.println("Metadata:");
267

    
268
            LTIMetadataDatabase metadata = this.getMetadata();
269

    
270
            for (int i = 0; i < metadata.getIndexCount(); i++) {
271
                LTIMetadataRecord rec = null;
272
                rec = metadata.getDataByIndex(i);
273
                System.out.println(rec.getTagName());
274

    
275
                if (rec.isScalar()) {
276
                    System.out.println(rec.getScalarData());
277
                } else if (rec.isVector()) {
278
                    String[] s = rec.getVectorData();
279

    
280
                    for (int j = 0; j < s.length; j++)
281
                        System.out.println("V" + j + "->" + s[j]);
282
                } else if (rec.isArray()) {
283
                    String[] s = rec.getArrayData();
284

    
285
                    for (int j = 0; j < s.length; j++)
286
                        System.out.println("A" + j + "->" + s[j]);
287
                } else {
288
                    System.out.println("");
289
                }
290
            }
291
        } catch (MrSIDException e) {
292
            // TODO Auto-generated catch block
293
            e.printStackTrace();
294
        }
295
    }
296

    
297
    void pintaPaleta() {
298
    }
299

    
300
    /**
301
     * Lee la escena de la imagen correspondiente a la vista seleccionada con
302
     * currentView a trav?s de la libreria de MrSid. Esta escena es cargada sobre
303
     * un buffer y asignada al par?metro de salida.
304
     * @param line        Escena leida
305
     * @throws MrSIDException Lanzada si ocurre un error en la lectura de la escena
306
     */
307
    public void readScene(int[] line) throws MrSIDException {
308
        int x = (int) Math.ceil(currentViewX);
309
        int y = (int) Math.ceil(currentViewY);
310
        int SceneWidth;
311
        int SceneHeight;
312

    
313
        try {
314
            if ((x == 0) && (y == 0)) {
315
                SceneWidth = currentFullWidth;
316
                SceneHeight = currentFullHeight;
317
            } else {
318
                                SceneWidth = (int) Math.ceil((((double) currentViewWidth) / viewportScale) + 1);
319
                                if (SceneWidth > currentFullWidth)
320
                                        SceneWidth = currentFullWidth;
321
                                SceneHeight = (int) Math.ceil((((double) currentViewHeight) / viewportScale) + 1);
322
                        if (SceneHeight > currentFullHeight)
323
                                SceneHeight = currentFullHeight;
324
            }
325

    
326
            if (SceneWidth == 0) {
327
                SceneWidth = 1;
328
            }
329

    
330
            if (SceneHeight == 0) {
331
                SceneHeight = 1;
332
            }
333

    
334
            if (pixel == null) {
335
                pixel = new LTIPixel(eColorSpace, nbands, eSampleType);
336
            }
337
            
338
            LTISceneBuffer buffer = null;
339
                        
340
            boolean  hecho = false;
341
                        while (!hecho){
342
                                LTIScene scene = new LTIScene(x, y, SceneWidth, SceneHeight, zoomoverview);
343

    
344
                                // Este deber?a ser el constructor con ventana
345
                                buffer = new LTISceneBuffer(pixel, SceneWidth, SceneHeight, true);
346

    
347
                                hecho = true;
348
                                try {
349
                                        ((LTIImageStage) this).read(scene, buffer);
350
                                        hecho = true;
351
                                } catch (MrSIDException ex) {
352
                                        SceneWidth--;
353
                                        SceneHeight--;
354
                                        hecho = false;
355
                                }
356
                        }
357
                        
358
            if ((dataType == LTIDataType.LTI_DATATYPE_UINT8) ||
359
                    (dataType == LTIDataType.LTI_DATATYPE_SINT8) ||
360
                    (dataType == LTIDataType.LTI_DATATYPE_SINT16) ||
361
                    (dataType == LTIDataType.LTI_DATATYPE_SINT32) ||
362
                    (dataType == LTIDataType.LTI_DATATYPE_UINT16) ||
363
                    (dataType == LTIDataType.LTI_DATATYPE_UINT32)) {
364
                int kd;
365
                int k;
366
                double scale = 1 / viewportScale;
367
                int alpha = (this.alpha & 0xff) << 24;
368
                             
369
                if (rBandNr == 1) {
370
                    bandR = buffer.buf1;
371
                } else if (rBandNr == 2) {
372
                    bandR = buffer.buf2;
373
                } else if (rBandNr == 3) {
374
                    bandR = buffer.buf3;
375
                }
376

    
377
                if (gBandNr == 1) {
378
                    bandG = buffer.buf1;
379
                } else if (gBandNr == 2) {
380
                    bandG = buffer.buf2;
381
                } else if (gBandNr == 3) {
382
                    bandG = buffer.buf3;
383
                }
384

    
385
                if (bBandNr == 1) {
386
                    bandB = buffer.buf1;
387
                } else if (bBandNr == 2) {
388
                    bandB = buffer.buf2;
389
                } else if (bBandNr == 3) {
390
                    bandB = buffer.buf3;
391
                }
392
                
393
                //Desplazamiento para la X y la Y leidas. Estas tienen efecto cuando un pixel no empieza a visualizarse
394
                //justo en su esquina superior izquierda y tiene que ser cortado en la visualizaci?n.
395
                double offsetX = Math.abs(currentViewX - ((int)currentViewX));
396
                double offsetY = Math.abs(currentViewY - ((int)currentViewY));
397
                for (int y1 = 0; y1 < currentViewHeight; y1++)
398
                   for (int x1 = 0; x1 < currentViewWidth; x1++) {
399
                      kd = (y1 * currentViewWidth) + x1;
400
                      k = (((int) ((y1 * scale) + offsetY)) * SceneWidth) + 
401
                                      (int) ((x1 * scale) + offsetX);
402

    
403
                      try {
404
                            line[kd] = alpha + ((0xff & bandR[k]) << 16) +
405
                                                                                                ((0xff & bandG[k]) << 8) +
406
                                                                                                (0xff & bandB[k]);
407
                      } catch (java.lang.ArrayIndexOutOfBoundsException e) {
408
                      }
409
                 }
410
                
411
            
412
            }
413
                /*if (eColorSpace == LTIColorSpace.LTI_COLORSPACE_GRAYSCALE) */
414
            
415
            buffer = null;
416
        } catch (MrSIDException e) {
417
            e.printStackTrace();
418
        }
419
    }
420

    
421
    /**
422
     * Lee una ventana de la imagen y devuelve un buffer de bytes
423
     * @param ulX        Coordenada X de la esquina superior izquierda
424
     * @param ulY        Coordenada Y de la esquina superior izquierda
425
     * @param sizeX        Tama?o X de la imagen
426
     * @param sizeY        Tama?o Y de la image
427
     * @param band        N?mero de bandas
428
     * @return        buffer con la ventana leida
429
     * @throws MrSIDException
430
     */
431
    public byte[] getWindow(int ulX, int ulY, int sizeX, int sizeY, int band)
432
                     throws MrSIDException {
433
        if (pixel == null) {
434
            pixel = new LTIPixel(eColorSpace, nbands, eSampleType);
435
        }
436

    
437
        LTIScene scene = new LTIScene(ulX, ulY, sizeX, sizeY, 1.0);
438
        LTISceneBuffer buffer = new LTISceneBuffer(pixel, sizeX, sizeY, true);
439
        ((LTIImageStage) this).read(scene, buffer);
440

    
441
        if (band == 1) {
442
            return buffer.buf1;
443
        } else if (band == 2) {
444
            return buffer.buf2;
445
        } else if (band == 3) {
446
            return buffer.buf3;
447
        }
448

    
449
        return null;
450
    }
451

    
452
    // Polilinea con extent
453
    class Contour extends Vector {
454
        final private static long serialVersionUID = -3370601314380922368L;
455
        public double minX = Double.MAX_VALUE;
456
        public double minY = Double.MAX_VALUE;
457
        public double maxX = -Double.MAX_VALUE;
458
        public double maxY = -Double.MAX_VALUE;
459

    
460
        public Contour() {
461
            super();
462
        }
463

    
464
        public void add(Point2D pt) {
465
            super.add(pt);
466

    
467
            if (pt.getX() > maxX) {
468
                maxX = pt.getX();
469
            }
470

    
471
            if (pt.getX() < minX) {
472
                minX = pt.getX();
473
            }
474

    
475
            if (pt.getY() > maxY) {
476
                maxY = pt.getY();
477
            }
478

    
479
            if (pt.getY() < minY) {
480
                minY = pt.getY();
481
            }
482
        }
483
    }
484
}
485

    
486

    
487
/**
488
 * @author Nacho Brodin <brodin_ign@gva.es>
489
 *
490
 * Clase encargada del acceso a los datos y repintado de imagenes MrSID. Estos
491
 * son registrados con la extensi?n sid
492
 */
493
public class MrSidFile extends GeoRasterFile {
494
    public final static int BAND_HEIGHT = 64;
495

    
496
    static {
497
        GeoRasterFile.registerExtension("sid", MrSidFile.class);
498
    }
499

    
500
    protected MrSidNative file = null;
501
    private Extent v = null;
502

    
503
    /**
504
     * Contructor. Abre el fichero mrsid
505
     * @param proj        Proyecci?n
506
     * @param fName        Nombre del fichero mrsid
507
     */
508
    public MrSidFile(IProjection proj, String fName) {
509
        super(proj, fName);
510
        
511
        extent = new Extent();
512

    
513
        try {
514
            file = new MrSidNative(fName);
515
            showOnOpen();
516
            load();
517
            bandCount = file.nbands;
518

    
519
            if (bandCount > 2) {
520
                setBand(RED_BAND, 0);
521
                setBand(GREEN_BAND, 1);
522
                setBand(BLUE_BAND, 2);
523
            } else {
524
                setBand(RED_BAND | GREEN_BAND | BLUE_BAND, 0);
525
            }
526
        } catch (Exception e) {
527
            System.out.println("Error en constructor de MrSID");
528
            e.printStackTrace();
529
            file = null;
530
        }
531
    }
532

    
533
        /**
534
         * Obtenemos o calculamos el extent de la imagen.
535
         */
536
    public GeoFile load() {
537
            
538
                   extent = new Extent(file.esq.minX, file.esq.minY, file.esq.maxX, file.esq.maxY);
539
            
540
            /*if((this.assignedExtent == GeoRasterFile.IMAGE_EXTENT || this.assignedExtent == GeoRasterFile.ORDER ) 
541
                    && file !=null        && file.esq != null){
542
                    extent = new Extent(file.esq.minX, file.esq.minY, file.esq.maxX, file.esq.maxY);
543
                    return this;
544
            }
545
            
546
            if((this.assignedExtent == GeoRasterFile.ASSIGNED_EXTENT || this.assignedExtent == GeoRasterFile.ORDER ) 
547
                    && this.getTempExtent() != null){
548
        
549
                extent = this.getTempExtent();
550
                        file.esq = file.new Contour();
551
                          file.esq.add(new Point2D.Double(extent.minX(), extent.minY()));
552
                          file.esq.add(new Point2D.Double(extent.minX()+(extent.maxX() - extent.minX()), extent.minY()));
553
                          file.esq.add(new Point2D.Double(extent.minX(), extent.minY()+(extent.maxY() - extent.minY())));
554
                          file.esq.add(new Point2D.Double(extent.minX()+(extent.maxX() - extent.minX()), extent.minY()+(extent.maxY() - extent.minY())));
555
        }*/ 
556
        
557
        return this;
558
    }
559

    
560
    /**
561
     * Libera el objeto que ha abierto el fichero
562
     */
563
    public void close() {
564
            if(file != null){
565
                    file.close();
566
                    file = null;
567
            }
568
    }
569

    
570
    /**
571
     * Asigna una banda R, G o B
572
     */
573
    public void setBand(int flag, int bandNr) {
574
        super.setBand(flag, bandNr);
575

    
576
        if ((flag & GeoRasterFile.RED_BAND) == GeoRasterFile.RED_BAND) {
577
            file.rBandNr = bandNr + 1;
578
        }
579

    
580
        if ((flag & GeoRasterFile.GREEN_BAND) == GeoRasterFile.GREEN_BAND) {
581
            file.gBandNr = bandNr + 1;
582
        }
583

    
584
        if ((flag & GeoRasterFile.BLUE_BAND) == GeoRasterFile.BLUE_BAND) {
585
            file.bBandNr = bandNr + 1;
586
        }
587
    }
588

    
589
    /**
590
     * Asigna el extent de la vista
591
     */
592
    public void setView(Extent e) {
593
        v = new Extent(e);
594
    }
595

    
596
    /**
597
     * Obtiene el Extent de la vista
598
     */
599
    public Extent getView() {
600
        return v;
601
    }
602

    
603
    /**
604
     * Obtiene el ancho de la imagen
605
     */
606
    public int getWidth() {
607
        return file.width;
608
    }
609

    
610
    /**
611
     * Obtiene el alto de la imagen
612
     */
613
    public int getHeight() {
614
        return file.height;
615
    }
616

    
617
    public void reProject(ICoordTrans rp) {
618
        // TODO Auto-generated method stub        
619
    }
620

    
621
    /**
622
     * Actualiza la imagen. Se encarga de llamar a la funci?n que calcula la vista
623
     * y luego a la que lee la escena sobre un buffer. Vuelca la informaci?n obtenida
624
     * sobre el Image que la visualiza.
625
     */
626
    public Image updateImage(int width, int height, ICoordTrans rp) {
627
        int line;
628
        int[] pRGBArray = null;
629
        Image image = null;
630
        
631
        if(mustVerifySize()){
632
                // Work out the correct aspect for the setView call.
633
                double dFileAspect = (double) v.width() / (double) v.height();
634
                double dWindowAspect = (double) width / (double) height;
635
        
636
                if (dFileAspect > dWindowAspect) {
637
                    height = (int) ((double) width / dFileAspect);
638
                } else {
639
                    width = (int) ((double) height * dFileAspect);
640
                }
641
        }
642
        
643
        // Set the view
644
        file.setView(v.minX(), v.maxY(), v.maxX(), v.minY(), width, height);
645

    
646
        //Impedimos que los valores de ancho y alto de la im?gen sean menores que 1
647
        if (width <= 0) {
648
            width = 1;
649
        }
650

    
651
        if (height <= 0) {
652
            height = 1;
653
        }
654

    
655
        image = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
656
        pRGBArray = new int[width * height];
657

    
658
        try {
659
            file.setAlpha(getAlpha());
660
            
661
            setBand(RED_BAND, rBandNr);
662
            setBand(GREEN_BAND, gBandNr);
663
            setBand(BLUE_BAND, bBandNr);
664
                     
665

    
666
            file.readScene(pRGBArray);
667
            ((BufferedImage) image).setRGB(0, 0, width, height, pRGBArray, 0,
668
                                           width);
669
        } catch (Exception e) {
670
            e.printStackTrace();
671
        }
672

    
673
        return image;
674
    }
675

    
676
    /**
677
     * Muestra informaci?n del fichero abierto.
678
     *
679
     */
680
    private void showOnOpen() {
681
        // Report en la apertura (quitar)
682
        System.out.println("Fichero MrSID '" + getName() + "' abierto.");
683
        System.out.println("Version = " + file.version);
684
        System.out.println("   Size = (" + file.width + "," + file.height +
685
                           ")");
686
        System.out.println("   NumBands = (" + file.nbands + ")");
687

    
688
        //file.pintaInfo();
689
        file.pintaPaleta();
690
    }
691

    
692
    /**
693
     * Asigna al objeto Image los valores con los dato de la imagen contenidos en el
694
     * vector de enteros.
695
     * @param image        imagen con los datos actuales
696
     * @param startX        inicio de la posici?n en X dentro de la imagen
697
     * @param startY        inicio de la posici?n en X dentro de la imagen
698
     * @param w        Ancho de la imagen
699
     * @param h        Alto de la imagen
700
     * @param rgbArray        vector que contiene la banda que se va a sustituir
701
     * @param offset        desplazamiento
702
     * @param scansize        tama?o de imagen recorrida por cada p
703
     */
704
    protected void setRGBLine(BufferedImage image, int startX, int startY,
705
                              int w, int h, int[] rgbArray, int offset,
706
                              int scansize) {
707
        image.setRGB(startX, startY, w, h, rgbArray, offset, scansize);
708
    }
709

    
710
    /**
711
     * Asigna al objeto Image la mezcla entre los valores que ya tiene y los valores
712
     * con los datos de la imagen contenidos en el vector de enteros. De los valores RGB
713
     * que ya contiene se mantienen las bandas que no coinciden con el valor de flags. La
714
     * banda correspondiente a flags es sustituida por los datos del vector.
715
     * @param image        imagen con los datos actuales
716
     * @param startX        inicio de la posici?n en X dentro de la imagen
717
     * @param startY        inicio de la posici?n en X dentro de la imagen
718
     * @param w        Ancho de la imagen
719
     * @param h        Alto de la imagen
720
     * @param rgbArray        vector que contiene la banda que se va a sustituir
721
     * @param offset        desplazamiento
722
     * @param scansize        tama?o de imagen recorrida por cada paso
723
     * @param flags        banda que se va a sustituir (Ctes de GeoRasterFile)
724
     */
725
    protected void setRGBLine(BufferedImage image, int startX, int startY,
726
                              int w, int h, int[] rgbArray, int offset,
727
                              int scansize, int flags) {
728
        int[] line = new int[rgbArray.length];
729
        image.getRGB(startX, startY, w, h, line, offset, scansize);
730

    
731
        if (flags == GeoRasterFile.RED_BAND) {
732
            for (int i = 0; i < line.length; i++)
733
                line[i] = (line[i] & 0x0000ffff) | (rgbArray[i] & 0xffff0000);
734
        } else if (flags == GeoRasterFile.GREEN_BAND) {
735
            for (int i = 0; i < line.length; i++)
736
                line[i] = (line[i] & 0x00ff00ff) | (rgbArray[i] & 0xff00ff00);
737
        } else if (flags == GeoRasterFile.BLUE_BAND) {
738
            for (int i = 0; i < line.length; i++)
739
                line[i] = (line[i] & 0x00ffff00) | (rgbArray[i] & 0xff0000ff);
740
        }
741

    
742
        image.setRGB(startX, startY, w, h, line, offset, scansize);
743
    }
744

    
745
    /**
746
     * Asigna al objeto Image la mezcla entre los valores que ya tiene y los valores
747
     * con los dato de la imagen contenidos en el vector de enteros. De los valores RGB
748
     * que ya contiene se mantienen las bandas que no coinciden con el valor de flags. La
749
     * banda correspondiente a flags es sustituida por los datos del vector.
750
     * @param image        imagen con los datos actuales
751
     * @param startX        inicio de la posici?n en X dentro de la imagen
752
     * @param startY        inicio de la posici?n en X dentro de la imagen
753
     * @param w        Ancho de la imagen
754
     * @param h        Alto de la imagen
755
     * @param rgbArray        vector que contiene la banda que se va a sustituir
756
     * @param offset        desplazamiento
757
     * @param scansize        tama?o de imagen recorrida por cada paso
758
     * @param origBand        Banda origen del GeoRasterFile
759
     * @param destBandFlag        banda que se va a sustituir (Ctes de GeoRasterFile)
760
     */
761
    protected void setRGBLine(BufferedImage image, int startX, int startY,
762
                              int w, int h, int[] rgbArray, int offset,
763
                              int scansize, int origBand, int destBandFlag) {
764
        int[] line = new int[rgbArray.length];
765
        image.getRGB(startX, startY, w, h, line, offset, scansize);
766

    
767
        if ((origBand == 0) && (destBandFlag == GeoRasterFile.RED_BAND)) {
768
            for (int i = 0; i < line.length; i++)
769
                line[i] = (line[i] & 0x0000ffff) | (rgbArray[i] & 0xffff0000);
770
        } else if ((origBand == 1) &&
771
                       (destBandFlag == GeoRasterFile.GREEN_BAND)) {
772
            for (int i = 0; i < line.length; i++)
773
                line[i] = (line[i] & 0x00ff00ff) | (rgbArray[i] & 0xff00ff00);
774
        } else if ((origBand == 2) &&
775
                       (destBandFlag == GeoRasterFile.BLUE_BAND)) {
776
            for (int i = 0; i < line.length; i++)
777
                line[i] = (line[i] & 0x00ffff00) | (rgbArray[i] & 0xff0000ff);
778
        } else if ((origBand == 0) &&
779
                       (destBandFlag == GeoRasterFile.GREEN_BAND)) {
780
            for (int i = 0; i < line.length; i++)
781
                line[i] = (line[i] & 0xffff00ff) |
782
                          ((rgbArray[i] & 0x00ff0000) >> 8);
783
        } else if ((origBand == 0) &&
784
                       (destBandFlag == GeoRasterFile.BLUE_BAND)) {
785
            for (int i = 0; i < line.length; i++)
786
                line[i] = (line[i] & 0xffffff00) |
787
                          ((rgbArray[i] & 0x00ff0000) >> 16);
788
        } else if ((origBand == 1) && (destBandFlag == GeoRasterFile.RED_BAND)) {
789
            for (int i = 0; i < line.length; i++)
790
                line[i] = (line[i] & 0xff00ffff) |
791
                          ((rgbArray[i] & 0x0000ff00) << 8);
792
        } else if ((origBand == 1) &&
793
                       (destBandFlag == GeoRasterFile.BLUE_BAND)) {
794
            for (int i = 0; i < line.length; i++)
795
                line[i] = (line[i] & 0xffffff00) |
796
                          ((rgbArray[i] & 0x0000ff00) >> 8);
797
        } else if ((origBand == 2) && (destBandFlag == GeoRasterFile.RED_BAND)) {
798
            for (int i = 0; i < line.length; i++)
799
                line[i] = (line[i] & 0xff00ffff) |
800
                          ((rgbArray[i] & 0x000000ff) << 16);
801
        } else if ((origBand == 2) &&
802
                       (destBandFlag == GeoRasterFile.GREEN_BAND)) {
803
            for (int i = 0; i < line.length; i++)
804
                line[i] = (line[i] & 0xffff00ff) |
805
                          ((rgbArray[i] & 0x000000ff) << 8);
806
        }
807

    
808
        image.setRGB(startX, startY, w, h, line, offset, scansize);
809
    }
810

    
811
    /* (non-Javadoc)
812
     * @see org.cresques.io.GeoRasterFile#updateImage(int, int, org.cresques.cts.ICoordTrans, java.awt.Image, int)
813
     */
814
    public Image updateImage(int width, int height, ICoordTrans rp, Image img,
815
                             int origBand, int destBandFlag) {
816
        int line;
817
        int[] pRGBArray = null;
818
        Image mrSidImage = null;
819

    
820
        if(mustVerifySize()){
821
                // Work out the correct aspect for the setView call.
822
                double dFileAspect = (double) v.width() / (double) v.height();
823
                double dWindowAspect = (double) width / (double) height;
824
        
825
                if (dFileAspect > dWindowAspect) {
826
                    height = (int) ((double) width / dFileAspect);
827
                } else {
828
                    width = (int) ((double) height * dFileAspect);
829
                }
830
        }
831
        // Set the view
832
        file.setView(v.minX(), v.maxY(), v.maxX(), v.minY(), width, height);
833

    
834
        //Impedimos que los valores de ancho y alto de la im?gen sean menores que 1
835
        if (width <= 0) {
836
            width = 1;
837
        }
838

    
839
        if (height <= 0) {
840
            height = 1;
841
        }
842

    
843
        file.setAlpha(getAlpha());
844
      
845
        setBand(RED_BAND, rBandNr);
846
        setBand(GREEN_BAND, gBandNr);
847
        setBand(BLUE_BAND, bBandNr);
848
       
849
        pRGBArray = new int[width * height];
850

    
851
        if (img == null) { //Caso en el que se crea una imagen
852
            mrSidImage = new BufferedImage(width, height,
853
                                           BufferedImage.TYPE_INT_ARGB);
854

    
855
            try {
856
                file.readScene(pRGBArray);
857
                setRGBLine((BufferedImage) mrSidImage, 0, 0, width, height,
858
                           pRGBArray, 0, width);
859
            } catch (Exception e) {
860
                e.printStackTrace();
861
            }
862

    
863
            return mrSidImage;
864
        } else { //Caso en el que se actualiza una banda del Image
865

    
866
            try {
867
                file.readScene(pRGBArray);
868
                setRGBLine((BufferedImage) img, 0, 0, width, height, pRGBArray,
869
                           0, width, origBand, destBandFlag);
870
            } catch (Exception e) {
871
                e.printStackTrace();
872
            }
873

    
874
            return img;
875
        }
876
    }
877

    
878
    /* (non-Javadoc)
879
     * @see org.cresques.io.GeoRasterFile#getData(int, int, int)
880
     */
881
    public Object getData(int x, int y, int band) {
882
        // TODO Auto-generated method stub
883
        return null;
884
    }
885

    
886
    /**
887
     * Devuelve los datos de una ventana solicitada
888
     * @param ulX        coordenada X superior izda.
889
     * @param ulY        coordenada Y superior derecha.
890
     * @param sizeX        tama?o en X de la ventana.
891
     * @param sizeY tama?o en Y de la ventana.
892
     * @param band        Banda solicitada.
893
     */
894
    public byte[] getWindow(int ulX, int ulY, int sizeX, int sizeY, int band) {
895
        try {
896
            return file.getWindow(ulX, ulY, sizeX, sizeY, band);
897
        } catch (MrSIDException e) {
898
            e.printStackTrace();
899
        }
900

    
901
        return null;
902
    }
903

    
904
    /**
905
     * Devuelve el tama?o de bloque
906
     * @return Tama?o de bloque
907
     */
908
    public int getBlockSize() {
909
        return file.blocksize;
910
    }
911
}