Index: trunk/src/org/openstreetmap/josm/data/gpx/WayPoint.java
===================================================================
--- trunk/src/org/openstreetmap/josm/data/gpx/WayPoint.java	(revision 4128)
+++ trunk/src/org/openstreetmap/josm/data/gpx/WayPoint.java	(revision 4129)
@@ -25,4 +25,16 @@
     public boolean drawLine;
     public int dir;
+
+    public WayPoint(WayPoint p) {
+        attr.putAll(p.attr);
+        lat = p.lat;
+        lon = p.lon;
+        east = p.east;
+        north = p.north;
+        time = p.time;
+        customColoring = p.customColoring;
+        drawLine = p.drawLine;
+        dir = p.dir;
+    }
 
     public WayPoint(LatLon ll) {
Index: trunk/src/org/openstreetmap/josm/data/osm/visitor/BoundingXYVisitor.java
===================================================================
--- trunk/src/org/openstreetmap/josm/data/osm/visitor/BoundingXYVisitor.java	(revision 4128)
+++ trunk/src/org/openstreetmap/josm/data/osm/visitor/BoundingXYVisitor.java	(revision 4129)
@@ -67,5 +67,5 @@
                 visit(((CachedLatLon)latlon).getEastNorth());
             } else {
-                visit(Main.proj.latlon2eastNorth(latlon));
+                visit(Main.getProjection().latlon2eastNorth(latlon));
             }
         }
Index: trunk/src/org/openstreetmap/josm/gui/layer/GpxLayer.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/layer/GpxLayer.java	(revision 4128)
+++ trunk/src/org/openstreetmap/josm/gui/layer/GpxLayer.java	(revision 4129)
@@ -461,12 +461,33 @@
         }
 
-        List<Collection<WayPoint>> visibleSegments = new ArrayList<Collection<WayPoint>>();
+        LinkedList<WayPoint> visibleSegments = new LinkedList<WayPoint>();
         for (GpxTrack trk: data.tracks) {
             for (GpxTrackSegment trkSeg: trk.getSegments()) {
-                if (trkSeg.getBounds() != null && trkSeg.getBounds().intersects(box)) {
-                    visibleSegments.add(trkSeg.getWayPoints());
-                }
-            }
-        }
+                WayPoint last = null;
+                for(WayPoint pt : trkSeg.getWayPoints())
+                {
+                    Bounds b = new Bounds(pt.getCoor());
+                    if(pt.drawLine) // last should never be null when this is true!
+                        b.extend(last.getCoor());
+                    if(b.intersects(box))
+                    {
+                        if(last != null && (visibleSegments.isEmpty()
+                        || visibleSegments.getLast() != last)) {
+                            if(last.drawLine) {
+                                WayPoint l = new WayPoint(last);
+                                l.drawLine = false;
+                                visibleSegments.add(l);
+                            } else {
+                                visibleSegments.add(last);
+                            }
+                        }
+                        visibleSegments.add(pt);
+                    }
+                    last = pt;
+                }
+            }
+        }
+        if(visibleSegments.isEmpty())
+            return;
 
         /****************************************************************
@@ -475,21 +496,19 @@
         if (lines) {
             Point old = null;
-            for (Collection<WayPoint> segment : visibleSegments) {
-                for (WayPoint trkPnt : segment) {
-                    LatLon c = trkPnt.getCoor();
-                    if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
-                        continue;
-                    }
-                    Point screen = mv.getPoint(trkPnt.getEastNorth());
-                    if (trkPnt.drawLine) {
-                        // skip points that are on the same screenposition
-                        if (old != null && ((old.x != screen.x) || (old.y != screen.y))) {
-                            g.setColor(trkPnt.customColoring);
-                            g.drawLine(old.x, old.y, screen.x, screen.y);
-                        }
-                    }
-                    old = screen;
-                } // end for trkpnt
-            } // end for segment
+            for (WayPoint trkPnt : visibleSegments) {
+                LatLon c = trkPnt.getCoor();
+                if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
+                    continue;
+                }
+                Point screen = mv.getPoint(trkPnt.getEastNorth());
+                if (trkPnt.drawLine) {
+                    // skip points that are on the same screenposition
+                    if (old != null && ((old.x != screen.x) || (old.y != screen.y))) {
+                        g.setColor(trkPnt.customColoring);
+                        g.drawLine(old.x, old.y, screen.x, screen.y);
+                    }
+                }
+                old = screen;
+            } // end for trkpnt
         } // end if lines
 
@@ -500,28 +519,26 @@
             Point old = null;
             Point oldA = null; // last arrow painted
-            for (Collection<WayPoint> segment : visibleSegments) {
-                for (WayPoint trkPnt : segment) {
-                    LatLon c = trkPnt.getCoor();
-                    if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
-                        continue;
-                    }
-                    if (trkPnt.drawLine) {
-                        Point screen = mv.getPoint(trkPnt.getEastNorth());
-                        // skip points that are on the same screenposition
-                        if (old != null
-                                && (oldA == null || screen.x < oldA.x - delta || screen.x > oldA.x + delta
-                                        || screen.y < oldA.y - delta || screen.y > oldA.y + delta)) {
-                            g.setColor(trkPnt.customColoring);
-                            double t = Math.atan2(screen.y - old.y, screen.x - old.x) + Math.PI;
-                            g.drawLine(screen.x, screen.y, (int) (screen.x + 10 * Math.cos(t - PHI)),
-                                    (int) (screen.y + 10 * Math.sin(t - PHI)));
-                            g.drawLine(screen.x, screen.y, (int) (screen.x + 10 * Math.cos(t + PHI)),
-                                    (int) (screen.y + 10 * Math.sin(t + PHI)));
-                            oldA = screen;
-                        }
-                        old = screen;
-                    }
-                } // end for trkpnt
-            } // end for segment
+            for (WayPoint trkPnt : visibleSegments) {
+                LatLon c = trkPnt.getCoor();
+                if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
+                    continue;
+                }
+                if (trkPnt.drawLine) {
+                    Point screen = mv.getPoint(trkPnt.getEastNorth());
+                    // skip points that are on the same screenposition
+                    if (old != null
+                            && (oldA == null || screen.x < oldA.x - delta || screen.x > oldA.x + delta
+                                    || screen.y < oldA.y - delta || screen.y > oldA.y + delta)) {
+                        g.setColor(trkPnt.customColoring);
+                        double t = Math.atan2(screen.y - old.y, screen.x - old.x) + Math.PI;
+                        g.drawLine(screen.x, screen.y, (int) (screen.x + 10 * Math.cos(t - PHI)),
+                                (int) (screen.y + 10 * Math.sin(t - PHI)));
+                        g.drawLine(screen.x, screen.y, (int) (screen.x + 10 * Math.cos(t + PHI)),
+                                (int) (screen.y + 10 * Math.sin(t + PHI)));
+                        oldA = screen;
+                    }
+                    old = screen;
+                }
+            } // end for trkpnt
         } // end if lines
 
@@ -532,27 +549,25 @@
             Point old = null;
             Point oldA = null; // last arrow painted
-            for (Collection<WayPoint> segment : visibleSegments) {
-                for (WayPoint trkPnt : segment) {
-                    LatLon c = trkPnt.getCoor();
-                    if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
-                        continue;
-                    }
-                    if (trkPnt.drawLine) {
-                        Point screen = mv.getPoint(trkPnt.getEastNorth());
-                        // skip points that are on the same screenposition
-                        if (old != null
-                                && (oldA == null || screen.x < oldA.x - delta || screen.x > oldA.x + delta
-                                        || screen.y < oldA.y - delta || screen.y > oldA.y + delta)) {
-                            g.setColor(trkPnt.customColoring);
-                            g.drawLine(screen.x, screen.y, screen.x + dir[trkPnt.dir][0], screen.y
-                                    + dir[trkPnt.dir][1]);
-                            g.drawLine(screen.x, screen.y, screen.x + dir[trkPnt.dir][2], screen.y
-                                    + dir[trkPnt.dir][3]);
-                            oldA = screen;
-                        }
-                        old = screen;
-                    }
-                } // end for trkpnt
-            } // end for segment
+            for (WayPoint trkPnt : visibleSegments) {
+                LatLon c = trkPnt.getCoor();
+                if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
+                    continue;
+                }
+                if (trkPnt.drawLine) {
+                    Point screen = mv.getPoint(trkPnt.getEastNorth());
+                    // skip points that are on the same screenposition
+                    if (old != null
+                            && (oldA == null || screen.x < oldA.x - delta || screen.x > oldA.x + delta
+                                    || screen.y < oldA.y - delta || screen.y > oldA.y + delta)) {
+                        g.setColor(trkPnt.customColoring);
+                        g.drawLine(screen.x, screen.y, screen.x + dir[trkPnt.dir][0], screen.y
+                                + dir[trkPnt.dir][1]);
+                        g.drawLine(screen.x, screen.y, screen.x + dir[trkPnt.dir][2], screen.y
+                                + dir[trkPnt.dir][3]);
+                        oldA = screen;
+                    }
+                    old = screen;
+                }
+            } // end for trkpnt
         } // end if lines
 
@@ -562,27 +577,25 @@
         if (large || hdopcircle) {
             g.setColor(neutralColor);
-            for (Collection<WayPoint> segment : visibleSegments) {
-                for (WayPoint trkPnt : segment) {
-                    LatLon c = trkPnt.getCoor();
-                    if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
-                        continue;
-                    }
-                    Point screen = mv.getPoint(trkPnt.getEastNorth());
-                    g.setColor(trkPnt.customColoring);
-                    if (hdopcircle && trkPnt.attr.get("hdop") != null) {
-                        // hdop value
-                        float hdop = ((Float)trkPnt.attr.get("hdop")).floatValue();
-                        if (hdop < 0) {
-                            hdop = 0;
-                        }
-                        // hdop pixels
-                        int hdopp = mv.getPoint(new LatLon(trkPnt.getCoor().lat(), trkPnt.getCoor().lon() + 2*6*hdop*360/40000000)).x - screen.x;
-                        g.drawArc(screen.x-hdopp/2, screen.y-hdopp/2, hdopp, hdopp, 0, 360);
-                    }
-                    if (large) {
-                        g.fillRect(screen.x-1, screen.y-1, 3, 3);
-                    }
-                } // end for trkpnt
-            } // end for segment
+            for (WayPoint trkPnt : visibleSegments) {
+                LatLon c = trkPnt.getCoor();
+                if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
+                    continue;
+                }
+                Point screen = mv.getPoint(trkPnt.getEastNorth());
+                g.setColor(trkPnt.customColoring);
+                if (hdopcircle && trkPnt.attr.get("hdop") != null) {
+                    // hdop value
+                    float hdop = ((Float)trkPnt.attr.get("hdop")).floatValue();
+                    if (hdop < 0) {
+                        hdop = 0;
+                    }
+                    // hdop pixels
+                    int hdopp = mv.getPoint(new LatLon(trkPnt.getCoor().lat(), trkPnt.getCoor().lon() + 2*6*hdop*360/40000000)).x - screen.x;
+                    g.drawArc(screen.x-hdopp/2, screen.y-hdopp/2, hdopp, hdopp, 0, 360);
+                }
+                if (large) {
+                    g.fillRect(screen.x-1, screen.y-1, 3, 3);
+                }
+            } // end for trkpnt
         } // end if large || hdopcircle
 
@@ -592,16 +605,14 @@
         if (!large && lines) {
             g.setColor(neutralColor);
-            for (Collection<WayPoint> segment : visibleSegments) {
-                for (WayPoint trkPnt : segment) {
-                    LatLon c = trkPnt.getCoor();
-                    if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
-                        continue;
-                    }
-                    if (!trkPnt.drawLine) {
-                        Point screen = mv.getPoint(trkPnt.getEastNorth());
-                        g.drawRect(screen.x, screen.y, 0, 0);
-                    }
-                } // end for trkpnt
-            } // end for segment
+            for (WayPoint trkPnt : visibleSegments) {
+                LatLon c = trkPnt.getCoor();
+                if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
+                    continue;
+                }
+                if (!trkPnt.drawLine) {
+                    Point screen = mv.getPoint(trkPnt.getEastNorth());
+                    g.drawRect(screen.x, screen.y, 0, 0);
+                }
+            } // end for trkpnt
         } // end if large
 
@@ -611,15 +622,13 @@
         if (!large && !lines) {
             g.setColor(neutralColor);
-            for (Collection<WayPoint> segment : visibleSegments) {
-                for (WayPoint trkPnt : segment) {
-                    LatLon c = trkPnt.getCoor();
-                    if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
-                        continue;
-                    }
-                    Point screen = mv.getPoint(trkPnt.getEastNorth());
-                    g.setColor(trkPnt.customColoring);
-                    g.drawRect(screen.x, screen.y, 0, 0);
-                } // end for trkpnt
-            } // end for segment
+            for (WayPoint trkPnt : visibleSegments) {
+                LatLon c = trkPnt.getCoor();
+                if (Double.isNaN(c.lat()) || Double.isNaN(c.lon())) {
+                    continue;
+                }
+                Point screen = mv.getPoint(trkPnt.getEastNorth());
+                g.setColor(trkPnt.customColoring);
+                g.drawRect(screen.x, screen.y, 0, 0);
+            } // end for trkpnt
         } // end if large
 
