Statistics
| Revision:

root / branches / v2_0_0_prep / extensions / org.gvsig.app.document.layout.app / org.gvsig.app.document.layout.app.mainplugin / src / main / java / org / gvsig / app / project / documents / layout / fframes / FFrameView.java @ 37191

History | View | Annotate | Download (37.2 KB)

1
/* gvSIG. Geographic Information System of the Valencian Government
2
 *
3
 * Copyright (C) 2007-2008 Infrastructures and Transports Department
4
 * of the Valencian Government (CIT)
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., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
20
 *
21
 */
22
package org.gvsig.app.project.documents.layout.fframes;
23

    
24
import java.awt.Color;
25
import java.awt.Dimension;
26
import java.awt.Graphics2D;
27
import java.awt.Point;
28
import java.awt.Rectangle;
29
import java.awt.geom.AffineTransform;
30
import java.awt.geom.Point2D;
31
import java.awt.geom.Rectangle2D;
32
import java.awt.image.BufferedImage;
33

    
34
import javax.swing.SwingUtilities;
35

    
36
import org.cresques.cts.IProjection;
37
import org.slf4j.Logger;
38
import org.slf4j.LoggerFactory;
39

    
40
import org.gvsig.andami.PluginServices;
41
import org.gvsig.andami.messages.NotificationManager;
42
import org.gvsig.app.project.Project;
43
import org.gvsig.app.project.documents.layout.DefaultLayoutNotification;
44
import org.gvsig.app.project.documents.layout.FLayoutUtilities;
45
import org.gvsig.app.project.documents.layout.LayoutNotification;
46
import org.gvsig.app.project.documents.view.DefaultViewDocument;
47
import org.gvsig.app.project.documents.view.ViewDocument;
48
import org.gvsig.compat.print.PrintAttributes;
49
import org.gvsig.fmap.dal.exception.ReadException;
50
import org.gvsig.fmap.geom.Geometry;
51
import org.gvsig.fmap.geom.Geometry.SUBTYPES;
52
import org.gvsig.fmap.geom.GeometryLocator;
53
import org.gvsig.fmap.geom.GeometryManager;
54
import org.gvsig.fmap.geom.exception.CreateEnvelopeException;
55
import org.gvsig.fmap.geom.primitive.Envelope;
56
import org.gvsig.fmap.mapcontext.MapContext;
57
import org.gvsig.fmap.mapcontext.MapContextException;
58
import org.gvsig.fmap.mapcontext.ViewPort;
59
import org.gvsig.fmap.mapcontext.events.ColorEvent;
60
import org.gvsig.fmap.mapcontext.events.ExtentEvent;
61
import org.gvsig.fmap.mapcontext.events.ProjectionEvent;
62
import org.gvsig.fmap.mapcontext.events.listeners.ViewPortListener;
63
import org.gvsig.fmap.mapcontext.rendering.legend.events.LegendChangedEvent;
64
import org.gvsig.fmap.mapcontext.rendering.legend.events.listeners.LegendListener;
65
import org.gvsig.tools.ToolsLocator;
66
import org.gvsig.tools.dynobject.DynStruct;
67
import org.gvsig.tools.persistence.PersistenceManager;
68
import org.gvsig.tools.persistence.PersistentState;
69
import org.gvsig.tools.persistence.exception.PersistenceException;
70

    
71
/**
72
 * FFrame para introducir una vista en el Layout.
73
 * 
74
 * @author Vicente Caballero Navarro
75
 */
76
public class FFrameView extends FFrame implements ViewPortListener,
77
    LegendListener, IFFrameUseProject, IFFrameUseFMap {
78

    
79
    public static final String PERSISTENCE_DEFINITION_NAME = "FFrameView";
80

    
81
    private static final String MODE_FIELD = "mode";
82
    private static final String TYPESCALE_FIELD = "typeScale";
83
    private static final String EXTENSION_FIELD = "extension";
84
    private static final String QUALITY_FIELD = "quality";
85
    private static final String VIEWING_FIELD = "viewing";
86
    private static final String BLINKED_FIELD = "bLinked";
87
    private static final String MAPUNITS_FIELD = "mapUnits";
88
    private static final String SCALE_FIELD = "scale";
89
    private static final String VIEW_FIELD = "view";
90
    private static final String ENVELOPE_FIELD = "envelope";
91
    private static final String SHOWGRID_FIELD = "showGrid";
92
    private static final String GRID_FIELD = "gridview";
93
    private static final String MAPCONTEXT_FIELD = "mapContext";
94

    
95
    private static final GeometryManager geomManager = GeometryLocator
96
        .getGeometryManager();
97
    private static final Logger logger = LoggerFactory
98
        .getLogger(FFrameView.class);
99
    public static final int PRESENTATION = 0;
100
    public static final int DRAFT = 1;
101
    protected int mode;
102
    protected int typeScale = AUTOMATICO;
103
    protected int extension = 0;
104
    protected int quality = PRESENTATION;
105
    protected int viewing = 0;
106
    protected boolean linked = true;
107
    protected ViewDocument viewDocument = null;
108
    protected MapContext mapContext = null;
109
    protected double mapScale = 0;
110
    protected int mapUnits = 1; // Meters.
111

    
112
    private BufferedImage m_image = null;
113
    private AffineTransform at = null;
114
    protected Project project = null;
115
    private double scaleAnt;
116
    private boolean refresh = false;
117
    private Point origin;
118
    private Point2D p1;
119
    private Point2D p2;
120
    private IFFrame grid;
121
    private boolean showGrid = false;
122

    
123
    /**
124
     * Creates a new FFrameView object.
125
     */
126
    public FFrameView() {
127
        num++;
128
    }
129

    
130
    /**
131
     * Devuelve una descripci?n del FFrameView.
132
     * 
133
     * @return Descripci?n.
134
     */
135
    public String toString() {
136
        if (getView() == null) {
137
            return "FFrameView " + num + ": " + "Vacio";
138
        }
139

    
140
        return "FFrameView " + num + ": " + getView().getName();
141
    }
142

    
143
    /**
144
     * Rellena la escala de la vista que contiene el fframe.
145
     * 
146
     * @param d
147
     *            escala de la vista.
148
     */
149
    public void setScale(double d) {
150
        mapScale = d;
151
    }
152

    
153
    /**
154
     * Inserta el nuevo extent a la FFrameView.
155
     * 
156
     * @param r
157
     *            Rect?ngulo a ocupar por el FFrameView.
158
     */
159
    public void setNewEnvelope(Envelope r) {
160
        getMapContext().getViewPort().setEnvelope(r);
161
        refresh = true;
162
        mapScale =
163
            FLayoutUtilities.getScaleView(getMapContext().getViewPort(),
164
                getBoundBox().width, getBoundingBox(null).width
165
                    / getBoundBox().width);
166
    }
167

    
168
    /**
169
     * Devuelve el FMap de la vista o una clonaci?n de este si se utiliza una
170
     * escala fija.
171
     * 
172
     * @return FMap.
173
     */
174
    public MapContext getMapContext() {
175
        return mapContext;
176
    }
177

    
178
    /**
179
     * Rellena la calidad que se quiere aplicar.
180
     * 
181
     * @param q
182
     *            entero que representa la calidad a aplicar.
183
     */
184
    public void setQuality(int q) {
185
        quality = q;
186
    }
187

    
188
    /**
189
     * Devuelve un entero que representa la calidad que est? seleccionada.
190
     * 
191
     * @return tipo de calidad selccionada.
192
     */
193
    public int getQuality() {
194
        return quality;
195
    }
196

    
197
    /**
198
     * Devuelve un entero que representa la forma en que se actualiza la vista.
199
     * 
200
     * @return forma que se actualiza la vista.
201
     */
202
    public int getViewing() {
203
        return viewing;
204
    }
205

    
206
    /**
207
     * Rellena la forma de actualizar la vista(cuando activo o siempre). De
208
     * momento esta opci?n esta deshabilitada.
209
     * 
210
     * @param v
211
     *            entero que representa la forma de actualizar la vista.
212
     */
213
    public void setViewing(int v) {
214
        viewing = v;
215
    }
216

    
217
    /**
218
     * Inserta el ProjectView de donde obtener las propiedades de la vista a
219
     * mostrar.
220
     * 
221
     * @param v
222
     *            Modelo de la vista.
223
     */
224
    public void setView(DefaultViewDocument v) {
225
        viewDocument = v;
226
        ViewPort vp = null;
227
        if (getMapContext() != null) {
228
            vp = getMapContext().getViewPort();
229
        }else{
230
            try {
231
                vp = (ViewPort) v.getMapContext().getViewPort().clone();
232
            } catch (CloneNotSupportedException e1) {
233
                NotificationManager.addError("Excepci?n :", e1);
234
            }
235

    
236
        }
237
        vp.setImageSize(new Dimension((int) getBoundingBox(null).width,
238
            (int) getBoundingBox(null).height));
239

    
240
        if (linked){
241
            if (getTypeScale() == AUTOMATICO) {
242
                try {
243
                    mapContext =
244
                        v.getMapContext().createNewFMap(
245
                            (ViewPort) v.getMapContext().getViewPort().clone());
246
                } catch (CloneNotSupportedException e1) {
247
                    NotificationManager.addError("Excepci?n :", e1);
248
                }
249

    
250
                mapContext.getViewPort().setImageSize(
251
                    new Dimension((int) getBoundingBox(null).width,
252
                        (int) getBoundingBox(null).height));
253
                v.getMapContext().getViewPort().addViewPortListener(this);
254
                v.getMapContext().addLayerListener(this);
255
            }else{
256
                if (getTypeScale() == CONSTANTE) {
257
                    mapContext = v.getMapContext().createNewFMap(vp);
258
                    vp.setEnvelope(getNewEnvelope(getScale()));
259
                    v.getMapContext().getViewPort().addViewPortListener(this);
260
                    v.getMapContext().addLayerListener(this);
261
                }else{
262
                    if (getTypeScale() == MANUAL) {
263
                        mapContext = v.getMapContext().createNewFMap(vp);
264
                        vp.setEnvelope(getNewEnvelope(getScale()));
265
                        v.getMapContext().getViewPort()
266
                            .addViewPortListener(this);
267
                        v.getMapContext().addLayerListener(this);
268
                    }
269
                }
270
            }
271
        }else{
272
            if (!linked) {
273

    
274
                if (getTypeScale() == AUTOMATICO) {
275
                    mapContext = v.getMapContext().cloneFMap(); // (v.getMapContext().getViewPort().cloneViewPort());
276
                    try {
277
                        mapContext.setViewPort((ViewPort) v.getMapContext()
278
                            .getViewPort().clone());
279
                    } catch (CloneNotSupportedException e1) {
280
                        NotificationManager.addError("Excepci?n :", e1);
281
                    }
282
                    mapContext.getViewPort().setImageSize(
283
                        new Dimension((int) getBoundingBox(null).width,
284
                            (int) getBoundingBox(null).height));
285
                    v.getMapContext().getViewPort().addViewPortListener(this);
286
                }else{
287
                    if (getTypeScale() == CONSTANTE) {
288
                        mapContext = v.getMapContext().cloneFMap();
289
                        vp.setEnvelope(getNewEnvelope(getScale()));
290
                        mapContext.setViewPort(vp);
291
                        v.getMapContext().getViewPort()
292
                            .addViewPortListener(this);
293
                    }else{
294
                        if (getTypeScale() == MANUAL) {
295
                            mapContext = v.getMapContext().cloneFMap();
296
                            vp.setEnvelope(getNewEnvelope(getScale()));
297
                            mapContext.setViewPort(vp);
298
                            v.getMapContext().getViewPort()
299
                                .addViewPortListener(this);
300
                        }
301
                    }
302
                }               
303
            }
304
        }
305
    }
306

    
307
    /**
308
     * Devuelve el modelo de la vista.
309
     * 
310
     * @return Modelo de la vista.
311
     */
312
    public ViewDocument getView() {
313
        return viewDocument;
314
    }
315

    
316
    /**
317
     * Devuelve un Rect?ngulo que representa el extent de la vista que se
318
     * requiere a partir de una escala.
319
     * 
320
     * @param scale
321
     *            Escala a mostrar.
322
     * 
323
     * @return Rect?ngulo.
324
     */
325
    protected Envelope getNewEnvelope(long scale) {
326
        double hview = getBoundBox().getHeight();
327
        double wview = getBoundBox().getWidth();
328
        double hextent = (scale * hview) / 100.0;
329
        double wextent = (scale * wview) / 100.0;
330

    
331
        if (mapContext.getViewPort().getEnvelope() == null) {
332
            try {
333
                return geomManager.createEnvelope(0, 0, 0, 0, SUBTYPES.GEOM2D);
334
            } catch (CreateEnvelopeException e) {
335
                logger.error("Error creating the envelope", e);
336
                return null;
337
            }
338
        }
339
        double newx =
340
            mapContext.getViewPort().getEnvelope().getCenter(Geometry.DIMENSIONS.X)
341
                - (wextent / 2.0);
342
        double newy =
343
            mapContext.getViewPort().getEnvelope().getCenter(Geometry.DIMENSIONS.Y)
344
                - (hextent / 2.0);
345
        IProjection proj = mapContext.getViewPort().getProjection();
346
        Envelope r = null;
347
        try {
348
            r =
349
                geomManager.createEnvelope(newx, newy, newx + wextent, newy
350
                    + hextent, SUBTYPES.GEOM2D);
351
        } catch (CreateEnvelopeException e) {
352
            logger.error("Error creating the envelope", e);
353
        }
354
        if (!proj.isProjected()) {
355
            Rectangle2D auxR =
356
                new Rectangle2D.Double(newx, newy, wextent, hextent);
357
            Rectangle2D aux =
358
                mapContext.getViewPort().getProjection()
359
                    .getExtent(auxR, scale, wview, hview, 1, 100, 2.54);
360
            try {
361
                r =
362
                    geomManager.createEnvelope(aux.getX(), aux.getY(),
363
                        aux.getMaxX(), aux.getMaxY(), SUBTYPES.GEOM2D);
364
            } catch (CreateEnvelopeException e) {
365
                logger.error("Error creating the envelope", e);
366
            }
367
        }
368
        return r;
369
    }
370

    
371
    /**
372
     * M?todo que dibuja sobre el graphics que se le pasa como par?metro, seg?n
373
     * la transformada afin que se debe de aplicar y el rect?ngulo que se debe
374
     * de dibujar.
375
     * 
376
     * @param g
377
     *            Graphics2D
378
     * @param at
379
     *            Transformada af?n.
380
     * @param rectangleView
381
     *            rect?ngulo sobre el que hacer un clip.
382
     * @param imgBase
383
     *            Imagen para acelerar el dibujado.
384
     */
385
    public void draw(Graphics2D g, AffineTransform at, Rectangle2D rectangleView, BufferedImage imgBase) {
386
        Rectangle2D.Double rectangleLayout = getBoundingBox(at);  
387
        Rectangle originalClip = preDraw(g, rectangleLayout);    
388
        if (intersects(rectangleView, rectangleLayout)) {
389
            if (getMapContext() == null) {
390
                drawEmpty(g);
391
            } else {      
392
                if (getQuality() == PRESENTATION) {
393
                    drawPresentation(g, at, rectangleLayout, rectangleView, imgBase);
394
                } else {
395
                    drawDraft(g);
396
                }               
397
            }
398
        }
399
        postDraw(g, rectangleLayout, rectangleView, imgBase, originalClip, at);    
400
    }
401
    
402
    private void drawPresentation(Graphics2D g, AffineTransform affineTransform, Rectangle2D.Double rectangleLayout, Rectangle2D rectangleView, BufferedImage imgBase){
403
        Point mapOrigin = new Point((int)rectangleView.getMinX(), (int)rectangleView.getMaxY());
404

    
405
        ViewPort viewPort = this.getMapContext().getViewPort();
406
        Color theBackColor = viewPort.getBackColor();
407

    
408
        //If it is possible to draw the previous loaded image
409
        if (origin != null
410
            && origin.equals(mapOrigin)
411
            && affineTransform.getScaleX() == scaleAnt
412
            && m_image != null
413
            && !refresh
414
            && !(rectangleLayout.getWidth() > rectangleView.getWidth() || rectangleLayout.getHeight() > rectangleView.getHeight())) {
415
            if (theBackColor != null) {
416
                g.setColor(theBackColor);
417
                g.fillRect((int) rectangleLayout.x, (int) rectangleLayout.y,
418
                    viewPort.getImageWidth(),
419
                    viewPort.getImageHeight());
420
            }
421
            g.translate(rectangleLayout.getX(), rectangleLayout.getY());
422
            g.drawImage(m_image, 0, 0, null);
423
            g.translate(-rectangleLayout.getX(), -rectangleLayout.getY());
424
            scaleAnt = affineTransform.getScaleX();
425
            origin = mapOrigin;
426
        } else {
427
            viewPort.setOffset(new Point2D.Double(rectangleLayout.x, rectangleLayout.y));
428
            viewPort.setImageSize(new Dimension((int) rectangleLayout.width, (int) rectangleLayout.height));
429
            viewPort.refreshExtent();
430

    
431
            m_image =
432
                new BufferedImage((int) rectangleLayout.getWidth(),
433
                    (int) rectangleLayout.getHeight(),
434
                    BufferedImage.TYPE_INT_ARGB);
435
            Graphics2D gimg = (Graphics2D) m_image.getGraphics();
436
            gimg.translate(-((int) rectangleLayout.getX()),
437
                -((int) rectangleLayout.getY()));
438
            try {
439
                getMapContext().draw(m_image, gimg, getScale());
440
            } catch (ReadException e) {
441
                LOG.error("Error reading the provider" , e);
442
            } catch (MapContextException mpex) {
443
                LOG.error("Error reading the provider" , e);
444
            }
445
            gimg.translate(((int) rectangleLayout.getX()),
446
                ((int) rectangleLayout.getY()));
447
            if (theBackColor != null) {
448
                g.setColor(theBackColor);
449
                g.fillRect((int) rectangleLayout.x, (int) rectangleLayout.y,
450
                    viewPort.getImageWidth(),
451
                    viewPort.getImageHeight());
452
            }
453
            g.drawImage(m_image, (int) rectangleLayout.getX(),
454
                (int) rectangleLayout.getY(), null);
455
            scaleAnt = affineTransform.getScaleX();
456
            origin = mapOrigin;
457
            refresh = false;
458
        }        
459
    }
460
    
461
    private Rectangle preDraw(Graphics2D g, Rectangle2D.Double rectangleLayout){
462
        Rectangle originalClip = null;
463
        if (g.getClipBounds() != null) {
464
            originalClip = (Rectangle) g.getClipBounds().clone();
465
        }
466
        if (getRotation() != 0) {
467
            g.rotate(Math.toRadians(getRotation()), rectangleLayout.getCenterX(), rectangleLayout.getCenterY()
468
                + (rectangleLayout.height / 2));
469
        }       
470
        g.clipRect((int) rectangleLayout.getMinX(), (int) rectangleLayout.getMinY(),
471
            (int) rectangleLayout.getWidth(), (int) rectangleLayout.getHeight());
472
        return originalClip;
473
    }
474
    
475
    private void postDraw(Graphics2D g, Rectangle2D.Double rectangleLayout, Rectangle2D rectangleView, BufferedImage imgBase, 
476
        Rectangle originalClip, AffineTransform at){
477
        if (getRotation() != 0) {
478
            g.rotate(Math.toRadians(-getRotation()), rectangleLayout.getCenterX(), rectangleLayout.getCenterY());
479
        }
480
        if (getMapContext() != null) {
481
            setATMap(getMapContext().getViewPort().getAffineTransform());
482
        }
483
        if (originalClip != null) {
484
            g.setClip(originalClip.x, originalClip.y, originalClip.width, originalClip.height);
485
        } 
486
        if (showGrid && grid != null) {
487
            ((FFrameGrid) grid).setFFrameDependence(this);
488
            grid.draw(g, at, rectangleView, imgBase);
489
        }        
490
    }
491

    
492
    private Envelope calculateEnvelope() {
493
        if (p1 == null || p2 == null) {
494
            try {
495
                return geomManager.createEnvelope(0, 0, 0, 0, SUBTYPES.GEOM2D);
496
            } catch (CreateEnvelopeException e) {
497
                logger.error("Error creating the envelope", e);
498
            }
499
        }
500
        Envelope r = null;
501
        try {
502
            r =
503
                geomManager.createEnvelope(p1.getX(), p1.getY(), p2.getX(),
504
                    p2.getY(), SUBTYPES.GEOM2D);
505
        } catch (CreateEnvelopeException e) {
506
            logger.error("Error creating the envelope", e);
507
        }
508
        return r;
509
    }
510

    
511
    public void print(Graphics2D g, AffineTransform at, Geometry geom,
512
        PrintAttributes printAttributes) {
513
        Rectangle2D.Double rectangleLayout = getBoundingBox(at);  
514
        
515
        Rectangle originalClip = preDraw(g, rectangleLayout);
516
        print(g, at, printAttributes);
517
        postDraw(g, rectangleLayout, null, null, originalClip, at);
518
    }
519

    
520
    private void print(Graphics2D g, AffineTransform at, PrintAttributes printAttributes) {
521
        Rectangle2D.Double layoutRectangle = getBoundingBox(at);
522
              
523
        ViewPort viewPort = this.getMapContext().getViewPort();
524
        
525
        viewPort.setOffset(new Point2D.Double(layoutRectangle.x, layoutRectangle.y));
526
        viewPort.setImageSize(new Dimension((int) layoutRectangle.width, (int) layoutRectangle.height));
527

    
528
        //Draw the backgroung color of the map
529
        Color theBackColor = viewPort.getBackColor();
530
        if (theBackColor != null) {
531
            g.setColor(theBackColor);
532
            g.fillRect((int) layoutRectangle.x, (int) layoutRectangle.y, viewPort
533
                    .getImageWidth(), viewPort
534
                    .getImageHeight());
535
        }        
536
        
537
        //Print the map
538
        try {
539
            this.getMapContext().print(g, getScale(), printAttributes);
540
        } catch (ReadException e) {
541
            NotificationManager.addError(e.getMessage(), e);
542
        } catch (MapContextException e) {
543
            NotificationManager.addError(e.getMessage(), e);
544
        }         
545
    }
546

    
547
    /**
548
     * Rellena la unidad de medida en la que est? la vista.
549
     * 
550
     * @param i
551
     *            entero que representa la unidad de medida de la vista.
552
     */
553
    public void setMapUnits(int i) {
554
        mapUnits = i;
555
    }
556

    
557
    /**
558
     * Obtiene la unidad de medida en la que est? la vista.
559
     * 
560
     * @return Unidad de medida.
561
     */
562
    public int getMapUnits() {
563
        return mapUnits;
564
    }
565

    
566
    /**
567
     * Devuelve la escala seg?n el tipo de escala que se haya seleccionado al
568
     * a?adida la vista.
569
     * 
570
     * @return escala.
571
     */
572
    public long getScale() {
573
        /*
574
         * if (m_bLinked){
575
         * return getScaleView1(METROS);
576
         * }
577
         */
578
        if (getMapContext() == null) {
579
            return 0;
580
        }
581
        if (getTypeScale() == AUTOMATICO) {
582
            return FLayoutUtilities.getScaleView(getMapContext().getViewPort(),
583
                getBoundBox().width, getBoundingBox(null).width);
584
        } else
585
            if (getTypeScale() == CONSTANTE) {
586
                return (long) mapScale;
587
            } else
588
                if (getTypeScale() == MANUAL) {
589
                    return (long) mapScale;
590
                }
591

    
592
        return (long) mapScale;
593
    }
594

    
595
    /**
596
     * Seleccionar si la vista esta relacionada o no con la original.
597
     * 
598
     * @param b
599
     *            true si est? ligada y false si no lo est?.
600
     */
601
    public void setLinked(boolean b) {
602
        linked = b;
603
    }
604

    
605
    /**
606
     * Devuelve si est? ligada o no el FFrameView con la vista.
607
     * 
608
     * @return True si la vista est? ligada.
609
     */
610
    public boolean getLinked() {
611
        return linked;
612
    }
613

    
614
    /**
615
     * Devuelve la opci?n seleccionada:Rellenar marco de la vista o recorte a
616
     * la vista.
617
     * 
618
     * @return entero que representa la opci?n elegida.
619
     */
620
    public int getExtension() {
621
        return extension;
622
    }
623

    
624
    /**
625
     * Devuelve el tipo de escala que est? seleccionada AUTOMATICO,CONSTANTE o
626
     * MANUAL.
627
     * 
628
     * @return entero que representa el tipo seleccionado.
629
     */
630
    public int getTypeScale() {
631
        return typeScale;
632
    }
633

    
634
    /**
635
     * Rellenar si se quiere:Rellenar marco de la vista o recorte a la vista.
636
     * 
637
     * @param i
638
     *            entero que representa la opci?n elegida.
639
     */
640
    public void setExtension(int i) {
641
        extension = i;
642
    }
643

    
644
    /**
645
     * Rellenar el tipo de escala que se desea.
646
     * 
647
     * @param i
648
     *            entero que representa el tipo de escala.
649
     */
650
    public void setTypeScale(int i) {
651
        typeScale = i;
652
    }
653

    
654
    /**
655
     * Inserta la imagen para repintar el FFrameView.
656
     * 
657
     * @param bi
658
     *            Imagen para repintar.
659
     */
660
    public void setBufferedImage(BufferedImage bi) {
661
        m_image = bi;
662
    }
663

    
664
    /**
665
     * Devuelve la imagen para repintar.
666
     * 
667
     * @return Imagen para repintar.
668
     */
669
    public BufferedImage getBufferedImage() {
670
        return m_image;
671
    }
672

    
673
    /**
674
     * Devuelve la MAtriz de transformaci?n utilizada por la FFrameView.
675
     * 
676
     * @return MAtriz de transformaci?n.
677
     */
678
    public AffineTransform getATMap() {
679
        return at;
680
    }
681

    
682
    /**
683
     * Inserta la matriz de transformaci?n.
684
     * 
685
     * @param transform
686
     *            Matriz de transformaci?n.
687
     */
688
    public void setATMap(AffineTransform transform) {
689
        at = transform;
690
    }
691

    
692
    /**
693
     * Inserta el proyecto.
694
     * 
695
     * @param p
696
     *            Proyecto.
697
     */
698
    public void setProject(Project p) {
699
        project = p;
700
    }
701

    
702
    /**
703
     * @see org.gvsig.app.project.documents.layout.fframes.IFFrame#getNameFFrame()
704
     */
705
    public String getNameFFrame() {
706
        return PluginServices.getText(this, "Vista") + num;
707
    }
708

    
709
    public String getName() {
710
        return PERSISTENCE_DEFINITION_NAME;
711
    }
712

    
713
    /**
714
     * @see com.iver.cit.gvsig.fmap.ExtentListener#extentChanged(org.gvsig.fmap.mapcontext.events.ExtentEvent)
715
     */
716
    public void extentChanged(ExtentEvent e) {
717
        if (linked){
718
            if (getTypeScale() == AUTOMATICO) {
719
                mapContext.getViewPort().setEnvelope(e.getNewExtent());
720
                observers.notifyObservers(this, 
721
                    new DefaultLayoutNotification(LayoutNotification.LAYOUT_INVALIDATED));      
722
            } else
723
                if (getTypeScale() == MANUAL) {
724
                    Envelope oldExtent = mapContext.getViewPort().getEnvelope();
725
                    Envelope newExtent = e.getNewExtent();
726
                    double xDif = newExtent.getCenter(0) - oldExtent.getCenter(0);
727
                    double yDif = newExtent.getCenter(1) - oldExtent.getCenter(1);
728
                    try {
729
                        mapContext.getViewPort().setEnvelope(
730
                            geomManager.createEnvelope(oldExtent.getMinimum(0)
731
                                + xDif, oldExtent.getMinimum(1) + yDif,
732
                                oldExtent.getMaximum(0) + xDif,
733
                                oldExtent.getMaximum(1) + yDif, SUBTYPES.GEOM2D));
734
                    } catch (CreateEnvelopeException e1) {
735
                        e1.printStackTrace();
736
                    }
737
                   
738
                    observers.notifyObservers(this, 
739
                        new DefaultLayoutNotification(LayoutNotification.LAYOUT_INVALIDATED));           
740
                  
741
                }
742
            refresh = true;
743
        }
744
    }
745

    
746
    /**
747
     * @see org.gvsig.fmap.mapcontext.events.listeners.ViewPortListener#backColorChanged(org.gvsig.fmap.mapcontext.events.ColorEvent)
748
     */
749
    public void backColorChanged(ColorEvent e) {
750
        if (getLinked()) {
751
            mapContext.getViewPort().setBackColor(e.getNewColor());
752
            observers.notifyObservers(this, 
753
                new DefaultLayoutNotification(LayoutNotification.LAYOUT_INVALIDATED));          
754
        }
755
    }
756

    
757
    /**
758
     * @see org.gvsig.fmap.mapcontext.events.listeners.ViewPortListener#projectionChanged(org.gvsig.fmap.mapcontext.events.ProjectionEvent)
759
     */
760
    public void projectionChanged(ProjectionEvent e) {
761
        if (getTypeScale() == AUTOMATICO) {
762
            mapContext.getViewPort().setProjection(e.getNewProjection());
763
            observers.notifyObservers(this, 
764
                new DefaultLayoutNotification(LayoutNotification.LAYOUT_INVALIDATED));      
765
        }
766
    }
767

    
768
    /**
769
     * DOCUMENT ME!
770
     * 
771
     * @param e
772
     *            DOCUMENT ME!
773
     */
774
    public void legendChanged(final LegendChangedEvent e) {
775
        if (!SwingUtilities.isEventDispatchThread()) {
776
            SwingUtilities.invokeLater(new Runnable() {
777

    
778
                public void run() {
779
                    legendChanged(e);
780
                }
781
            });
782
            return;
783
        }
784
        if (getLinked()) {
785
            observers.notifyObservers(this, 
786
                new DefaultLayoutNotification(LayoutNotification.LAYOUT_INVALIDATED));      
787
            refresh = true;
788
        }
789
    }
790

    
791
    /**
792
     * DOCUMENT ME!
793
     * 
794
     * @param arg0
795
     *            DOCUMENT ME!
796
     * 
797
     * @return DOCUMENT ME!
798
     */
799
    public boolean compare(Object arg0) {
800
        if (!(arg0 instanceof FFrameView)) {
801
            return false;
802
        }
803

    
804
        if (!this.getName().equals(((FFrameView) arg0).getName())) {
805
            return false;
806
        }
807

    
808
        if (Math.abs(this.getBoundBox().getWidth()
809
            - (((FFrameView) arg0).getBoundBox().getWidth())) > 0.05) {
810
            return false;
811
        }
812
        if (Math.abs(this.getBoundBox().getHeight()
813
            - (((FFrameView) arg0).getBoundBox().getHeight())) > 0.05) {
814
            return false;
815
        }
816

    
817
        if (!this.toString().equals(((FFrameView) arg0).toString())) {
818
            return false;
819
        }
820

    
821
        if (this.getMapContext() != null
822
            && !this.getMapContext()
823
                .equals(((FFrameView) arg0).getMapContext())) {
824
            return false;
825
        }
826

    
827
        if (this.getRotation() != ((FFrameView) arg0).getRotation()) {
828
            return false;
829
        }
830
        return true;
831
    }
832

    
833
    /**
834
     * DOCUMENT ME!
835
     * 
836
     * @param arg0
837
     *            DOCUMENT ME!
838
     * 
839
     * @return DOCUMENT ME!
840
     */
841
    public boolean equals(Object arg0) {
842
        return this.compare(arg0);
843
    }
844

    
845
    public void refresh() {
846
        if (viewDocument != null
847
            && (getTypeScale() == MANUAL || getTypeScale() == CONSTANTE)) {
848
            getMapContext().getViewPort().setEnvelope(
849
                getNewEnvelope(getScale()));
850
        }
851
        refresh = true;
852
    }
853

    
854
    public void fullExtent() throws ReadException {
855
        setNewEnvelope(getMapContext().getFullEnvelope());
856
    }
857

    
858
    public void setPointsToZoom(Point2D px1, Point2D px2) {
859
        p1 = px1;
860
        p2 = px2;
861
    }
862

    
863
    public void movePoints(Point2D px1, Point2D px2) {
864
        double difX = -px2.getX() + px1.getX();
865
        double difY = -px2.getY() + px1.getY();
866
        if (p1 != null) {
867
            p1.setLocation(p1.getX() + difX, p1.getY() + difY);
868
            p2.setLocation(p2.getX() + difX, p2.getY() + difY);
869
        }
870
    }
871

    
872
    protected void cloneActions(IFFrame frame) {
873
        if (viewDocument == null || viewDocument.getMapContext() == null) {
874
            return;
875
        }
876
        if (linked) {
877
            if (getTypeScale() == AUTOMATICO) {
878
                viewDocument.getMapContext().getViewPort().addViewPortListener(this);
879
                viewDocument.getMapContext().addLayerListener(this);
880
            } else
881
                if (getTypeScale() == CONSTANTE) {
882
                    viewDocument.getMapContext().getViewPort()
883
                        .removeViewPortListener(this);
884
                    viewDocument.getMapContext().addLayerListener(this);
885
                } else
886
                    if (getTypeScale() == MANUAL) {
887
                        viewDocument.getMapContext().getViewPort()
888
                            .removeViewPortListener(this);
889
                        viewDocument.getMapContext().addLayerListener(this);
890
                    }
891
        } else
892
            if (!linked) {
893
                if (getTypeScale() == AUTOMATICO) {
894
                    viewDocument.getMapContext().getViewPort()
895
                        .addViewPortListener(this);
896
                } else
897
                    if (getTypeScale() == CONSTANTE) {
898
                        viewDocument.getMapContext().getViewPort()
899
                            .removeViewPortListener(this);
900
                    } else
901
                        if (getTypeScale() == MANUAL) {
902
                            viewDocument.getMapContext().getViewPort()
903
                                .removeViewPortListener(this);
904
                        }
905
            }
906
        ((FFrameView) frame).viewDocument.getMapContext().removeLayerListener(
907
            (FFrameView) frame);
908
        ((FFrameView) frame).viewDocument.getMapContext().getViewPort()
909
            .removeViewPortListener((FFrameView) frame);
910
    }
911

    
912
    public Object clone() throws CloneNotSupportedException {
913
        FFrameView frame = (FFrameView) super.clone();
914

    
915
        frame.setSelected(this.getSelected() != IFFrame.NOSELECT);
916

    
917
        if (grid != null) {
918
            FFrameGrid newGrid = (FFrameGrid) this.grid.clone();
919
            newGrid.setFFrameDependence(frame);
920
            frame.setGrid(newGrid);
921
        }
922
        cloneActions(frame);
923
        return frame;
924
    }
925

    
926
    public void setGrid(IFFrame grid) {
927
        this.grid = grid;
928
        this.grid.setRotation(this.getRotation());
929
    }
930

    
931
    public IFFrame getGrid() {
932
        return this.grid;
933
    }
934

    
935
    public void setRotation(double rotation) {
936
        super.setRotation(rotation);
937
        if (grid != null) {
938
            grid.setRotation(rotation);
939
        }
940
    }
941

    
942
    public void showGrid(boolean b) {
943
        showGrid = b;
944
    }
945

    
946
    public boolean isShowGrid() {
947
        return showGrid;
948
    }
949

    
950
    public void refreshOriginalExtent() {
951
        if (getTypeScale() == AUTOMATICO) {
952
            viewDocument.getMapContext().getViewPort()
953
                .setEnvelope(getMapContext().getViewPort().getEnvelope());
954
            viewDocument.getMapContext().getViewPort().refreshExtent();
955
        } else
956
            if (getTypeScale() == MANUAL) {
957
                Envelope oldExtent =
958
                    viewDocument.getMapContext().getViewPort().getEnvelope();
959
                Envelope newExtent =
960
                    getMapContext().getViewPort().getEnvelope();
961
                double xDif = newExtent.getCenter(0) - oldExtent.getCenter(0);
962
                double yDif = newExtent.getCenter(1) - oldExtent.getCenter(1);
963
                try {
964
                    viewDocument.getMapContext()
965
                        .getViewPort()
966
                        .setEnvelope(
967
                            geomManager.createEnvelope(oldExtent.getMinimum(0)
968
                                + xDif, oldExtent.getMinimum(1) + yDif,
969
                                oldExtent.getMaximum(0) + xDif,
970
                                oldExtent.getMaximum(1) + yDif, SUBTYPES.GEOM2D));
971
                } catch (CreateEnvelopeException e) {
972
                    e.printStackTrace();
973
                }
974
                viewDocument.getMapContext().getViewPort().refreshExtent();
975
            }
976
    }
977

    
978
    public static void registerPersistent() {
979
        PersistenceManager manager = ToolsLocator.getPersistenceManager();
980
        if (manager.getDefinition(PERSISTENCE_DEFINITION_NAME) == null) {
981
            DynStruct definition =
982
                manager.addDefinition(FFrameView.class,
983
                    PERSISTENCE_DEFINITION_NAME,
984
                    "FFrameView persistence definition", null, null);
985

    
986
            definition.extend(manager
987
                .getDefinition(FFrame.PERSISTENCE_DEFINITION_NAME));
988

    
989
            definition.addDynFieldInt(MODE_FIELD).setMandatory(true);
990
            definition.addDynFieldInt(TYPESCALE_FIELD).setMandatory(true);
991
            definition.addDynFieldInt(EXTENSION_FIELD).setMandatory(true);
992
            definition.addDynFieldInt(QUALITY_FIELD).setMandatory(true);
993
            definition.addDynFieldInt(VIEWING_FIELD).setMandatory(true);
994
            definition.addDynFieldBoolean(BLINKED_FIELD).setMandatory(true);
995
            definition.addDynFieldInt(MAPUNITS_FIELD).setMandatory(true);
996
            definition.addDynFieldDouble(SCALE_FIELD).setMandatory(true);
997
            definition.addDynFieldObject(VIEW_FIELD)
998
                .setClassOfValue(ViewDocument.class).setMandatory(false);
999
            definition.addDynFieldObject(ENVELOPE_FIELD)
1000
                .setClassOfValue(Envelope.class).setMandatory(false);
1001
            definition.addDynFieldBoolean(SHOWGRID_FIELD).setMandatory(true);
1002
            definition.addDynFieldObject(GRID_FIELD)
1003
                .setClassOfValue(IFFrame.class).setMandatory(false);
1004
            definition.addDynFieldObject(MAPCONTEXT_FIELD)
1005
                .setClassOfValue(MapContext.class).setMandatory(false);
1006
        }
1007
    }
1008

    
1009
    @Override
1010
    public void loadFromState(PersistentState state)
1011
        throws PersistenceException {
1012
        super.loadFromState(state);
1013
        mode = state.getInt(MODE_FIELD);
1014
        typeScale = state.getInt(TYPESCALE_FIELD);
1015
        extension = state.getInt(EXTENSION_FIELD);
1016
        quality = state.getInt(QUALITY_FIELD);
1017
        viewing = state.getInt(VIEWING_FIELD);
1018
        linked = state.getBoolean(BLINKED_FIELD);
1019
        mapUnits = state.getInt(MAPUNITS_FIELD);
1020
        mapScale = state.getDouble(SCALE_FIELD);
1021
        viewDocument = (ViewDocument) state.get(VIEW_FIELD);
1022

    
1023
        if (state.hasValue(MAPCONTEXT_FIELD)) {
1024
            mapContext = (MapContext) state.get(MAPCONTEXT_FIELD);
1025
            mapContext.getViewPort().setEnvelope(
1026
                (Envelope) state.get(ENVELOPE_FIELD));
1027
        }
1028

    
1029
        showGrid = state.getBoolean(SHOWGRID_FIELD);
1030
        grid = (IFFrame) state.get(GRID_FIELD);
1031
    }
1032

    
1033
    @Override
1034
    public void saveToState(PersistentState state) throws PersistenceException {
1035
        super.saveToState(state);
1036
        state.set(MODE_FIELD, mode);
1037
        state.set(TYPESCALE_FIELD, typeScale);
1038
        state.set(EXTENSION_FIELD, extension);
1039
        state.set(QUALITY_FIELD, quality);
1040
        state.set(VIEWING_FIELD, viewing);
1041
        state.set(BLINKED_FIELD, linked);
1042
        state.set(MAPUNITS_FIELD, mapUnits);
1043
        state.set(SCALE_FIELD, mapScale);
1044
        state.set(VIEW_FIELD, viewDocument);
1045

    
1046
        if (getMapContext() != null
1047
            && getMapContext().getViewPort().getEnvelope() != null) {
1048
            state.set(ENVELOPE_FIELD, getMapContext().getViewPort()
1049
                .getEnvelope());
1050
            state.set(MAPCONTEXT_FIELD, mapContext);
1051
        }
1052

    
1053
        state.set(SHOWGRID_FIELD, showGrid);
1054
        state.set(GRID_FIELD, grid);
1055
    }
1056
    
1057
    @Override
1058
    public void setBoundBox(Rectangle2D r) {      
1059
        super.setBoundBox(r);
1060
        refresh();
1061
    }   
1062
}