void construct(PlanningSegment seg, WorldLocation origin, HiResDate date) {
      // check we have some data
      if (date == null || origin == null) return;

      double timeTravelledMillis = getSecsTravelled(seg) * 1000;

      // ditch the existing items
      seg.removeAllElements();

      // ok build for this segment
      double courseDegs = seg.getCourse();
      double courseRads = MWC.Algorithms.Conversions.Degs2Rads(courseDegs);

      long timeMillis = date.getDate().getTime();
      final long timeStepMillis;
      final long ONE_MIN = 60 * 1000;
      final long ONE_HOUR = 60 * ONE_MIN;
      final long ONE_DAY = 24 * ONE_HOUR;

      // use a time step appropriate to how long we're generating the track for
      if (timeTravelledMillis <= 4 * ONE_HOUR) timeStepMillis = ONE_MIN;
      else if (timeTravelledMillis <= 12 * ONE_HOUR) timeStepMillis = 10 * ONE_MIN;
      else if (timeTravelledMillis <= 2 * ONE_DAY) timeStepMillis = 30 * ONE_MIN;
      else timeStepMillis = ONE_HOUR;

      // now work out how far he will have travelled in a time step
      double distPerMinute = getMinuteDelta(seg);
      double distPerStep = distPerMinute * (timeStepMillis / ONE_MIN);
      WorldVector vec =
          new WorldVector(courseRads, new WorldDistance(distPerStep, WorldDistance.METRES), null);

      for (long tNow = timeMillis;
          tNow <= timeMillis + timeTravelledMillis;
          tNow += timeStepMillis) {
        HiResDate thisDtg = new HiResDate(tNow);

        // ok, do this fix
        Fix thisF =
            new Fix(thisDtg, origin, courseRads, seg.getSpeed().getValueIn(WorldSpeed.ft_sec) / 3);

        // override the depth
        thisF.getLocation().setDepth(seg.getDepth().getValueIn(WorldDistance.METRES));

        FixWrapper fw = new FixWrapper(thisF);

        fw.setColor(seg.getColor());

        // and store it
        seg.add(fw);

        // reset the name, we're not going to use a human generated one
        fw.resetName();

        // produce a new position
        origin = origin.add(vec);
      }
    }
  @Override
  protected void paintThisFix(CanvasType dest, WorldLocation lastLocation, FixWrapper fw) {
    // set the label format to ]my label format
    if (_lastLabelFormat != null) fw.setLabelFormat(_lastLabelFormat);

    // set the fix font-size to be my font-size
    fw.setFont(this.getTrackFont());

    // and now let it paint
    super.paintThisFix(dest, lastLocation, fw);
  }
  @Override
  public void findNearestHotSpotIn(
      Point cursorPos,
      WorldLocation cursorLoc,
      ComponentConstruct currentNearest,
      Layer parentLayer) {
    // initialise thisDist, since we're going to be over-writing it
    WorldDistance thisDist = new WorldDistance(0, WorldDistance.DEGS);

    Enumeration<Editable> numer = getSegments().elements();
    while (numer.hasMoreElements()) {
      final PlanningSegment thisSeg = (PlanningSegment) numer.nextElement();
      if (thisSeg.getVisible()) {
        // produce a location for the end
        FixWrapper endFix = (FixWrapper) thisSeg.last();
        if (endFix != null) {

          // how far away is it?
          thisDist = endFix.getLocation().rangeFrom(cursorLoc, thisDist);

          final WorldLocation fixLocation =
              new WorldLocation(endFix.getLocation()) {
                private static final long serialVersionUID = 1L;

                @Override
                public void addToMe(WorldVector delta) {
                  super.addToMe(delta);

                  // so, what's the bearing back to the leg start?
                  double newBearing = super.bearingFrom(thisSeg.first().getBounds().getCentre());

                  newBearing = MWC.Algorithms.Conversions.Rads2Degs(newBearing);

                  // limit the bearing to the nearest 5 deg marker
                  int m = ((int) newBearing / 10);
                  newBearing = m * 10d;

                  // trim it to being positive
                  if (newBearing < 0) newBearing += 360;

                  thisSeg.setCourse(newBearing);
                }
              };

          // try range
          currentNearest.checkMe(this, thisDist, null, parentLayer, fixLocation);
        }
      }
    }
  }