Statistics
| Revision:

root / trunk / libraries / libRaster / src / org / gvsig / raster / driver / GdalWriter.java @ 10740

History | View | Annotate | Download (34.9 KB)

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

    
21
import java.io.BufferedOutputStream;
22
import java.io.DataOutputStream;
23
import java.io.File;
24
import java.io.FileOutputStream;
25
import java.io.IOException;
26

    
27
import org.cresques.cts.IProjection;
28
import org.gvsig.raster.dataaccess.buffer.RasterBuffer;
29
import org.gvsig.raster.shared.Extent;
30
import org.gvsig.raster.shared.RasterUtilities;
31

    
32
import es.gva.cit.jgdal.Gdal;
33
import es.gva.cit.jgdal.GdalBuffer;
34
import es.gva.cit.jgdal.GdalDriver;
35
import es.gva.cit.jgdal.GdalException;
36
import es.gva.cit.jgdal.GdalRasterBand;
37
import es.gva.cit.jgdal.GeoTransform;
38

    
39

    
40
/**
41
 * Driver para la escritura a trav?s de Gdal.
42
 * Puede exportar un fichero de un formato a otro desde un GeoRasterFile
43
 * en cualquier formato soportado por la lectura a un formato que este incluido
44
 * en la lista supportedDrv.
45
 *
46
 * Puede salvar a disco en un formato que este incluido en la lista supportedDrv
47
 * obteniendo los datos que van siendo servidos desde el cliente. Este cliente
48
 * debe implementar un IDataWriter o tener un objeto que lo implemente. Inicialmente
49
 * le pasar? los par?metros de la imagen de salida y cuando el driver comience a
50
 * escribir le ir? solicitando m?s a trav?s del m?todo readData de IDataWriter.
51
 * El cliente ser? el que lleve el control de lo que va sirviendo y lo que le queda
52
 * por servir.
53
 * @author Nacho Brodin (nachobrodin@gmail.com)
54
 */
55
public class GdalWriter extends GeoRasterWriter {
56
        
57
        //Datos de registro de drivers
58
    static {
59
        GeoRasterWriter.registerWriterExtension("tif", GdalWriter.class);
60
        //GeoRasterWriter.registerWriterExtension("tiff", GdalWriter.class);
61
        typeList.put("tif", "GTiff");
62
        //typeList.put("tiff", "GTiff");
63
    }
64

    
65
    public final int                                 windowSizeX = 386;
66
    public final int                                 windowSizeY = 195;
67
    public final int                                 panelSizeX = 358;
68
    public final int                                 panelSizeY = 105;
69
    public final String                         panelLayout = "BorderLayout";
70
    private GdalDriver                                 drv;
71
    private Gdal                                         dset_destino = null;
72
    private GdalRasterBand                         rband = null;
73
    private GeoTransform                         geot = null; //Datos de georeferenciaci?n
74
    //private OGRSpatialReference         oSRS; //Datos de proyecci?n                                                
75
    private GdalBuffer                                 buf = null; //Buffer de origen de gdal
76
    private GdalBuffer[]                        bufBands = null;
77
    private int                                         nBlocks = 0; //N?mero de bloques en Y en el que se divide la imagen para escribir
78
    private int                                         anchoResto = 0; //Tama?o del ?ltimo bloque de la imagen.
79
    private String[]                                 params = null; //Par?metros de creaci?n del dataset.
80
    private GdalSupportOptions                 support = null;
81
    private boolean                                 consulta = false;
82
    private        boolean                                        write = true; //Cuando est? a true se puede escribir en la imagen de salida. Si est? a false el proceso es interrumpido
83
    private int                                         dataType = RasterBuffer.TYPE_UNDEFINED;
84

    
85
    /**
86
     * Constructor para la obtenci?n de par?metros del driver
87
     * @param drvType        Tipo de driver
88
     */
89
    public GdalWriter(String fileName) {
90
            ident = fileName.toLowerCase().substring(fileName.lastIndexOf(".") + 1); 
91
            driver = (String)typeList.get(ident);
92
        support = new GdalSupportOptions(driver);
93
        support.setBlockSize(blockSizeDefault);
94
        support.setPhotometric("RGB");
95
        support.setInterleave("BAND");
96
        support.setCompress("NONE");
97
        support.setWriteGeoref(true);
98
        support.setTfw(false);
99
        consulta = true;
100
    }
101

    
102
    /**
103
     * Constructor para salvar una sola imagen completa
104
     * @param raster        PxRaster de la imagen de  origen
105
     * @param outfilename        Nombre del fichero de salida
106
     * @param infilename        Nombre del fichero de entrada
107
     * @param drvType        Tipo de driver
108
     */
109
    /*public GdalWriter(PxRaster raster, String outFileName, String inFileName) throws GdalException, IOException {
110
            ident = outFileName.toLowerCase().substring(outFileName.lastIndexOf(".") + 1); 
111
            driver = (String)typeList.get(ident);
112
        support = new GdalSupportOptions(driver);   
113
        
114
        this.outFileName = outFileName;
115
        this.inFileName = inFileName;
116
        currentRaster = raster;
117

118
        sizeWindowX = raster.getFWidth();
119
        sizeWindowY = raster.getFHeight();
120

121
        //Obtenemos la georeferenciaci?n
122
        if (support.getGeoref()) {
123
            double maxX = currentRaster.getExtent().maxX();
124
            double minX = currentRaster.getExtent().minX();
125
            double maxY = currentRaster.getExtent().maxY();
126
            double minY = currentRaster.getExtent().minY();
127

128
            geot = new GeoTransform();
129
            geot.adfgeotransform[0] = minX;
130
            geot.adfgeotransform[3] = maxY;
131
            geot.adfgeotransform[1] = (maxX - minX) / currentRaster.getFWidth();
132
            geot.adfgeotransform[5] = (minY - maxY) / currentRaster.getFHeight();
133
        }
134

135
        nBands = currentRaster.getBandCount();
136

137
        this.support.setBlockSize(64currentRaster.getBlockSize());
138

139
        if ((sizeWindowX < 0) || (sizeWindowY < 0)) {
140
            throw new IOException("Tama?o del fichero de salida erroneo.");
141
        }
142

143
        if (nBands == 3) {
144
            this.support.setPhotometric("PHOTOMETRIC=RGB");
145
        } else if (nBands == 1) {
146
            this.support.setPhotometric("PHOTOMETRIC=MINISBLACK");
147
        } else {
148
            this.support.setPhotometric("");
149
        }
150

151
        params = new String[2];
152
        params[0] = new String("TILED=YES");
153
        params[1] = new String(this.support.getPhotometric());
154

155
        init();*/
156

    
157
        /*oSRS = new OGRSpatialReference();
158
        try{
159
                oSRS.setUTM(currentRaster.geoFile.getUTM(), currentRaster.geoFile.getZone());
160
                  oSRS.setWellKnownGeogCS(currentRaster.geoFile.getGeogCS());
161
                  //System.out.println(currentRaster.geoFile.getGeogCS()+"Nueva Proyecci?n ==> "+oSRS.exportToWkt());
162
                  dset_destino.setProjection(oSRS.exportToWkt());
163
        }catch(Exception e){
164
                e.printStackTrace();
165
        }*/
166
    //}
167

    
168
    /**
169
     * Constructor para salvar datos servidos por el cliente
170
     * @param dataWriter               Objeto servidor de datos para el driver de escritura
171
     * @param outFilename              Fichero de salida
172
     * @param blockSize                Tama?o de bloque
173
     * @param Extent                   extent
174
     * @param compresion                   Compresi?n si la tiene
175
     * @param outSizeX                          Tama?o de salida en X
176
     * @param outSizeY                        Tama?o de salida en Y
177
     * @param dataType                        Tipo de dato 
178
     * @throws GdalException
179
     * @throws IOException
180
     */
181
    public GdalWriter(        IDataWriter dataWriter, 
182
                                             String outFileName, 
183
                                             Integer blockSize, 
184
                                             Integer nBands,
185
                                             Extent ex,
186
                                             Integer compresion,
187
                                             Integer outSizeX,
188
                                             Integer outSizeY,
189
                                             Integer dataType)throws GdalException, IOException {
190
               
191
            ident = outFileName.toLowerCase().substring(outFileName.lastIndexOf(".") + 1); 
192
            driver = (String)typeList.get(ident);
193
        support = new GdalSupportOptions(driver);
194
        this.dataType = dataType.intValue();
195
        
196
        this.dataWriter = dataWriter;
197
        this.outFileName = outFileName;
198

    
199
        this.sizeWindowX = outSizeX.intValue();
200
        this.sizeWindowY = outSizeY.intValue();
201

    
202
        if ((sizeWindowX < 0) || (sizeWindowY < 0)) {
203
            throw new IOException("Tama?o del fichero de salida erroneo.");
204
        }
205

    
206
        this.nBands = nBands.intValue();
207

    
208
        //Calculamos la georeferenciaci?n a partir del extend pasado por el cliente.
209
        if (support.getGeoref()) {
210
            double maxX = ex.maxX();
211
            double minX = ex.minX();
212
            double maxY = ex.maxY();
213
            double minY = ex.minY();
214

    
215
            this.support.setBlockSize(blockSize.intValue());
216
            
217
            geot = new GeoTransform();
218
            geot.adfgeotransform[0] = minX;
219
            geot.adfgeotransform[3] = maxY; //-((pixelSizeY * outSizeY)-minY);
220
            geot.adfgeotransform[1] = (double) ((maxX - minX) / outSizeX.intValue()); //pixelSizeX;
221
            geot.adfgeotransform[5] = (double) ((minY - maxY) / outSizeY.intValue()); //pixelSizeY;
222
        }
223

    
224
        setParams();
225

    
226
        init();
227
    }
228

    
229
    /**
230
     *Asigna par?metros de creaci?n del dataset de Gdal
231
     */
232
    private void setParams() {
233
        params = new String[5];
234

    
235
        params[0] = new String("TILED=YES");
236
        params[1] = new String("PHOTOMETRIC=" + this.support.getPhotometric());
237
        params[2] = new String("INTERLEAVE=" + this.support.getInterleave());
238
        params[3] = new String("COMPRESS=" + this.support.getCompress());
239

    
240
        String tfw = null;
241

    
242
        if (this.support.getTfw()) {
243
            tfw = new String("YES");
244
        } else {
245
            tfw = new String("NO");
246
        }
247

    
248
        params[4] = new String("TFW=" + tfw);
249
    }
250

    
251
    /**
252
     * Asigna el tipo de driver con el que se salvar? la imagen
253
     * @param drvType        Tipo de driver
254
     */
255
    public void setDriverType(String drvType) {
256
        this.driver = drvType;
257
    }
258

    
259
    /**
260
     * Creaci?n del dataset de destino.
261
     * @throws EcwException
262
     */
263
    private void init() throws GdalException {
264
        //Controlamos que el tipo de driver sea correcto
265
        if (driver == null) {
266
            throw new GdalException("Tipo de driver sin especificar.");
267
        }
268

    
269
        boolean okdrvtype = false;
270

    
271
        String[] types = GeoRasterWriter.getDriversType();
272
        for (int i = 0; i < GeoRasterWriter.getNTypes(); i++)
273
            if (driver.equals(types[i])) {
274
                okdrvtype = true;
275
            }
276

    
277
        if (okdrvtype == false) {
278
            throw new GdalException("El tipo de driver "+driver+" no est? soportado por GdalWriter.");
279
        }
280

    
281
        //Obtenemos el driver y creamos el dataset del destino
282
        drv = Gdal.getDriverByName(driver);
283
        
284
        if (dset_destino != null) {
285
            dset_destino.close();
286
            dset_destino = null;
287
        }
288
                
289
        dset_destino = drv.create(outFileName, sizeWindowX, sizeWindowY,
290
                                  nBands, RasterUtilities.getGdalTypeFromRasterBufType(dataType), params);
291

    
292
        if (this.support.getGeoref()) {
293
            dset_destino.setGeoTransform(geot);
294
        }
295

    
296
        nBlocks = (int) (sizeWindowY / this.support.getBlockSize());
297
        anchoResto = sizeWindowY - (nBlocks * this.support.getBlockSize());
298
    }
299
    
300
    public void anotherFile(String fileName)throws GdalException{
301
            dset_destino = drv.create(fileName, sizeWindowX, sizeWindowY,
302
                nBands, RasterUtilities.getGdalTypeFromRasterBufType(dataType), params);
303
    }
304

    
305
    /**
306
     * A partir de un elemento que contiene una propiedad y un valor
307
     * lo parsea y asigna el valor a su variable.
308
     * @param propValue        elemento con la forma propiedad=valor
309
     */
310
    private void readProperty(String propValue) {
311
        String prop = propValue.substring(0, propValue.indexOf("="));
312

    
313
        if (propValue.startsWith(prop)) {
314
            String value = propValue.substring(propValue.indexOf("=") + 1,
315
                                               propValue.length());
316

    
317
            if ((value != null) && !value.equals("")) {
318
                if (prop.equals("BLOCKSIZE")) {
319
                    this.support.setBlockSize(Integer.parseInt(value));
320
                }
321

    
322
                if (prop.equals("GEOREF")) {
323
                    boolean georef = true;
324

    
325
                    if (value.equals("yes")) {
326
                        georef = true;
327
                    } else {
328
                        georef = false;
329
                    }
330

    
331
                    this.support.setWriteGeoref(georef);
332
                }
333

    
334
                if (prop.equals("INTERLEAVE")) {
335
                    this.support.setInterleave(value);
336
                }
337

    
338
                if (prop.equals("PHOTOMETRIC")) {
339
                    this.support.setPhotometric(value);
340
                }
341

    
342
                if (prop.equals("COMPRESS")) {
343
                    this.support.setCompress(value);
344
                }
345

    
346
                if (prop.equals("TFW")) {
347
                    boolean tfw = true;
348

    
349
                    if (value.equals("yes")) {
350
                        tfw = true;
351
                    } else {
352
                        tfw = false;
353
                    }
354

    
355
                    this.support.setTfw(tfw);
356
                }
357
            }
358
        }
359
    }
360

    
361
    /**
362
     * Asigna propiedades al driver a partir de un vector de
363
     * strings donde cada elemento tiene la estructura de
364
     * propiedad=valor.
365
     * @param props        Propiedades
366
     */
367
    public void setProps(String[] props) {
368
        for (int iProps = 0; iProps < props.length; iProps++)
369
            readProperty(props[iProps]);
370

    
371
        setParams();
372

    
373
        try {
374
            if (!consulta) {
375
                init();
376
            }
377
        } catch (GdalException e) {
378
            e.printStackTrace();
379
        }
380
    }
381

    
382
    /**
383
     * Escritura de datos tipo Byte.
384
     * @param sizeY Alto del bloque que se escribe.
385
     * @param posicionY Posici?ny a partir desde donde se comienza.
386
     */
387
    public void writeByteBand(int sizeY, int posicionY){
388
            byte[][] buftmp = dataWriter.readByteData(sizeWindowX, sizeY);
389
            for(int iBand = 0; iBand < nBands; iBand ++)
390
                bufBands[iBand].buffByte = new byte[buftmp[iBand].length];        
391
  
392
            //Escribimos el bloque destino
393
            for (int iBand = 0; iBand < buftmp.length; iBand++)
394
                    for (int i = 0; i < buftmp[iBand].length; i++)
395
                            bufBands[iBand].buffByte[i] = buftmp[iBand][i];
396
            
397
        for (int iBand = 0; iBand < buftmp.length; iBand++){
398
                try {
399
                                rband = dset_destino.getRasterBand(iBand + 1);
400
                                rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[iBand], Gdal.GDT_Byte);
401
                } catch (GdalException e) {
402
                                //No se est? escribiendo ...
403
                        }
404
        }
405
    }
406
    
407
    /**
408
     * Escritura de datos tipo Short.
409
     * @param sizeY Alto del bloque que se escribe.
410
     * @param posicionY Posici?ny a partir desde donde se comienza.
411
     */
412
    public void writeShortBand(int sizeY, int posicionY){
413
            short[][] buftmp = dataWriter.readShortData(sizeWindowX, sizeY);
414
            for(int iBand = 0; iBand < nBands; iBand ++)
415
                bufBands[iBand].buffShort = new short[buftmp[iBand].length];        
416
  
417
            //Escribimos el bloque destino
418
            for (int iBand = 0; iBand < buftmp.length; iBand++)
419
                    for (int i = 0; i < buftmp[iBand].length; i++)
420
                            bufBands[iBand].buffShort[i] = buftmp[iBand][i];
421
            
422
        for (int iBand = 0; iBand < buftmp.length; iBand++){
423
                try {
424
                                rband = dset_destino.getRasterBand(iBand + 1);
425
                                rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[iBand], Gdal.GDT_Int16);
426
                } catch (GdalException e) {
427
                                //No se est? escribiendo ...
428
                        }
429
        }
430
    }
431
        
432
    /**
433
     * Escritura de datos tipo Int.
434
     * @param sizeY Alto del bloque que se escribe.
435
     * @param posicionY Posici?ny a partir desde donde se comienza.
436
     */
437
    public void writeIntBand(int sizeY, int posicionY){
438
            int[][] buftmp = dataWriter.readIntData(sizeWindowX, sizeY);
439
            for(int iBand = 0; iBand < nBands; iBand ++)
440
                bufBands[iBand].buffInt = new int[buftmp[iBand].length];        
441
  
442
            //Escribimos el bloque destino
443
            for (int iBand = 0; iBand < buftmp.length; iBand++)
444
                    for (int i = 0; i < buftmp[iBand].length; i++)
445
                            bufBands[iBand].buffInt[i] = buftmp[iBand][i];
446
            
447
        for (int iBand = 0; iBand < buftmp.length; iBand++){
448
                try {
449
                                rband = dset_destino.getRasterBand(iBand + 1);
450
                                rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[iBand], Gdal.GDT_Int32);
451
                } catch (GdalException e) {
452
                                //No se est? escribiendo ...
453
                        }
454
        }
455
    }
456
    
457
    /**
458
     * Escritura de datos tipo Float.
459
     * @param sizeY Alto del bloque que se escribe.
460
     * @param posicionY Posici?ny a partir desde donde se comienza.
461
     */
462
    public void writeFloatBand(int sizeY, int posicionY){
463
            float[][] buftmp = dataWriter.readFloatData(sizeWindowX, sizeY);
464
            for(int iBand = 0; iBand < nBands; iBand ++)
465
                bufBands[iBand].buffFloat = new float[buftmp[iBand].length];        
466
  
467
            //Escribimos el bloque destino
468
            for (int iBand = 0; iBand < buftmp.length; iBand++)
469
                    for (int i = 0; i < buftmp[iBand].length; i++)
470
                            bufBands[iBand].buffFloat[i] = buftmp[iBand][i];
471
            
472
        for (int iBand = 0; iBand < buftmp.length; iBand++){
473
                try {
474
                                rband = dset_destino.getRasterBand(iBand + 1);
475
                                rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[iBand], Gdal.GDT_Float32);
476
                } catch (GdalException e) {
477
                                //No se est? escribiendo ...
478
                        }
479
        }
480
    }
481
    
482
    /**
483
     * Escritura de datos tipo Double.
484
     * @param sizeY Alto del bloque que se escribe.
485
     * @param posicionY Posici?ny a partir desde donde se comienza.
486
     */
487
    public void writeDoubleBand(int sizeY, int posicionY){
488
            double[][] buftmp = dataWriter.readDoubleData(sizeWindowX, sizeY);
489
            for(int iBand = 0; iBand < nBands; iBand ++)
490
                bufBands[iBand].buffDouble = new double[buftmp[iBand].length];        
491
  
492
            //Escribimos el bloque destino
493
            for (int iBand = 0; iBand < buftmp.length; iBand++)
494
                    for (int i = 0; i < buftmp[iBand].length; i++)
495
                            bufBands[iBand].buffDouble[i] = buftmp[iBand][i];
496
            
497
        for (int iBand = 0; iBand < buftmp.length; iBand++){
498
                try {
499
                                rband = dset_destino.getRasterBand(iBand + 1);
500
                                rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[iBand], Gdal.GDT_Float64);
501
                } catch (GdalException e) {
502
                                //No se est? escribiendo ...
503
                        }
504
        }
505
    }
506
    /**
507
     * Escritura para tipo de dato ARGB.
508
     * @param sizeY Alto del bloque que se escribe.
509
     * @param posicionY Posici?ny a partir desde donde se comienza.
510
     */
511
    public void writeARGBBand(int sizeY, int posicionY){
512
            int[] buftmp = dataWriter.readARGBData(sizeWindowX, sizeY, 0);
513
             for(int iBand = 0; iBand < nBands; iBand ++)
514
                 bufBands[iBand].buffByte = new byte[buftmp.length];        
515
             
516
         //Escribimos el bloque destino
517
         for (int i = 0; i < buftmp.length; i++) {
518
             bufBands[0].buffByte[i] = (byte) (((buftmp[i] & 0xff0000) >> 16) &
519
                                    0xff);
520
             bufBands[1].buffByte[i] = (byte) (((buftmp[i] & 0xff00) >> 8) & 0xff);
521
             bufBands[2].buffByte[i] = (byte) ((buftmp[i] & 0xff) & 0xff);
522
         }
523

    
524
         try {
525
             rband = dset_destino.getRasterBand(1);
526
             rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[0],
527
                               Gdal.GDT_Byte);
528
             rband = dset_destino.getRasterBand(2);
529
             rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[1],
530
                               Gdal.GDT_Byte);
531
             rband = dset_destino.getRasterBand(3);
532
             rband.writeRaster(0, posicionY, sizeWindowX, sizeY, bufBands[2],
533
                               Gdal.GDT_Byte);
534
         } catch (GdalException e) {
535
             e.printStackTrace();
536
         }
537
    }
538
    
539
    /**
540
     * Escribe tres bandas en el GDALRasterBand desde el IDataWriter con una
541
     * altura definida por sizeY.
542
     * @param buftmp        Buffer
543
     * @param sizeY        Altura en pixels del bloque leido
544
     * @param posicionY        Posici?n y a partir de la cual se escribe en el GDALRasterBand destino
545
     */
546
    private void writeBands(int sizeY, int posicionY) {
547
        //leemos el bloque origen
548
        
549
        switch(dataType){
550
        case RasterBuffer.TYPE_IMAGE: 
551
                writeARGBBand(sizeY, posicionY);
552
                break;
553
        case RasterBuffer.TYPE_BYTE:
554
                writeByteBand(sizeY, posicionY);
555
                break;
556
        case RasterBuffer.TYPE_SHORT:
557
                writeShortBand(sizeY, posicionY);
558
                break;
559
        case RasterBuffer.TYPE_INT:
560
                writeIntBand(sizeY, posicionY);
561
                break;
562
        case RasterBuffer.TYPE_FLOAT:
563
                writeFloatBand(sizeY, posicionY);
564
                break;
565
        case RasterBuffer.TYPE_DOUBLE:
566
                writeDoubleBand(sizeY, posicionY);
567
                break;
568
        }
569
    }
570

    
571
    /**
572
     * Funci?n que gestiona la lectura desde el origen y la escritura
573
     * de Gdal sobre el fichero destino.
574
     * @param mode        Modo de escritura
575
     * @throws IOException
576
     */
577
    private void write(int mode) throws IOException {
578
        buf = new GdalBuffer();
579
        bufBands = new GdalBuffer[nBands];
580
        for(int iBand = 0; iBand < nBands; iBand ++)
581
                bufBands[iBand] = new GdalBuffer();
582
        
583
       // int[] buftmp = null;
584

    
585
        //long t1 = System.currentTimeMillis();
586
        //try {
587
            if (mode == Mode.fileWrite) {
588
                /*for (int iBand = 0; iBand < this.nBands; iBand++) {
589
                    rband = dset_destino.getRasterBand(iBand + 1);
590

591
                    for (int iBlock = 0; iBlock < nBlocks; iBlock++) {
592
                            if(write){
593
                                //leemos el bloque origen
594
                                buf.buffByte = currentRaster.getGeoFile().getWindow(0,
595
                                                                                    iBlock * this.support.getBlockSize(),
596
                                                                                    sizeWindowX,
597
                                                                                    this.support.getBlockSize(),
598
                                                                                    iBand +
599
                                                                                    1);
600
        
601
                                //Escribimos el bloque destino
602
                                rband.writeRaster(0,
603
                                                  iBlock * this.support.getBlockSize(),
604
                                                  sizeWindowX,
605
                                                  this.support.getBlockSize(), buf,
606
                                                  Gdal.GDT_Byte);
607
                            }//else
608
                                    //this.writeClose();
609
                    }
610
                }*/
611
            } else if (mode == Mode.dataWrite) {
612
                //for(int iBlock=1;iBlock<=nBlocks;iBlock++){
613
                for (int iBlock = 0; iBlock < nBlocks; iBlock++) {
614
                    int posicionY = iBlock * this.support.getBlockSize();
615
                    if(write)
616
                            writeBands( this.support.getBlockSize(), posicionY);
617
                    /*else
618
                            this.writeClose();*/
619
                }
620
            }
621

    
622
            if (anchoResto != 0) {
623
                if (mode == Mode.fileWrite) {
624
                    /*for (int iBand = 0; iBand < this.nBands; iBand++) {
625
                        rband = dset_destino.getRasterBand(iBand + 1);
626
                        if(write){
627
                                //leemos el bloque origen
628
                                buf.buffByte = currentRaster.getGeoFile().getWindow(0,
629
                                                                                    nBlocks * this.support.getBlockSize(),
630
                                                                                    sizeWindowX,
631
                                                                                    anchoResto,
632
                                                                                    iBand +
633
                                                                                    1);
634
        
635
                                //Escribimos el bloque destino
636
                                rband.writeRaster(0,
637
                                                  nBlocks * this.support.getBlockSize(),
638
                                                  sizeWindowX, anchoResto, buf,
639
                                                  Gdal.GDT_Byte);
640
                        }//else
641
                                //this.writeClose();
642
                    }*/
643
                } else if (mode == Mode.dataWrite) {
644
                    int posicionY = nBlocks * this.support.getBlockSize();
645
                    if(write)
646
                            writeBands(anchoResto, posicionY);
647
                    /*else
648
                            this.writeClose();*/
649
                }
650
            }
651
        /*} catch (GdalException e) {
652
            e.printStackTrace();
653
        }*/
654
    }
655

    
656
    /**
657
     * Realiza la funci?n de compresi?n a partir de un GeoRasterFile.
658
     * @throws IOException
659
     */
660
    public void fileWrite() throws IOException {
661
        /*if (currentRaster == null) {
662
            throw new IOException("No se ha asignado un fichero de entrada.");
663
        }*/
664

    
665
        this.write(Mode.fileWrite);
666
    }
667

    
668
    /**
669
     * Realiza una copia en el formato especificado.
670
     * @throws IOException
671
     */
672
    public static void createCopy(GdalDriver driverDst, String dst, String src, 
673
                    boolean bstrict, String[] params, IProjection proj) throws IOException, GdalException {
674
        if (dst == null || src == null) {
675
            throw new IOException("No se ha asignado un fichero de entrada.");
676
        }
677

    
678
        org.gvsig.raster.driver.GdalDriver gdalFile;
679
                try {
680
                        gdalFile = new org.gvsig.raster.driver.GdalDriver(proj, src);
681
                driverDst.createCopy(dst, gdalFile.getNative(), bstrict, params);
682
                if(dst.endsWith(".jpg") || dst.endsWith(".jpeg"))
683
                        GdalWriter.createWorldFile(dst, gdalFile);
684
                gdalFile.close();
685
                } catch (NotSupportedExtensionException e) {
686
                        e.printStackTrace();
687
                }
688
    }
689
    
690
    /**
691
         * Crea un fichero de georeferenciaci?n
692
         * @param img
693
         * @param name
694
         * @return
695
         * @throws IOException
696
         */
697
        private static void createWorldFile(String name, org.gvsig.raster.driver.GdalDriver gdalFile) throws IOException{
698
            File tfw = null;
699
            
700
            String extWorldFile = ".wld";
701
            if(name.endsWith("tif"))
702
                    extWorldFile = ".tfw";
703
            if(name.endsWith("jpg") || name.endsWith("jpeg"))
704
                    extWorldFile = ".jpgw";
705
                                
706
            tfw = new File(name.substring(0, name.lastIndexOf(".")) + extWorldFile);
707
            
708
            //Generamos un world file para gdal
709
            DataOutputStream dos = new DataOutputStream( new BufferedOutputStream(new FileOutputStream(tfw)) );
710
            dos.writeBytes((gdalFile.getExtent().getMax().getX() - gdalFile.getExtent().getMin().getX())/gdalFile.getWidth()+"\n");
711
            dos.writeBytes("0.0\n");
712
            dos.writeBytes("0.0\n");
713
            dos.writeBytes((gdalFile.getExtent().getMax().getY() - gdalFile.getExtent().getMin().getY())/gdalFile.getHeight()+"\n");
714
            dos.writeBytes(""+gdalFile.getExtent().getMin().getX()+"\n");
715
            dos.writeBytes(""+gdalFile.getExtent().getMin().getY()+"\n");
716
            dos.close();    
717
        }
718

    
719
    
720
    /**
721
     * Realiza la escritura de datos con los datos que le pasa el cliente.
722
     * @throws IOException
723
     */
724
    public void dataWrite() throws IOException {
725
        if (dataWriter == null) {
726
            throw new IOException("No se ha obtenido un objeto de entrada para la escritura valido.");
727
        }
728

    
729
        this.write(Mode.dataWrite);
730
    }
731

    
732
    /**
733
     * Cancela el salvado de datos.
734
     * @throws GdalException
735
     */
736
    public void writeClose() {
737
        try {
738
                if(dset_destino != null)
739
                        dset_destino.close();
740
           //oSRS = null;
741
        } catch (GdalException e) {
742
            e.printStackTrace();
743
        }
744
    }
745

    
746
    /**
747
     * Cancela el salvado de datos.
748
     */
749
    public void writeCancel() {
750
       write = false; 
751
    }
752
    
753
    /**
754
     * Devuelve la configuraci?n de la ventana de dialogo
755
     * para las propiedades del driver de escritura de Gdal.
756
     * @return XML de configuraci?n del dialogo.
757
     */
758
    public String getXMLPropertiesDialog() {
759
        StringBuffer options = null;
760
        options = new StringBuffer();
761
        options.append("<window sizex=\"" + this.windowSizeX + "\" sizey=\"" +
762
                       this.windowSizeY + "\">");
763
        options.append("<panel sizex=\"" + this.panelSizeX + "\" sizey=\"" +
764
                       this.panelSizeY + "\" layout=\"" + this.panelLayout +
765
                       "\" border=\"yes\">");
766

    
767
        options.append("<panel layout=\"FlowLayout\" position=\"North\" align=\"left\">");
768
        options.append("<label>Block Size:</label>");
769
        options.append("<combo ident=\"BLOCKSIZE\" selected=\"" +
770
                       this.support.getBlockSize() + "\">");
771

    
772
        for (int i = 0; i < this.support.getBlockSizeList().length; i++)
773
            options.append("<elem>" + this.support.getBlockSizeList()[i] +
774
                           "</elem>");
775

    
776
        options.append("</combo>");
777
        //options.append("<label>Georef Si/No:</label>");
778

    
779
        String sel = null;
780

    
781
        if (this.support.getGeoref()) {
782
            sel = new String("yes");
783
        } else {
784
            sel = new String("no");
785
        }
786

    
787
        /*options.append("<check ident=\"GEOREF\" selected=\"" + sel +
788
                       "\" text=\"\">");
789
        options.append("</check>");*/
790
        options.append("</panel>");
791

    
792
        options.append("<panel layout=\"FlowLayout\" position=\"Center\" align=\"left\">");
793
        options.append("<label>Photometric:</label>");
794
        options.append("<combo ident=\"PHOTOMETRIC\" selected=\"" +
795
                       this.support.getPhotometric() + "\">");
796

    
797
        for (int i = 0; i < this.support.getPhotometricList().length; i++)
798
            options.append("<elem>" + this.support.getPhotometricList()[i] +
799
                           "</elem>");
800

    
801
        options.append("</combo>");
802
        options.append("<label>Interleave:</label>");
803
        options.append("<combo ident=\"INTERLEAVE\" selected=\"" +
804
                       this.support.getInterleave() + "\">");
805

    
806
        for (int i = 0; i < this.support.getInterleaveList().length; i++)
807
            options.append("<elem>" + this.support.getInterleaveList()[i] +
808
                           "</elem>");
809

    
810
        options.append("</combo>");
811
        options.append("</panel>");
812

    
813
        options.append("<panel layout=\"FlowLayout\" position=\"South\" align=\"left\">");
814
        options.append("<label>Compresi?n:</label>");
815
        options.append("<combo ident=\"COMPRESS\" selected=\"" +
816
                       this.support.getCompress() + "\">");
817

    
818
        for (int i = 0; i < this.support.getCompressList().length; i++)
819
            options.append("<elem>" + this.support.getCompressList()[i] +
820
                           "</elem>");
821

    
822
        options.append("</combo>");
823
        options.append("<label>Generar Tfw:</label>");
824
        sel = null;
825

    
826
        if (this.support.getTfw()) {
827
            sel = new String("yes");
828
        } else {
829
            sel = new String("no");
830
        }
831

    
832
        options.append("<check ident=\"TFW\" selected=\"" + sel +
833
                       "\" text=\"\">");
834
        options.append("</check>");
835
        options.append("</panel>");
836

    
837
        options.append("</panel>");
838
        options.append("</window>");
839

    
840
        return options.toString();
841
    }
842

    
843
    /**
844
     * Obtiene el valor a la variable write que estar? a true cuando se est? escribiendo
845
     *  o puede escribirse la imagen de salida. El cancelar la operaci?n de escritura
846
     * pondr? esta variable a false deteniendose la escritura y cerrandose el dataset
847
     * de salida. 
848
     * @return True si puede escribirse y false si no puede
849
     */
850
    public boolean isWrite() {
851
                return write;
852
        }
853

    
854
    /**
855
     * Asigna el valor a la variable write que estar? a true cuando se est? escribiendo
856
     *  o puede escribirse la imagen de salida. El cancelar la operaci?n de escritura
857
     * pondr? esta variable a false deteniendose la escritura y cerrandose el dataset
858
     * de salida. 
859
     * @param write Variable booleana. True si puede escribirse y false si no puede
860
     */
861
        public void setWrite(boolean write) {
862
                this.write = write;
863
        }
864
        
865
        /**
866
         * Obtiene las opciones de salvado.
867
         * @return GdalSupportOptions
868
         */
869
        public GdalSupportOptions getSupport(){
870
            return this.support; 
871
    }
872
        
873
    /**
874
     *
875
     * @author Nacho Brodin (brodin_ign@gva.es)
876
     *
877
     * Opciones que soporta el driver de escritura de Gdal.
878
     */
879
    public class GdalSupportOptions extends WriterSupportOptions {
880
        private String[]         photometric = {
881
                                           "YCBR", "MINISBLACK", "MINISWHITE",
882
                                           "RGB", "CMYK", "CIELAB", "ICCLAB",
883
                                           "ITULAB", "CBCR"
884
                                       };
885
        private String[]         interleave = { "BAND", "PIXEL" };
886
        private String[]         compress = { "LZW", "PACKBITS", "DEFLATE", "NONE" };
887
        private String                 photometricDefault = "RGB";
888
        private String                 interleaveDefault = "BAND";
889
        private String                 compressDefault = "NONE";
890
       
891
        private boolean tfw = false;
892

    
893
        public GdalSupportOptions(String ext) {
894
            super(ext);
895
        }
896

    
897
        /**
898
         * @param defaultPhot        Tipo de imagen
899
         */
900
        public void setPhotometric(String defaultPhot) {
901
            this.photometricDefault = defaultPhot;
902
        }
903

    
904
        /**
905
         * @param defaultInt
906
         */
907
        public void setInterleave(String defaultInt) {
908
            this.interleaveDefault = defaultInt;
909
        }
910

    
911
        /**
912
         * @param defaultComp
913
         */
914
        public void setCompress(String defaultComp) {
915
            this.compressDefault = defaultComp;
916
        }
917

    
918
        /**
919
         * Asigna true o false si se desea generar un fichero tfw con la
920
         * georeferenciaci?n o no;
921
         * @param tfw true se genera el fichero tfw y false no se genera
922
         */
923
        public void setTfw(boolean tfw) {
924
            this.tfw = tfw;
925
        }
926

    
927
        /**
928
         * @return
929
         */
930
        public String[] getPhotometricList() {
931
            return photometric;
932
        }
933

    
934
        /**
935
         * @return
936
         */
937
        public String[] getInterleaveList() {
938
            return interleave;
939
        }
940

    
941
        /**
942
         * @return
943
         */
944
        public String[] getCompressList() {
945
            return compress;
946
        }
947

    
948
        /**
949
         * @return
950
         */
951
        public String getPhotometric() {
952
            return photometricDefault;
953
        }
954

    
955
        /**
956
         * @return
957
         */
958
        public String getInterleave() {
959
            return interleaveDefault;
960
        }
961

    
962
        /**
963
         * Obtiene el par?metro de compresi?n
964
         * @return
965
         */
966
        public String getCompress() {
967
            return compressDefault;
968
        }
969

    
970
        /**
971
         * Devuelve true o false si se genera un fichero tfw con la
972
         * georeferenciaci?n o no;
973
         * @param tfw true se genera el fichero tfw y false no se genera
974
         */
975
        public boolean getTfw() {
976
            return tfw;
977
        }
978
    }
979

    
980
    private class Mode {
981
        public final static int fileWrite = 0;
982
        public final static int dataWrite = 1;
983
    }
984
}