/* * Projet : * Package : com.horstmann.violet.framework.util * Auteur : a.depellegrin * Cr le : 26 mai 08 */ package com.horstmann.violet.framework.util; import java.awt.geom.GeneralPath; import java.awt.geom.PathIterator; import java.awt.geom.Point2D; import java.util.ArrayList; import java.util.List; public class ShortestPathConverter { public static GeneralPath getShortestPath(GeneralPath path) { List<Point2D> points = extractPointsFromGeneralPath(path); List<Point2D> sortedPoints = new ArrayList<Point2D>(); while (points.size() > 0) { Point2D currentPoint = null; if (sortedPoints.size() > 0) { currentPoint = sortedPoints.get(sortedPoints.size() - 1); } else { currentPoint = points.get(0); } points.remove(currentPoint); Point2D closestPoint = getClosestPoint(currentPoint, points); if (closestPoint != null) { sortedPoints.add(closestPoint); currentPoint = closestPoint; } } GeneralPath newPath = buildPath(sortedPoints); return newPath; } private static List<Point2D> extractPointsFromGeneralPath(GeneralPath path) { List<Point2D> points = new ArrayList<Point2D>(); double seg[] = new double[6]; for (PathIterator i = path.getPathIterator(null); !i.isDone(); i.next()) { int segType = i.currentSegment(seg); switch (segType) { case PathIterator.SEG_MOVETO: points.add(new Point2D.Double(seg[0], seg[1])); break; case PathIterator.SEG_LINETO: points.add(new Point2D.Double(seg[0], seg[1])); break; } } return points; } private static Point2D getClosestPoint(Point2D refPoint, List<Point2D> pointList) { Point2D closestPoint = null; double shortestDistance = -1; for (Point2D aPoint : pointList) { double distance = refPoint.distance(aPoint); if (shortestDistance < 0 || distance < shortestDistance) { closestPoint = aPoint; shortestDistance = distance; } } return closestPoint; } private static GeneralPath buildPath(List<Point2D> points) { GeneralPath newPath = null; if (points == null) { return new GeneralPath(); } if (points.isEmpty()) { return new GeneralPath(); } for (Point2D aPoint : points) { if (newPath == null) { newPath = new GeneralPath(); newPath.moveTo((float) aPoint.getX(), (float) aPoint.getY()); } else { newPath.lineTo((float) aPoint.getX(), (float) aPoint.getY()); } } return newPath; } }