Changeset 9077 in josm for trunk/src/org/openstreetmap
- Timestamp:
- 2015-12-01T15:50:50+01:00 (8 years ago)
- Location:
- trunk/src/org/openstreetmap/josm/data/osm/visitor/paint
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/org/openstreetmap/josm/data/osm/visitor/paint/StyledMapRenderer.java
r9076 r9077 469 469 * far to fill from the boundary towards the center of the area; 470 470 * if null, area will be filled completely 471 * @param pfClip clipping area for partial fill 471 472 * @param unclosedHighlight true, if the fact that the way / multipolygon is not 472 473 * properly closed should be highlighted; this parameter is only used … … 475 476 * @param text The text to write on the area. 476 477 */ 477 protected void drawArea(OsmPrimitive osm, Path2D.Double path, Color color, MapImage fillImage, Float extent, boolean unclosedHighlight,478 protected void drawArea(OsmPrimitive osm, Path2D.Double path, Color color, MapImage fillImage, Float extent, Path2D.Double pfClip, boolean unclosedHighlight, 478 479 boolean disabled, TextElement text) { 479 480 … … 495 496 g.draw(area); 496 497 } else { 497 Shape clip = g.getClip(); 498 g.clip(area); 498 Shape oldClip = g.getClip(); 499 Shape clip = area; 500 if (pfClip != null) { 501 clip = pfClip.createTransformedShape(nc.getAffineTransform()); 502 } 503 g.clip(clip); 499 504 g.setStroke(new BasicStroke(2 * extent, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER)); 500 505 g.draw(area); 501 g.setClip( clip);506 g.setClip(oldClip); 502 507 } 503 508 } … … 518 523 g.draw(area); 519 524 } else { 520 Shape clip = g.getClip();525 Shape oldClip = g.getClip(); 521 526 BasicStroke stroke = new BasicStroke(2 * extent, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER); 522 527 g.clip(stroke.createStrokedShape(area)); 523 g.fill(area); 524 g.setClip(clip); 528 Shape fill = area; 529 if (pfClip != null) { 530 fill = pfClip.createTransformedShape(nc.getAffineTransform()); 531 } 532 g.fill(fill); 533 g.setClip(oldClip); 525 534 } 526 535 } … … 623 632 for (PolyData pd : multipolygon.getCombinedPolygons()) { 624 633 Path2D.Double p = pd.get(); 634 Path2D.Double pfClip = null; 625 635 if (!isAreaVisible(p)) { 626 636 continue; … … 637 647 } else { 638 648 unclosedHighlight = isUnclosedAreaHighlight; 649 pfClip = getPFClip(pd, extent * scale); 639 650 } 640 651 } 641 652 drawArea(r, p, 642 653 pd.selected ? paintSettings.getRelationSelectedColor(color.getAlpha()) : color, 643 fillImage, extent, unclosedHighlight, disabled, text);654 fillImage, extent, pfClip, unclosedHighlight, disabled, text); 644 655 } 645 656 } … … 658 669 */ 659 670 public void drawArea(Way w, Color color, MapImage fillImage, Float extent, boolean disabled, TextElement text) { 660 if (extent != null && w.isClosed()) { 661 AreaAndPerimeter ap = Geometry.getAreaAndPerimeter(w.getNodes()); 662 // if partial fill would only leave a small gap in the center ... 663 if (ap.getPerimeter() * extent * scale > partialFillThreshold / 100 * ap.getArea()) { 664 // ... turn it off and fill completely 665 extent = null; 666 } 667 } 668 drawArea(w, getPath(w), color, fillImage, extent, isUnclosedAreaHighlight && !w.isClosed(), disabled, text); 671 Path2D.Double pfClip = null; 672 if (extent != null) { 673 if (w.isClosed()) { 674 AreaAndPerimeter ap = Geometry.getAreaAndPerimeter(w.getNodes()); 675 // if partial fill would only leave a small gap in the center ... 676 if (ap.getPerimeter() * extent * scale > partialFillThreshold / 100 * ap.getArea()) { 677 // ... turn it off and fill completely 678 extent = null; 679 } 680 } else { 681 pfClip = getPFClip(w, extent * scale); 682 } 683 } 684 drawArea(w, getPath(w), color, fillImage, extent, pfClip, isUnclosedAreaHighlight && !w.isClosed(), disabled, text); 669 685 } 670 686 … … 1585 1601 } 1586 1602 1603 private static Path2D.Double getPFClip(Way w, double extent) { 1604 Path2D.Double clip = new Path2D.Double(); 1605 buildPFClip(clip, w.getNodes(), extent); 1606 return clip; 1607 } 1608 1609 private static Path2D.Double getPFClip(PolyData pd, double extent) { 1610 Path2D.Double clip = new Path2D.Double(); 1611 clip.setWindingRule(Path2D.WIND_EVEN_ODD); 1612 buildPFClip(clip, pd.getNodes(), extent); 1613 for (PolyData pdInner : pd.getInners()) { 1614 buildPFClip(clip, pdInner.getNodes(), extent); 1615 } 1616 return clip; 1617 } 1618 1619 private static void buildPFClip(Path2D.Double clip, List<Node> nodes, double extent) { 1620 boolean initial = true; 1621 for (Node n : nodes) { 1622 EastNorth p = n.getEastNorth(); 1623 if (p != null) { 1624 if (initial) { 1625 clip.moveTo(p.getX(), p.getY()); 1626 initial = false; 1627 } else { 1628 clip.lineTo(p.getX(), p.getY()); 1629 } 1630 } 1631 } 1632 if (nodes.size() >= 3) { 1633 EastNorth fst = nodes.get(0).getEastNorth(); 1634 EastNorth snd = nodes.get(1).getEastNorth(); 1635 EastNorth lst = nodes.get(nodes.size() - 1).getEastNorth(); 1636 EastNorth lbo = nodes.get(nodes.size() - 2).getEastNorth(); 1637 1638 EastNorth cLst = getPFDisplacedEndPoint(lbo, lst, fst, extent); 1639 EastNorth cFst = getPFDisplacedEndPoint(snd, fst, cLst != null ? cLst : lst, extent); 1640 if (cLst == null && cFst != null) { 1641 cLst = getPFDisplacedEndPoint(lbo, lst, cFst, extent); 1642 } 1643 if (cLst != null) { 1644 clip.lineTo(cLst.getX(), cLst.getY()); 1645 } 1646 if (cFst != null) { 1647 clip.lineTo(cFst.getX(), cFst.getY()); 1648 } 1649 } 1650 } 1651 1652 private static EastNorth getPFDisplacedEndPoint(EastNorth p1, EastNorth p2, EastNorth p3, double extent) { 1653 double dx1 = p2.getX() - p1.getX(); 1654 double dy1 = p2.getY() - p1.getY(); 1655 double dx2 = p3.getX() - p2.getX(); 1656 double dy2 = p3.getY() - p2.getY(); 1657 if (dx1 * dx2 + dy1 * dy2 < 0) { 1658 double len = Math.sqrt(dx1 * dx1 + dy1 * dy1); 1659 double dxm = - dy1 * extent / len; 1660 double dym = dx1 * extent / len; 1661 if (dx1 * dy2 - dx2 * dy1 < 0) { 1662 dxm = -dxm; 1663 dym = -dym; 1664 } 1665 return new EastNorth(p2.getX() + dxm, p2.getY() + dym); 1666 } 1667 return null; 1668 } 1669 1587 1670 private boolean isAreaVisible(Path2D.Double area) { 1588 1671 Rectangle2D bounds = area.getBounds2D(); -
trunk/src/org/openstreetmap/josm/data/osm/visitor/paint/relations/Multipolygon.java
r9063 r9077 296 296 public List<Node> getNodes() { 297 297 return nodes; 298 } 299 300 public List<PolyData> getInners() { 301 return inners; 298 302 } 299 303
Note:
See TracChangeset
for help on using the changeset viewer.