svn-gvsig-desktop / tags / gvSIGv0_6_1RELEASE / libraries / libCq CMS for java.old / src / org / cresques / io / raster / RasterFilterStackManager.java @ 5222
History | View | Annotate | Download (35.5 KB)
1 | 2809 | nacho | /*
|
---|---|---|---|
2 | * Cresques Mapping Suite. Graphic Library for constructing mapping applications.
|
||
3 | *
|
||
4 | * Copyright (C) 2004-5.
|
||
5 | *
|
||
6 | * This program is free software; you can redistribute it and/or
|
||
7 | * modify it under the terms of the GNU General Public License
|
||
8 | * as published by the Free Software Foundation; either version 2
|
||
9 | * of the License, or (at your option) any later version.
|
||
10 | *
|
||
11 | * This program is distributed in the hope that it will be useful,
|
||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||
14 | * GNU General Public License for more details.
|
||
15 | *
|
||
16 | * You should have received a copy of the GNU General Public License
|
||
17 | * along with this program; if not, write to the Free Software
|
||
18 | * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,USA.
|
||
19 | *
|
||
20 | * For more information, contact:
|
||
21 | *
|
||
22 | * cresques@gmail.com
|
||
23 | */
|
||
24 | package org.cresques.io.raster; |
||
25 | |||
26 | import java.lang.reflect.Constructor; |
||
27 | import java.util.ArrayList; |
||
28 | import java.util.Hashtable; |
||
29 | import java.util.StringTokenizer; |
||
30 | import java.util.regex.Matcher; |
||
31 | import java.util.regex.Pattern; |
||
32 | |||
33 | 3791 | nacho | import org.cresques.io.GeoRasterFile; |
34 | 2809 | nacho | |
35 | 3791 | nacho | |
36 | 2809 | nacho | /**
|
37 | * Esta clase es de la parte cliente y es la encargada de la gesti?n
|
||
38 | * de la pila de filtros. Es la que conoce el orden en que se deben apilar
|
||
39 | * estos para que la ejecuci?n sea correcta. Un cliente que desee aplicar un
|
||
40 | * filtro deber? introducirlo en la pila usando para ello esta clase.
|
||
41 | * @author Nacho Brodin (brodin_ign@gva.es)
|
||
42 | *
|
||
43 | */
|
||
44 | public class RasterFilterStackManager implements IStackManager { |
||
45 | 4160 | nacho | protected RasterFilterStack filterStack = null; |
46 | private boolean debug = false; |
||
47 | protected Hashtable typeFilters = new Hashtable(); |
||
48 | public int[] order = null; |
||
49 | private ArrayList managers = new ArrayList(); |
||
50 | protected ArrayList filterList = null; |
||
51 | 2809 | nacho | |
52 | /**
|
||
53 | * Constructor
|
||
54 | * @param filterStack
|
||
55 | */
|
||
56 | public RasterFilterStackManager(RasterFilterStack filterStack) {
|
||
57 | this.filterStack = filterStack;
|
||
58 | typeFilters.put("transparency", new Integer(0)); |
||
59 | typeFilters.put("enhanced", new Integer(1)); |
||
60 | typeFilters.put("computeminmax", new Integer(2)); |
||
61 | typeFilters.put("tail", new Integer(3)); |
||
62 | typeFilters.put("removebands", new Integer(4)); |
||
63 | 3791 | nacho | typeFilters.put("sharpening", new Integer(5)); |
64 | 2809 | nacho | init(); |
65 | this.filterStack.setOrder(order);
|
||
66 | } |
||
67 | |||
68 | /**
|
||
69 | * Registra un manager del sistema
|
||
70 | * @param manager
|
||
71 | */
|
||
72 | protected void register(IStackManager manager) { |
||
73 | managers.add(manager); |
||
74 | } |
||
75 | |||
76 | /**
|
||
77 | * Inicializaci?n. Asigna el orden de los filtros
|
||
78 | *
|
||
79 | */
|
||
80 | protected void init() { |
||
81 | order = new int[typeFilters.size()]; |
||
82 | 3791 | nacho | order[0] = ((Integer) typeFilters.get("sharpening")).intValue(); |
83 | order[1] = ((Integer) typeFilters.get("computeminmax")).intValue(); |
||
84 | order[2] = ((Integer) typeFilters.get("tail")).intValue(); |
||
85 | order[3] = ((Integer) typeFilters.get("enhanced")).intValue(); |
||
86 | order[4] = ((Integer) typeFilters.get("transparency")).intValue(); |
||
87 | order[5] = ((Integer) typeFilters.get("removebands")).intValue(); |
||
88 | 2809 | nacho | } |
89 | |||
90 | /**
|
||
91 | * A?ade un nuevo tipo de filtro
|
||
92 | * @param key Nombre del filtro
|
||
93 | * @param type Constante entera asignada a ese tipo
|
||
94 | */
|
||
95 | protected void addTypeFilter(String key, int type, int position) { |
||
96 | typeFilters.put(key, new Integer(type)); |
||
97 | |||
98 | int[] newOrder = new int[order.length + 1]; |
||
99 | |||
100 | for (int i = 0; i < position; i++) |
||
101 | newOrder[i] = order[i]; |
||
102 | |||
103 | newOrder[position] = type; |
||
104 | |||
105 | for (int i = position + 1; i < newOrder.length; i++) |
||
106 | newOrder[i] = order[i - 1];
|
||
107 | |||
108 | order = newOrder; |
||
109 | this.filterStack.setOrder(order);
|
||
110 | } |
||
111 | |||
112 | /**
|
||
113 | * Obtiene la constante correspondiente a un tipo de filtro
|
||
114 | * @param key Clave para obtener la constante que corresponde al nombre del filtro
|
||
115 | * @return Tipo de filtro
|
||
116 | */
|
||
117 | public int getTypeFilter(String key) { |
||
118 | return ((Integer) typeFilters.get(key)).intValue(); |
||
119 | } |
||
120 | |||
121 | /**
|
||
122 | * A?ade un filtro de transparencia
|
||
123 | * @param red Intervalos de la banda del rojo a poner transparentes
|
||
124 | * @param green Intervalos de la banda del verde a poner transparentes
|
||
125 | * @param blue Intervalos de la banda del azul a poner transparentes
|
||
126 | * @param alpha Transparencia
|
||
127 | * @param transparencyRed Color en la banda del rojo de la transparencia
|
||
128 | * @param transparencyGreen Color en la banda del verde de la transparencia
|
||
129 | * @param transparencyBlue Color en la banda del azul de la transparencia
|
||
130 | */
|
||
131 | public void addTransparencyFilter(int[][] red, int[][] green, int[][] blue, |
||
132 | int alpha, int transparencyRed, |
||
133 | int transparencyGreen,
|
||
134 | int transparencyBlue) {
|
||
135 | RasterFilter filtro = null;
|
||
136 | |||
137 | switch (filterStack.getDataTypeInFilter(((Integer) typeFilters.get("transparency")).intValue())) { |
||
138 | case RasterBuf.TYPE_IMAGE:
|
||
139 | filtro = new TransparencyImageFilter();
|
||
140 | break;
|
||
141 | case RasterBuf.TYPE_SHORT:
|
||
142 | case RasterBuf.TYPE_USHORT:
|
||
143 | case RasterBuf.TYPE_INT:
|
||
144 | filtro = new TransparencyShortFilter();
|
||
145 | break;
|
||
146 | } |
||
147 | |||
148 | 4197 | nacho | if(filtro != null){ |
149 | if (red != null) { |
||
150 | filtro.addParam("red", red);
|
||
151 | } |
||
152 | |||
153 | if (green != null) { |
||
154 | filtro.addParam("green", green);
|
||
155 | } |
||
156 | |||
157 | if (blue != null) { |
||
158 | filtro.addParam("blue", blue);
|
||
159 | } |
||
160 | |||
161 | filtro.addParam("alpha", new Integer(alpha)); |
||
162 | filtro.addParam("transparencyRed", new Integer(transparencyRed)); |
||
163 | filtro.addParam("transparencyGreen", new Integer(transparencyGreen)); |
||
164 | filtro.addParam("transparencyBlue", new Integer(transparencyBlue)); |
||
165 | |||
166 | //Elimina los filtros que son equivalentes a este
|
||
167 | /*for(int i=0;i<filterStack.lenght();i++){
|
||
168 | if( filterStack.get(i) instanceof TransparencyImageFilter ||
|
||
169 | filterStack.get(i) instanceof TransparencyShortFilter){
|
||
170 | |||
171 | //Si este filtro es equivalente a uno de la pila se elimina este
|
||
172 | if(((TransparencyFilter)filtro).isEquivalent((TransparencyFilter)filterStack.get(i)))
|
||
173 | filterStack.removeFilter(filterStack.get(i));
|
||
174 | |||
175 | }
|
||
176 | }
|
||
177 | |||
178 | //A?ade el filtro si no hay uno equivalente
|
||
179 | |||
180 | boolean equivalentFilter = false;
|
||
181 | for(int i=0;i<filterStack.lenght();i++){
|
||
182 | if( filterStack.get(i) instanceof TransparencyImageFilter ||
|
||
183 | filterStack.get(i) instanceof TransparencyShortFilter){
|
||
184 | |||
185 | //Si no existe en la pila un filtro equivalente se a?ade
|
||
186 | if(((TransparencyFilter)filterStack.get(i)).isEquivalent((TransparencyFilter)filtro)){
|
||
187 | equivalentFilter = true;
|
||
188 | break;
|
||
189 | }
|
||
190 | }
|
||
191 | }
|
||
192 | if(!equivalentFilter)*/
|
||
193 | filterStack.removeFilter(((Integer) typeFilters.get("transparency")).intValue()); |
||
194 | filterStack.addFilter(((Integer) typeFilters.get("transparency")).intValue(), |
||
195 | filtro); |
||
196 | this.controlTypes();
|
||
197 | 2809 | nacho | } |
198 | } |
||
199 | |||
200 | /**
|
||
201 | * Obtiene el rango de rojo del filtro de transparencia de la pila
|
||
202 | * @return rango de rojo
|
||
203 | */
|
||
204 | public int[][] getTransparecyR() { |
||
205 | for (int i = 0; i < filterStack.lenght(); i++) { |
||
206 | if (filterStack.get(i) instanceof TransparencyImageFilter || |
||
207 | filterStack.get(i) instanceof TransparencyShortFilter) {
|
||
208 | return ((TransparencyFilter) filterStack.get(i)).rangesR;
|
||
209 | } |
||
210 | } |
||
211 | |||
212 | return null; |
||
213 | } |
||
214 | |||
215 | /**
|
||
216 | * Obtiene el rango de verde del filtro de transparencia de la pila
|
||
217 | * @return rango de verde
|
||
218 | */
|
||
219 | public int[][] getTransparecyG() { |
||
220 | for (int i = 0; i < filterStack.lenght(); i++) { |
||
221 | if (filterStack.get(i) instanceof TransparencyImageFilter || |
||
222 | filterStack.get(i) instanceof TransparencyShortFilter) {
|
||
223 | return ((TransparencyFilter) filterStack.get(i)).rangesG;
|
||
224 | } |
||
225 | } |
||
226 | |||
227 | return null; |
||
228 | } |
||
229 | |||
230 | /**
|
||
231 | * Obtiene el rango de azul del filtro de transparencia de la pila
|
||
232 | * @return rango de azul
|
||
233 | */
|
||
234 | public int[][] getTransparecyB() { |
||
235 | for (int i = 0; i < filterStack.lenght(); i++) { |
||
236 | if (filterStack.get(i) instanceof TransparencyImageFilter || |
||
237 | filterStack.get(i) instanceof TransparencyShortFilter) {
|
||
238 | return ((TransparencyFilter) filterStack.get(i)).rangesB;
|
||
239 | } |
||
240 | } |
||
241 | |||
242 | return null; |
||
243 | } |
||
244 | |||
245 | /**
|
||
246 | * A?ade un filtro de eliminado de bandas. Las pone a 0
|
||
247 | * @param bands
|
||
248 | */
|
||
249 | public void addRemoveBands(String bands) { |
||
250 | RasterFilter filtro = null;
|
||
251 | |||
252 | switch (filterStack.getDataTypeInFilter(((Integer) typeFilters.get("removebands")).intValue())) { |
||
253 | case RasterBuf.TYPE_IMAGE:
|
||
254 | filtro = new RemoveBandsImageFilter();
|
||
255 | break;
|
||
256 | case RasterBuf.TYPE_SHORT:
|
||
257 | case RasterBuf.TYPE_USHORT:
|
||
258 | case RasterBuf.TYPE_INT:
|
||
259 | filtro = new RemoveBandsShortFilter();
|
||
260 | break;
|
||
261 | } |
||
262 | 4197 | nacho | |
263 | if(filtro != null){ |
||
264 | filtro.addParam("stats", filterStack.getStats());
|
||
265 | filtro.addParam("bands", bands);
|
||
266 | |||
267 | filterStack.removeFilter(((Integer) typeFilters.get("removebands")).intValue()); |
||
268 | filterStack.addFilter(((Integer) typeFilters.get("removebands")).intValue(), |
||
269 | filtro); |
||
270 | this.controlTypes();
|
||
271 | } |
||
272 | 2809 | nacho | } |
273 | |||
274 | /**
|
||
275 | * A?ade un filtro de recorte de colas.
|
||
276 | * @param tail porcentaje de recorte
|
||
277 | * @param samples porcentaje de muestras tomadas del total de la imagen
|
||
278 | */
|
||
279 | public void addTailFilter(double tail, double samples, |
||
280 | boolean removeMaxValue) {
|
||
281 | if (filterStack.isActive(((Integer) typeFilters.get("tail")).intValue())) { |
||
282 | filterStack.removeFilter(((Integer) typeFilters.get("tail")).intValue()); |
||
283 | } |
||
284 | |||
285 | RasterFilter filtro = null;
|
||
286 | |||
287 | switch (filterStack.getDataTypeInFilter(((Integer) typeFilters.get("tail")).intValue())) { |
||
288 | case RasterBuf.TYPE_IMAGE:
|
||
289 | filtro = new PercentTailTrimImageFilter();
|
||
290 | break;
|
||
291 | case RasterBuf.TYPE_SHORT:
|
||
292 | case RasterBuf.TYPE_USHORT:
|
||
293 | case RasterBuf.TYPE_INT:
|
||
294 | filtro = new PercentTailTrimShortFilter();
|
||
295 | break;
|
||
296 | } |
||
297 | 4197 | nacho | |
298 | if(filtro != null){ |
||
299 | filtro.addParam("stats", filterStack.getStats());
|
||
300 | filtro.addParam("tail", new Double(tail)); |
||
301 | filtro.addParam("samples", new Double(samples)); |
||
302 | filtro.addParam("remove", new Boolean(removeMaxValue)); |
||
303 | |||
304 | filterStack.addFilter(((Integer) typeFilters.get("tail")).intValue(), |
||
305 | filtro); |
||
306 | this.controlTypes();
|
||
307 | } |
||
308 | 2809 | nacho | } |
309 | |||
310 | /**
|
||
311 | * A?ade un filtro de realce. Esta versi?n tiene el par?metro para a?adirle el nombre
|
||
312 | * del fichero. Esto se usa para que si a un fichero se le ha calculado ya el recorte de colas
|
||
313 | * no se vuelva a calcular, evitando as? que si hacemos un draw a una imagen por bloques cada
|
||
314 | * bloque tenga un calculo distinto para el recorte.
|
||
315 | */
|
||
316 | public void addEnhancedFilter(boolean remove, String fileName) { |
||
317 | if (filterStack.isActive(((Integer) typeFilters.get("enhanced")).intValue())) { |
||
318 | filterStack.removeFilter(((Integer) typeFilters.get("enhanced")).intValue()); |
||
319 | } |
||
320 | |||
321 | RasterFilter filtro = null;
|
||
322 | 4197 | nacho | |
323 | 2809 | nacho | switch (filterStack.getDataTypeInFilter(((Integer) typeFilters.get("enhanced")).intValue())) { |
324 | case RasterBuf.TYPE_IMAGE:
|
||
325 | filtro = new LinearEnhancementImageFilter();
|
||
326 | break;
|
||
327 | case RasterBuf.TYPE_SHORT:
|
||
328 | case RasterBuf.TYPE_USHORT:
|
||
329 | case RasterBuf.TYPE_INT:
|
||
330 | filtro = new LinearEnhancementShortFilter();
|
||
331 | break;
|
||
332 | } |
||
333 | |||
334 | 4197 | nacho | if(filtro != null){ |
335 | filtro.addParam("stats", filterStack.getStats());
|
||
336 | |||
337 | if (remove) {
|
||
338 | filtro.addParam("remove", new Boolean(true)); |
||
339 | } else {
|
||
340 | filtro.addParam("remove", new Boolean(false)); |
||
341 | } |
||
342 | |||
343 | if (fileName != null) { |
||
344 | filtro.addParam("filename", fileName);
|
||
345 | } else {
|
||
346 | filtro.addParam("filename", new String("")); |
||
347 | } |
||
348 | |||
349 | filterStack.addFilter(((Integer) typeFilters.get("enhanced")).intValue(), |
||
350 | filtro); |
||
351 | this.controlTypes();
|
||
352 | 2809 | nacho | } |
353 | } |
||
354 | |||
355 | /**
|
||
356 | * A?ade un filtro de realce
|
||
357 | */
|
||
358 | public void addEnhancedFilter(boolean remove) { |
||
359 | addEnhancedFilter(remove, "");
|
||
360 | } |
||
361 | |||
362 | /**
|
||
363 | * A?ade un filtro ComputeMinMax
|
||
364 | */
|
||
365 | public void addComputeMinMaxFilter() { |
||
366 | if (!filterStack.isActive(((Integer) typeFilters.get("computeminmax")).intValue())) { //Solo lo a?adimos si no est? |
||
367 | |||
368 | RasterFilter filtro = null;
|
||
369 | |||
370 | switch (filterStack.getDataTypeInFilter(((Integer) typeFilters.get("computeminmax")).intValue())) { |
||
371 | case RasterBuf.TYPE_IMAGE:
|
||
372 | filtro = new ComputeMinMaxImageFilter();
|
||
373 | break;
|
||
374 | case RasterBuf.TYPE_SHORT:
|
||
375 | case RasterBuf.TYPE_USHORT:
|
||
376 | case RasterBuf.TYPE_INT:
|
||
377 | filtro = new ComputeMinMaxShortFilter();
|
||
378 | break;
|
||
379 | } |
||
380 | 4197 | nacho | |
381 | if(filtro != null){ |
||
382 | filtro.addParam("stats", filterStack.getStats());
|
||
383 | filterStack.addFilter(((Integer) typeFilters.get("computeminmax")).intValue(), |
||
384 | filtro); |
||
385 | } |
||
386 | 2809 | nacho | } |
387 | |||
388 | this.controlTypes();
|
||
389 | } |
||
390 | |||
391 | /**
|
||
392 | 3791 | nacho | * A?ade un filtro ComputeMinMax
|
393 | * @param files Ficheros que componen la imagen
|
||
394 | * @param i Posici?n de la imagen de refinado dentro de la lista de GeoRasterFile
|
||
395 | * @param order Orden de visualizado de las bandas RGB
|
||
396 | * @param alpha Alpha aplicado a toda la imagen
|
||
397 | * @param method M?todo de calculo del refinado
|
||
398 | * @param coef Coeficiente
|
||
399 | */
|
||
400 | public void addSharpeningFilter(GeoRasterFile[] files, int i, int[] order, int alpha, String method, double coef, int coefBrovey) { |
||
401 | //Si ya hay un filtro de sharpening nos lo cargamos
|
||
402 | if (filterStack.isActive(((Integer) typeFilters.get("sharpening")).intValue())) { |
||
403 | filterStack.removeFilter(((Integer) typeFilters.get("sharpening")).intValue()); |
||
404 | } |
||
405 | |||
406 | RasterFilter filtro = null;
|
||
407 | |||
408 | switch (filterStack.getDataTypeInFilter(((Integer) typeFilters.get("sharpening")).intValue())) { |
||
409 | case RasterBuf.TYPE_IMAGE:
|
||
410 | filtro = new SharpeningImageFilter();
|
||
411 | break;
|
||
412 | case RasterBuf.TYPE_SHORT:
|
||
413 | case RasterBuf.TYPE_USHORT:
|
||
414 | case RasterBuf.TYPE_INT:
|
||
415 | //filtro = new SharpeningShortFilter();
|
||
416 | break;
|
||
417 | } |
||
418 | |||
419 | 4197 | nacho | if(filtro != null){ |
420 | filtro.addParam("stats", filterStack.getStats());
|
||
421 | filtro.addParam("pancromatica", new Integer(i)); |
||
422 | filtro.addParam("files", files);
|
||
423 | filtro.addParam("order", order);
|
||
424 | filtro.addParam("alpha", new Integer(alpha)); |
||
425 | filtro.addParam("method", method);
|
||
426 | filtro.addParam("coef", new Double(coef)); |
||
427 | filtro.addParam("coefBrovey", new Integer(coefBrovey)); |
||
428 | filterStack.addFilter(((Integer) typeFilters.get("sharpening")).intValue(),filtro); |
||
429 | |||
430 | this.controlTypes();
|
||
431 | } |
||
432 | 3791 | nacho | } |
433 | |||
434 | /**
|
||
435 | * Obtiene de la pila el primer filtro del tipo solicitado si existe sino devuelve null
|
||
436 | * @param type Tipo de filtro
|
||
437 | * @return Filtro
|
||
438 | */
|
||
439 | public RasterFilter getFilter(String type){ |
||
440 | int intType = getTypeFilter(type);
|
||
441 | return filterStack.getByType(intType);
|
||
442 | |||
443 | } |
||
444 | |||
445 | /**
|
||
446 | 2809 | nacho | * Obtiene el tipo de filtro a partir del objeto RasterFilter
|
447 | * @param rasterFilter Objeto RasterFilter del cual se quiere saber que tipo de filtro contiene
|
||
448 | * @return Tipo de filtro seg?n las constantes contenidas en RasterFilterStackManager
|
||
449 | */
|
||
450 | protected int getType(RasterFilter rasterFilter) { |
||
451 | if (rasterFilter instanceof TransparencyFilter) { |
||
452 | return 0; |
||
453 | } |
||
454 | |||
455 | if (rasterFilter instanceof LinearEnhancementFilter) { |
||
456 | return 1; |
||
457 | } |
||
458 | |||
459 | if (rasterFilter instanceof ComputeMinMaxFilter) { |
||
460 | return 2; |
||
461 | } |
||
462 | |||
463 | if (rasterFilter instanceof PercentTailTrimFilter) { |
||
464 | return 3; |
||
465 | } |
||
466 | |||
467 | return -1; |
||
468 | } |
||
469 | |||
470 | /**
|
||
471 | * Controla que los tipos de los filtros de la pila sean correctos, es decir, que
|
||
472 | * el tipo de salida de un filtro de salida coincida con el tipo de la entrada del
|
||
473 | * siguiente. En caso de no ser as? crea el filtro de tipo adecuado y lo sustituye
|
||
474 | * en el no coincidente. Esto es necesario ya que en la eliminaci?n de filtros puede
|
||
475 | * quedarse en inconsistencia de tipos.
|
||
476 | */
|
||
477 | protected void controlTypes() { |
||
478 | if (debug) {
|
||
479 | filterStack.show(); |
||
480 | } |
||
481 | |||
482 | for (int i = filterStack.lenght(); i >= 0; i--) { |
||
483 | if ((i - 1) >= 0) { |
||
484 | //Para el primer filtro comprobamos con el tipo de dato de entrada a la pila
|
||
485 | if (i == filterStack.lenght()) {
|
||
486 | 3791 | nacho | if (filterStack.getInitDataType() !=
|
487 | filterStack.get(i - 1).getInRasterDataType()) {
|
||
488 | String oldClass = filterStack.get(i - 1). |
||
489 | getClass(). |
||
490 | toString(). |
||
491 | substring(filterStack.get(i - 1).
|
||
492 | getClass(). |
||
493 | toString(). |
||
494 | lastIndexOf(".") +1, |
||
495 | filterStack.get(i - 1).
|
||
496 | getClass(). |
||
497 | toString(). |
||
498 | length()); |
||
499 | Pattern p = Pattern.compile(RasterBuf.typesToString(filterStack.get(i - 1).getInRasterDataType())); |
||
500 | 2809 | nacho | Matcher m = p.matcher(oldClass);
|
501 | String newClass = m.replaceAll(RasterBuf.typesToString(filterStack.getInitDataType()));
|
||
502 | |||
503 | try {
|
||
504 | Class filterClass = Class.forName("org.cresques.io.raster." + |
||
505 | newClass); |
||
506 | Constructor con = filterClass.getConstructor(null); |
||
507 | RasterFilter newFilter = (RasterFilter) con.newInstance(null);
|
||
508 | newFilter.params = filterStack.get(i - 1).params;
|
||
509 | filterStack.replace(newFilter, i - 1,
|
||
510 | this.getType(newFilter));
|
||
511 | } catch (Exception e) { |
||
512 | e.printStackTrace(); |
||
513 | } |
||
514 | } |
||
515 | |||
516 | //Desde el filtro 2 en adelante se compara la salida de uno con la entrada del siguiente
|
||
517 | 3791 | nacho | } else if (filterStack.get(i).getOutRasterDataType() != |
518 | filterStack.get(i - 1).getInRasterDataType()) {
|
||
519 | String oldClass = filterStack.get(i - 1).getClass(). |
||
520 | toString().substring(filterStack.get(i - 1).
|
||
521 | getClass(). |
||
522 | toString(). |
||
523 | lastIndexOf(".") + 1, |
||
524 | filterStack.get(i - 1).
|
||
525 | getClass(). |
||
526 | toString(). |
||
527 | length()); |
||
528 | Pattern p = Pattern.compile(RasterBuf.typesToString(filterStack.get(i - 1).getInRasterDataType())); |
||
529 | 2809 | nacho | Matcher m = p.matcher(oldClass);
|
530 | 3791 | nacho | String newClass = m.replaceAll(RasterBuf.typesToString(filterStack.get(i).getOutRasterDataType()));
|
531 | 2809 | nacho | |
532 | try {
|
||
533 | Class filterClass = Class.forName("org.cresques.io.raster." + |
||
534 | newClass); |
||
535 | Constructor con = filterClass.getConstructor(null); |
||
536 | RasterFilter newFilter = (RasterFilter) con.newInstance(null);
|
||
537 | newFilter.params = filterStack.get(i - 1).params;
|
||
538 | filterStack.replace(newFilter, i - 1,
|
||
539 | this.getType(newFilter));
|
||
540 | } catch (Exception e) { |
||
541 | e.printStackTrace(); |
||
542 | } |
||
543 | } |
||
544 | } |
||
545 | } |
||
546 | |||
547 | if (debug) {
|
||
548 | filterStack.show(); |
||
549 | } |
||
550 | } |
||
551 | |||
552 | /**
|
||
553 | * M?todo que devuelve true si el tipo de filtro pasado por par?metro est? en la
|
||
554 | * pila y false si no lo est?.
|
||
555 | * @param filter Tipo de filtro a comprobar
|
||
556 | * @return true si est? en la pila y false si no lo est?
|
||
557 | */
|
||
558 | public boolean isActive(int type) { |
||
559 | return filterStack.isActive(type);
|
||
560 | } |
||
561 | |||
562 | /**
|
||
563 | * Elimina los filtros de la pila de un determinado tipo
|
||
564 | * @param type Tipo de filtro a eliminar
|
||
565 | */
|
||
566 | public void removeFilter(int type) { |
||
567 | filterStack.removeFilter(type); |
||
568 | this.controlTypes();
|
||
569 | } |
||
570 | |||
571 | /**
|
||
572 | * Resetea el flag de temporalidad de los filtros de la pila.
|
||
573 | * Esto equivale a fijar los filtros que ya existen en la pila. A partir de
|
||
574 | * ese momento los filtros que se introduzcan podr?n ser eliminados de golpe
|
||
575 | * llamando a la funci?n deleteTempFilters
|
||
576 | */
|
||
577 | public void resetTempFilters() { |
||
578 | filterStack.resetTempFilters(); |
||
579 | } |
||
580 | |||
581 | /**
|
||
582 | * Elimina los filtros temporales, es decir, todos los filtros introducidos desde
|
||
583 | * el ?ltimo resetTempFilters que se ha realizado.
|
||
584 | */
|
||
585 | public void deleteTempFilters() { |
||
586 | filterStack.deleteTempFilters(); |
||
587 | } |
||
588 | |||
589 | /**
|
||
590 | * Obtiene el objeto de estadisticas asignado a la pila.
|
||
591 | * @return
|
||
592 | */
|
||
593 | public RasterStats getStackStats() {
|
||
594 | return filterStack.getStats();
|
||
595 | } |
||
596 | |||
597 | /* (non-Javadoc)
|
||
598 | * @see org.cresques.io.raster.StackManager#getStringsFromStack()
|
||
599 | */
|
||
600 | public ArrayList getStringsFromStack() { |
||
601 | filterList = new ArrayList(); |
||
602 | |||
603 | for (int i = 0; i < filterStack.lenght(); i++) { |
||
604 | RasterFilter rf = filterStack.get(i); |
||
605 | |||
606 | if (rf instanceof TransparencyFilter) { |
||
607 | filterList.add("filter.transparency.active=true");
|
||
608 | filterList.add("filter.transparency.rangeR=" +
|
||
609 | rangeToString(((TransparencyFilter) rf).getRangeR())); |
||
610 | filterList.add("filter.transparency.rangeG=" +
|
||
611 | rangeToString(((TransparencyFilter) rf).getRangeG())); |
||
612 | filterList.add("filter.transparency.rangeB=" +
|
||
613 | rangeToString(((TransparencyFilter) rf).getRangeB())); |
||
614 | } else if (rf instanceof LinearEnhancementFilter) { |
||
615 | filterList.add("filter.enhanced.active=true");
|
||
616 | filterList.add("filter.enhanced.remove=" +
|
||
617 | ((LinearEnhancementFilter) rf).getRemoveExtrema() |
||
618 | .toString()); |
||
619 | } else if (rf instanceof ComputeMinMaxFilter) { |
||
620 | filterList.add("filter.computeminmax.active=true");
|
||
621 | } else if (rf instanceof PercentTailTrimFilter) { |
||
622 | filterList.add("filter.tail.active=true");
|
||
623 | filterList.add("filter.tail.value=" +
|
||
624 | this.getStackStats().tailPercent);
|
||
625 | filterList.add("filter.tail.remove=" +
|
||
626 | ((PercentTailTrimFilter) rf).removeMaxValue()); |
||
627 | } else if (rf instanceof RemoveBandsFilter) { |
||
628 | filterList.add("filter.removebands.active=true");
|
||
629 | filterList.add("filter.removebands.bands=" +
|
||
630 | ((RemoveBandsFilter) rf).bands); |
||
631 | 4160 | nacho | } else if (rf instanceof SharpeningFilter) { |
632 | SharpeningFilter sharp = ((SharpeningFilter) rf); |
||
633 | filterList.add("filter.pansharpening.active=true");
|
||
634 | filterList.add("filter.pansharpening.posPancromatica="+sharp.posPancromatica);
|
||
635 | filterList.add("filter.pansharpening.bandOrder="+sharp.bandOrder[0]+","+sharp.bandOrder[1]+","+sharp.bandOrder[2]); |
||
636 | for(int file=0;file<sharp.files.length;file++) |
||
637 | filterList.add("filter.pansharpening.file"+file+"="+sharp.files[file].getName()); |
||
638 | filterList.add("filter.pansharpening.method="+sharp.method);
|
||
639 | filterList.add("filter.pansharpening.coefHSL="+sharp.coef);
|
||
640 | filterList.add("filter.pansharpening.coefBrovey="+sharp.coefBrovey);
|
||
641 | filterList.add("filter.pansharpening.alpha="+sharp.alpha);
|
||
642 | 2809 | nacho | } else { //Se recorren todos los managers registrados comprobando si corresponde a la clase del filtro |
643 | |||
644 | for (int j = 0; j < managers.size(); j++) |
||
645 | ((IStackManager) managers.get(j)).getStringsFromStack(); |
||
646 | } |
||
647 | } |
||
648 | |||
649 | return filterList;
|
||
650 | } |
||
651 | |||
652 | /**
|
||
653 | * Crea una pila de filtros a partir de un Array de Strings. Cada elemento del array debe
|
||
654 | * tener la forma elemento=valor.
|
||
655 | * @param filters
|
||
656 | */
|
||
657 | public void createStackFromStrings(ArrayList f) { |
||
658 | this.createStackFromStrings(f, new Integer(0)); |
||
659 | } |
||
660 | 4160 | nacho | |
661 | private GeoRasterFile[] grfList = null; |
||
662 | |||
663 | /**
|
||
664 | * Crea una pila de filtros a partir de un Array de Strings. Cada elemento del array debe
|
||
665 | * tener la forma elemento=valor.
|
||
666 | * @param filters
|
||
667 | 2809 | nacho | */
|
668 | 4160 | nacho | public void createStackFromStrings(ArrayList f, GeoRasterFile[] grfList) { |
669 | this.grfList = grfList;
|
||
670 | this.createStackFromStrings(f, new Integer(0)); |
||
671 | } |
||
672 | |||
673 | 2809 | nacho | public void createStackFromStrings(ArrayList f, Integer pos) { |
674 | ArrayList filters = (ArrayList) f.clone(); |
||
675 | filterStack.clear(); |
||
676 | |||
677 | int filteri = pos.intValue();
|
||
678 | |||
679 | //Busca un filtro activo y despu?s todas las propiedades que necesita ese filtro para
|
||
680 | //ser creado. Una vez las tiene a?ade en la pila el tipo de filtro.
|
||
681 | while ((filters.size() > 0) && (filteri < filters.size())) { |
||
682 | String fil = (String) filters.get(filteri); |
||
683 | |||
684 | if (fil.startsWith("filter.transparency.active") && |
||
685 | getValue(fil).equals("true")) {
|
||
686 | filters.remove(filteri); |
||
687 | |||
688 | int[][] r = null; |
||
689 | int[][] g = null; |
||
690 | int[][] b = null; |
||
691 | |||
692 | 4160 | nacho | for (int propFilter = 0;propFilter < filters.size();propFilter++) { |
693 | 2809 | nacho | String elem = (String) filters.get(propFilter); |
694 | |||
695 | if (elem.startsWith("filter.transparency.rangeR")) { |
||
696 | r = stringToRange(getValue(elem)); |
||
697 | filters.remove(propFilter); |
||
698 | propFilter--; |
||
699 | } |
||
700 | |||
701 | if (elem.startsWith("filter.transparency.rangeG")) { |
||
702 | g = stringToRange(getValue(elem)); |
||
703 | filters.remove(propFilter); |
||
704 | propFilter--; |
||
705 | } |
||
706 | |||
707 | if (elem.startsWith("filter.transparency.rangeB")) { |
||
708 | b = stringToRange(getValue(elem)); |
||
709 | filters.remove(propFilter); |
||
710 | propFilter--; |
||
711 | } |
||
712 | } |
||
713 | |||
714 | this.addTransparencyFilter(r, g, b, 0x10, 0xff, 0xff, 0xff); |
||
715 | filteri = -1;
|
||
716 | } |
||
717 | |||
718 | if (fil.startsWith("filter.enhanced.active") && |
||
719 | getValue(fil).equals("true")) {
|
||
720 | filters.remove(filteri); |
||
721 | |||
722 | 4160 | nacho | for (int propFilter = 0;propFilter < filters.size();propFilter++) { |
723 | 2809 | nacho | String elem = (String) filters.get(propFilter); |
724 | |||
725 | if (elem.startsWith("filter.enhanced.remove")) { |
||
726 | this.addEnhancedFilter(Boolean.valueOf(getValue(elem)) |
||
727 | .booleanValue()); |
||
728 | filters.remove(propFilter); |
||
729 | propFilter--; |
||
730 | } |
||
731 | } |
||
732 | |||
733 | this.addComputeMinMaxFilter();
|
||
734 | filteri = -1;
|
||
735 | } |
||
736 | |||
737 | if (fil.startsWith("filter.tail.active") && |
||
738 | getValue(fil).equals("true")) {
|
||
739 | filters.remove(filteri); |
||
740 | this.removeFilter(this.getTypeFilter("computeminmax")); |
||
741 | |||
742 | double recorte = 0D; |
||
743 | boolean remove = false; |
||
744 | |||
745 | 4160 | nacho | for (int propFilter = 0; propFilter < filters.size();propFilter++) { |
746 | 2809 | nacho | String elem = (String) filters.get(propFilter); |
747 | |||
748 | if (elem.startsWith("filter.tail.value")) { |
||
749 | recorte = Double.parseDouble(getValue(elem));
|
||
750 | filters.remove(propFilter); |
||
751 | propFilter--; |
||
752 | } |
||
753 | |||
754 | if (elem.startsWith("filter.tail.remove")) { |
||
755 | remove = Boolean.valueOf(getValue(elem)).booleanValue();
|
||
756 | filters.remove(propFilter); |
||
757 | propFilter--; |
||
758 | } |
||
759 | } |
||
760 | |||
761 | this.addTailFilter(recorte, 0D, remove); |
||
762 | filteri = -1;
|
||
763 | } |
||
764 | |||
765 | if (fil.startsWith("filter.removebands.active") && |
||
766 | getValue(fil).equals("true")) {
|
||
767 | filters.remove(filteri); |
||
768 | |||
769 | 4160 | nacho | for (int propFilter = 0;propFilter < filters.size();propFilter++) { |
770 | 2809 | nacho | String elem = (String) filters.get(propFilter); |
771 | |||
772 | if (elem.startsWith("filter.removebands.bands")) { |
||
773 | this.addRemoveBands(getValue(elem));
|
||
774 | filters.remove(propFilter); |
||
775 | propFilter--; |
||
776 | } |
||
777 | } |
||
778 | 4160 | nacho | filteri = -1;
|
779 | } |
||
780 | 2809 | nacho | |
781 | 4160 | nacho | if (fil.startsWith("filter.pansharpening.active") && |
782 | getValue(fil).equals("true")) {
|
||
783 | filters.remove(filteri); |
||
784 | |||
785 | int posPancromatica = 0; |
||
786 | int[] bandOrder = {0, 1, 2}; |
||
787 | ArrayList files = new ArrayList(); |
||
788 | int alpha = 0; |
||
789 | String method = ""; |
||
790 | double coef = 0D; |
||
791 | int coefBrovey = 0; |
||
792 | |||
793 | for (int propFilter = 0;propFilter < filters.size();propFilter++) { |
||
794 | String elem = (String) filters.get(propFilter); |
||
795 | |||
796 | if (elem.startsWith("filter.pansharpening.posPancromatica")) { |
||
797 | posPancromatica = Integer.parseInt(getValue(elem));
|
||
798 | filters.remove(propFilter); |
||
799 | propFilter--; |
||
800 | } |
||
801 | if (elem.startsWith("filter.pansharpening.bandOrder")) { |
||
802 | String rango = getValue(elem);
|
||
803 | bandOrder[0] = Integer.parseInt(rango.substring(0, rango.indexOf(","))); |
||
804 | bandOrder[1] = Integer.parseInt(rango.substring(rango.indexOf(",") + 1, rango.lastIndexOf(","))); |
||
805 | bandOrder[2] = Integer.parseInt(rango.substring(rango.lastIndexOf(",") + 1, rango.length())); |
||
806 | filters.remove(propFilter); |
||
807 | propFilter--; |
||
808 | } |
||
809 | if (elem.startsWith("filter.pansharpening.file")) { |
||
810 | files.add(getValue(elem)); |
||
811 | filters.remove(propFilter); |
||
812 | propFilter--; |
||
813 | } |
||
814 | if (elem.startsWith("filter.pansharpening.alpha")) { |
||
815 | alpha = Integer.parseInt(getValue(elem));
|
||
816 | filters.remove(propFilter); |
||
817 | propFilter--; |
||
818 | } |
||
819 | if (elem.startsWith("filter.pansharpening.method")) { |
||
820 | method = getValue(elem); |
||
821 | filters.remove(propFilter); |
||
822 | propFilter--; |
||
823 | } |
||
824 | if (elem.startsWith("filter.pansharpening.coefHSL")) { |
||
825 | coef = Double.parseDouble(getValue(elem));
|
||
826 | filters.remove(propFilter); |
||
827 | propFilter--; |
||
828 | } |
||
829 | if (elem.startsWith("filter.pansharpening.coefBrovey")) { |
||
830 | coefBrovey = Integer.parseInt(getValue(elem));
|
||
831 | //filters.remove(propFilter);
|
||
832 | //propFilter--;
|
||
833 | } |
||
834 | } |
||
835 | |||
836 | addSharpeningFilter(this.grfList, posPancromatica, bandOrder, alpha, method, coef, coefBrovey);
|
||
837 | 2809 | nacho | filteri = -1;
|
838 | } |
||
839 | 4160 | nacho | |
840 | 2809 | nacho | for (int j = 0; j < managers.size(); j++) |
841 | 4160 | nacho | ((IStackManager) managers.get(j)).createStackFromStrings(filters, new Integer(filteri)); |
842 | 2809 | nacho | |
843 | filteri++; |
||
844 | } |
||
845 | } |
||
846 | |||
847 | /**
|
||
848 | * Obtiene el elemento de una cadena de la forma elemento=valor
|
||
849 | * @param cadena
|
||
850 | * @return
|
||
851 | */
|
||
852 | public String getElem(String cadena) { |
||
853 | if (cadena != null) { |
||
854 | return cadena.substring(0, cadena.indexOf("=")); |
||
855 | } else {
|
||
856 | return null; |
||
857 | } |
||
858 | } |
||
859 | |||
860 | /**
|
||
861 | * Obtiene el valor de una cadena de la forma elemento=valor
|
||
862 | * @param cadena
|
||
863 | * @return
|
||
864 | */
|
||
865 | public String getValue(String cadena) { |
||
866 | if (cadena != null) { |
||
867 | return cadena.substring(cadena.indexOf("=") + 1, cadena.length()); |
||
868 | } else {
|
||
869 | return null; |
||
870 | } |
||
871 | } |
||
872 | |||
873 | /**
|
||
874 | * Convierte un rango contenido en una array doble en una cadena
|
||
875 | * de strings para poder salvar a xml
|
||
876 | * @param rang
|
||
877 | * @return
|
||
878 | */
|
||
879 | private String rangeToString(int[][] rang) { |
||
880 | StringBuffer rangoStr = new StringBuffer(); |
||
881 | |||
882 | if (rang != null) { |
||
883 | for (int i = 0; i < rang.length; i++) { |
||
884 | rangoStr.append(String.valueOf(rang[i][0]) + ":"); |
||
885 | rangoStr.append(String.valueOf(rang[i][1]) + ":"); |
||
886 | } |
||
887 | |||
888 | String r = rangoStr.toString();
|
||
889 | |||
890 | if (r.endsWith(":")) { |
||
891 | r = r.substring(0, r.length() - 1); |
||
892 | } |
||
893 | |||
894 | return r;
|
||
895 | } else {
|
||
896 | return null; |
||
897 | } |
||
898 | } |
||
899 | |||
900 | /**
|
||
901 | * Convierte una cadena en una lista de rangos numericos para poder
|
||
902 | * asignar transparencias a la imagen
|
||
903 | * @param rang
|
||
904 | * @return
|
||
905 | */
|
||
906 | private int[][] stringToRange(String rang) { |
||
907 | if ((rang != null) && !rang.equals("null")) { |
||
908 | ArrayList lista = new ArrayList(); |
||
909 | StringTokenizer tokenizer = new StringTokenizer(rang, ":"); |
||
910 | |||
911 | while (tokenizer.hasMoreTokens())
|
||
912 | lista.add(tokenizer.nextToken()); |
||
913 | |||
914 | int[][] intervalos = new int[(int) (lista.size() / 2)][2]; |
||
915 | |||
916 | for (int i = 0; i < lista.size(); i = i + 2) { |
||
917 | intervalos[i / 2][0] = Integer.valueOf((String) lista.get(i)) |
||
918 | .intValue(); |
||
919 | intervalos[i / 2][1] = Integer.valueOf((String) lista.get(i + |
||
920 | 1))
|
||
921 | .intValue(); |
||
922 | } |
||
923 | |||
924 | return intervalos;
|
||
925 | } else {
|
||
926 | return null; |
||
927 | } |
||
928 | } |
||
929 | } |