Statistics
| Revision:

svn-gvsig-desktop / trunk / extensions / extRasterTools-SE / src / org / gvsig / rastertools / histogram / HistogramPanelListener.java @ 12307

History | View | Annotate | Download (14.2 KB)

1
/* gvSIG. Sistema de Informaci?n Geogr?fica de la Generalitat Valenciana
2
*
3
* Copyright (C) 2005 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.rastertools.histogram;
20

    
21
import java.awt.Color;
22
import java.awt.Component;
23
import java.awt.event.ActionEvent;
24
import java.awt.event.ActionListener;
25
import java.beans.PropertyChangeEvent;
26
import java.beans.PropertyChangeListener;
27
import java.io.File;
28
import java.io.IOException;
29
import java.io.RandomAccessFile;
30
import java.nio.channels.FileChannel;
31
import java.nio.channels.WritableByteChannel;
32
import java.util.ArrayList;
33

    
34
import javax.swing.JButton;
35
import javax.swing.JComboBox;
36
import javax.swing.JFileChooser;
37
import javax.swing.JOptionPane;
38
import javax.swing.table.DefaultTableModel;
39

    
40
import org.gvsig.gui.beans.graphic.GraphicEvent;
41
import org.gvsig.gui.beans.graphic.GraphicListener;
42
import org.gvsig.gui.beans.incrementabletask.IncrementableTask;
43
import org.gvsig.raster.util.Histogram;
44
import org.gvsig.raster.util.HistogramClass;
45
import org.gvsig.raster.util.HistogramException;
46
import org.gvsig.raster.util.IHistogramable;
47
import org.gvsig.rastertools.histogram.ui.HistogramPanel;
48

    
49
import com.hardcode.driverManager.DriverLoadException;
50
import com.hardcode.gdbms.driver.exceptions.ReadDriverException;
51
import com.hardcode.gdbms.engine.data.DataSource;
52
import com.hardcode.gdbms.engine.data.DataSourceFactory;
53
import com.hardcode.gdbms.engine.data.NoSuchTableException;
54
import com.hardcode.gdbms.engine.values.Value;
55
import com.hardcode.gdbms.engine.values.ValueFactory;
56
import com.iver.andami.PluginServices;
57
import com.iver.cit.gvsig.ProjectExtension;
58
import com.iver.cit.gvsig.fmap.drivers.shp.DbaseFileHeaderNIO;
59
import com.iver.cit.gvsig.fmap.drivers.shp.DbaseFileWriterNIO;
60
import com.iver.cit.gvsig.fmap.edition.EditableAdapter;
61
import com.iver.cit.gvsig.fmap.layers.LayerFactory;
62
import com.iver.cit.gvsig.fmap.layers.SelectableDataSource;
63
import com.iver.cit.gvsig.project.ProjectFactory;
64
import com.iver.cit.gvsig.project.documents.table.ProjectTable;
65
import com.iver.cit.gvsig.project.documents.table.gui.Table;
66
/**
67
 * Listener para eventos del panel de histograma
68
 *
69
 * @version 20/03/2007
70
 * @author Nacho Brodin (brodin_ign@gva.es)
71
 * @author Borja Sanchez Zamorano (borja.sanchez@iver.es)
72
 */
73
public class HistogramPanelListener implements GraphicListener, ActionListener, PropertyChangeListener {
74
        private HistogramPanel                                histogramPanel = null;
75
        private Histogram                                        lastHistogram = null;
76

    
77
        public boolean                                                eventsEnabled = false;
78
        
79
        /**
80
         * Bandas que se est?n mostrando en el gr?fico. Se inicializa con las 3 bandas
81
         * RGB de la visualizaci?n. Este array puede tener m?s elementos ya que si las 
82
         * bandas no son de visualizaci?n (bandas de la imagen en disco) tendr? un elemento
83
         * por cada una. 
84
         */
85
        private boolean[]                                        showBands = null;
86

    
87
  private Color[]                                                bandsColor = {
88
                  Color.red,
89
                  Color.green,
90
                  Color.blue,
91
                  Color.cyan,
92
                  Color.black,
93
                  Color.darkGray,
94
                  Color.gray,
95
                  Color.magenta,
96
                  Color.yellow,
97
                  Color.orange};
98

    
99
        public HistogramPanelListener(HistogramPanel p){
100
                histogramPanel = p;
101
        }
102
        
103
        public HistogramPanel getHistogramPanel() {
104
                return histogramPanel;
105
        }
106
        
107
        public void setControlListeners(){
108
                getHistogramPanel().getGraphicContainer().addValueChangedListener(this);
109
        }
110

    
111
        /**
112
         * Actualizar cuadro de estad?sticas
113
         */
114
        private void updateStatistic() {
115
                int first = (int) getHistogramPanel().getBoxesValues(true)[1];
116
                int end = (int) getHistogramPanel().getBoxesValues(true)[0];
117

    
118
                getHistogramPanel().setStatistic(getLastHistogram().getBasicStats((int) first, (int) end, showBands));
119
        }
120

    
121
        /**
122
         * Tratamiento de todos los eventos visuales.
123
         */
124
        public void actionPerformed(ActionEvent e) {
125
                if (!eventsEnabled) return;
126
                
127
                // Boton de desmarcar todas las bandas
128
                if (e.getSource() == getHistogramPanel().getButtonClean()) {
129
                        getHistogramPanel().refreshBands(false);
130
                        for (int i = 0; i < showBands.length; i++)
131
                                showBands[i] = false;
132
                        updateStatistic();
133
                        updateGraphic();
134
                        return;
135
                }
136

    
137
                // Boton de marcar todas las bandas
138
                if (e.getSource() == getHistogramPanel().getButtonShowAll()) {
139
                        getHistogramPanel().refreshBands(true);
140
                        for (int i = 0; i < showBands.length; i++)
141
                                showBands[i] = true;
142
                        updateStatistic();
143
                        updateGraphic();
144
                        return;
145
                }
146

    
147
                //--------------------------------------
148
                //Selecci?n de fuente de datos del histograma
149
                JComboBox cbo = getHistogramPanel().getComboBoxSource();
150
                if (e.getSource() == cbo) {
151
                        showHistogram();
152
                        return;
153
                }
154
                
155
                // Checkbox de eliminas extremos
156
                if (e.getSource() == getHistogramPanel().getCBDeleteEdges()) {
157
                        updateGraphic();
158
                        return;
159
                }
160
                                
161
                //--------------------------------------
162
                //Selecci?n de histograma acumulado y no acumulado
163
                JComboBox cbt = getHistogramPanel().getComboBoxType();
164
                if (e.getSource() == cbt) {
165
                        updateStatistic();
166
                        updateGraphic();
167
                        return;
168
                }
169
                
170
                //--------------------------------------
171
                // Boton Crear Tabla
172
                JButton table = getHistogramPanel().getBCreateTable();
173
                if (e.getSource() == table) {
174
                        try {
175
//                        -------Mostrar un fileChooser------------------
176
                                String fName;
177
                                JFileChooser chooser = new JFileChooser();
178
                                chooser.setDialogTitle(PluginServices.getText(this, "guardar_tabla"));
179
                            
180
                                int returnVal = chooser.showOpenDialog(getHistogramPanel());
181
                                if (returnVal == JFileChooser.APPROVE_OPTION) {
182
                                        fName = chooser.getSelectedFile().toString();
183
                                        if (!fName.endsWith(".dbf"))
184
                                                fName += ".dbf";
185
                             
186
                                        //-------------Crear el dbf----------------------
187
                            
188
                                        DbaseFileWriterNIO dbfWrite = null;
189
                                        DbaseFileHeaderNIO myHeader;
190
                                        Value[] record;
191
                                
192
                                        HistogramClass[][] histogram = getLastHistogram().getHistogram();
193
                                        int numBands = histogram.length;
194
                                        int numRecors = histogram[0].length;
195
                                
196
                                        File file = new File(fName);
197
                                
198
                                        String names[] = new String[numBands+1];
199
                                        int types[] = new int [numBands+1];
200
                                        int lengths[] = new int [numBands+1];
201
                                
202
                                        names[0]="Value";
203
                                        types[0]=4;
204
                                        lengths[0]=15;
205
                                        for (int band = 0; band < numBands; band++){
206
                                                names[band+1]="Band"+band;
207
                                                types[band+1]=4;
208
                                                lengths[band+1]=15;
209
                                        }
210
                                
211
                                        myHeader = DbaseFileHeaderNIO.createDbaseHeader(names,types,lengths);
212
        
213
                                        myHeader.setNumRecords(numRecors);
214
                                        dbfWrite = new DbaseFileWriterNIO(myHeader, (FileChannel) getWriteChannel(file.getPath()));
215
                                        record = new Value[numBands+1];
216
        
217
                                        for (int j = 0; j < numRecors; j++) {
218
                                                record[0] = ValueFactory.createValue(j);
219
                                                for (int r = 0; r < numBands; r++) {
220
                                                        record[r+1] = ValueFactory.createValue(histogram[r][j].getValue());
221
                                                }
222
        
223
                                                dbfWrite.write(record);
224
                                        }
225
        
226
                                        dbfWrite.close();
227
                            
228
                                        //------------A?adir el dbf al proyecto--------------
229
                                        ProjectExtension ext = (ProjectExtension) PluginServices.getExtension(ProjectExtension.class);
230
                                        String name = file.getName();
231
                                        LayerFactory.getDataSourceFactory().addFileDataSource("gdbms dbf driver", name, fName);
232
                                        DataSource dataSource;
233
                                        dataSource = LayerFactory.getDataSourceFactory().createRandomDataSource(name, DataSourceFactory.AUTOMATIC_OPENING);
234
                                        
235
                                        SelectableDataSource sds = new SelectableDataSource(dataSource);
236
                                        EditableAdapter auxea=new EditableAdapter();
237
                                        auxea.setOriginalDataSource(sds);
238
                                        ProjectTable projectTable = ProjectFactory.createTable(name, auxea);
239
                                        //ext.getProject().addTable(projectTable);
240
                                        ext.getProject().addDocument(projectTable);
241
                                        
242
                                        Table t = new Table();
243
                                        t.setModel(projectTable);
244
                                        //projectTable.setAndamiWindow(t);
245
                                        PluginServices.getMDIManager().addWindow(t);
246
                                }
247
                        } catch (IOException e1) {
248
                                JOptionPane.showMessageDialog((Component)PluginServices.getMainFrame(),getHistogramPanel().getName() + " " + PluginServices.getText(this,"table_not_create"));
249
                        } catch (DriverLoadException e1) {
250
                                JOptionPane.showMessageDialog((Component)PluginServices.getMainFrame(),getHistogramPanel().getName() + " " + PluginServices.getText(this,"table_not_create"));
251
                        } catch (NoSuchTableException e1) {
252
                                JOptionPane.showMessageDialog((Component)PluginServices.getMainFrame(),getHistogramPanel().getName() + " " + PluginServices.getText(this,"table_not_create"));
253
                        } catch (ReadDriverException e1) {
254
                                JOptionPane.showMessageDialog((Component)PluginServices.getMainFrame(),getHistogramPanel().getName() + " " + PluginServices.getText(this,"table_not_create"));
255
                        }
256
                }
257
        }
258

    
259
        /**
260
         * Actualizar la variable de las bandas visibles y su componente visual.
261
         */
262
        private void refreshBands() {
263
                getHistogramPanel().refreshBands(true);
264
                showBands = new boolean[getLastHistogram().getNumBands()];
265
                for (int i = 0; i < showBands.length; i++)
266
                        showBands[i] = true;
267
        }
268
        
269
        /**
270
         * Lanza los dos threads para procesar el histograma y visualizar la
271
         * ventana de incremento
272
         */
273
        public void showHistogram() {
274
                if (getHistogramPanel().getComboBoxSource().getSelectedIndex() < 0) 
275
                        return;
276

    
277
                int dataSrc = getHistogramPanel().getComboBoxSource().getSelectedIndex();
278
                IHistogramable iaux = (IHistogramable) ((ArrayList) getHistogramPanel().getComboSource().get(dataSrc)).get(0);
279

    
280
                if (lastHistogram == null) {
281
                        try {
282
                                setNewHistogram(iaux.getHistogram());
283
                        } catch (HistogramException e) {
284
                                e.printStackTrace();
285
                        }
286
                        return;
287
                }
288
                
289
                HistogramProcess histogramProcess = new HistogramProcess(iaux, this);
290
                IncrementableTask incrementableTask = new IncrementableTask(histogramProcess);
291
                histogramProcess.setIncrementableTask(incrementableTask);
292
                incrementableTask.showWindow();
293
                iaux.resetPercent();
294
                histogramProcess.start();
295
                incrementableTask.start();
296
        }
297

    
298
        /**
299
         * A?ade o elimina una banda de la visualizaci?n. Si la banda se est? visualizando
300
         * se elimina y si no entonces se muestra
301
         * @param band banda a visualizar o borrar del gr?fico
302
         */
303
        public void addOrRemoveGraphicBand(int band){
304
                if (band > showBands.length) return;
305
                showBands[band] = !showBands[band];
306
        }
307

    
308
        /**
309
         * Actualiza la grafica con los datos que ya teniamos del histograma.
310
         */
311
        private void updateGraphic() {
312
                if (getLastHistogram() == null) return;
313
                HistogramClass[][] histogramClass = getLastHistogram().getHistogramByType(Histogram.getType(getHistogramPanel().getComboBoxType().getSelectedIndex()));
314
                if (histogramClass == null) return;
315

    
316
                double[][][] datos = new double[histogramClass.length][histogramClass[0].length][2];
317
                for (int iBand=0; iBand < histogramClass.length; iBand++) {
318
                        for (int i=0; i<histogramClass[iBand].length; i++) {
319
                                datos[iBand][i][0] = histogramClass[iBand][i].getMin();
320
                                datos[iBand][i][1] = histogramClass[iBand][i].getValue();
321
                        }
322
                }
323

    
324
                // Definimos el principio y final de la grafica, sirve para descartar valores.
325
                int first = (int) getHistogramPanel().getBoxesValues(false)[1];
326
                int end = (int) getHistogramPanel().getBoxesValues(false)[0];
327

    
328
                // Si hay que eliminar los limites, quitamos el ultimo y primer valor de la grafica
329
                if (getHistogramPanel().getCBDeleteEdges().isSelected()) {
330
                        if ((first + 1) <= end)
331
                                first++;
332
                        if ((end - 1) >= first)
333
                                end--;
334
                }
335

    
336
                int bandCount = 0;
337
                for (int i = 0; i < showBands.length; i++) {
338
                        if (showBands[i]) bandCount++;
339
                }
340

    
341
                double[][][] newHistogram = new double[bandCount][end - first][2];
342
                String[] bandNames = new String[bandCount];
343
                
344
                bandCount = datos.length;
345

    
346
                int numBand = 0;
347
                for (int iBand = 0; iBand < datos.length; iBand++) {
348
                        if (!showBands[iBand]) continue;
349
                        
350
                        for (int j=first; j<end; j++) {
351
                                newHistogram[numBand][j-first][0] = datos[iBand][j][0];
352
                                newHistogram[numBand][j-first][1] = datos[iBand][j][1];
353
                        }
354
                        bandNames[numBand] = (String) ((DefaultTableModel) getHistogramPanel().getJTableBands().getModel()).getValueAt(iBand, 1);
355

    
356
                        getHistogramPanel().getGraphicContainer().setBandColor(numBand, bandsColor[iBand % bandsColor.length]);
357

    
358
                        numBand++;
359
                }
360

    
361
                getHistogramPanel().getGraphicContainer().getPGraphic().setNewChart(newHistogram, bandNames);
362
        }
363

    
364
        /**
365
         * Definir el nuevo histograma, metodo pu?blico para ser invocado desde
366
         * histogramProcess
367
         * @param histograma nuevo
368
         */
369
        public void setNewHistogram(Histogram value) {
370
                getHistogramPanel().panelInizialited = false;
371
                eventsEnabled = false;
372
                lastHistogram = value;
373
                refreshBands();
374
                updateGraphic();
375
                updateStatistic();
376

    
377
                // Activo la ejecucion de los eventos porque seguro que ya tenemos un histograma
378
                eventsEnabled = true;
379
                getHistogramPanel().panelInizialited = true;
380
        }
381

    
382
        /**
383
         * Obtener ?ltimo histograma
384
         * @return Histogram
385
         */
386
        public Histogram getLastHistogram() {
387
                return lastHistogram;
388
        }
389

    
390
        /**
391
         * Eventos de los BoxValues
392
         */
393
        public void actionValueChanged(GraphicEvent e) {
394
                updateStatistic();
395
        }
396
        
397
        /**
398
         * Proceso para guardar una estadistica en un fichero.
399
         * @param path
400
         * @return
401
         * @throws IOException
402
         */
403
        private WritableByteChannel getWriteChannel(String path) throws IOException {
404
                WritableByteChannel channel;
405
                
406
                File f = new File(path);
407
                
408
                if (!f.exists()) {
409
                        System.out.println("Creando fichero " + f.getAbsolutePath());
410
                        
411
                        if (!f.createNewFile()) {
412
                                throw new IOException("Cannot create file " + f);
413
                        }
414
                }
415
                
416
                RandomAccessFile raf = new RandomAccessFile(f, "rw");
417
                channel = raf.getChannel();
418
                
419
                return channel;
420
        }
421

    
422
        /**
423
         *  Cuando se selecciona/deselecciona una banda
424
         */
425
        public void propertyChange(PropertyChangeEvent evt) {
426
                if (!eventsEnabled) return;
427
                int countRow = ((DefaultTableModel) histogramPanel.getJTableBands().getModel()).getRowCount();
428
                for (int i=0; i<countRow; i++) {
429
                        showBands[i] = ((Boolean) ((DefaultTableModel) histogramPanel.getJTableBands().getModel()).getValueAt(i, 0)).booleanValue();
430
                }
431
                updateGraphic();
432
                updateStatistic();
433
        }
434
}