/** * Match a list of photos to a gpx track with a given offset. All images need a exifTime attribute * and the List must be sorted according to these times. * * @param images images to match * @param selectedGpx selected GPX data * @param offset offset * @return number of matched points */ static int matchGpxTrack(List<ImageEntry> images, GpxData selectedGpx, long offset) { int ret = 0; for (GpxTrack trk : selectedGpx.tracks) { for (GpxTrackSegment segment : trk.getSegments()) { long prevWpTime = 0; WayPoint prevWp = null; for (WayPoint curWp : segment.getWayPoints()) { try { final Date parsedTime = curWp.setTimeFromAttribute(); if (parsedTime != null) { final long curWpTime = parsedTime.getTime() + offset; ret += matchPoints(images, prevWp, prevWpTime, curWp, curWpTime, offset); prevWp = curWp; prevWpTime = curWpTime; continue; } } catch (Exception e) { Main.warn(e); } prevWp = null; prevWpTime = 0; } } } return ret; }
@Override public void actionPerformed(ActionEvent arg0) { GpxDataWrapper gpxW = selectedGPX(true); if (gpxW == null) return; GpxData gpx = gpxW.data; List<ImageEntry> imgs = getSortedImgList(); // no images found, exit if (imgs.isEmpty()) { JOptionPane.showMessageDialog( Main.parent, tr("The selected photos do not contain time information."), tr("Photos do not contain time information"), JOptionPane.WARNING_MESSAGE); return; } // Init variables long firstExifDate = imgs.get(0).getExifTime().getTime() / 1000; long firstGPXDate = -1; // Finds first GPX point outer: for (GpxTrack trk : gpx.tracks) { for (GpxTrackSegment segment : trk.getSegments()) { for (WayPoint curWp : segment.getWayPoints()) { try { final Date parsedTime = curWp.setTimeFromAttribute(); if (parsedTime != null) { firstGPXDate = parsedTime.getTime(); break outer; } } catch (Exception e) { Main.warn(e); } } } } // No GPX timestamps found, exit if (firstGPXDate < 0) { JOptionPane.showMessageDialog( Main.parent, tr("The selected GPX track does not contain timestamps. Please select another one."), tr("GPX Track has no time information"), JOptionPane.WARNING_MESSAGE); return; } // seconds long diff = firstExifDate - firstGPXDate; double diffInH = (double) diff / (60 * 60); // hours // Find day difference int dayOffset = (int) Math.round(diffInH / 24); // days double tz = diff - dayOffset * 24 * 60 * 60L; // seconds // In hours, rounded to two decimal places tz = (double) Math.round(tz * 100 / (60 * 60)) / 100; // Due to imprecise clocks we might get a "+3:28" timezone, which should obviously be 3:30 // with // -2 minutes offset. This determines the real timezone and finds offset. timezone = (double) Math.round(tz * 2) / 2; // hours, rounded to one decimal place delta = Math.round(diff - timezone * 60 * 60); // seconds tfTimezone.getDocument().removeDocumentListener(statusBarUpdater); tfOffset.getDocument().removeDocumentListener(statusBarUpdater); tfTimezone.setText(formatTimezone(timezone)); tfOffset.setText(Long.toString(delta)); tfOffset.requestFocus(); tfTimezone.getDocument().addDocumentListener(statusBarUpdater); tfOffset.getDocument().addDocumentListener(statusBarUpdater); statusBarUpdater.updateStatusBar(); yLayer.updateBufferAndRepaint(); }