Index: /applications/editors/josm/plugins/public_transport/src/public_transport/RoutePatternAction.java
===================================================================
--- /applications/editors/josm/plugins/public_transport/src/public_transport/RoutePatternAction.java	(revision 27841)
+++ /applications/editors/josm/plugins/public_transport/src/public_transport/RoutePatternAction.java	(revision 27842)
@@ -286,10 +286,10 @@
     }
 
-    public void addRow(Node node, String role) {
-      insertRow(-1, node, role);
-    }
-
-    public void insertRow(int insPos, Node node, String role) {
-      String[] buf = { "", "", "" };
+    public void addRow(Node node, String role, double distance) {
+      insertRow(-1, node, role, distance);
+    }
+
+    public void insertRow(int insPos, Node node, String role, double distance) {
+      String[] buf = { "", "", "", "" };
       String curName = node.get("name");
       if (curName != null)
@@ -307,4 +307,6 @@
       }
       buf[STOPLIST_ROLE_COLUMN] = role;
+      buf[3] = Double.toString(((double)(int)(distance*40000/360.0*100))/100);
+
       if (insPos == -1)
       {
@@ -340,6 +342,10 @@
     public double length;
     public double d1, d2, o1, o2;
-
-    public SegmentMetric(double fromLat, double fromLon, double toLat, double toLon) {
+    public double distance;
+
+    public SegmentMetric(double fromLat, double fromLon, double toLat, double toLon,
+                         double distance) {
+      this.distance = distance;
+
       aLat = fromLat;
       aLon = fromLon;
@@ -415,4 +421,5 @@
   private static JTextField tfSuggestStopsLimit = null;
   private static Relation currentRoute = null;
+  private static Vector< SegmentMetric > segmentMetrics = null;
   private static Vector< RelationMember > markedWays = new Vector< RelationMember >();
   private static Vector< RelationMember > markedNodes = new Vector< RelationMember >();
@@ -863,4 +870,5 @@
       stoplistData.addColumn(tr("Ref"));
       stoplistData.addColumn(tr("Role"));
+      stoplistData.addColumn(tr("km"));
       stoplistTable.setModel(stoplistData);
       /*JScrollPane*/ tableSP = new JScrollPane(stoplistTable);
@@ -1286,4 +1294,5 @@
 
       itineraryData.cleanupGaps();
+      segmentMetrics = fillSegmentMetrics();
       rebuildWays();
     }
@@ -1300,4 +1309,5 @@
 
       itineraryData.cleanupGaps();
+      segmentMetrics = fillSegmentMetrics();
       rebuildWays();
     }
@@ -1377,4 +1387,5 @@
 
       itineraryData.cleanupGaps();
+      segmentMetrics = fillSegmentMetrics();
       rebuildWays();
     }
@@ -1444,4 +1455,5 @@
 
       itineraryData.cleanupGaps();
+      segmentMetrics = fillSegmentMetrics();
       rebuildWays();
     }
@@ -1529,5 +1541,10 @@
         if ((curMember.isNode()) && (mainDataSet.isSelected(curMember.getNode())))
         {
-          stoplistData.insertRow(insPos, curMember.getNode(), curMember.getRole());
+          StopReference sr = detectMinDistance
+              (curMember.getNode(), segmentMetrics, cbRight.isSelected(), cbLeft.isSelected());
+          double offset = segmentMetrics.elementAt((sr.index+1) / 2).distance;
+          if (sr.index % 2 == 0)
+            offset += sr.pos;
+          stoplistData.insertRow(insPos, curMember.getNode(), curMember.getRole(), offset);
           if (insPos >= 0)
             ++insPos;
@@ -1545,5 +1562,10 @@
         if (!(addedNodes.contains(curMember)))
         {
-          stoplistData.insertRow(insPos, curMember, "");
+          StopReference sr = detectMinDistance
+              (curMember, segmentMetrics, cbRight.isSelected(), cbLeft.isSelected());
+          double offset = segmentMetrics.elementAt((sr.index+1) / 2).distance;
+          if (sr.index % 2 == 0)
+            offset += sr.pos;
+          stoplistData.insertRow(insPos, curMember, "", offset);
           if (insPos >= 0)
             ++insPos;
@@ -1580,40 +1602,4 @@
       // Prepare Segments: The segments of all usable ways are arranged in a linear
       // list such that a coor can directly be checked concerning position and offset
-      Vector<SegmentMetric> segmentMetrics = new Vector<SegmentMetric>();
-      for (int i = 0; i < itineraryData.getRowCount(); ++i)
-      {
-        if (itineraryData.ways.elementAt(i) != null)
-        {
-          Way way = itineraryData.ways.elementAt(i);
-          if (!(way.isIncomplete()))
-          {
-            if ("backward".equals((String)(itineraryData.getValueAt(i, 1))))
-            {
-              for (int j = way.getNodesCount()-2; j >= 0; --j)
-              {
-            SegmentMetric sm = new SegmentMetric
-                (way.getNode(j+1).getCoor().lat(), way.getNode(j+1).getCoor().lon(),
-                way.getNode(j).getCoor().lat(), way.getNode(j).getCoor().lon());
-            segmentMetrics.add(sm);
-              }
-            }
-            else
-            {
-              for (int j = 0; j < way.getNodesCount()-1; ++j)
-              {
-            SegmentMetric sm = new SegmentMetric
-                (way.getNode(j).getCoor().lat(), way.getNode(j).getCoor().lon(),
-                way.getNode(j+1).getCoor().lat(), way.getNode(j+1).getCoor().lon());
-            segmentMetrics.add(sm);
-              }
-            }
-          }
-        }
-        else
-        {
-          segmentMetrics.add(null);
-        }
-      }
-
       Vector< StopReference > srm = new Vector< StopReference >();
       int insPos = stoplistTable.getSelectedRow();
@@ -1686,5 +1672,10 @@
       for (int i = 0; i < srm.size(); ++i)
       {
-        stoplistData.insertRow(insPos, srm.elementAt(i).node, srm.elementAt(i).role);
+        StopReference sr = detectMinDistance
+            (srm.elementAt(i).node, segmentMetrics, cbRight.isSelected(), cbLeft.isSelected());
+        double offset = segmentMetrics.elementAt((sr.index+1) / 2).distance;
+        if (sr.index % 2 == 0)
+          offset += sr.pos;
+        stoplistData.insertRow(insPos, srm.elementAt(i).node, srm.elementAt(i).role, offset);
         if (insPos >= 0)
           ++insPos;
@@ -1695,5 +1686,6 @@
     else if ("routePattern.stoplistReflect".equals(event.getActionCommand()))
     {
-      Vector<RelationMember> itemsToReflect = new Vector<RelationMember>();
+      Vector< RelationMember > itemsToReflect = new Vector< RelationMember >();
+      Vector< Double > distancesToReflect = new Vector< Double >();
       int insPos = stoplistTable.getSelectedRow();
 
@@ -1706,5 +1698,5 @@
             String role = (String)(stoplistData.getValueAt(i, STOPLIST_ROLE_COLUMN));
             RelationMember markedNode = new RelationMember
-            (role, stoplistData.nodes.elementAt(i));
+                (role, stoplistData.nodes.elementAt(i));
             itemsToReflect.addElement(markedNode);
 
@@ -1734,5 +1726,10 @@
         if (curMember.isNode())
         {
-          stoplistData.insertRow(insPos, curMember.getNode(), curMember.getRole());
+          StopReference sr = detectMinDistance
+              (curMember.getNode(), segmentMetrics, cbRight.isSelected(), cbLeft.isSelected());
+          double offset = segmentMetrics.elementAt((sr.index+1) / 2).distance;
+          if (sr.index % 2 == 0)
+            offset += sr.pos;
+          stoplistData.insertRow(insPos, curMember.getNode(), curMember.getRole(), offset);
           if (insPos >= 0)
             ++insPos;
@@ -1748,40 +1745,4 @@
       // Prepare Segments: The segments of all usable ways are arranged in a linear
       // list such that a coor can directly be checked concerning position and offset
-      Vector<SegmentMetric> segmentMetrics = new Vector<SegmentMetric>();
-      for (int i = 0; i < itineraryData.getRowCount(); ++i)
-      {
-        if (itineraryData.ways.elementAt(i) != null)
-        {
-          Way way = itineraryData.ways.elementAt(i);
-          if (!(way.isIncomplete()))
-          {
-            if ("backward".equals((String)(itineraryData.getValueAt(i, 1))))
-            {
-              for (int j = way.getNodesCount()-2; j >= 0; --j)
-              {
-            SegmentMetric sm = new SegmentMetric
-                (way.getNode(j+1).getCoor().lat(), way.getNode(j+1).getCoor().lon(),
-                way.getNode(j).getCoor().lat(), way.getNode(j).getCoor().lon());
-            segmentMetrics.add(sm);
-              }
-            }
-            else
-            {
-              for (int j = 0; j < way.getNodesCount()-1; ++j)
-              {
-            SegmentMetric sm = new SegmentMetric
-                (way.getNode(j).getCoor().lat(), way.getNode(j).getCoor().lon(),
-                way.getNode(j+1).getCoor().lat(), way.getNode(j+1).getCoor().lon());
-            segmentMetrics.add(sm);
-              }
-            }
-          }
-        }
-        else
-        {
-          segmentMetrics.add(null);
-        }
-      }
-
       Vector< StopReference > srm = new Vector< StopReference >();
       // Determine for each member its position on the itinerary: position means here the
@@ -1848,8 +1809,4 @@
       }
 
-      /*for (int i = 0; i < stoplistData.getRowCount(); ++i)
-      {
-      }*/
-
       Collections.sort(srm);
 
@@ -1857,5 +1814,10 @@
       for (int i = 0; i < srm.size(); ++i)
       {
-        stoplistData.addRow(srm.elementAt(i).node, srm.elementAt(i).role);
+        StopReference sr = detectMinDistance
+            (srm.elementAt(i).node, segmentMetrics, cbRight.isSelected(), cbLeft.isSelected());
+        double offset = segmentMetrics.elementAt((sr.index+1) / 2).distance;
+        if (sr.index % 2 == 0)
+          offset += sr.pos;
+        stoplistData.addRow(srm.elementAt(i).node, srm.elementAt(i).role, offset);
       }
 
@@ -2142,4 +2104,5 @@
     }
     itineraryData.cleanupGaps();
+    segmentMetrics = fillSegmentMetrics();
   }
 
@@ -2151,9 +2114,60 @@
       if (curMember.isNode())
       {
-    stoplistData.insertRow(insPos, curMember.getNode(), curMember.getRole());
-    if (insPos >= 0)
-      ++insPos;
-      }
-    }
+        StopReference sr = detectMinDistance
+            (curMember.getNode(), segmentMetrics, cbRight.isSelected(), cbLeft.isSelected());
+        double offset = segmentMetrics.elementAt((sr.index+1) / 2).distance;
+        System.out.print(sr.index);
+        System.out.print(" ");
+        System.out.print(offset);
+        System.out.print(" ");
+        System.out.println(sr.pos);
+        if (sr.index % 2 == 0)
+          offset += sr.pos;
+        stoplistData.insertRow(insPos, curMember.getNode(), curMember.getRole(), offset);
+        if (insPos >= 0)
+          ++insPos;
+      }
+    }
+  }
+
+  private Vector< SegmentMetric > fillSegmentMetrics()
+  {
+    Vector< SegmentMetric > segmentMetrics = new Vector< SegmentMetric >();
+    double distance = 0;
+    for (int i = 0; i < itineraryData.getRowCount(); ++i)
+    {
+      if (itineraryData.ways.elementAt(i) != null)
+      {
+        Way way = itineraryData.ways.elementAt(i);
+        if (!(way.isIncomplete()))
+        {
+          if ("backward".equals((String)(itineraryData.getValueAt(i, 1))))
+          {
+            for (int j = way.getNodesCount()-2; j >= 0; --j)
+            {
+              SegmentMetric sm = new SegmentMetric
+                  (way.getNode(j+1).getCoor().lat(), way.getNode(j+1).getCoor().lon(),
+                  way.getNode(j).getCoor().lat(), way.getNode(j).getCoor().lon(), distance);
+              segmentMetrics.add(sm);
+              distance += sm.length;
+            }
+          }
+          else
+          {
+            for (int j = 0; j < way.getNodesCount()-1; ++j)
+            {
+              SegmentMetric sm = new SegmentMetric
+                  (way.getNode(j).getCoor().lat(), way.getNode(j).getCoor().lon(),
+                  way.getNode(j+1).getCoor().lat(), way.getNode(j+1).getCoor().lon(), distance);
+              segmentMetrics.add(sm);
+              distance += sm.length;
+            }
+          }
+        }
+      }
+      else
+        segmentMetrics.add(null);
+    }
+    return segmentMetrics;
   }
 
@@ -2161,4 +2175,7 @@
       (Node node, Vector< SegmentMetric > segmentMetrics,
        boolean rhsPossible, boolean lhsPossible) {
+    if (node == null)
+      return null;
+
     int minIndex = -1;
     double position = -1.0;
