Statistics
| Revision:

svn-gvsig-desktop / branches / CqCMSDvp / libraries / libCq CMS for java.old / src / org / cresques / io / MrSidFile.java @ 1735

History | View | Annotate | Download (16.3 KB)

1
/*
2
 * Created on 25-sep-2004 (20-oct-2004)
3
 */
4
package org.cresques.io;
5

    
6
import java.awt.Image;
7
import java.awt.geom.Point2D;
8
import java.awt.image.BufferedImage;
9
import java.io.IOException;
10
import java.util.Vector;
11

    
12
import org.cresques.cts.ICoordTrans;
13
import org.cresques.cts.IProjection;
14
import org.cresques.io.GeoFile;
15
import org.cresques.io.GeoRasterFile;
16
import org.cresques.px.Extent;
17

    
18
import es.gva.cit.jmrsid.*;
19

    
20

    
21

    
22
/**
23
 * 
24
 * @author nacho
25
 *
26
 * TODO To change the template for this generated type comment go to
27
 * Window - Preferences - Java - Code Style - Code Templates
28
 */
29

    
30
class MrSidNative extends MrSIDImageReader {
31
        
32
        static boolean WITH_OVERVIEWS = true;
33
        // Polilinea con extent
34
        class Contour extends Vector {
35
                public double minX = Double.MAX_VALUE, minY = Double.MAX_VALUE;
36
                public double maxX = -Double.MAX_VALUE, maxY = -Double.MAX_VALUE;
37
                public Contour() {
38
                        super();
39
                }
40
                public void add(Point2D pt) {
41
                        super.add(pt);
42
                        if (pt.getX() > maxX) maxX = pt.getX();
43
                        if (pt.getX() < minX) minX = pt.getX();
44
                        if (pt.getY() > maxY) maxY = pt.getY();
45
                        if (pt.getY() < minY) minY = pt.getY();
46
                }
47
        }
48
        
49
        /**
50
         * Contorno en coordenadas geogr?ficas. (y Extent del raster).
51
         */
52
        public Contour esq = new Contour();
53
        public int width = 0, height = 0;
54
        public double originX = 0D, originY = 0D;
55
        public String version = "";
56
        public LTIMetadataDatabase metadata;
57
        public LTIPixel pixel=null;
58
        
59
        
60
        
61
        private int alpha = 0;
62
        protected int rBandNr = 1, gBandNr = 2, bBandNr = 3;
63
        protected byte [] bandR, bandG, bandB;
64
        private int dataType = LTIDataType.LTI_DATATYPE_UINT8;
65
        
66
        //View
67
        
68
        double currentViewY = -1;
69
        int currentFullWidth = -1;
70
        int currentFullHeight = -1;
71
        int currentViewWidth = -1;
72
        int currentViewHeight = -1;
73
        double currentViewX = 0D;
74
        double viewportScale = 0D;
75
        double step = 0D;
76
        int currentOverview = -1;
77
        private double zoomoverview=0.0;
78
        int eColorSpace;
79
        int eSampleType;
80
        public int nbands;
81
        int noverviews;
82
        public int xini,yini,anchoOver, altoOver;
83
        public int blocksize = 1;
84
        
85
        
86
        public MrSidNative(String fName) throws MrSIDException, IOException {
87
                super(fName);
88
                init(fName);
89
        }
90
        
91
        /********************************************************************/
92
        
93
        private void init(String fName) throws MrSIDException, IOException {
94
                
95
                this.initialize();
96
                
97
                String ext = fName.toLowerCase().substring(fName.lastIndexOf('.')+1);
98

    
99
                width = this.getWidth();
100
                height = this.getHeight();
101
                eSampleType = this.getDataType();
102
                nbands = this.getNumBands();
103
                eColorSpace = this.getColorSpace();
104
                noverviews = this.getNumLevels();
105
                                
106
                metadata = this.getMetadata();
107
                double ox=0D, oy=0D, resx=0D, resy=0D;
108
                        
109
                LTIGeoCoord geoc = this.getGeoCoord();
110
                
111
                ox = geoc.getX();
112
                oy = geoc.getY();
113
                resx = geoc.getXRes();
114
                resy = geoc.getYRes();
115
                        
116
                System.out.println("Origin = ("+ox+","+oy+")");
117
                System.out.println("Pixel Size = ("+resx+","+resy+")");
118
                  esq.add(new Point2D.Double(ox, oy));
119
                  esq.add(new Point2D.Double(ox+resx*width, oy));
120
                  esq.add(new Point2D.Double(ox, oy+resy*height));
121
                  esq.add(new Point2D.Double(ox+resx*width, oy+resy*height));
122
                  
123
                  blocksize = this.getStripHeight();
124
                  System.out.println("StripHeight = ("+blocksize+")");
125
                
126
        }
127
        
128
        /********************************************************************/
129
        
130
        public void setAlpha(int a) { alpha = a; }
131
        
132
        /********************************************************************/
133
        
134
        public void setDataType(int dt) { dataType = dt; }
135
        
136
        /********************************************************************/
137
        
138
        //         Supone rasters no girados
139
        public Point2D worldToRaster(Point2D pt) {
140
                double x = (((double) currentFullWidth)/(esq.maxX-esq.minX))*(pt.getX()-esq.minX);
141
                double y = (((double) currentFullHeight)/(esq.maxY-esq.minY))*(esq.maxY-pt.getY());
142
                Point2D ptRes = new Point2D.Double(x, y);
143
                return ptRes;
144
        }
145
                
146
        /********************************************************************/
147
        
148
        public void setView(double dWorldTLX, double dWorldTLY,
149
                                    double dWorldBRX, double dWorldBRY,
150
                                                int nWidth, int nHeight) {
151
                
152
                //Ancho y alto de la im?gen en pixeles (pixeles de la overview)
153
                currentFullWidth = width;
154
                currentFullHeight = height;
155
                
156
                //Ventana de la imagen. (en tama?o completo)
157
                //tl->esq sup izda en pixeles
158
                //br->esq inf der en pixeles
159
                
160
                Point2D tl = worldToRaster(new Point2D.Double(dWorldTLX, dWorldTLY));
161
                Point2D br = worldToRaster(new Point2D.Double(dWorldBRX, dWorldBRY));
162
                //System.out.println("2========>"+tl.getX()+","+tl.getY()+","+br.getX()+","+br.getY()+","+width+","+height);
163
                
164
                //Ancho y alto de la im?gen (pixeles en pantalla)
165
                currentViewWidth = nWidth;
166
                currentViewHeight = nHeight;
167

    
168
                currentViewX = tl.getX();
169
                currentViewY = tl.getY();
170
                
171
                viewportScale = (double) currentViewWidth/(br.getX()-tl.getX());
172
                //System.out.println("2.4========>"+currentViewWidth+","+br.getX()+" "+tl.getX()+" "+viewportScale);
173
                currentViewY = tl.getY();
174
                try {
175
                        // calcula el overview a usar
176
                        
177
                        
178
                        int[] dims=null;
179
                        double zoom=1.0;
180
                        zoomoverview=1.0;
181
                        currentOverview = -1;
182
                        if (WITH_OVERVIEWS && noverviews-1 > 0) {
183
                                for (int i=(noverviews-1); i>0; i--) {
184
                                        zoom = LTIUtils.levelToMag(i);
185
                                        dims=this.getDimsAtMag(zoom);
186
                                        //System.out.println("2.5========>"+viewportScale+", dims="+dims[0]+","+dims[1]+
187
                                                        //" zoom="+zoom+" this.getWidth()"+this.getWidth()+"\nviewportScale"+viewportScale);
188
                                        if (dims[0]>this.getWidth()*viewportScale) {
189
                                                currentOverview = i;
190
                                                //System.out.println("2.6========>OVERVIEW SELECC="+i+" zoom="+zoom+" dims="+dims[0]+","+dims[1]);
191
                                                zoomoverview=zoom;
192
                                                viewportScale /= zoomoverview;
193
                                                currentFullWidth = dims[0];
194
                                    currentFullHeight = dims[1];
195
                                    tl = worldToRaster(new Point2D.Double(dWorldTLX, dWorldTLY));
196
                                    currentViewX = tl.getX();
197
                                    currentViewY = tl.getY();
198
                                    break;
199
                                        }
200
                                }
201
                        }
202
                        
203
                        // Selecciona las bandas y los overviews necesarios
204

    
205
                        setDataType(eSampleType);
206
                        
207
                        
208
                } catch (MrSIDException e) {
209
                        e.printStackTrace();
210
                }
211

    
212
                System.out.println("MrSIDFile: TL=("+dWorldTLX+","+dWorldTLY+
213
                        "); BR=("+dWorldBRX+","+dWorldBRY+")\n"+
214
                        "MrSIDFile: escala="+viewportScale+"\n"+
215
                    "Actual Raster Size="+currentFullWidth+"x"+currentFullHeight);
216
                
217
        }
218
        
219
        /********************************************************************/
220
        
221
        void pintaInfo() {
222
                try {
223

    
224
                        System.out.println("GeoTransform:");
225
                        LTIGeoCoord geoc = this.getGeoCoord();
226
                        
227
                        System.out.println("  param[0]="+geoc.getX());
228
                        System.out.println("  param[0]="+geoc.getY());
229
                        System.out.println("  param[0]="+geoc.getXRes());
230
                        System.out.println("  param[0]="+geoc.getYRes());
231
                        System.out.println("  param[0]="+geoc.getXRot());
232
                        System.out.println("  param[0]="+geoc.getYRot());
233
                        System.out.println("Metadata:");
234
                        LTIMetadataDatabase metadata = this.getMetadata();
235
                        for (int i=0; i<metadata.getIndexCount(); i++)
236
                           {
237
                         LTIMetadataRecord rec = null;
238
                         rec = metadata.getDataByIndex(i);
239
                         System.out.println(rec.getTagName());
240
                         
241
                         if(rec.isScalar())System.out.println(rec.getScalarData());
242
                         else if(rec.isVector()){
243
                                 String[] s = rec.getVectorData();
244
                                 for(int j=0;j<s.length;j++)System.out.println("V"+j+"->"+s[j]);
245
                         }else if(rec.isArray()){
246
                                 String[] s = rec.getArrayData();
247
                                 for(int j=0;j<s.length;j++)System.out.println("A"+j+"->"+s[j]);
248
                         }
249
                         
250
                         else System.out.println("");
251
                       }
252
                } catch (MrSIDException e) {
253
                        // TODO Auto-generated catch block
254
                        e.printStackTrace();
255
                }
256
                
257
        }
258
        
259
        /********************************************************************/
260
        
261
        void pintaPaleta() {
262
        }
263
        
264
        /********************************************************************/
265
        
266
        public int readScene(int [] line) throws MrSIDException {
267
                //int a = 0;
268
                int x = (int)currentViewX;
269
            int y = (int)currentViewY;
270
        int SceneWidth;
271
        int SceneHeight;
272
        
273
        try{
274
                if(x==0 && y==0){
275
                        SceneWidth = currentFullWidth;
276
                            SceneHeight = currentFullHeight;
277
                }else{
278
                            SceneWidth = (int) (((double)currentViewWidth)/viewportScale);
279
                            SceneHeight = (int) (((double)currentViewHeight)/viewportScale);
280
                }
281
                         
282
                        if(SceneWidth==0)SceneWidth=1;
283
                        if(SceneHeight==0)SceneHeight=1;
284
                        //System.out.println("2.9========>ColorSpace="+eColorSpace+" nbands="+nbands+" eSampleType="+eSampleType);
285
                        if(pixel==null)pixel = new LTIPixel(eColorSpace, nbands, eSampleType);
286
                        LTIScene scene = new LTIScene(x, y, SceneWidth, SceneHeight, zoomoverview);
287
                        // Este deber?a ser el constructor con ventana
288
                        LTISceneBuffer buffer = new LTISceneBuffer(pixel, SceneWidth, SceneHeight, true);
289
                        /*System.out.println("3========>currentViewX/Y=("+currentViewX+","+currentViewY+
290
                                ")\n\t currentView Size=("+currentViewWidth+","+currentViewHeight+
291
                                ")\n\t currentScene Size=("+SceneWidth+","+SceneHeight+
292
                                ")\n\t (x,y)=("+x+","+y+") CurrentFull=("+currentFullWidth+","+currentFullHeight+
293
                                ")\n\t AnchoAlto=("+this.getWidth()+","+this.getHeight()+
294
                                ")\n\t Buff-length="+buffer.buf1.length+" zoom="+zoomoverview + 
295
                                ")\n\t viewportscale="+viewportScale);*/
296
                        ((LTIImageStage)this).read(scene, buffer);
297

    
298
                                  
299
                          if (dataType == LTIDataType.LTI_DATATYPE_UINT8 ||
300
                                  dataType == LTIDataType.LTI_DATATYPE_SINT8 ||
301
                                dataType == LTIDataType.LTI_DATATYPE_SINT16 ||
302
                                dataType == LTIDataType.LTI_DATATYPE_SINT32 ||
303
                                dataType == LTIDataType.LTI_DATATYPE_UINT16 ||
304
                                dataType == LTIDataType.LTI_DATATYPE_UINT32){
305
                                  
306
                                  int kd, k;
307
                                  double scale = 1/viewportScale;
308
                                  int alpha = (this.alpha & 0xff) << 24;
309
                                  if (rBandNr == 1) bandR = buffer.buf1;
310
                                  else if (rBandNr == 2) bandR = buffer.buf2;
311
                                  else if (rBandNr == 3) bandR = buffer.buf3;
312
                                  if (gBandNr == 1) bandG = buffer.buf1;
313
                                  else if (gBandNr == 2) bandG = buffer.buf2;
314
                                  else if (gBandNr == 3) bandG = buffer.buf3;
315
                                  if (bBandNr == 1) bandB = buffer.buf1;
316
                                  else if (bBandNr == 2) bandB = buffer.buf2;
317
                                  else if (bBandNr == 3) bandB = buffer.buf3;
318
                                  if (eColorSpace==LTIColorSpace.LTI_COLORSPACE_RGB)
319
                                          //for(int k=0;k<buffer.size;k++)
320
                                          for (int y1=0; y1<currentViewHeight; y1++)
321
                                                  for (int x1=0; x1<currentViewWidth; x1++) {
322
                                                          kd = y1*currentViewWidth+x1;
323
                                                          k = ((int) (y1*scale))*SceneWidth+ (int)(((double) x1)*scale);
324
                                                          try {
325
                                                                  line[kd] = alpha + ((0xff & bandR[k])<<16) + (( 0xff & bandG[k])<<8) + (0xff & bandB[k]);
326
                                                          } catch (java.lang.ArrayIndexOutOfBoundsException e) {
327
                                                          }
328
                                                  }
329
                                  
330
                                  if(eColorSpace==LTIColorSpace.LTI_COLORSPACE_GRAYSCALE)
331
                                          for (int y1=0; y1<currentViewHeight; y1++)
332
                                                  for (int x1=0; x1<currentViewWidth; x1++) {
333
                                                          kd = y1*currentViewWidth+x1;
334
                                                          k = ((int) (y1*scale))*SceneWidth+ (int)(((double) x1)*scale);
335
                                                          try {
336
                                                                  line[kd] = alpha + bandR[k];
337
                                                          } catch (java.lang.ArrayIndexOutOfBoundsException e) {
338
                                                          }
339
                                                  }
340
                                           
341
                                  
342
                          } else if (dataType == LTIDataType.LTI_DATATYPE_FLOAT32 ||
343
                                  dataType == LTIDataType.LTI_DATATYPE_FLOAT32) {
344
                          }
345
                          
346
                        buffer=null;
347
        }catch(MrSIDException e){
348
                e.printStackTrace();
349
        }
350
                
351
       return 0;
352
        }
353
        
354
        /**
355
         * Lee una ventana de la imagen y devuelve un buffer de bytes
356
         * @param ulX
357
         * @param ulY
358
         * @param sizeX
359
         * @param sizeY
360
         * @param band
361
         * @return
362
         * @throws MrSIDException
363
         */
364
        public byte[] getWindow(int ulX, int ulY, int sizeX, int sizeY, int band)throws MrSIDException{
365
                
366
                if(pixel==null)pixel = new LTIPixel(eColorSpace, nbands, eSampleType);
367
                
368
                LTIScene scene=new LTIScene(ulX, ulY, sizeX, sizeY, 1.0);
369
                   LTISceneBuffer buffer=new LTISceneBuffer(pixel, sizeX, sizeY, true);
370
                   ((LTIImageStage)this).read(scene,buffer);
371
                   if(band==1)return buffer.buf1;
372
                   else if(band==2)return buffer.buf2;
373
                   else if(band==3)return buffer.buf3;
374
                   return null;
375
        }
376
        
377
        
378
        
379
}
380

    
381
public class MrSidFile extends GeoRasterFile {
382
        public final static int BAND_HEIGHT = 64;
383
        protected MrSidNative file = null;
384

    
385
        private Extent v = null;
386
        
387
        static {
388
                GeoRasterFile.registerExtension("sid", MrSidFile.class);
389
        }
390
        
391
        public MrSidFile(IProjection proj, String fName) {
392
                super(proj, fName);
393
                extent = new Extent();
394
                try {
395
                        file = new MrSidNative(fName); 
396
                        showOnOpen();
397
                        load();
398
                        bandCount = file.nbands;
399
                        if ( bandCount > 2) {
400
                                setBand(RED_BAND,   0);
401
                                setBand(GREEN_BAND, 1);
402
                                setBand(BLUE_BAND,  2);
403
                        } else
404
                                setBand(RED_BAND|GREEN_BAND|BLUE_BAND, 0);
405
                } catch(Exception e){
406
                          System.out.println("Error en constructor de MrSID");
407
                          e.printStackTrace();
408
                          file = null;
409
                }
410
        }
411
        
412
        public GeoFile load() {
413
                extent = new Extent(file.esq.minX, file.esq.minY, file.esq.maxX, file.esq.maxY);
414
                return this;
415
        }
416
        
417
        public void close() {
418
                file=null;
419
        }
420
        
421
        public void setBand(int flag, int bandNr) {
422
                super.setBand(flag, bandNr);
423
                if ((flag & GeoRasterFile.RED_BAND) == GeoRasterFile.RED_BAND) file.rBandNr = bandNr+1;
424
                if ((flag & GeoRasterFile.GREEN_BAND) == GeoRasterFile.GREEN_BAND) file.gBandNr = bandNr+1;
425
                if ((flag & GeoRasterFile.BLUE_BAND) == GeoRasterFile.BLUE_BAND) file.bBandNr = bandNr+1;
426
        }
427
        public void setView(Extent e) { v = new Extent(e); }
428
        public Extent getView() { return v; }
429
        
430
        public int getWidth() {        return file.width; }
431
        public int getHeight() { return file.height;}
432

    
433
        /* (non-Javadoc)
434
         * @see org.cresques.io.GeoRasterFile#reProject(org.cresques.cts.ICoordTrans)
435
         */
436
        public void reProject(ICoordTrans rp) {
437
                // TODO Auto-generated method stub
438
                
439
        }
440
        /* (non-Javadoc)
441
         * @see org.cresques.io.GeoRasterFile#updateImage(int, int, org.cresques.cts.ICoordTrans)
442
         */
443
        public Image updateImage(int width, int height, ICoordTrans rp) {
444
                double dFileAspect, dWindowAspect;
445
                int line, pRGBArray[] = null;
446
                Image image = null;
447
                
448
                // Work out the correct aspect for the setView call.
449
                dFileAspect = (double)v.width()/(double)v.height();
450
                dWindowAspect = (double)width /(double)height;
451

    
452
                if (dFileAspect > dWindowAspect) {
453
                  height =(int)((double)width/dFileAspect);
454
                } else {
455
                  width = (int)((double)height*dFileAspect);
456
                }
457
                
458
                // Set the view
459
                
460
                file.setView(v.minX(), v.maxY(), v.maxX(), v.minY(),width, height);
461
                //System.out.println("1========>"+v.minX()+","+ v.maxY()+","+v.maxX()+","+v.minY()+","+width+","+height);
462
                
463
                //Impedimos que los valores de ancho y alto de la im?gen sean menores que 1
464
                
465
                if(width<=0)width=1;
466
                if(height<=0)height=1;
467
                
468
                
469
                image = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
470
                pRGBArray = new int[width*height];
471
                
472
                try {                
473
                        //System.out.println("1.5========>"+width+","+height);
474
                        file.setAlpha(getAlpha());
475
                        setBand(RED_BAND,   rBandNr);
476
                        setBand(GREEN_BAND, gBandNr);
477
                        setBand(BLUE_BAND,  bBandNr);
478

    
479
                        file.readScene(pRGBArray);
480
                        ((BufferedImage)image).setRGB(0, 0, width, height, pRGBArray, 0, width);
481
                        
482
                        
483
                } catch (Exception e) {
484
                        e.printStackTrace();
485
                }
486
                
487
                return image;
488
        }
489
        
490
        
491
        private void showOnOpen() {
492
                  // Report en la apertura (quitar)
493
                  System.out.println("Fichero MrSID '"+getName()+"' abierto.");
494
                  System.out.println("Version = "+file.version);
495
                  System.out.println("   Size = ("+file.width+","+file.height+")");
496
                System.out.println("   NumBands = ("+file.nbands+")");
497
        
498
                  file.pintaInfo();
499
                  file.pintaPaleta();
500

    
501
        }
502

    
503
        /* (non-Javadoc)
504
         * @see org.cresques.io.GeoRasterFile#updateImage(int, int, org.cresques.cts.ICoordTrans, java.awt.Image, int)
505
         */
506
        public Image updateImage(int width, int height, ICoordTrans rp, Image img, int flags) {
507
                // TODO Auto-generated method stub
508
                return null;
509
        }
510

    
511
        /* (non-Javadoc)
512
         * @see org.cresques.io.GeoRasterFile#getData(int, int, int)
513
         */
514
        public Object getData(int x, int y, int band) {
515
                // TODO Auto-generated method stub
516
                return null;
517
        }
518
        
519
        /**
520
         * Devuelve los datos de una ventana solicitada
521
         * @param ulX        coordenada X superior izda.
522
         * @param ulY        coordenada Y superior derecha.
523
         * @param sizeX        tama?o en X de la ventana.
524
         * @param sizeY tama?o en Y de la ventana.
525
         * @param band        Banda solicitada.
526
         */
527
        public byte[] getWindow(int ulX, int ulY, int sizeX, int sizeY, int band){
528
                try{
529
                        return file.getWindow(ulX, ulY, sizeX, sizeY, band);
530
                }catch(MrSIDException e){
531
                        e.printStackTrace();
532
                }
533
                return null;
534
        }
535
        
536
                
537
        /**
538
         * Devuelve el tama?o de bloque
539
         * @return Tama?o de bloque
540
         */
541
        public int getBlockSize(){
542
     //TODO Nacho: Implementar getBlockSize de EcwFile        
543
          return file.blocksize;
544
        }
545
}
546

    
547