felix@3018: package de.intevation.flys.jfree;
felix@3018: 
ingo@3765: import java.awt.Shape;
ingo@3765: import java.awt.geom.Rectangle2D;
ingo@3765: import java.util.Iterator;
ingo@3765: import java.util.Random;
ingo@3765: 
ingo@3765: import org.apache.log4j.Logger;
ingo@3765: import org.jfree.chart.entity.ChartEntity;
ingo@3765: import org.jfree.chart.entity.EntityCollection;
ingo@3765: import org.w3c.dom.Document;
ingo@3765: 
sascha@3109: import de.intevation.flys.artifacts.math.Function;
sascha@3109: 
felix@3018: public class JFreeUtil {
sascha@3772: 
ingo@3765:     private static final Logger logger = Logger.getLogger(JFreeUtil.class);
sascha@3076: 
felix@3018:     /** Do not instantiate. */
felix@3018:     private JFreeUtil() {
felix@3018:     }
felix@3018: 
felix@3018: 
felix@3018:     /**
felix@3018:      * True if \param hotspot collides with a Entity in \param entities.
felix@3018:      * @param hotspot Shape to compare against other shapes (bounds only).
felix@3018:      * @param entities entities against which to compare shape.
felix@3023:      * @param exclusiveEntityClass If not null, consider only entities of
felix@3023:      *        given class.
felix@3023:      * @return true if a collision (non-zero intersection) exists between
felix@3018:      *        shapes.
felix@3018:      */
felix@3023:     public static boolean collides(Shape hotspot, EntityCollection entities,
felix@3023:         Class exclusiveEntityClass) {
felix@3018:         if (entities == null) return false;
felix@3018: 
felix@3018:         Rectangle2D hotspotBox = hotspot.getBounds2D();
sascha@3076: 
felix@3018:         for (Iterator i = entities.iterator(); i.hasNext(); ) {
felix@3018:             Object next = i.next();
felix@3018:             ChartEntity entity = (ChartEntity) next;
felix@3023:             if (exclusiveEntityClass == null
felix@3023:                 || exclusiveEntityClass.isInstance(entity))
felix@3023:                 {
felix@3023:                 if (entity.getArea().intersects(hotspotBox)) {
felix@3023:                     // Found collision, early stop.
felix@3023:                     return true;
felix@3023:                 }
felix@3018:             }
felix@3018:         }
felix@3018: 
felix@3018:         return false;
felix@3018:     }
sascha@3772: 
sascha@3772: 
ingo@3765:     /**
ingo@3765:      * This function samples a randomized line that contains of x and y values
ingo@3765:      * between <i>startX</i>, <i>endX</i>, <i>startY</i> and <i>endY</i>. The
ingo@3765:      * number of points in the line is specified by <i>num</i>.
sascha@3772:      *
ingo@3765:      * @param num The number of points in the line.
ingo@3765:      * @param startX The min value of the x values.
ingo@3765:      * @param endX The max value of the x values.
ingo@3765:      * @param startY The min value of the y values.
ingo@3765:      * @param endY The max value of the y values.
ingo@3765:      * @return an array with [allX-values, allY-values].
ingo@3765:      * @throws IllegalArgumentException
ingo@3765:      */
ingo@3765:     public static double[][] randomizeLine(
ingo@3765:         int    num,
ingo@3765:         double startX,
ingo@3765:         double endX,
ingo@3765:         double startY,
ingo@3765:         double endY
ingo@3765:     ) throws IllegalArgumentException
ingo@3765:     {
ingo@3765:         if (num <= 0) {
ingo@3765:             throw new IllegalArgumentException("Parameter 'num' has to be > 0");
ingo@3765:         }
sascha@3772: 
ingo@3765:         Random random = new Random();
sascha@3772: 
ingo@3765:         double[] x = new double[num];
ingo@3765:         double[] y = new double[num];
sascha@3772: 
ingo@3765:         for (int i = 0; i < num; i++) {
ingo@3765:             double xFac = random.nextDouble();
ingo@3765:             double yFac = random.nextDouble();
sascha@3772: 
ingo@3765:             x[i] = startX + xFac * (endX - startX);
ingo@3765:             y[i] = startY + yFac * (endY - startY);
sascha@3772: 
ingo@3765:             logger.debug("Created new point: " + x[i] + "|" + y[i]);
ingo@3765:         }
sascha@3772: 
ingo@3765:         return new double[][] { x, y };
ingo@3765:     }
ingo@3105: 
ingo@3105: 
ingo@3105:     public static StyledXYSeries sampleFunction2D(
sascha@3109:         Function func,
sascha@3109:         Document theme,
sascha@3109:         String   seriesKey,
sascha@3109:         int      samples,
sascha@3109:         double   start,
sascha@3109:         double   end
ingo@3105:     ) {
ingo@3105:         StyledXYSeries series = new StyledXYSeries(seriesKey, theme);
ingo@3105: 
ingo@3105:         double step = (end - start) / (samples - 1);
ingo@3105: 
ingo@3105:         for (int i = 0; i < samples; i++) {
ingo@3105:             double x = start + (step * i);
sascha@3109:             series.add(x, func.value(x));
ingo@3105:         }
ingo@3105: 
ingo@3105:         return series;
ingo@3105:     }
teichmann@4564: 
teichmann@4564:     public static StyledXYSeries sampleFunction2DPositive(
teichmann@4564:         Function func,
teichmann@4564:         Document theme,
teichmann@4564:         String   seriesKey,
teichmann@4564:         int      samples,
teichmann@4564:         double   start,
teichmann@4564:         double   end
teichmann@4564:     ) {
teichmann@4564:         StyledXYSeries series = new StyledXYSeries(seriesKey, theme);
teichmann@4564: 
teichmann@4564:         double step = (end - start) / (samples - 1);
teichmann@4564: 
teichmann@4564:         for (int i = 0; i < samples; i++) {
teichmann@4564:             double x = start + (step * i);
teichmann@4564:             double v = func.value(x);
teichmann@4564:             if (x > 0d && v > 0d) {
teichmann@4564:                 series.add(x, v);
teichmann@4564:             }
teichmann@4564:         }
teichmann@4564: 
teichmann@4564:         return series;
teichmann@4564:     }
felix@3018: }
sascha@3083: // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 :