Statistics
| Revision:

svn-gvsig-desktop / branches / v2_0_0_prep / applications / appgvSIG / src / org / gvsig / app / project / documents / layout / FLayoutZooms.java @ 33420

History | View | Annotate | Download (14.8 KB)

1
/*
2
 * Created on 17-sep-2004
3
 *
4
 */
5
/* gvSIG. Sistema de Informaci?n Geogr?fica de la Generalitat Valenciana
6
 *
7
 * Copyright (C) 2004 IVER T.I. and Generalitat Valenciana.
8
 *
9
 * This program is free software; you can redistribute it and/or
10
 * modify it under the terms of the GNU General Public License
11
 * as published by the Free Software Foundation; either version 2
12
 * of the License, or (at your option) any later version.
13
 *
14
 * This program is distributed in the hope that it will be useful,
15
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
 * GNU General Public License for more details.
18
 *
19
 * You should have received a copy of the GNU General Public License
20
 * along with this program; if not, write to the Free Software
21
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307,USA.
22
 *
23
 * For more information, contact:
24
 *
25
 *  Generalitat Valenciana
26
 *   Conselleria d'Infraestructures i Transport
27
 *   Av. Blasco Ib??ez, 50
28
 *   46010 VALENCIA
29
 *   SPAIN
30
 *
31
 *      +34 963862235
32
 *   gvsig@gva.es
33
 *      www.gvsig.gva.es
34
 *
35
 *    or
36
 *
37
 *   IVER T.I. S.A
38
 *   Salamanca 50
39
 *   46005 Valencia
40
 *   Spain
41
 *
42
 *   +34 963163400
43
 *   dac@iver.es
44
 */
45
package org.gvsig.app.project.documents.layout;
46

    
47
import java.awt.Point;
48
import java.awt.Toolkit;
49
import java.awt.geom.AffineTransform;
50
import java.awt.geom.Point2D;
51
import java.awt.geom.Rectangle2D;
52
import java.util.prefs.Preferences;
53

    
54
import org.slf4j.Logger;
55
import org.slf4j.LoggerFactory;
56

    
57
import org.gvsig.app.project.documents.layout.fframes.IFFrame;
58
import org.gvsig.app.project.documents.layout.fframes.IFFrameUseFMap;
59
import org.gvsig.app.project.documents.layout.gui.LayoutPanel;
60
import org.gvsig.fmap.geom.GeometryLocator;
61
import org.gvsig.fmap.geom.GeometryManager;
62
import org.gvsig.fmap.geom.Geometry.SUBTYPES;
63
import org.gvsig.fmap.geom.exception.CreateEnvelopeException;
64
import org.gvsig.fmap.mapcontext.MapContext;
65

    
66

    
67

    
68
/**
69
 * Clase encargada de realizar los zooms al Layout.
70
 *
71
 * @author Vicente Caballero Navarro
72
 */
73
public class FLayoutZooms {
74
        private static final GeometryManager geomManager = GeometryLocator.getGeometryManager();
75
        private static final Logger logger = LoggerFactory.getLogger(FLayoutZooms.class);
76
        private LayoutPanel layout = null;
77

    
78
        public FLayoutZooms(LayoutPanel l) {
79
                layout = l;
80
        }
81

    
82
        /**
83
         * Realiza un zoom por rect?ngulo o por punto con un escalado por defecto
84
         * sobre el Layout que se le pasa como par?metro.
85
         *
86
         * @param p1 punto de inicio del rect?ngulo.
87
         * @param p2 punto final del rec?ngulo.
88
         */
89
        public void setZoomIn(Point p1, Point p2) {
90
                if (java.lang.Math.abs(layout.getLayoutControl().getFirstPoint().x - p2.x) < 4) {
91
                        double difw = 2;
92
                        setZoom(difw, p2);
93
                } else {
94
                        if (p1.getX() > p2.getX()) {
95
                                int aux = p2.x;
96
                                p2.x = p1.x;
97
                                p1.x = aux;
98
                        }
99

    
100
                        if (p1.getY() > p2.getY()) {
101
                                int aux = p2.y;
102
                                p2.y = p1.y;
103
                                p1.y = aux;
104
                        }
105

    
106
                        Point2D.Double pSheet1 = FLayoutUtilities.toSheetPoint(
107
                                        new Point2D.Double(p1.getX(), p1.getY()), layout.getLayoutControl().getAT());
108
                        Point2D.Double pSheet2 = FLayoutUtilities.toSheetPoint(
109
                                        new Point2D.Double(p2.getX(), p2.getY()), layout.getLayoutControl().getAT());
110

    
111
                        double xmin;
112
                        double xmax;
113
                        double ymin;
114
                        double ymax = 0;
115

    
116
                        if (pSheet1.x > pSheet2.x) {
117
                                xmin = pSheet2.x;
118
                                xmax = pSheet1.x;
119
                        } else {
120
                                xmin = pSheet1.x;
121
                                xmax = pSheet2.x;
122
                        }
123

    
124
                        if (pSheet1.y > pSheet2.y) {
125
                                ymin = pSheet2.y;
126
                                ymax = pSheet1.y;
127
                        } else {
128
                                ymin = pSheet1.y;
129
                                ymax = pSheet2.y;
130
                        }
131

    
132
                        Rectangle2D.Double rScreen = new Rectangle2D.Double();
133
                        Rectangle2D.Double rSheet = new Rectangle2D.Double();
134
                        double x = FLayoutUtilities.toSheetDistance(
135
                                        layout.getLayoutControl().getRect().getX(), layout.getLayoutControl().getAT());
136
                        double y = FLayoutUtilities.toSheetDistance(
137
                                        layout.getLayoutControl().getRect().getY(), layout.getLayoutControl().getAT());
138
                        double w = FLayoutUtilities.toSheetDistance(layout.getLayoutControl().getRect()
139
                                        .getWidth(), layout.getLayoutControl().getAT());
140
                        double h = FLayoutUtilities.toSheetDistance(layout.getLayoutControl().getRect()
141
                                        .getHeight(), layout.getLayoutControl().getAT());
142

    
143
                        double wv = FLayoutUtilities.toSheetDistance(layout
144
                                        .getVisibleRect().getWidth(), layout.getLayoutControl().getAT());
145
                        double hv = FLayoutUtilities.toSheetDistance(layout
146
                                        .getVisibleRect().getHeight(), layout.getLayoutControl().getAT());
147
                        double mw = xmax - xmin;
148
                        double mh = ymax - ymin;
149
                        double difw = wv / mw;
150
                        double difh = hv / mh;
151

    
152
                        if (difw < difh) {
153
                                rSheet.x = (-xmin * difw)
154
                                - x
155
                                + ((wv - ((pSheet2.getX() - pSheet1.getX()) * difw)) / 2);
156
                                rSheet.y = (-ymin * difw)
157
                                - y
158
                                + ((hv - ((pSheet2.getY() - pSheet1.getY()) * difw)) / 2);
159

    
160
                                rSheet.width = w * difw;
161
                                rSheet.height = h * difw;
162
                        } else {
163
                                rSheet.x = (-xmin * difh)
164
                                - x
165
                                + ((wv - ((pSheet2.getX() - pSheet1.getX()) * difh)) / 2);
166
                                rSheet.y = (-ymin * difh)
167
                                - y
168
                                + ((hv - ((pSheet2.getY() - pSheet1.getY()) * difh)) / 2);
169

    
170
                                rSheet.width = w * difh;
171
                                rSheet.height = h * difh;
172
                        }
173
                        setPointsToZoom(p1, p2);
174
                        rScreen.setRect(FLayoutUtilities.fromSheetRect(rSheet, layout.getLayoutControl()
175
                                        .getAT()));
176
                        if (FLayoutUtilities.isPosible(rScreen)) {
177
                                layout.getLayoutControl().getRect().setRect(rScreen);
178
                        }
179
                }
180
        }
181

    
182
        /**
183
         * Realiza un zoom out sobre el Layout que se le pasa como par?metro.
184
         *
185
         * @param p2 punto central del rect?ngulo.
186
         */
187
        public void setZoomOut(Point p2) {
188
                double difw = 0.5;
189
                setZoom(difw,p2);
190
        }
191

    
192
        /**
193
         * Realiza un zoom out sobre el Layout que se le pasa como par?metro.
194
         *
195
         * @param dif factor.
196
         * @param p2 punto final del rec?ngulo.
197
         */
198
        public void setZoom(double dif, Point p2) {
199
                Point2D.Double pSheet2 = FLayoutUtilities.toSheetPoint(new Point2D.Double(
200
                                p2.getX(), p2.getY()), layout.getLayoutControl().getAT());
201
                Rectangle2D.Double rScreen = new Rectangle2D.Double();
202
                Rectangle2D.Double rSheet = new Rectangle2D.Double();
203

    
204
                double difw = dif;
205

    
206
                rSheet.x = (-pSheet2.getX() * difw) -
207
                FLayoutUtilities.toSheetDistance(layout.getLayoutControl().getRect().getX(),
208
                                layout.getLayoutControl().getAT()) +
209
                                FLayoutUtilities.toSheetDistance(layout.getWidth() / 2,
210
                                                layout.getLayoutControl().getAT());
211
                rSheet.y = (-pSheet2.getY() * difw) -
212
                FLayoutUtilities.toSheetDistance(layout.getLayoutControl().getRect().getY(),
213
                                layout.getLayoutControl().getAT()) +
214
                                FLayoutUtilities.toSheetDistance(layout.getHeight() / 2,
215
                                                layout.getLayoutControl().getAT());
216

    
217
                rSheet.width = FLayoutUtilities.toSheetDistance(layout.getLayoutControl().getRect()
218
                                .getWidth(),
219
                                layout.getLayoutControl().getAT()) * difw;
220
                rSheet.height = FLayoutUtilities.toSheetDistance(layout.getLayoutControl().getRect()
221
                                .getHeight(),
222
                                layout.getLayoutControl().getAT()) * difw;
223

    
224
                rScreen.setRect(FLayoutUtilities.fromSheetRect(rSheet, layout.getLayoutControl().getAT()));
225

    
226
                if (FLayoutUtilities.isPosible(rScreen)) {
227
                        layout.getLayoutControl().getRect().setRect(rScreen);
228
                }
229

    
230
                //                Para realizar el zoom a partir de un punto.
231
                Point p1 = new Point((int) (p2.getX() -
232
                                (layout.getWidth() / (difw * 2))),
233
                                (int) (p2.getY() - (layout.getHeight() / (difw * 2))));
234
                p2 = new Point((int) (p2.getX() + (layout.getWidth() / (difw * 2))),
235
                                (int) (p2.getY() + (layout.getHeight() / (difw * 2))));
236
                setPointsToZoom(p1, p2);
237
        }
238
        /**
239
         * Introduce los puntos de control para controlar el zoom del Layout.
240
         */
241
        private void setPointsToZoom(Point p1, Point p2) {
242
                IFFrame[] fframes = layout.getLayoutContext().getFFrames();
243

    
244
                for (int i = 0; i < fframes.length; i++) {
245
                        if (fframes[i] instanceof IFFrameUseFMap) {
246
                                IFFrameUseFMap fframe = (IFFrameUseFMap) fframes[i];
247
                                if (fframe.getATMap()!=null) {
248
                                        Point2D px1 = FLayoutFunctions.toMapPoint(p1, fframe.getATMap());
249
                                        Point2D px2 = FLayoutFunctions.toMapPoint(p2, fframe.getATMap());
250
                                        fframe.setPointsToZoom(px1, px2);
251
                                }
252
                        }
253
                }
254
        }
255

    
256
        /**
257
         * Aplica el zoom real teniendo en cuenta la resoluci?n de pantalla.
258
         */
259
        public void realZoom() {
260
                Preferences prefsResolution = Preferences.userRoot().node( "gvsig.configuration.screen" );
261
                double cm = layout.getLayoutContext().getAttributes().getPixXCm(layout.getLayoutControl().getRect());
262
                Toolkit kit = Toolkit.getDefaultToolkit();
263
                double dpi = prefsResolution.getInt("dpi",kit.getScreenResolution());
264
                double dif = (cm * Attributes.PULGADA) / dpi;
265
                setZoom(1 / dif,
266
                                new Point(layout.getWidth() / 2, layout.getHeight() / 2));
267
                layout.getLayoutControl().refresh();
268
        }
269

    
270
        /**
271
         * Realiza un zoom in a partir del zoom actual de la vista.
272
         */
273
        public void zoomIn() {
274
                setZoom(2, new Point(layout.getWidth() / 2, layout.getHeight() / 2));
275
                layout.getLayoutControl().refresh();
276
        }
277

    
278
        /**
279
         * Realiza un zoom out a partir del zoom actual de la vista.
280
         */
281
        public void zoomOut() {
282
                setZoom(0.5, new Point(layout.getWidth() / 2, layout.getHeight() / 2));
283
                layout.getLayoutControl().refresh();
284
        }
285

    
286
        /**
287
         * Realiza un zoom a los elementos que esten seleccionados, si no hay
288
         * ning?n elemento seleccionado no realiza ning?n zoom
289
         */
290
        public void zoomSelect() {
291
                Rectangle2D.Double recaux = null;
292
                IFFrame[] fframes=layout.getLayoutContext().getFFrames();
293
                for (int i = 0; i < fframes.length; i++) {
294
                        if (fframes[i].getSelected() != IFFrame.NOSELECT) {
295
                                if (recaux == null) {
296
                                        recaux = fframes[i].getBoundingBox(layout.getLayoutControl().getAT());
297
                                } else {
298
                                        recaux.add(fframes[i].getBoundingBox(
299
                                                        layout.getLayoutControl().getAT()));
300
                                }
301
                        }
302
                }
303

    
304
                if (recaux != null) {
305
                        Point p1 = new Point((int) recaux.x, (int) recaux.y);
306
                        Point p2 = new Point((int) recaux.getMaxX(), (int) recaux.getMaxY());
307
                        setZoomIn(p1, p2);
308
                        layout.getLayoutControl().refresh();
309
                }
310
        }
311
        /**
312
         * Realiza un zoom a todos los elementos del layout.
313
         */
314
        public void zoomAllFrames() {
315
                Rectangle2D.Double recaux = null;
316
                IFFrame[] fframes=layout.getLayoutControl().getLayoutContext().getFFrames();
317
                for (int i = 0; i < fframes.length; i++) {
318
                        if (recaux == null) {
319
                                recaux = fframes[i].getBoundingBox(layout.getLayoutControl().getAT());
320
                        } else {
321
                                recaux.add(fframes[i].getBoundingBox(
322
                                                layout.getLayoutControl().getAT()));
323
                        }
324
                }
325

    
326
                if (recaux != null) {
327
                        Point p1 = new Point((int) recaux.x, (int) recaux.y);
328
                        Point p2 = new Point((int) recaux.getMaxX(), (int) recaux.getMaxY());
329
                        setZoomIn(p1, p2);
330
                        layout.getLayoutControl().refresh();
331
                }
332
        }
333

    
334
        /**
335
         * Realiza un zoom in a las vista a?adidas al Layout que esten seleccionadas
336
         *
337
         * @param p1 Punto inicial del rect?ngulo
338
         * @param p2 Punto final del rect?ngulo
339
         */
340
        public void setViewZoomIn(Point2D p1, Point2D p2) {
341
                IFFrame[] fframes=layout.getLayoutContext().getFFrames();
342
                for (int i = 0; i < fframes.length; i++) {
343
                        if (fframes[i] instanceof IFFrameUseFMap) {
344
                                IFFrameUseFMap fframe = (IFFrameUseFMap) fframes[i];
345

    
346
                                if (((IFFrame) fframe).getSelected() != IFFrame.NOSELECT) {
347
                                        //IFFrameUseFMap fframeAux=(IFFrameUseFMap)((IFFrame)fframe).cloneFFrame(layout);
348
                                        p1 = FLayoutFunctions.toMapPoint(p1, fframe.getATMap());
349
                                        p2 = FLayoutFunctions.toMapPoint(p2, fframe.getATMap());
350

    
351

    
352
                                        // Borramos el anterior
353
                                        layout.getLayoutControl().setStatus(LayoutControl.DESACTUALIZADO);
354
                                        Rectangle2D.Double r = new Rectangle2D.Double();
355

    
356
                                        if (java.lang.Math.abs(p1.getX() - p2.getX()) <= 3) {
357
                                                double nuevoX;
358
                                                double nuevoY;
359
                                                double cX;
360
                                                double cY;
361

    
362
                                                cX = p2.getX();
363
                                                cY = p2.getY();
364

    
365
                                                double factor = 1/MapContext.ZOOMINFACTOR;
366

    
367
                                                Rectangle2D extent=fframe.getMapContext().getViewPort().getExtent();
368
                                                if (extent!=null){
369
                                                        nuevoX = cX -
370
                                                        ((extent.getWidth() * factor) / 2.0);
371
                                                        nuevoY = cY -
372
                                                        ((extent.getHeight() * factor) / 2.0);
373
                                                        r.x = nuevoX;
374
                                                        r.y = nuevoY;
375
                                                        r.width = extent.getWidth() * factor;
376
                                                        r.height = extent.getHeight() * factor;
377
                                                }
378

    
379
                                                //fframeAux.setNewExtent(r);
380
                                        } else {
381
                                                //        Fijamos el nuevo extent
382

    
383
                                                r.setFrameFromDiagonal(p1, p2);
384

    
385
                                                //fframeAux.setNewExtent(r);
386
                                        }
387

    
388
                                        /*if (fframe.getTypeScale()!=IFFrameUseFMap.AUTOMATICO) {
389
                            fframeAux.setNewExtent(r);
390
                            fframeAux.refresh();
391
                            layout.getEFS().modifyFFrame((IFFrame)fframe,(IFFrame)fframeAux);
392
                            ((IFFrame)fframeAux).getBoundingBox(layout.getAT());
393
                            layout.updateFFrames();
394
                            layout.setIsReSel(true);
395
                    }else {*/
396
                                        try {
397
                                                fframe.setNewEnvelope(geomManager.createEnvelope(r.getX(),r.getY(),r.getMaxX(),r.getMaxY(), SUBTYPES.GEOM2D));
398
                                        } catch (CreateEnvelopeException e) {
399
                                                logger.error("Error creating the envelope", e);
400
                                        }
401
                                        fframe.refresh();
402
                                        fframe.refreshOriginalExtent();
403
                                        ///}
404
                                        // Fin del else
405
                                        //layout.repaint();
406
                                }
407
                        }
408
                }
409
        }
410

    
411
        /**
412
         * Realiza un zoom out a las vistas a?adidas al Layout y que est?n seleccionadas
413
         *
414
         * @param p2 Punto central
415
         */
416
        public void setViewZoomOut(Point p2) {
417
                Point2D.Double pWorld;
418
                IFFrame[] fframes=layout.getLayoutContext().getFFrames();
419
                for (int i = 0; i < fframes.length; i++) {
420
                        if (fframes[i] instanceof IFFrameUseFMap) {
421
                                IFFrameUseFMap fframe = (IFFrameUseFMap) fframes[i];
422

    
423
                                if (((IFFrame) fframe).getSelected() != IFFrame.NOSELECT) {
424
                                        //IFFrameUseFMap fframeAux=(IFFrameUseFMap)((IFFrame)fframe).cloneFFrame(layout);
425
                                        double nuevoX;
426
                                        double nuevoY;
427
                                        double cX;
428
                                        double cY;
429
                                        Point pScreen = new Point((int) p2.getX(), (int) p2.getY());
430
                                        pWorld = FLayoutFunctions.toMapPoint(pScreen,
431
                                                        fframe.getATMap());
432

    
433
                                        cX = pWorld.getX();
434
                                        cY = pWorld.getY();
435

    
436
                                        double factor = 1/MapContext.ZOOMOUTFACTOR;
437
                                        Rectangle2D extent = fframe.getMapContext()
438
                                        .getViewPort().getExtent();
439
                                        if (extent != null) {
440
                                                nuevoX = cX - ((extent.getWidth() * factor) / 2.0);
441
                                                nuevoY = cY - ((extent.getHeight() * factor) / 2.0);
442
                                                double x = nuevoX;
443
                                                double y = nuevoY;
444
                                                double width = extent.getWidth() * factor;
445
                                                double height = extent.getHeight() * factor;
446
                                                try {
447
                                                        fframe.setNewEnvelope(geomManager.createEnvelope(x,y,x+width,y+height, SUBTYPES.GEOM2D));
448
                                                } catch (CreateEnvelopeException e) {
449
                                                        logger.error("Error creating the envelope", e);
450
                                                }
451
                                                fframe.refresh();
452
                                                fframe.refreshOriginalExtent();
453
                                        }
454
                                }
455
                        }
456
                }
457
        }
458

    
459
        /**
460
         * Modifica los puntos de control para generar el zoom del Layout
461
         *
462
         * @param p1 Punto inicial
463
         * @param p2 Punto final
464
         */
465
        public void setPan(Point p1, Point p2) {
466
                IFFrame[] fframes = layout.getLayoutContext().getFFrames();
467

    
468
                for (int i = 0; i < fframes.length; i++) {
469
                        if (fframes[i] instanceof IFFrameUseFMap) {
470
                                IFFrameUseFMap fframe = (IFFrameUseFMap) fframes[i];
471
                                AffineTransform at=fframe.getATMap();
472
                                if (at!=null) {
473
                                        Point2D px1 = FLayoutFunctions.toMapPoint(p1, at);
474
                                        Point2D px2 = FLayoutFunctions.toMapPoint(p2, at);
475
                                        fframe.movePoints(px1, px2);
476
                                }
477
                        }
478
                }
479
        }
480
}