diff options
-rw-r--r-- | CMakeLists.txt | 2 | ||||
-rw-r--r-- | dive.c | 30 | ||||
-rw-r--r-- | dive.h | 9 | ||||
-rw-r--r-- | exif.cpp (renamed from qt-ui/exif.cpp) | 19 | ||||
-rw-r--r-- | exif.h (renamed from qt-ui/exif.h) | 2 | ||||
-rw-r--r-- | qt-ui/divelistview.cpp | 50 | ||||
-rw-r--r-- | qt-ui/simplewidgets.cpp | 21 | ||||
-rw-r--r-- | qthelper.cpp | 20 | ||||
-rw-r--r-- | subsurface.pro | 4 |
9 files changed, 87 insertions, 70 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt index ab46d3748..596d86f6a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -106,6 +106,7 @@ SET(SUBSURFACE_CORE_LIB_SRCS #dirk ported some core functionality to c++. qthelper.cpp divecomputer.cpp + exif.cpp ) #the interface, in C++ @@ -132,7 +133,6 @@ SET(SUBSURFACE_INTERFACE qt-ui/starwidget.cpp qt-ui/subsurfacewebservices.cpp qt-ui/tableview.cpp - qt-ui/exif.cpp qt-ui/divelogimportdialog.cpp qt-ui/tagwidget.cpp qt-ui/groupedlineedit.cpp @@ -2260,14 +2260,26 @@ int average_depth(struct diveplan *dive) return integral / last_time; } -void picture_load_exif_data(struct picture *p) +struct picture *alloc_picture() { - + struct picture *pic = malloc(sizeof(struct picture)); + if (!pic) + exit(1); + memset(pic, 0, sizeof(struct picture)); + return pic; } -struct picture* dive_add_picture(struct dive *d, char *picture) +void dive_add_picture(struct dive *d, struct picture *picture) { - + if (d->picture_list == NULL) { + d->picture_list = picture; + return; + } + struct picture *last = d->picture_list; + while( last->next ) + last = last->next; + last->next = picture; + return; } uint dive_get_picture_count(struct dive *d) @@ -2278,7 +2290,15 @@ uint dive_get_picture_count(struct dive *d) return i; } -void dive_remove_picture(struct dive *d, char *picture) +void dive_set_geodata_from_picture(struct dive *d, struct picture *pic) +{ + if (!d->latitude.udeg && pic->latitude.udeg) { + d->latitude = pic->latitude; + d->longitude = pic->longitude; + } +} + +void dive_remove_picture(struct dive *d, struct picture *p) { } @@ -286,16 +286,21 @@ struct dive { struct picture { char *filename; time_t timestamp; + degrees_t latitude; + degrees_t longitude; struct picture *next; }; #define FOR_EACH_PICTURE( DIVE ) \ for(struct picture *picture = DIVE->picture_list; picture; picture = picture->next) -extern struct picture *dive_add_picture(struct dive *d, char *picture); -extern void dive_remove_picture(struct dive *d, char *picture); + +extern struct picture *alloc_picture(); +extern void dive_add_picture(struct dive *d, struct picture *pic); +extern void dive_remove_picture(struct dive *d, struct picture *pic); extern uint dive_get_picture_count(struct dive *d); extern void picture_load_exif_data(struct picture *p); +extern void dive_set_geodata_from_picture(struct dive *d, struct picture *pic); static inline int dive_has_gps_location(struct dive *dive) diff --git a/qt-ui/exif.cpp b/exif.cpp index 1aee47acb..0b1cda2bc 100644 --- a/qt-ui/exif.cpp +++ b/exif.cpp @@ -30,6 +30,7 @@ EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #include <algorithm> +#include "dive.h" #include "exif.h" using std::string; @@ -566,3 +567,21 @@ void EXIFInfo::clear() GeoLocation.LonComponents.seconds = 0; GeoLocation.LonComponents.direction = 0; } + +time_t EXIFInfo::epoch() +{ + struct tm tm; + int year, month, day, hour, min, sec; + + if (DateTimeOriginal.size()) + sscanf(DateTimeOriginal.c_str(), "%d:%d:%d %d:%d:%d", &year, &month, &day, &hour, &min, &sec); + else + sscanf(DateTime.c_str(), "%d:%d:%d %d:%d:%d", &year, &month, &day, &hour, &min, &sec); + tm.tm_year = year; + tm.tm_mon = month - 1; + tm.tm_mday = day; + tm.tm_hour = hour; + tm.tm_min = min; + tm.tm_sec = sec; + return (utc_mktime(&tm)); +} @@ -129,6 +129,8 @@ public: { clear(); } + + time_t epoch(); }; // Parse was successful diff --git a/qt-ui/divelistview.cpp b/qt-ui/divelistview.cpp index 837886187..57ad3f21f 100644 --- a/qt-ui/divelistview.cpp +++ b/qt-ui/divelistview.cpp @@ -764,63 +764,33 @@ void DiveListView::shiftTimes() void DiveListView::loadImages() { - struct memblock mem; - EXIFInfo exif; - int retval; - time_t imagetime; - struct divecomputer *dc; - time_t when; - int duration_s; QStringList fileNames = QFileDialog::getOpenFileNames(this, tr("Open Image Files"), lastUsedImageDir(), tr("Image Files (*.jpg *.jpeg *.pnm *.tif *.tiff)")); - if (fileNames.isEmpty()) return; updateLastUsedImageDir(QFileInfo(fileNames[0]).dir().path()); - ShiftImageTimesDialog shiftDialog(this); shiftDialog.setOffset(lastImageTimeOffset()); shiftDialog.exec(); updateLastImageTimeOffset(shiftDialog.amount()); - for (int i = 0; i < fileNames.size(); ++i) { - if (readfile(fileNames.at(i).toUtf8().data(), &mem) <= 0) - continue; - //TODO: This inner code should be ported to C-Code. - retval = exif.parseFrom((const unsigned char *)mem.buffer, (unsigned)mem.size); - free(mem.buffer); - if (retval != PARSE_EXIF_SUCCESS) - continue; - imagetime = shiftDialog.epochFromExiv(&exif); - if (!imagetime) - continue; - imagetime += shiftDialog.amount(); // TODO: this should be cached and passed to the C-function + Q_FOREACH(const QString& fileName, fileNames) { + picture *p = alloc_picture(); + p->filename = qstrdup(fileName.toUtf8().data()); + picture_load_exif_data(p); + + if (p->timestamp) + p->timestamp += shiftDialog.amount(); // TODO: this should be cached and passed to the C-function int j = 0; struct dive *dive; for_each_dive (j, dive) { if (!dive->selected) continue; - for_each_dc (dive, dc) { - when = dc->when ? dc->when : dive->when; - duration_s = dc->duration.seconds ? dc->duration.seconds : dive->duration.seconds; - if (when - 3600 < imagetime && when + duration_s + 3600 > imagetime) { - if (when > imagetime) { - // Before dive - add_event(dc, 0, 123, 0, 0, fileNames.at(i).toUtf8().data()); - } else if (when + duration_s < imagetime) { - // After dive - add_event(dc, duration_s, 123, 0, 0, fileNames.at(i).toUtf8().data()); - } else { - add_event(dc, imagetime - when, 123, 0, 0, fileNames.at(i).toUtf8().data()); - } - if (!dive->latitude.udeg && !IS_FP_SAME(exif.GeoLocation.Latitude, 0.0)) { - dive->latitude.udeg = lrint(1000000.0 * exif.GeoLocation.Latitude); - dive->longitude.udeg = lrint(1000000.0 * exif.GeoLocation.Longitude); - } - } - } + dive_add_picture(dive, p); + dive_set_geodata_from_picture(dive, p); } } + mark_divelist_changed(true); MainWindow::instance()->refreshDisplay(); MainWindow::instance()->graphics()->replot(); diff --git a/qt-ui/simplewidgets.cpp b/qt-ui/simplewidgets.cpp index 18e176b0d..bb6d2ff2d 100644 --- a/qt-ui/simplewidgets.cpp +++ b/qt-ui/simplewidgets.cpp @@ -247,31 +247,12 @@ void ShiftImageTimesDialog::syncCameraClicked() free(mem.buffer); if (retval != PARSE_EXIF_SUCCESS) return; - dcImageEpoch = epochFromExiv(&exiv); + dcImageEpoch = exiv.epoch(); dcDateTime.setTime_t(dcImageEpoch); ui.dcTime->setDateTime(dcDateTime); connect(ui.dcTime, SIGNAL(dateTimeChanged(const QDateTime &)), this, SLOT(dcDateTimeChanged(const QDateTime &))); } -//TODO: This should be moved to C-Code. -time_t ShiftImageTimesDialog::epochFromExiv(EXIFInfo *exif) -{ - struct tm tm; - int year, month, day, hour, min, sec; - - if (strlen(exif->DateTimeOriginal.c_str())) - sscanf(exif->DateTimeOriginal.c_str(), "%d:%d:%d %d:%d:%d", &year, &month, &day, &hour, &min, &sec); - else - sscanf(exif->DateTime.c_str(), "%d:%d:%d %d:%d:%d", &year, &month, &day, &hour, &min, &sec); - tm.tm_year = year; - tm.tm_mon = month - 1; - tm.tm_mday = day; - tm.tm_hour = hour; - tm.tm_min = min; - tm.tm_sec = sec; - return (utc_mktime(&tm)); -} - void ShiftImageTimesDialog::dcDateTimeChanged(const QDateTime &newDateTime) { if (!dcImageEpoch) diff --git a/qthelper.cpp b/qthelper.cpp index d8626f9d7..1dd25e241 100644 --- a/qthelper.cpp +++ b/qthelper.cpp @@ -1,5 +1,8 @@ #include "qthelper.h" #include "qt-gui.h" +#include "dive.h" +#include <exif.h> +#include "file.h" #include <QRegExp> #include <QDir> @@ -260,3 +263,20 @@ extern "C" xsltStylesheetPtr get_stylesheet(const char *name) return xslt; } + +extern "C" void picture_load_exif_data(struct picture *p) +{ + EXIFInfo exif; + memblock mem; + + if (readfile(p->filename, &mem) <= 0) + goto picture_load_exit; + if (exif.parseFrom((const unsigned char *)mem.buffer, (unsigned)mem.size) != PARSE_EXIF_SUCCESS) + goto picture_load_exit; + p->timestamp = exif.epoch(); + p->longitude.udeg= lrint(1000000.0 * exif.GeoLocation.Longitude); + p->latitude.udeg = lrint(1000000.0 * exif.GeoLocation.Latitude); + picture_load_exit: + free(mem.buffer); + return; +} diff --git a/subsurface.pro b/subsurface.pro index 462344832..a0891f4d7 100644 --- a/subsurface.pro +++ b/subsurface.pro @@ -58,7 +58,7 @@ HEADERS = \ qt-ui/starwidget.h \ qt-ui/subsurfacewebservices.h \ qt-ui/tableview.h \ - qt-ui/exif.h \ + exif.h \ sha1.h \ statistics.h \ subsurfacestartup.h \ @@ -131,7 +131,7 @@ SOURCES = \ qt-ui/starwidget.cpp \ qt-ui/subsurfacewebservices.cpp \ qt-ui/tableview.cpp \ - qt-ui/exif.cpp \ + exif.cpp \ save-git.c \ save-xml.c \ sha1.c \ |