Source Code Cross Referenced for ContourPlot.java in  » Chart » jfreechart » org » jfree » chart » plot » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Chart » jfreechart » org.jfree.chart.plot 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /* ===========================================================
0002:         * JFreeChart : a free chart library for the Java(tm) platform
0003:         * ===========================================================
0004:         *
0005:         * (C) Copyright 2000-2007, by Object Refinery Limited and Contributors.
0006:         *
0007:         * Project Info:  http://www.jfree.org/jfreechart/index.html
0008:         *
0009:         * This library is free software; you can redistribute it and/or modify it 
0010:         * under the terms of the GNU Lesser General Public License as published by 
0011:         * the Free Software Foundation; either version 2.1 of the License, or 
0012:         * (at your option) any later version.
0013:         *
0014:         * This library is distributed in the hope that it will be useful, but 
0015:         * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 
0016:         * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public 
0017:         * License for more details.
0018:         *
0019:         * You should have received a copy of the GNU Lesser General Public
0020:         * License along with this library; if not, write to the Free Software
0021:         * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, 
0022:         * USA.  
0023:         *
0024:         * [Java is a trademark or registered trademark of Sun Microsystems, Inc. 
0025:         * in the United States and other countries.]
0026:         *
0027:         * ----------------
0028:         * ContourPlot.java
0029:         * ----------------
0030:         * (C) Copyright 2002-2007, by David M. O'Donnell and Contributors.
0031:         *
0032:         * Original Author:  David M. O'Donnell;
0033:         * Contributor(s):   David Gilbert (for Object Refinery Limited);
0034:         *                   Arnaud Lelievre;
0035:         *                   Nicolas Brodu;
0036:         *
0037:         * $Id: ContourPlot.java,v 1.16.2.5 2007/01/31 15:56:18 mungady Exp $
0038:         *
0039:         * Changes
0040:         * -------
0041:         * 26-Nov-2002 : Version 1 contributed by David M. O'Donnell (DG);
0042:         * 14-Jan-2003 : Added crosshair attributes (DG);
0043:         * 23-Jan-2003 : Removed two constructors (DG);
0044:         * 21-Mar-2003 : Bug fix 701744 (DG);
0045:         * 26-Mar-2003 : Implemented Serializable (DG);
0046:         * 09-Jul-2003 : Changed ColorBar from extending axis classes to enclosing 
0047:         *               them (DG);
0048:         * 05-Aug-2003 : Applied changes in bug report 780298 (DG);
0049:         * 08-Sep-2003 : Added internationalization via use of properties 
0050:         *               resourceBundle (RFE 690236) (AL);
0051:         * 11-Sep-2003 : Cloning support (NB); 
0052:         * 16-Sep-2003 : Changed ChartRenderingInfo --> PlotRenderingInfo (DG);
0053:         * 17-Jan-2004 : Removed references to DefaultContourDataset class, replaced 
0054:         *               with ContourDataset interface (with changes to the interface). 
0055:         *               See bug 741048 (DG);
0056:         * 21-Jan-2004 : Update for renamed method in ValueAxis (DG);
0057:         * 25-Feb-2004 : Replaced CrosshairInfo with CrosshairState (DG);
0058:         * 06-Oct-2004 : Updated for changes in DatasetUtilities class (DG);
0059:         * 11-Nov-2004 : Renamed zoom methods to match ValueAxisPlot interface (DG);
0060:         * 25-Nov-2004 : Small update to clone() implementation (DG);
0061:         * 11-Jan-2005 : Removed deprecated code in preparation for 1.0.0 release (DG);
0062:         * 05-May-2005 : Updated draw() method parameters (DG);
0063:         * 16-Jun-2005 : Added default constructor (DG);
0064:         * 01-Sep-2005 : Moved dataAreaRatio from Plot to here (DG);
0065:         * ------------- JFREECHART 1.0.x ---------------------------------------------
0066:         * 31-Jan-2007 : Deprecated (DG);
0067:         * 
0068:         */
0069:
0070:        package org.jfree.chart.plot;
0071:
0072:        import java.awt.AlphaComposite;
0073:        import java.awt.Composite;
0074:        import java.awt.Graphics2D;
0075:        import java.awt.Paint;
0076:        import java.awt.RenderingHints;
0077:        import java.awt.Shape;
0078:        import java.awt.Stroke;
0079:        import java.awt.geom.Ellipse2D;
0080:        import java.awt.geom.GeneralPath;
0081:        import java.awt.geom.Line2D;
0082:        import java.awt.geom.Point2D;
0083:        import java.awt.geom.Rectangle2D;
0084:        import java.awt.geom.RectangularShape;
0085:        import java.beans.PropertyChangeEvent;
0086:        import java.beans.PropertyChangeListener;
0087:        import java.io.Serializable;
0088:        import java.util.Iterator;
0089:        import java.util.List;
0090:        import java.util.ResourceBundle;
0091:
0092:        import org.jfree.chart.ClipPath;
0093:        import org.jfree.chart.annotations.XYAnnotation;
0094:        import org.jfree.chart.axis.AxisSpace;
0095:        import org.jfree.chart.axis.ColorBar;
0096:        import org.jfree.chart.axis.NumberAxis;
0097:        import org.jfree.chart.axis.ValueAxis;
0098:        import org.jfree.chart.entity.ContourEntity;
0099:        import org.jfree.chart.entity.EntityCollection;
0100:        import org.jfree.chart.event.AxisChangeEvent;
0101:        import org.jfree.chart.event.PlotChangeEvent;
0102:        import org.jfree.chart.labels.ContourToolTipGenerator;
0103:        import org.jfree.chart.labels.StandardContourToolTipGenerator;
0104:        import org.jfree.chart.renderer.xy.XYBlockRenderer;
0105:        import org.jfree.chart.urls.XYURLGenerator;
0106:        import org.jfree.data.Range;
0107:        import org.jfree.data.contour.ContourDataset;
0108:        import org.jfree.data.general.DatasetChangeEvent;
0109:        import org.jfree.data.general.DatasetUtilities;
0110:        import org.jfree.ui.RectangleEdge;
0111:        import org.jfree.ui.RectangleInsets;
0112:        import org.jfree.util.ObjectUtilities;
0113:
0114:        /**
0115:         * A class for creating shaded contours.
0116:         * 
0117:         * @deprecated This plot is no longer supported, please use {@link XYPlot} with
0118:         *     an {@link XYBlockRenderer}.
0119:         */
0120:        public class ContourPlot extends Plot implements  ContourValuePlot,
0121:                ValueAxisPlot, PropertyChangeListener, Serializable, Cloneable {
0122:
0123:            /** For serialization. */
0124:            private static final long serialVersionUID = 7861072556590502247L;
0125:
0126:            /** The default insets. */
0127:            protected static final RectangleInsets DEFAULT_INSETS = new RectangleInsets(
0128:                    2.0, 2.0, 100.0, 10.0);
0129:
0130:            /** The domain axis (used for the x-values). */
0131:            private ValueAxis domainAxis;
0132:
0133:            /** The range axis (used for the y-values). */
0134:            private ValueAxis rangeAxis;
0135:
0136:            /** The dataset. */
0137:            private ContourDataset dataset;
0138:
0139:            /** The colorbar axis (used for the z-values). */
0140:            private ColorBar colorBar = null;
0141:
0142:            /** The color bar location. */
0143:            private RectangleEdge colorBarLocation;
0144:
0145:            /** A flag that controls whether or not a domain crosshair is drawn..*/
0146:            private boolean domainCrosshairVisible;
0147:
0148:            /** The domain crosshair value. */
0149:            private double domainCrosshairValue;
0150:
0151:            /** The pen/brush used to draw the crosshair (if any). */
0152:            private transient Stroke domainCrosshairStroke;
0153:
0154:            /** The color used to draw the crosshair (if any). */
0155:            private transient Paint domainCrosshairPaint;
0156:
0157:            /** 
0158:             * A flag that controls whether or not the crosshair locks onto actual data
0159:             * points. 
0160:             */
0161:            private boolean domainCrosshairLockedOnData = true;
0162:
0163:            /** A flag that controls whether or not a range crosshair is drawn..*/
0164:            private boolean rangeCrosshairVisible;
0165:
0166:            /** The range crosshair value. */
0167:            private double rangeCrosshairValue;
0168:
0169:            /** The pen/brush used to draw the crosshair (if any). */
0170:            private transient Stroke rangeCrosshairStroke;
0171:
0172:            /** The color used to draw the crosshair (if any). */
0173:            private transient Paint rangeCrosshairPaint;
0174:
0175:            /** 
0176:             * A flag that controls whether or not the crosshair locks onto actual data
0177:             * points. 
0178:             */
0179:            private boolean rangeCrosshairLockedOnData = true;
0180:
0181:            /** 
0182:             * Defines dataArea rectangle as the ratio formed from dividing height by 
0183:             * width (of the dataArea).  Modifies plot area calculations.
0184:             * ratio>0 will attempt to layout the plot so that the
0185:             * dataArea.height/dataArea.width = ratio.
0186:             * ratio<0 will attempt to layout the plot so that the
0187:             * dataArea.height/dataArea.width in plot units (not java2D units as when 
0188:             * ratio>0) = -1.*ratio.
0189:             */
0190:            //dmo
0191:            private double dataAreaRatio = 0.0; //zero when the parameter is not set
0192:
0193:            /** A list of markers (optional) for the domain axis. */
0194:            private List domainMarkers;
0195:
0196:            /** A list of markers (optional) for the range axis. */
0197:            private List rangeMarkers;
0198:
0199:            /** A list of annotations (optional) for the plot. */
0200:            private List annotations;
0201:
0202:            /** The tool tip generator. */
0203:            private ContourToolTipGenerator toolTipGenerator;
0204:
0205:            /** The URL text generator. */
0206:            private XYURLGenerator urlGenerator;
0207:
0208:            /** 
0209:             * Controls whether data are render as filled rectangles or rendered as 
0210:             * points 
0211:             */
0212:            private boolean renderAsPoints = false;
0213:
0214:            /** 
0215:             * Size of points rendered when renderAsPoints = true.  Size is relative to
0216:             * dataArea 
0217:             */
0218:            private double ptSizePct = 0.05;
0219:
0220:            /** Contains the a ClipPath to "trim" the contours. */
0221:            private transient ClipPath clipPath = null;
0222:
0223:            /** Set to Paint to represent missing values. */
0224:            private transient Paint missingPaint = null;
0225:
0226:            /** The resourceBundle for the localization. */
0227:            protected static ResourceBundle localizationResources = ResourceBundle
0228:                    .getBundle("org.jfree.chart.plot.LocalizationBundle");
0229:
0230:            /**
0231:             * Creates a new plot with no dataset or axes.
0232:             */
0233:            public ContourPlot() {
0234:                this (null, null, null, null);
0235:            }
0236:
0237:            /**
0238:             * Constructs a contour plot with the specified axes (other attributes take
0239:             * default values).
0240:             *
0241:             * @param dataset  The dataset.
0242:             * @param domainAxis  The domain axis.
0243:             * @param rangeAxis  The range axis.
0244:             * @param colorBar  The z-axis axis.
0245:             */
0246:            public ContourPlot(ContourDataset dataset, ValueAxis domainAxis,
0247:                    ValueAxis rangeAxis, ColorBar colorBar) {
0248:
0249:                super ();
0250:
0251:                this .dataset = dataset;
0252:                if (dataset != null) {
0253:                    dataset.addChangeListener(this );
0254:                }
0255:
0256:                this .domainAxis = domainAxis;
0257:                if (domainAxis != null) {
0258:                    domainAxis.setPlot(this );
0259:                    domainAxis.addChangeListener(this );
0260:                }
0261:
0262:                this .rangeAxis = rangeAxis;
0263:                if (rangeAxis != null) {
0264:                    rangeAxis.setPlot(this );
0265:                    rangeAxis.addChangeListener(this );
0266:                }
0267:
0268:                this .colorBar = colorBar;
0269:                if (colorBar != null) {
0270:                    colorBar.getAxis().setPlot(this );
0271:                    colorBar.getAxis().addChangeListener(this );
0272:                    colorBar.configure(this );
0273:                }
0274:                this .colorBarLocation = RectangleEdge.LEFT;
0275:
0276:                this .toolTipGenerator = new StandardContourToolTipGenerator();
0277:
0278:            }
0279:
0280:            /**
0281:             * Returns the color bar location.
0282:             * 
0283:             * @return The color bar location.
0284:             */
0285:            public RectangleEdge getColorBarLocation() {
0286:                return this .colorBarLocation;
0287:            }
0288:
0289:            /**
0290:             * Sets the color bar location and sends a {@link PlotChangeEvent} to all 
0291:             * registered listeners.
0292:             * 
0293:             * @param edge  the location.
0294:             */
0295:            public void setColorBarLocation(RectangleEdge edge) {
0296:                this .colorBarLocation = edge;
0297:                notifyListeners(new PlotChangeEvent(this ));
0298:            }
0299:
0300:            /**
0301:             * Returns the primary dataset for the plot.
0302:             * 
0303:             * @return The primary dataset (possibly <code>null</code>).
0304:             */
0305:            public ContourDataset getDataset() {
0306:                return this .dataset;
0307:            }
0308:
0309:            /**
0310:             * Sets the dataset for the plot, replacing the existing dataset if there
0311:             * is one.
0312:             * 
0313:             * @param dataset  the dataset (<code>null</code> permitted).
0314:             */
0315:            public void setDataset(ContourDataset dataset) {
0316:
0317:                // if there is an existing dataset, remove the plot from the list of 
0318:                // change listeners...
0319:                ContourDataset existing = this .dataset;
0320:                if (existing != null) {
0321:                    existing.removeChangeListener(this );
0322:                }
0323:
0324:                // set the new dataset, and register the chart as a change listener...
0325:                this .dataset = dataset;
0326:                if (dataset != null) {
0327:                    setDatasetGroup(dataset.getGroup());
0328:                    dataset.addChangeListener(this );
0329:                }
0330:
0331:                // send a dataset change event to self...
0332:                DatasetChangeEvent event = new DatasetChangeEvent(this , dataset);
0333:                datasetChanged(event);
0334:
0335:            }
0336:
0337:            /**
0338:             * Returns the domain axis for the plot.
0339:             *
0340:             * @return The domain axis.
0341:             */
0342:            public ValueAxis getDomainAxis() {
0343:
0344:                ValueAxis result = this .domainAxis;
0345:
0346:                return result;
0347:
0348:            }
0349:
0350:            /**
0351:             * Sets the domain axis for the plot (this must be compatible with the plot
0352:             * type or an exception is thrown).
0353:             *
0354:             * @param axis The new axis.
0355:             */
0356:            public void setDomainAxis(ValueAxis axis) {
0357:
0358:                if (isCompatibleDomainAxis(axis)) {
0359:
0360:                    if (axis != null) {
0361:                        axis.setPlot(this );
0362:                        axis.addChangeListener(this );
0363:                    }
0364:
0365:                    // plot is likely registered as a listener with the existing axis...
0366:                    if (this .domainAxis != null) {
0367:                        this .domainAxis.removeChangeListener(this );
0368:                    }
0369:
0370:                    this .domainAxis = axis;
0371:                    notifyListeners(new PlotChangeEvent(this ));
0372:
0373:                }
0374:
0375:            }
0376:
0377:            /**
0378:             * Returns the range axis for the plot.
0379:             *
0380:             * @return The range axis.
0381:             */
0382:            public ValueAxis getRangeAxis() {
0383:
0384:                ValueAxis result = this .rangeAxis;
0385:
0386:                return result;
0387:
0388:            }
0389:
0390:            /**
0391:             * Sets the range axis for the plot.
0392:             * <P>
0393:             * An exception is thrown if the new axis and the plot are not mutually
0394:             * compatible.
0395:             *
0396:             * @param axis The new axis (null permitted).
0397:             */
0398:            public void setRangeAxis(ValueAxis axis) {
0399:
0400:                if (axis != null) {
0401:                    axis.setPlot(this );
0402:                    axis.addChangeListener(this );
0403:                }
0404:
0405:                // plot is likely registered as a listener with the existing axis...
0406:                if (this .rangeAxis != null) {
0407:                    this .rangeAxis.removeChangeListener(this );
0408:                }
0409:
0410:                this .rangeAxis = axis;
0411:                notifyListeners(new PlotChangeEvent(this ));
0412:
0413:            }
0414:
0415:            /**
0416:             * Sets the colorbar for the plot.
0417:             *
0418:             * @param axis The new axis (null permitted).
0419:             */
0420:            public void setColorBarAxis(ColorBar axis) {
0421:
0422:                this .colorBar = axis;
0423:                notifyListeners(new PlotChangeEvent(this ));
0424:
0425:            }
0426:
0427:            /**
0428:             * Returns the data area ratio.
0429:             *
0430:             * @return The ratio.
0431:             */
0432:            public double getDataAreaRatio() {
0433:                return this .dataAreaRatio;
0434:            }
0435:
0436:            /**
0437:             * Sets the data area ratio.
0438:             *
0439:             * @param ratio  the ratio.
0440:             */
0441:            public void setDataAreaRatio(double ratio) {
0442:                this .dataAreaRatio = ratio;
0443:            }
0444:
0445:            /**
0446:             * Adds a marker for the domain axis.
0447:             * <P>
0448:             * Typically a marker will be drawn by the renderer as a line perpendicular
0449:             * to the range axis, however this is entirely up to the renderer.
0450:             *
0451:             * @param marker the marker.
0452:             */
0453:            public void addDomainMarker(Marker marker) {
0454:
0455:                if (this .domainMarkers == null) {
0456:                    this .domainMarkers = new java.util.ArrayList();
0457:                }
0458:                this .domainMarkers.add(marker);
0459:                notifyListeners(new PlotChangeEvent(this ));
0460:
0461:            }
0462:
0463:            /**
0464:             * Clears all the domain markers.
0465:             */
0466:            public void clearDomainMarkers() {
0467:                if (this .domainMarkers != null) {
0468:                    this .domainMarkers.clear();
0469:                    notifyListeners(new PlotChangeEvent(this ));
0470:                }
0471:            }
0472:
0473:            /**
0474:             * Adds a marker for the range axis.
0475:             * <P>
0476:             * Typically a marker will be drawn by the renderer as a line perpendicular
0477:             * to the range axis, however this is entirely up to the renderer.
0478:             *
0479:             * @param marker The marker.
0480:             */
0481:            public void addRangeMarker(Marker marker) {
0482:
0483:                if (this .rangeMarkers == null) {
0484:                    this .rangeMarkers = new java.util.ArrayList();
0485:                }
0486:                this .rangeMarkers.add(marker);
0487:                notifyListeners(new PlotChangeEvent(this ));
0488:
0489:            }
0490:
0491:            /**
0492:             * Clears all the range markers.
0493:             */
0494:            public void clearRangeMarkers() {
0495:                if (this .rangeMarkers != null) {
0496:                    this .rangeMarkers.clear();
0497:                    notifyListeners(new PlotChangeEvent(this ));
0498:                }
0499:            }
0500:
0501:            /**
0502:             * Adds an annotation to the plot.
0503:             *
0504:             * @param annotation  the annotation.
0505:             */
0506:            public void addAnnotation(XYAnnotation annotation) {
0507:
0508:                if (this .annotations == null) {
0509:                    this .annotations = new java.util.ArrayList();
0510:                }
0511:                this .annotations.add(annotation);
0512:                notifyListeners(new PlotChangeEvent(this ));
0513:
0514:            }
0515:
0516:            /**
0517:             * Clears all the annotations.
0518:             */
0519:            public void clearAnnotations() {
0520:                if (this .annotations != null) {
0521:                    this .annotations.clear();
0522:                    notifyListeners(new PlotChangeEvent(this ));
0523:                }
0524:            }
0525:
0526:            /**
0527:             * Checks the compatibility of a domain axis, returning true if the axis is
0528:             * compatible with the plot, and false otherwise.
0529:             *
0530:             * @param axis The proposed axis.
0531:             *
0532:             * @return <code>true</code> if the axis is compatible with the plot.
0533:             */
0534:            public boolean isCompatibleDomainAxis(ValueAxis axis) {
0535:
0536:                return true;
0537:
0538:            }
0539:
0540:            /**
0541:             * Draws the plot on a Java 2D graphics device (such as the screen or a 
0542:             * printer).
0543:             * <P>
0544:             * The optional <code>info</code> argument collects information about the 
0545:             * rendering of the plot (dimensions, tooltip information etc).  Just pass
0546:             * in <code>null</code> if you do not need this information.
0547:             *
0548:             * @param g2  the graphics device.
0549:             * @param area  the area within which the plot (including axis labels)
0550:             *              should be drawn.
0551:             * @param anchor  the anchor point (<code>null</code> permitted).
0552:             * @param parentState  the state from the parent plot, if there is one.
0553:             * @param info  collects chart drawing information (<code>null</code> 
0554:             *              permitted).
0555:             */
0556:            public void draw(Graphics2D g2, Rectangle2D area, Point2D anchor,
0557:                    PlotState parentState, PlotRenderingInfo info) {
0558:
0559:                // if the plot area is too small, just return...
0560:                boolean b1 = (area.getWidth() <= MINIMUM_WIDTH_TO_DRAW);
0561:                boolean b2 = (area.getHeight() <= MINIMUM_HEIGHT_TO_DRAW);
0562:                if (b1 || b2) {
0563:                    return;
0564:                }
0565:
0566:                // record the plot area...
0567:                if (info != null) {
0568:                    info.setPlotArea(area);
0569:                }
0570:
0571:                // adjust the drawing area for plot insets (if any)...
0572:                RectangleInsets insets = getInsets();
0573:                insets.trim(area);
0574:
0575:                AxisSpace space = new AxisSpace();
0576:
0577:                space = this .domainAxis.reserveSpace(g2, this , area,
0578:                        RectangleEdge.BOTTOM, space);
0579:                space = this .rangeAxis.reserveSpace(g2, this , area,
0580:                        RectangleEdge.LEFT, space);
0581:
0582:                Rectangle2D estimatedDataArea = space.shrink(area, null);
0583:
0584:                AxisSpace space2 = new AxisSpace();
0585:                space2 = this .colorBar.reserveSpace(g2, this , area,
0586:                        estimatedDataArea, this .colorBarLocation, space2);
0587:                Rectangle2D adjustedPlotArea = space2.shrink(area, null);
0588:
0589:                Rectangle2D dataArea = space.shrink(adjustedPlotArea, null);
0590:
0591:                Rectangle2D colorBarArea = space2.reserved(area,
0592:                        this .colorBarLocation);
0593:
0594:                // additional dataArea modifications
0595:                if (getDataAreaRatio() != 0.0) { //check whether modification is
0596:                    double ratio = getDataAreaRatio();
0597:                    Rectangle2D tmpDataArea = (Rectangle2D) dataArea.clone();
0598:                    double h = tmpDataArea.getHeight();
0599:                    double w = tmpDataArea.getWidth();
0600:
0601:                    if (ratio > 0) { // ratio represents pixels
0602:                        if (w * ratio <= h) {
0603:                            h = ratio * w;
0604:                        } else {
0605:                            w = h / ratio;
0606:                        }
0607:                    } else { // ratio represents axis units
0608:                        ratio *= -1.0;
0609:                        double xLength = getDomainAxis().getRange().getLength();
0610:                        double yLength = getRangeAxis().getRange().getLength();
0611:                        double unitRatio = yLength / xLength;
0612:
0613:                        ratio = unitRatio * ratio;
0614:
0615:                        if (w * ratio <= h) {
0616:                            h = ratio * w;
0617:                        } else {
0618:                            w = h / ratio;
0619:                        }
0620:                    }
0621:
0622:                    dataArea.setRect(tmpDataArea.getX()
0623:                            + tmpDataArea.getWidth() / 2 - w / 2, tmpDataArea
0624:                            .getY(), w, h);
0625:                }
0626:
0627:                if (info != null) {
0628:                    info.setDataArea(dataArea);
0629:                }
0630:
0631:                CrosshairState crosshairState = new CrosshairState();
0632:                crosshairState.setCrosshairDistance(Double.POSITIVE_INFINITY);
0633:
0634:                // draw the plot background...
0635:                drawBackground(g2, dataArea);
0636:
0637:                double cursor = dataArea.getMaxY();
0638:                if (this .domainAxis != null) {
0639:                    this .domainAxis.draw(g2, cursor, adjustedPlotArea,
0640:                            dataArea, RectangleEdge.BOTTOM, info);
0641:                }
0642:
0643:                if (this .rangeAxis != null) {
0644:                    cursor = dataArea.getMinX();
0645:                    this .rangeAxis.draw(g2, cursor, adjustedPlotArea, dataArea,
0646:                            RectangleEdge.LEFT, info);
0647:                }
0648:
0649:                if (this .colorBar != null) {
0650:                    cursor = 0.0;
0651:                    cursor = this .colorBar.draw(g2, cursor, adjustedPlotArea,
0652:                            dataArea, colorBarArea, this .colorBarLocation);
0653:                }
0654:                Shape originalClip = g2.getClip();
0655:                Composite originalComposite = g2.getComposite();
0656:
0657:                g2.clip(dataArea);
0658:                g2.setComposite(AlphaComposite.getInstance(
0659:                        AlphaComposite.SRC_OVER, getForegroundAlpha()));
0660:                render(g2, dataArea, info, crosshairState);
0661:
0662:                if (this .domainMarkers != null) {
0663:                    Iterator iterator = this .domainMarkers.iterator();
0664:                    while (iterator.hasNext()) {
0665:                        Marker marker = (Marker) iterator.next();
0666:                        drawDomainMarker(g2, this , getDomainAxis(), marker,
0667:                                dataArea);
0668:                    }
0669:                }
0670:
0671:                if (this .rangeMarkers != null) {
0672:                    Iterator iterator = this .rangeMarkers.iterator();
0673:                    while (iterator.hasNext()) {
0674:                        Marker marker = (Marker) iterator.next();
0675:                        drawRangeMarker(g2, this , getRangeAxis(), marker,
0676:                                dataArea);
0677:                    }
0678:                }
0679:
0680:                // TO DO:  these annotations only work with XYPlot, see if it is possible to 
0681:                // make ContourPlot a subclass of XYPlot (DG);
0682:
0683:                //        // draw the annotations...
0684:                //        if (this.annotations != null) {
0685:                //            Iterator iterator = this.annotations.iterator();
0686:                //            while (iterator.hasNext()) {
0687:                //                Annotation annotation = (Annotation) iterator.next();
0688:                //                if (annotation instanceof XYAnnotation) {
0689:                //                    XYAnnotation xya = (XYAnnotation) annotation;
0690:                //                    // get the annotation to draw itself...
0691:                //                    xya.draw(g2, this, dataArea, getDomainAxis(), 
0692:                //                             getRangeAxis());
0693:                //                }
0694:                //            }
0695:                //        }
0696:
0697:                g2.setClip(originalClip);
0698:                g2.setComposite(originalComposite);
0699:                drawOutline(g2, dataArea);
0700:
0701:            }
0702:
0703:            /**
0704:             * Draws a representation of the data within the dataArea region, using the
0705:             * current renderer.
0706:             * <P>
0707:             * The <code>info</code> and <code>crosshairState</code> arguments may be 
0708:             * <code>null</code>.
0709:             *
0710:             * @param g2  the graphics device.
0711:             * @param dataArea  the region in which the data is to be drawn.
0712:             * @param info  an optional object for collection dimension information.
0713:             * @param crosshairState  an optional object for collecting crosshair info.
0714:             */
0715:            public void render(Graphics2D g2, Rectangle2D dataArea,
0716:                    PlotRenderingInfo info, CrosshairState crosshairState) {
0717:
0718:                // now get the data and plot it (the visual representation will depend
0719:                // on the renderer that has been set)...
0720:                ContourDataset data = getDataset();
0721:                if (data != null) {
0722:
0723:                    ColorBar zAxis = getColorBar();
0724:
0725:                    if (this .clipPath != null) {
0726:                        GeneralPath clipper = getClipPath().draw(g2, dataArea,
0727:                                this .domainAxis, this .rangeAxis);
0728:                        if (this .clipPath.isClip()) {
0729:                            g2.clip(clipper);
0730:                        }
0731:                    }
0732:
0733:                    if (this .renderAsPoints) {
0734:                        pointRenderer(g2, dataArea, info, this ,
0735:                                this .domainAxis, this .rangeAxis, zAxis, data,
0736:                                crosshairState);
0737:                    } else {
0738:                        contourRenderer(g2, dataArea, info, this ,
0739:                                this .domainAxis, this .rangeAxis, zAxis, data,
0740:                                crosshairState);
0741:                    }
0742:
0743:                    // draw vertical crosshair if required...
0744:                    setDomainCrosshairValue(crosshairState.getCrosshairX(),
0745:                            false);
0746:                    if (isDomainCrosshairVisible()) {
0747:                        drawVerticalLine(g2, dataArea,
0748:                                getDomainCrosshairValue(),
0749:                                getDomainCrosshairStroke(),
0750:                                getDomainCrosshairPaint());
0751:                    }
0752:
0753:                    // draw horizontal crosshair if required...
0754:                    setRangeCrosshairValue(crosshairState.getCrosshairY(),
0755:                            false);
0756:                    if (isRangeCrosshairVisible()) {
0757:                        drawHorizontalLine(g2, dataArea,
0758:                                getRangeCrosshairValue(),
0759:                                getRangeCrosshairStroke(),
0760:                                getRangeCrosshairPaint());
0761:                    }
0762:
0763:                } else if (this .clipPath != null) {
0764:                    getClipPath().draw(g2, dataArea, this .domainAxis,
0765:                            this .rangeAxis);
0766:                }
0767:
0768:            }
0769:
0770:            /**
0771:             * Fills the plot.
0772:             *
0773:             * @param g2  the graphics device.
0774:             * @param dataArea  the area within which the data is being drawn.
0775:             * @param info  collects information about the drawing.
0776:             * @param plot  the plot (can be used to obtain standard color 
0777:             *              information etc).
0778:             * @param horizontalAxis  the domain (horizontal) axis.
0779:             * @param verticalAxis  the range (vertical) axis.
0780:             * @param colorBar  the color bar axis.
0781:             * @param data  the dataset.
0782:             * @param crosshairState  information about crosshairs on a plot.
0783:             */
0784:            public void contourRenderer(Graphics2D g2, Rectangle2D dataArea,
0785:                    PlotRenderingInfo info, ContourPlot plot,
0786:                    ValueAxis horizontalAxis, ValueAxis verticalAxis,
0787:                    ColorBar colorBar, ContourDataset data,
0788:                    CrosshairState crosshairState) {
0789:
0790:                // setup for collecting optional entity info...
0791:                Rectangle2D.Double entityArea = null;
0792:                EntityCollection entities = null;
0793:                if (info != null) {
0794:                    entities = info.getOwner().getEntityCollection();
0795:                }
0796:
0797:                Rectangle2D.Double rect = null;
0798:                rect = new Rectangle2D.Double();
0799:
0800:                //turn off anti-aliasing when filling rectangles
0801:                Object antiAlias = g2
0802:                        .getRenderingHint(RenderingHints.KEY_ANTIALIASING);
0803:                g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
0804:                        RenderingHints.VALUE_ANTIALIAS_OFF);
0805:
0806:                // get the data points
0807:                Number[] xNumber = data.getXValues();
0808:                Number[] yNumber = data.getYValues();
0809:                Number[] zNumber = data.getZValues();
0810:
0811:                double[] x = new double[xNumber.length];
0812:                double[] y = new double[yNumber.length];
0813:
0814:                for (int i = 0; i < x.length; i++) {
0815:                    x[i] = xNumber[i].doubleValue();
0816:                    y[i] = yNumber[i].doubleValue();
0817:                }
0818:
0819:                int[] xIndex = data.indexX();
0820:                int[] indexX = data.getXIndices();
0821:                boolean vertInverted = ((NumberAxis) verticalAxis).isInverted();
0822:                boolean horizInverted = false;
0823:                if (horizontalAxis instanceof  NumberAxis) {
0824:                    horizInverted = ((NumberAxis) horizontalAxis).isInverted();
0825:                }
0826:                double transX = 0.0;
0827:                double transXm1 = 0.0;
0828:                double transXp1 = 0.0;
0829:                double transDXm1 = 0.0;
0830:                double transDXp1 = 0.0;
0831:                double transDX = 0.0;
0832:                double transY = 0.0;
0833:                double transYm1 = 0.0;
0834:                double transYp1 = 0.0;
0835:                double transDYm1 = 0.0;
0836:                double transDYp1 = 0.0;
0837:                double transDY = 0.0;
0838:                int iMax = xIndex[xIndex.length - 1];
0839:                for (int k = 0; k < x.length; k++) {
0840:                    int i = xIndex[k];
0841:                    if (indexX[i] == k) { // this is a new column
0842:                        if (i == 0) {
0843:                            transX = horizontalAxis.valueToJava2D(x[k],
0844:                                    dataArea, RectangleEdge.BOTTOM);
0845:                            transXm1 = transX;
0846:                            transXp1 = horizontalAxis.valueToJava2D(
0847:                                    x[indexX[i + 1]], dataArea,
0848:                                    RectangleEdge.BOTTOM);
0849:                            transDXm1 = Math.abs(0.5 * (transX - transXm1));
0850:                            transDXp1 = Math.abs(0.5 * (transX - transXp1));
0851:                        } else if (i == iMax) {
0852:                            transX = horizontalAxis.valueToJava2D(x[k],
0853:                                    dataArea, RectangleEdge.BOTTOM);
0854:                            transXm1 = horizontalAxis.valueToJava2D(
0855:                                    x[indexX[i - 1]], dataArea,
0856:                                    RectangleEdge.BOTTOM);
0857:                            transXp1 = transX;
0858:                            transDXm1 = Math.abs(0.5 * (transX - transXm1));
0859:                            transDXp1 = Math.abs(0.5 * (transX - transXp1));
0860:                        } else {
0861:                            transX = horizontalAxis.valueToJava2D(x[k],
0862:                                    dataArea, RectangleEdge.BOTTOM);
0863:                            transXp1 = horizontalAxis.valueToJava2D(
0864:                                    x[indexX[i + 1]], dataArea,
0865:                                    RectangleEdge.BOTTOM);
0866:                            transDXm1 = transDXp1;
0867:                            transDXp1 = Math.abs(0.5 * (transX - transXp1));
0868:                        }
0869:
0870:                        if (horizInverted) {
0871:                            transX -= transDXp1;
0872:                        } else {
0873:                            transX -= transDXm1;
0874:                        }
0875:
0876:                        transDX = transDXm1 + transDXp1;
0877:
0878:                        transY = verticalAxis.valueToJava2D(y[k], dataArea,
0879:                                RectangleEdge.LEFT);
0880:                        transYm1 = transY;
0881:                        if (k + 1 == y.length) {
0882:                            continue;
0883:                        }
0884:                        transYp1 = verticalAxis.valueToJava2D(y[k + 1],
0885:                                dataArea, RectangleEdge.LEFT);
0886:                        transDYm1 = Math.abs(0.5 * (transY - transYm1));
0887:                        transDYp1 = Math.abs(0.5 * (transY - transYp1));
0888:                    } else if ((i < indexX.length - 1 && indexX[i + 1] - 1 == k)
0889:                            || k == x.length - 1) {
0890:                        // end of column
0891:                        transY = verticalAxis.valueToJava2D(y[k], dataArea,
0892:                                RectangleEdge.LEFT);
0893:                        transYm1 = verticalAxis.valueToJava2D(y[k - 1],
0894:                                dataArea, RectangleEdge.LEFT);
0895:                        transYp1 = transY;
0896:                        transDYm1 = Math.abs(0.5 * (transY - transYm1));
0897:                        transDYp1 = Math.abs(0.5 * (transY - transYp1));
0898:                    } else {
0899:                        transY = verticalAxis.valueToJava2D(y[k], dataArea,
0900:                                RectangleEdge.LEFT);
0901:                        transYp1 = verticalAxis.valueToJava2D(y[k + 1],
0902:                                dataArea, RectangleEdge.LEFT);
0903:                        transDYm1 = transDYp1;
0904:                        transDYp1 = Math.abs(0.5 * (transY - transYp1));
0905:                    }
0906:                    if (vertInverted) {
0907:                        transY -= transDYm1;
0908:                    } else {
0909:                        transY -= transDYp1;
0910:                    }
0911:
0912:                    transDY = transDYm1 + transDYp1;
0913:
0914:                    rect.setRect(transX, transY, transDX, transDY);
0915:                    if (zNumber[k] != null) {
0916:                        g2
0917:                                .setPaint(colorBar.getPaint(zNumber[k]
0918:                                        .doubleValue()));
0919:                        g2.fill(rect);
0920:                    } else if (this .missingPaint != null) {
0921:                        g2.setPaint(this .missingPaint);
0922:                        g2.fill(rect);
0923:                    }
0924:
0925:                    entityArea = rect;
0926:
0927:                    // add an entity for the item...
0928:                    if (entities != null) {
0929:                        String tip = "";
0930:                        if (getToolTipGenerator() != null) {
0931:                            tip = this .toolTipGenerator
0932:                                    .generateToolTip(data, k);
0933:                        }
0934:                        //              Shape s = g2.getClip();
0935:                        //              if (s.contains(rect) || s.intersects(rect)) {
0936:                        String url = null;
0937:                        // if (getURLGenerator() != null) {    //dmo: look at this later
0938:                        //      url = getURLGenerator().generateURL(data, series, item);
0939:                        // }
0940:                        // Unlike XYItemRenderer, we need to clone entityArea since it 
0941:                        // reused.
0942:                        ContourEntity entity = new ContourEntity(
0943:                                (Rectangle2D.Double) entityArea.clone(), tip,
0944:                                url);
0945:                        entity.setIndex(k);
0946:                        entities.add(entity);
0947:                        //              }
0948:                    }
0949:
0950:                    // do we need to update the crosshair values?
0951:                    if (plot.isDomainCrosshairLockedOnData()) {
0952:                        if (plot.isRangeCrosshairLockedOnData()) {
0953:                            // both axes
0954:                            crosshairState.updateCrosshairPoint(x[k], y[k],
0955:                                    transX, transY, PlotOrientation.VERTICAL);
0956:                        } else {
0957:                            // just the horizontal axis...
0958:                            crosshairState.updateCrosshairX(transX);
0959:                        }
0960:                    } else {
0961:                        if (plot.isRangeCrosshairLockedOnData()) {
0962:                            // just the vertical axis...
0963:                            crosshairState.updateCrosshairY(transY);
0964:                        }
0965:                    }
0966:                }
0967:
0968:                g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, antiAlias);
0969:
0970:                return;
0971:
0972:            }
0973:
0974:            /**
0975:             * Draws the visual representation of a single data item.
0976:             *
0977:             * @param g2  the graphics device.
0978:             * @param dataArea  the area within which the data is being drawn.
0979:             * @param info  collects information about the drawing.
0980:             * @param plot  the plot (can be used to obtain standard color 
0981:             *              information etc).
0982:             * @param domainAxis  the domain (horizontal) axis.
0983:             * @param rangeAxis  the range (vertical) axis.
0984:             * @param colorBar  the color bar axis.
0985:             * @param data  the dataset.
0986:             * @param crosshairState  information about crosshairs on a plot.
0987:             */
0988:            public void pointRenderer(Graphics2D g2, Rectangle2D dataArea,
0989:                    PlotRenderingInfo info, ContourPlot plot,
0990:                    ValueAxis domainAxis, ValueAxis rangeAxis,
0991:                    ColorBar colorBar, ContourDataset data,
0992:                    CrosshairState crosshairState) {
0993:
0994:                // setup for collecting optional entity info...
0995:                RectangularShape entityArea = null;
0996:                EntityCollection entities = null;
0997:                if (info != null) {
0998:                    entities = info.getOwner().getEntityCollection();
0999:                }
1000:
1001:                //      Rectangle2D.Double rect = null;
1002:                //      rect = new Rectangle2D.Double();
1003:                RectangularShape rect = new Ellipse2D.Double();
1004:
1005:                //turn off anti-aliasing when filling rectangles
1006:                Object antiAlias = g2
1007:                        .getRenderingHint(RenderingHints.KEY_ANTIALIASING);
1008:                g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
1009:                        RenderingHints.VALUE_ANTIALIAS_OFF);
1010:
1011:                // if (tooltips!=null) tooltips.clearToolTips(); // reset collection
1012:                // get the data points
1013:                Number[] xNumber = data.getXValues();
1014:                Number[] yNumber = data.getYValues();
1015:                Number[] zNumber = data.getZValues();
1016:
1017:                double[] x = new double[xNumber.length];
1018:                double[] y = new double[yNumber.length];
1019:
1020:                for (int i = 0; i < x.length; i++) {
1021:                    x[i] = xNumber[i].doubleValue();
1022:                    y[i] = yNumber[i].doubleValue();
1023:                }
1024:
1025:                double transX = 0.0;
1026:                double transDX = 0.0;
1027:                double transY = 0.0;
1028:                double transDY = 0.0;
1029:                double size = dataArea.getWidth() * this .ptSizePct;
1030:                for (int k = 0; k < x.length; k++) {
1031:
1032:                    transX = domainAxis.valueToJava2D(x[k], dataArea,
1033:                            RectangleEdge.BOTTOM)
1034:                            - 0.5 * size;
1035:                    transY = rangeAxis.valueToJava2D(y[k], dataArea,
1036:                            RectangleEdge.LEFT)
1037:                            - 0.5 * size;
1038:                    transDX = size;
1039:                    transDY = size;
1040:
1041:                    rect.setFrame(transX, transY, transDX, transDY);
1042:
1043:                    if (zNumber[k] != null) {
1044:                        g2
1045:                                .setPaint(colorBar.getPaint(zNumber[k]
1046:                                        .doubleValue()));
1047:                        g2.fill(rect);
1048:                    } else if (this .missingPaint != null) {
1049:                        g2.setPaint(this .missingPaint);
1050:                        g2.fill(rect);
1051:                    }
1052:
1053:                    entityArea = rect;
1054:
1055:                    // add an entity for the item...
1056:                    if (entities != null) {
1057:                        String tip = null;
1058:                        if (getToolTipGenerator() != null) {
1059:                            tip = this .toolTipGenerator
1060:                                    .generateToolTip(data, k);
1061:                        }
1062:                        String url = null;
1063:                        // if (getURLGenerator() != null) {   //dmo: look at this later
1064:                        //   url = getURLGenerator().generateURL(data, series, item);
1065:                        // }
1066:                        // Unlike XYItemRenderer, we need to clone entityArea since it 
1067:                        // reused.
1068:                        ContourEntity entity = new ContourEntity(
1069:                                (RectangularShape) entityArea.clone(), tip, url);
1070:                        entity.setIndex(k);
1071:                        entities.add(entity);
1072:                    }
1073:
1074:                    // do we need to update the crosshair values?
1075:                    if (plot.isDomainCrosshairLockedOnData()) {
1076:                        if (plot.isRangeCrosshairLockedOnData()) {
1077:                            // both axes
1078:                            crosshairState.updateCrosshairPoint(x[k], y[k],
1079:                                    transX, transY, PlotOrientation.VERTICAL);
1080:                        } else {
1081:                            // just the horizontal axis...
1082:                            crosshairState.updateCrosshairX(transX);
1083:                        }
1084:                    } else {
1085:                        if (plot.isRangeCrosshairLockedOnData()) {
1086:                            // just the vertical axis...
1087:                            crosshairState.updateCrosshairY(transY);
1088:                        }
1089:                    }
1090:                }
1091:
1092:                g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, antiAlias);
1093:
1094:                return;
1095:
1096:            }
1097:
1098:            /**
1099:             * Utility method for drawing a crosshair on the chart (if required).
1100:             *
1101:             * @param g2  The graphics device.
1102:             * @param dataArea  The data area.
1103:             * @param value  The coordinate, where to draw the line.
1104:             * @param stroke  The stroke to use.
1105:             * @param paint  The paint to use.
1106:             */
1107:            protected void drawVerticalLine(Graphics2D g2,
1108:                    Rectangle2D dataArea, double value, Stroke stroke,
1109:                    Paint paint) {
1110:
1111:                double xx = getDomainAxis().valueToJava2D(value, dataArea,
1112:                        RectangleEdge.BOTTOM);
1113:                Line2D line = new Line2D.Double(xx, dataArea.getMinY(), xx,
1114:                        dataArea.getMaxY());
1115:                g2.setStroke(stroke);
1116:                g2.setPaint(paint);
1117:                g2.draw(line);
1118:
1119:            }
1120:
1121:            /**
1122:             * Utility method for drawing a crosshair on the chart (if required).
1123:             *
1124:             * @param g2  The graphics device.
1125:             * @param dataArea  The data area.
1126:             * @param value  The coordinate, where to draw the line.
1127:             * @param stroke  The stroke to use.
1128:             * @param paint  The paint to use.
1129:             */
1130:            protected void drawHorizontalLine(Graphics2D g2,
1131:                    Rectangle2D dataArea, double value, Stroke stroke,
1132:                    Paint paint) {
1133:
1134:                double yy = getRangeAxis().valueToJava2D(value, dataArea,
1135:                        RectangleEdge.LEFT);
1136:                Line2D line = new Line2D.Double(dataArea.getMinX(), yy,
1137:                        dataArea.getMaxX(), yy);
1138:                g2.setStroke(stroke);
1139:                g2.setPaint(paint);
1140:                g2.draw(line);
1141:
1142:            }
1143:
1144:            /**
1145:             * Handles a 'click' on the plot by updating the anchor values...
1146:             *
1147:             * @param x  x-coordinate, where the click occured.
1148:             * @param y  y-coordinate, where the click occured.
1149:             * @param info  An object for collection dimension information.
1150:             */
1151:            public void handleClick(int x, int y, PlotRenderingInfo info) {
1152:
1153:                /*        // set the anchor value for the horizontal axis...
1154:                 ValueAxis hva = getDomainAxis();
1155:                 if (hva != null) {
1156:                 double hvalue = hva.translateJava2DtoValue(
1157:                 (float) x, info.getDataArea()
1158:                 );
1159:
1160:                 hva.setAnchorValue(hvalue);
1161:                 setDomainCrosshairValue(hvalue);
1162:                 }
1163:
1164:                 // set the anchor value for the vertical axis...
1165:                 ValueAxis vva = getRangeAxis();
1166:                 if (vva != null) {
1167:                 double vvalue = vva.translateJava2DtoValue(
1168:                 (float) y, info.getDataArea()
1169:                 );
1170:                 vva.setAnchorValue(vvalue);
1171:                 setRangeCrosshairValue(vvalue);
1172:                 }
1173:                 */
1174:            }
1175:
1176:            /**
1177:             * Zooms the axis ranges by the specified percentage about the anchor point.
1178:             *
1179:             * @param percent  The amount of the zoom.
1180:             */
1181:            public void zoom(double percent) {
1182:
1183:                if (percent > 0) {
1184:                    //  double range = this.domainAxis.getRange().getLength();
1185:                    //  double scaledRange = range * percent;
1186:                    //  domainAxis.setAnchoredRange(scaledRange);
1187:
1188:                    //  range = this.rangeAxis.getRange().getLength();
1189:                    //  scaledRange = range * percent;
1190:                    //   rangeAxis.setAnchoredRange(scaledRange);
1191:                } else {
1192:                    getRangeAxis().setAutoRange(true);
1193:                    getDomainAxis().setAutoRange(true);
1194:                }
1195:
1196:            }
1197:
1198:            /**
1199:             * Returns the plot type as a string.
1200:             *
1201:             * @return A short string describing the type of plot.
1202:             */
1203:            public String getPlotType() {
1204:                return localizationResources.getString("Contour_Plot");
1205:            }
1206:
1207:            /**
1208:             * Returns the range for an axis.
1209:             *
1210:             * @param axis  the axis.
1211:             *
1212:             * @return The range for an axis.
1213:             */
1214:            public Range getDataRange(ValueAxis axis) {
1215:
1216:                if (this .dataset == null) {
1217:                    return null;
1218:                }
1219:
1220:                Range result = null;
1221:
1222:                if (axis == getDomainAxis()) {
1223:                    result = DatasetUtilities.findDomainBounds(this .dataset);
1224:                } else if (axis == getRangeAxis()) {
1225:                    result = DatasetUtilities.findRangeBounds(this .dataset);
1226:                }
1227:
1228:                return result;
1229:
1230:            }
1231:
1232:            /**
1233:             * Returns the range for the Contours.
1234:             *
1235:             * @return The range for the Contours (z-axis).
1236:             */
1237:            public Range getContourDataRange() {
1238:
1239:                Range result = null;
1240:
1241:                ContourDataset data = getDataset();
1242:
1243:                if (data != null) {
1244:                    Range h = getDomainAxis().getRange();
1245:                    Range v = getRangeAxis().getRange();
1246:                    result = this .visibleRange(data, h, v);
1247:                }
1248:
1249:                return result;
1250:            }
1251:
1252:            /**
1253:             * Notifies all registered listeners of a property change.
1254:             * <P>
1255:             * One source of property change events is the plot's renderer.
1256:             *
1257:             * @param event  Information about the property change.
1258:             */
1259:            public void propertyChange(PropertyChangeEvent event) {
1260:                notifyListeners(new PlotChangeEvent(this ));
1261:            }
1262:
1263:            /**
1264:             * Receives notification of a change to the plot's dataset.
1265:             * <P>
1266:             * The chart reacts by passing on a chart change event to all registered
1267:             * listeners.
1268:             *
1269:             * @param event  Information about the event (not used here).
1270:             */
1271:            public void datasetChanged(DatasetChangeEvent event) {
1272:                if (this .domainAxis != null) {
1273:                    this .domainAxis.configure();
1274:                }
1275:                if (this .rangeAxis != null) {
1276:                    this .rangeAxis.configure();
1277:                }
1278:                if (this .colorBar != null) {
1279:                    this .colorBar.configure(this );
1280:                }
1281:                super .datasetChanged(event);
1282:            }
1283:
1284:            /**
1285:             * Returns the colorbar.
1286:             *
1287:             * @return The colorbar.
1288:             */
1289:            public ColorBar getColorBar() {
1290:                return this .colorBar;
1291:            }
1292:
1293:            /**
1294:             * Returns a flag indicating whether or not the domain crosshair is visible.
1295:             *
1296:             * @return The flag.
1297:             */
1298:            public boolean isDomainCrosshairVisible() {
1299:                return this .domainCrosshairVisible;
1300:            }
1301:
1302:            /**
1303:             * Sets the flag indicating whether or not the domain crosshair is visible.
1304:             *
1305:             * @param flag  the new value of the flag.
1306:             */
1307:            public void setDomainCrosshairVisible(boolean flag) {
1308:
1309:                if (this .domainCrosshairVisible != flag) {
1310:                    this .domainCrosshairVisible = flag;
1311:                    notifyListeners(new PlotChangeEvent(this ));
1312:                }
1313:
1314:            }
1315:
1316:            /**
1317:             * Returns a flag indicating whether or not the crosshair should "lock-on"
1318:             * to actual data values.
1319:             *
1320:             * @return The flag.
1321:             */
1322:            public boolean isDomainCrosshairLockedOnData() {
1323:                return this .domainCrosshairLockedOnData;
1324:            }
1325:
1326:            /**
1327:             * Sets the flag indicating whether or not the domain crosshair should 
1328:             * "lock-on" to actual data values.
1329:             *
1330:             * @param flag  the flag.
1331:             */
1332:            public void setDomainCrosshairLockedOnData(boolean flag) {
1333:                if (this .domainCrosshairLockedOnData != flag) {
1334:                    this .domainCrosshairLockedOnData = flag;
1335:                    notifyListeners(new PlotChangeEvent(this ));
1336:                }
1337:            }
1338:
1339:            /**
1340:             * Returns the domain crosshair value.
1341:             *
1342:             * @return The value.
1343:             */
1344:            public double getDomainCrosshairValue() {
1345:                return this .domainCrosshairValue;
1346:            }
1347:
1348:            /**
1349:             * Sets the domain crosshair value.
1350:             * <P>
1351:             * Registered listeners are notified that the plot has been modified, but
1352:             * only if the crosshair is visible.
1353:             *
1354:             * @param value  the new value.
1355:             */
1356:            public void setDomainCrosshairValue(double value) {
1357:                setDomainCrosshairValue(value, true);
1358:            }
1359:
1360:            /**
1361:             * Sets the domain crosshair value.
1362:             * <P>
1363:             * Registered listeners are notified that the axis has been modified, but
1364:             * only if the crosshair is visible.
1365:             *
1366:             * @param value  the new value.
1367:             * @param notify  a flag that controls whether or not listeners are 
1368:             *                notified.
1369:             */
1370:            public void setDomainCrosshairValue(double value, boolean notify) {
1371:                this .domainCrosshairValue = value;
1372:                if (isDomainCrosshairVisible() && notify) {
1373:                    notifyListeners(new PlotChangeEvent(this ));
1374:                }
1375:            }
1376:
1377:            /**
1378:             * Returns the Stroke used to draw the crosshair (if visible).
1379:             *
1380:             * @return The crosshair stroke.
1381:             */
1382:            public Stroke getDomainCrosshairStroke() {
1383:                return this .domainCrosshairStroke;
1384:            }
1385:
1386:            /**
1387:             * Sets the Stroke used to draw the crosshairs (if visible) and notifies
1388:             * registered listeners that the axis has been modified.
1389:             *
1390:             * @param stroke  the new crosshair stroke.
1391:             */
1392:            public void setDomainCrosshairStroke(Stroke stroke) {
1393:                this .domainCrosshairStroke = stroke;
1394:                notifyListeners(new PlotChangeEvent(this ));
1395:            }
1396:
1397:            /**
1398:             * Returns the domain crosshair color.
1399:             *
1400:             * @return The crosshair color.
1401:             */
1402:            public Paint getDomainCrosshairPaint() {
1403:                return this .domainCrosshairPaint;
1404:            }
1405:
1406:            /**
1407:             * Sets the Paint used to color the crosshairs (if visible) and notifies
1408:             * registered listeners that the axis has been modified.
1409:             *
1410:             * @param paint the new crosshair paint.
1411:             */
1412:            public void setDomainCrosshairPaint(Paint paint) {
1413:                this .domainCrosshairPaint = paint;
1414:                notifyListeners(new PlotChangeEvent(this ));
1415:            }
1416:
1417:            /**
1418:             * Returns a flag indicating whether or not the range crosshair is visible.
1419:             *
1420:             * @return The flag.
1421:             */
1422:            public boolean isRangeCrosshairVisible() {
1423:                return this .rangeCrosshairVisible;
1424:            }
1425:
1426:            /**
1427:             * Sets the flag indicating whether or not the range crosshair is visible.
1428:             *
1429:             * @param flag  the new value of the flag.
1430:             */
1431:            public void setRangeCrosshairVisible(boolean flag) {
1432:                if (this .rangeCrosshairVisible != flag) {
1433:                    this .rangeCrosshairVisible = flag;
1434:                    notifyListeners(new PlotChangeEvent(this ));
1435:                }
1436:            }
1437:
1438:            /**
1439:             * Returns a flag indicating whether or not the crosshair should "lock-on"
1440:             * to actual data values.
1441:             *
1442:             * @return The flag.
1443:             */
1444:            public boolean isRangeCrosshairLockedOnData() {
1445:                return this .rangeCrosshairLockedOnData;
1446:            }
1447:
1448:            /**
1449:             * Sets the flag indicating whether or not the range crosshair should 
1450:             * "lock-on" to actual data values.
1451:             *
1452:             * @param flag  the flag.
1453:             */
1454:            public void setRangeCrosshairLockedOnData(boolean flag) {
1455:                if (this .rangeCrosshairLockedOnData != flag) {
1456:                    this .rangeCrosshairLockedOnData = flag;
1457:                    notifyListeners(new PlotChangeEvent(this ));
1458:                }
1459:            }
1460:
1461:            /**
1462:             * Returns the range crosshair value.
1463:             *
1464:             * @return The value.
1465:             */
1466:            public double getRangeCrosshairValue() {
1467:                return this .rangeCrosshairValue;
1468:            }
1469:
1470:            /**
1471:             * Sets the domain crosshair value.
1472:             * <P>
1473:             * Registered listeners are notified that the plot has been modified, but
1474:             * only if the crosshair is visible.
1475:             *
1476:             * @param value  the new value.
1477:             */
1478:            public void setRangeCrosshairValue(double value) {
1479:                setRangeCrosshairValue(value, true);
1480:            }
1481:
1482:            /**
1483:             * Sets the range crosshair value.
1484:             * <P>
1485:             * Registered listeners are notified that the axis has been modified, but
1486:             * only if the crosshair is visible.
1487:             *
1488:             * @param value  the new value.
1489:             * @param notify  a flag that controls whether or not listeners are 
1490:             *                notified.
1491:             */
1492:            public void setRangeCrosshairValue(double value, boolean notify) {
1493:                this .rangeCrosshairValue = value;
1494:                if (isRangeCrosshairVisible() && notify) {
1495:                    notifyListeners(new PlotChangeEvent(this ));
1496:                }
1497:            }
1498:
1499:            /**
1500:             * Returns the Stroke used to draw the crosshair (if visible).
1501:             *
1502:             * @return The crosshair stroke.
1503:             */
1504:            public Stroke getRangeCrosshairStroke() {
1505:                return this .rangeCrosshairStroke;
1506:            }
1507:
1508:            /**
1509:             * Sets the Stroke used to draw the crosshairs (if visible) and notifies
1510:             * registered listeners that the axis has been modified.
1511:             *
1512:             * @param stroke  the new crosshair stroke.
1513:             */
1514:            public void setRangeCrosshairStroke(Stroke stroke) {
1515:                this .rangeCrosshairStroke = stroke;
1516:                notifyListeners(new PlotChangeEvent(this ));
1517:            }
1518:
1519:            /**
1520:             * Returns the range crosshair color.
1521:             *
1522:             * @return The crosshair color.
1523:             */
1524:            public Paint getRangeCrosshairPaint() {
1525:                return this .rangeCrosshairPaint;
1526:            }
1527:
1528:            /**
1529:             * Sets the Paint used to color the crosshairs (if visible) and notifies
1530:             * registered listeners that the axis has been modified.
1531:             *
1532:             * @param paint the new crosshair paint.
1533:             */
1534:            public void setRangeCrosshairPaint(Paint paint) {
1535:                this .rangeCrosshairPaint = paint;
1536:                notifyListeners(new PlotChangeEvent(this ));
1537:            }
1538:
1539:            /**
1540:             * Returns the tool tip generator.
1541:             *
1542:             * @return The tool tip generator (possibly null).
1543:             */
1544:            public ContourToolTipGenerator getToolTipGenerator() {
1545:                return this .toolTipGenerator;
1546:            }
1547:
1548:            /**
1549:             * Sets the tool tip generator.
1550:             *
1551:             * @param generator  the tool tip generator (null permitted).
1552:             */
1553:            public void setToolTipGenerator(ContourToolTipGenerator generator) {
1554:                //Object oldValue = this.toolTipGenerator;
1555:                this .toolTipGenerator = generator;
1556:            }
1557:
1558:            /**
1559:             * Returns the URL generator for HTML image maps.
1560:             *
1561:             * @return The URL generator (possibly null).
1562:             */
1563:            public XYURLGenerator getURLGenerator() {
1564:                return this .urlGenerator;
1565:            }
1566:
1567:            /**
1568:             * Sets the URL generator for HTML image maps.
1569:             *
1570:             * @param urlGenerator  the URL generator (null permitted).
1571:             */
1572:            public void setURLGenerator(XYURLGenerator urlGenerator) {
1573:                //Object oldValue = this.urlGenerator;
1574:                this .urlGenerator = urlGenerator;
1575:            }
1576:
1577:            /**
1578:             * Draws a vertical line on the chart to represent a 'range marker'.
1579:             *
1580:             * @param g2  the graphics device.
1581:             * @param plot  the plot.
1582:             * @param domainAxis  the domain axis.
1583:             * @param marker  the marker line.
1584:             * @param dataArea  the axis data area.
1585:             */
1586:            public void drawDomainMarker(Graphics2D g2, ContourPlot plot,
1587:                    ValueAxis domainAxis, Marker marker, Rectangle2D dataArea) {
1588:
1589:                if (marker instanceof  ValueMarker) {
1590:                    ValueMarker vm = (ValueMarker) marker;
1591:                    double value = vm.getValue();
1592:                    Range range = domainAxis.getRange();
1593:                    if (!range.contains(value)) {
1594:                        return;
1595:                    }
1596:
1597:                    double x = domainAxis.valueToJava2D(value, dataArea,
1598:                            RectangleEdge.BOTTOM);
1599:                    Line2D line = new Line2D.Double(x, dataArea.getMinY(), x,
1600:                            dataArea.getMaxY());
1601:                    Paint paint = marker.getOutlinePaint();
1602:                    Stroke stroke = marker.getOutlineStroke();
1603:                    g2.setPaint(paint != null ? paint
1604:                            : Plot.DEFAULT_OUTLINE_PAINT);
1605:                    g2.setStroke(stroke != null ? stroke
1606:                            : Plot.DEFAULT_OUTLINE_STROKE);
1607:                    g2.draw(line);
1608:                }
1609:
1610:            }
1611:
1612:            /**
1613:             * Draws a horizontal line across the chart to represent a 'range marker'.
1614:             *
1615:             * @param g2  the graphics device.
1616:             * @param plot  the plot.
1617:             * @param rangeAxis  the range axis.
1618:             * @param marker  the marker line.
1619:             * @param dataArea  the axis data area.
1620:             */
1621:            public void drawRangeMarker(Graphics2D g2, ContourPlot plot,
1622:                    ValueAxis rangeAxis, Marker marker, Rectangle2D dataArea) {
1623:
1624:                if (marker instanceof  ValueMarker) {
1625:                    ValueMarker vm = (ValueMarker) marker;
1626:                    double value = vm.getValue();
1627:                    Range range = rangeAxis.getRange();
1628:                    if (!range.contains(value)) {
1629:                        return;
1630:                    }
1631:
1632:                    double y = rangeAxis.valueToJava2D(value, dataArea,
1633:                            RectangleEdge.LEFT);
1634:                    Line2D line = new Line2D.Double(dataArea.getMinX(), y,
1635:                            dataArea.getMaxX(), y);
1636:                    Paint paint = marker.getOutlinePaint();
1637:                    Stroke stroke = marker.getOutlineStroke();
1638:                    g2.setPaint(paint != null ? paint
1639:                            : Plot.DEFAULT_OUTLINE_PAINT);
1640:                    g2.setStroke(stroke != null ? stroke
1641:                            : Plot.DEFAULT_OUTLINE_STROKE);
1642:                    g2.draw(line);
1643:                }
1644:
1645:            }
1646:
1647:            /**
1648:             * Returns the clipPath.
1649:             * @return ClipPath
1650:             */
1651:            public ClipPath getClipPath() {
1652:                return this .clipPath;
1653:            }
1654:
1655:            /**
1656:             * Sets the clipPath.
1657:             * @param clipPath The clipPath to set
1658:             */
1659:            public void setClipPath(ClipPath clipPath) {
1660:                this .clipPath = clipPath;
1661:            }
1662:
1663:            /**
1664:             * Returns the ptSizePct.
1665:             * @return double
1666:             */
1667:            public double getPtSizePct() {
1668:                return this .ptSizePct;
1669:            }
1670:
1671:            /**
1672:             * Returns the renderAsPoints.
1673:             * @return boolean
1674:             */
1675:            public boolean isRenderAsPoints() {
1676:                return this .renderAsPoints;
1677:            }
1678:
1679:            /**
1680:             * Sets the ptSizePct.
1681:             * @param ptSizePct The ptSizePct to set
1682:             */
1683:            public void setPtSizePct(double ptSizePct) {
1684:                this .ptSizePct = ptSizePct;
1685:            }
1686:
1687:            /**
1688:             * Sets the renderAsPoints.
1689:             * @param renderAsPoints The renderAsPoints to set
1690:             */
1691:            public void setRenderAsPoints(boolean renderAsPoints) {
1692:                this .renderAsPoints = renderAsPoints;
1693:            }
1694:
1695:            /**
1696:             * Receives notification of a change to one of the plot's axes.
1697:             *
1698:             * @param event  information about the event.
1699:             */
1700:            public void axisChanged(AxisChangeEvent event) {
1701:                Object source = event.getSource();
1702:                if (source.equals(this .rangeAxis)
1703:                        || source.equals(this .domainAxis)) {
1704:                    ColorBar cba = this .colorBar;
1705:                    if (this .colorBar.getAxis().isAutoRange()) {
1706:                        cba.getAxis().configure();
1707:                    }
1708:
1709:                }
1710:                super .axisChanged(event);
1711:            }
1712:
1713:            /**
1714:             * Returns the visible z-range.
1715:             *
1716:             * @param data  the dataset.
1717:             * @param x  the x range.
1718:             * @param y  the y range.
1719:             *
1720:             * @return The range.
1721:             */
1722:            public Range visibleRange(ContourDataset data, Range x, Range y) {
1723:                Range range = null;
1724:                range = data.getZValueRange(x, y);
1725:                return range;
1726:            }
1727:
1728:            /**
1729:             * Returns the missingPaint.
1730:             * @return Paint
1731:             */
1732:            public Paint getMissingPaint() {
1733:                return this .missingPaint;
1734:            }
1735:
1736:            /**
1737:             * Sets the missingPaint.
1738:             * 
1739:             * @param paint  the missingPaint to set.
1740:             */
1741:            public void setMissingPaint(Paint paint) {
1742:                this .missingPaint = paint;
1743:            }
1744:
1745:            /**
1746:             * Multiplies the range on the domain axis/axes by the specified factor 
1747:             * (to be implemented).
1748:             * 
1749:             * @param x  the x-coordinate (in Java2D space).
1750:             * @param y  the y-coordinate (in Java2D space).
1751:             * @param factor  the zoom factor.
1752:             */
1753:            public void zoomDomainAxes(double x, double y, double factor) {
1754:                // TODO: to be implemented
1755:            }
1756:
1757:            /**
1758:             * Zooms the domain axes (not yet implemented).
1759:             * 
1760:             * @param x  the x-coordinate (in Java2D space).
1761:             * @param y  the y-coordinate (in Java2D space).
1762:             * @param lowerPercent  the new lower bound.
1763:             * @param upperPercent  the new upper bound.
1764:             */
1765:            public void zoomDomainAxes(double x, double y, double lowerPercent,
1766:                    double upperPercent) {
1767:                // TODO: to be implemented
1768:            }
1769:
1770:            /**
1771:             * Multiplies the range on the range axis/axes by the specified factor.
1772:             * 
1773:             * @param x  the x-coordinate (in Java2D space).
1774:             * @param y  the y-coordinate (in Java2D space).
1775:             * @param factor  the zoom factor.
1776:             */
1777:            public void zoomRangeAxes(double x, double y, double factor) {
1778:                // TODO: to be implemented
1779:            }
1780:
1781:            /**
1782:             * Zooms the range axes (not yet implemented).
1783:             * 
1784:             * @param x  the x-coordinate (in Java2D space).
1785:             * @param y  the y-coordinate (in Java2D space).
1786:             * @param lowerPercent  the new lower bound.
1787:             * @param upperPercent  the new upper bound.
1788:             */
1789:            public void zoomRangeAxes(double x, double y, double lowerPercent,
1790:                    double upperPercent) {
1791:                // TODO: to be implemented
1792:            }
1793:
1794:            /**
1795:             * Returns <code>false</code>.
1796:             * 
1797:             * @return A boolean.
1798:             */
1799:            public boolean isDomainZoomable() {
1800:                return false;
1801:            }
1802:
1803:            /**
1804:             * Returns <code>false</code>.
1805:             * 
1806:             * @return A boolean.
1807:             */
1808:            public boolean isRangeZoomable() {
1809:                return false;
1810:            }
1811:
1812:            /** 
1813:             * Extends plot cloning to this plot type
1814:             * @see org.jfree.chart.plot.Plot#clone()
1815:             */
1816:            public Object clone() throws CloneNotSupportedException {
1817:                ContourPlot clone = (ContourPlot) super .clone();
1818:
1819:                if (this .domainAxis != null) {
1820:                    clone.domainAxis = (ValueAxis) this .domainAxis.clone();
1821:                    clone.domainAxis.setPlot(clone);
1822:                    clone.domainAxis.addChangeListener(clone);
1823:                }
1824:                if (this .rangeAxis != null) {
1825:                    clone.rangeAxis = (ValueAxis) this .rangeAxis.clone();
1826:                    clone.rangeAxis.setPlot(clone);
1827:                    clone.rangeAxis.addChangeListener(clone);
1828:                }
1829:
1830:                if (clone.dataset != null) {
1831:                    clone.dataset.addChangeListener(clone);
1832:                }
1833:
1834:                if (this .colorBar != null) {
1835:                    clone.colorBar = (ColorBar) this .colorBar.clone();
1836:                }
1837:
1838:                clone.domainMarkers = (List) ObjectUtilities
1839:                        .deepClone(this .domainMarkers);
1840:                clone.rangeMarkers = (List) ObjectUtilities
1841:                        .deepClone(this .rangeMarkers);
1842:                clone.annotations = (List) ObjectUtilities
1843:                        .deepClone(this .annotations);
1844:
1845:                if (this .clipPath != null) {
1846:                    clone.clipPath = (ClipPath) this.clipPath.clone();
1847:                }
1848:
1849:                return clone;
1850:            }
1851:
1852:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.