/* ============================================================ * * This file is a part of kipi-plugins project * http://www.kipi-plugins.org * * Date : 2006-10-18 * Description : EXIF date and time settings page. * * Copyright (C) 2006-2007 by Gilles Caulier * * This program is free software; you can redistribute it * and/or modify it under the terms of the GNU General * Public License as published by the Free Software Foundation; * either version 2, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * ============================================================ */ // QT includes. #include #include #include #include #include // KDE includes. #include #include #include #include #include #include #include // LibKExiv2 includes. #include // Local includes. #include "exifdatetime.h" #include "exifdatetime.moc" namespace KIPIMetadataEditPlugin { class EXIFDateTimePriv { public: EXIFDateTimePriv() { dateCreatedSel = 0; dateOriginalSel = 0; dateDigitalizedSel = 0; dateCreatedSubSecEdit = 0; dateOriginalSubSecEdit = 0; dateDigitalizedSubSecEdit = 0; dateCreatedCheck = 0; dateOriginalCheck = 0; dateDigitalizedCheck = 0; dateCreatedSubSecCheck = 0; dateOriginalSubSecCheck = 0; dateDigitalizedSubSecCheck = 0; syncHOSTDateCheck = 0; syncIPTCDateCheck = 0; } TQCheckBox *dateCreatedCheck; TQCheckBox *dateOriginalCheck; TQCheckBox *dateDigitalizedCheck; TQCheckBox *dateCreatedSubSecCheck; TQCheckBox *dateOriginalSubSecCheck; TQCheckBox *dateDigitalizedSubSecCheck; TQCheckBox *syncHOSTDateCheck; TQCheckBox *syncIPTCDateCheck; KIntSpinBox *dateCreatedSubSecEdit; KIntSpinBox *dateOriginalSubSecEdit; KIntSpinBox *dateDigitalizedSubSecEdit; KDateTimeWidget *dateCreatedSel; KDateTimeWidget *dateOriginalSel; KDateTimeWidget *dateDigitalizedSel; }; EXIFDateTime::EXIFDateTime(TQWidget* parent) : TQWidget(parent) { d = new EXIFDateTimePriv; TQGridLayout* grid = new TQGridLayout(parent, 9, 3, KDialog::spacingHint()); // -------------------------------------------------------- d->dateCreatedCheck = new TQCheckBox(i18n("Creation date and time"), parent); d->dateCreatedSubSecCheck = new TQCheckBox(i18n("Creation sub-second"), parent); d->dateCreatedSel = new KDateTimeWidget(parent); d->dateCreatedSubSecEdit = new KIntSpinBox(0, 999, 1, 0, 10, parent); d->dateCreatedSel->setDateTime(TQDateTime::currentDateTime()); d->syncHOSTDateCheck = new TQCheckBox(i18n("Sync creation date entered through %1") .arg(TDEApplication::kApplication()->aboutData()->appName()), parent); d->syncIPTCDateCheck = new TQCheckBox(i18n("Sync IPTC creation date"), parent); KSeparator *line = new KSeparator(Horizontal, parent); grid->addMultiCellWidget(d->dateCreatedCheck, 0, 0, 0, 0); grid->addMultiCellWidget(d->dateCreatedSubSecCheck, 0, 0, 1, 2); grid->addMultiCellWidget(d->dateCreatedSel, 1, 1, 0, 0); grid->addMultiCellWidget(d->dateCreatedSubSecEdit, 1, 1, 1, 1); grid->addMultiCellWidget(d->syncHOSTDateCheck, 2, 2, 0, 3); grid->addMultiCellWidget(d->syncIPTCDateCheck, 3, 3, 0, 3); grid->addMultiCellWidget(line, 4, 4, 0, 3); TQWhatsThis::add(d->dateCreatedSel, i18n("

Set here the date and time of image creation. " "In this standard it is the date and time the file was changed.")); TQWhatsThis::add(d->dateCreatedSubSecEdit, i18n("

Set here the fractions of seconds for the date " "and time of image creation.")); // -------------------------------------------------------- d->dateOriginalCheck = new TQCheckBox(i18n("Original date and time"), parent); d->dateOriginalSubSecCheck = new TQCheckBox(i18n("Original sub-second"), parent); d->dateOriginalSel = new KDateTimeWidget(parent); d->dateOriginalSubSecEdit = new KIntSpinBox(0, 999, 1, 0, 10, parent); d->dateOriginalSel->setDateTime(TQDateTime::currentDateTime()); grid->addMultiCellWidget(d->dateOriginalCheck, 5, 5, 0, 0); grid->addMultiCellWidget(d->dateOriginalSubSecCheck, 5, 5, 1, 2); grid->addMultiCellWidget(d->dateOriginalSel, 6, 6, 0, 0); grid->addMultiCellWidget(d->dateOriginalSubSecEdit, 6, 6, 1, 1); TQWhatsThis::add(d->dateOriginalSel, i18n("

Set here the date and time when the original image " "data was generated. For a digital still camera the date and " "time the picture was taken are recorded.")); TQWhatsThis::add(d->dateOriginalSubSecEdit, i18n("

Set here the fractions of seconds for the date " "and time when the original image data was generated.")); // -------------------------------------------------------- d->dateDigitalizedCheck = new TQCheckBox(i18n("Digitization date and time"), parent); d->dateDigitalizedSubSecCheck = new TQCheckBox(i18n("Digitization sub-second"), parent); d->dateDigitalizedSel = new KDateTimeWidget(parent); d->dateDigitalizedSubSecEdit = new KIntSpinBox(0, 999, 1, 0, 10, parent); d->dateDigitalizedSel->setDateTime(TQDateTime::currentDateTime()); grid->addMultiCellWidget(d->dateDigitalizedCheck, 7, 7, 0, 0); grid->addMultiCellWidget(d->dateDigitalizedSubSecCheck, 7, 7, 1, 2); grid->addMultiCellWidget(d->dateDigitalizedSel, 8, 8, 0, 0); grid->addMultiCellWidget(d->dateDigitalizedSubSecEdit, 8, 8, 1, 1); TQWhatsThis::add(d->dateDigitalizedSel, i18n("

Set here the date and time when the image was " "stored as digital data. If, for example, an image was " "captured by a digital still camera and at the same " "time the file was recorded, then Original and Digitization " "date and time will have the same contents.")); TQWhatsThis::add(d->dateDigitalizedSubSecEdit, i18n("

Set here the fractions of seconds for the date " "and time when the image was stored as digital data.")); grid->setColStretch(3, 10); grid->setRowStretch(9, 10); // -------------------------------------------------------- connect(d->dateCreatedCheck, TQT_SIGNAL(toggled(bool)), d->dateCreatedSel, TQT_SLOT(setEnabled(bool))); connect(d->dateOriginalCheck, TQT_SIGNAL(toggled(bool)), d->dateOriginalSel, TQT_SLOT(setEnabled(bool))); connect(d->dateDigitalizedCheck, TQT_SIGNAL(toggled(bool)), d->dateDigitalizedSel, TQT_SLOT(setEnabled(bool))); connect(d->dateCreatedSubSecCheck, TQT_SIGNAL(toggled(bool)), d->dateCreatedSubSecEdit, TQT_SLOT(setEnabled(bool))); connect(d->dateOriginalSubSecCheck, TQT_SIGNAL(toggled(bool)), d->dateOriginalSubSecEdit, TQT_SLOT(setEnabled(bool))); connect(d->dateDigitalizedSubSecCheck, TQT_SIGNAL(toggled(bool)), d->dateDigitalizedSubSecEdit, TQT_SLOT(setEnabled(bool))); connect(d->dateCreatedCheck, TQT_SIGNAL(toggled(bool)), d->syncHOSTDateCheck, TQT_SLOT(setEnabled(bool))); connect(d->dateCreatedCheck, TQT_SIGNAL(toggled(bool)), d->syncIPTCDateCheck, TQT_SLOT(setEnabled(bool))); // -------------------------------------------------------- connect(d->dateCreatedCheck, TQT_SIGNAL(toggled(bool)), this, TQT_SIGNAL(signalModified())); connect(d->dateOriginalCheck, TQT_SIGNAL(toggled(bool)), this, TQT_SIGNAL(signalModified())); connect(d->dateDigitalizedCheck, TQT_SIGNAL(toggled(bool)), this, TQT_SIGNAL(signalModified())); connect(d->dateCreatedSubSecCheck, TQT_SIGNAL(toggled(bool)), this, TQT_SIGNAL(signalModified())); connect(d->dateOriginalSubSecCheck, TQT_SIGNAL(toggled(bool)), this, TQT_SIGNAL(signalModified())); connect(d->dateDigitalizedSubSecCheck, TQT_SIGNAL(toggled(bool)), this, TQT_SIGNAL(signalModified())); // -------------------------------------------------------- connect(d->dateCreatedSubSecEdit, TQT_SIGNAL(valueChanged(int)), this, TQT_SIGNAL(signalModified())); connect(d->dateOriginalSubSecEdit, TQT_SIGNAL(valueChanged(int)), this, TQT_SIGNAL(signalModified())); connect(d->dateDigitalizedSubSecEdit, TQT_SIGNAL(valueChanged(int)), this, TQT_SIGNAL(signalModified())); connect(d->dateCreatedSel, TQT_SIGNAL(valueChanged (const TQDateTime &)), this, TQT_SIGNAL(signalModified())); connect(d->dateOriginalSel, TQT_SIGNAL(valueChanged (const TQDateTime &)), this, TQT_SIGNAL(signalModified())); connect(d->dateDigitalizedSel, TQT_SIGNAL(valueChanged (const TQDateTime &)), this, TQT_SIGNAL(signalModified())); } EXIFDateTime::~EXIFDateTime() { delete d; } bool EXIFDateTime::syncHOSTDateIsChecked() { return d->syncHOSTDateCheck->isChecked(); } bool EXIFDateTime::syncIPTCDateIsChecked() { return d->syncIPTCDateCheck->isChecked(); } void EXIFDateTime::setCheckedSyncHOSTDate(bool c) { d->syncHOSTDateCheck->setChecked(c); } void EXIFDateTime::setCheckedSyncIPTCDate(bool c) { d->syncIPTCDateCheck->setChecked(c); } TQDateTime EXIFDateTime::getEXIFCreationDate() { return d->dateCreatedSel->dateTime(); } void EXIFDateTime::readMetadata(TQByteArray& exifData) { blockSignals(true); KExiv2Iface::KExiv2 exiv2Iface; exiv2Iface.setExif(exifData); TQDateTime datetime; TQString datetimeStr, data; d->dateCreatedSel->setDateTime(TQDateTime::currentDateTime()); d->dateCreatedCheck->setChecked(false); datetimeStr = exiv2Iface.getExifTagString("Exif.Image.DateTime", false); if (!datetimeStr.isEmpty()) { datetime = TQDateTime::fromString(datetimeStr, Qt::ISODate); if (datetime.isValid()) { d->dateCreatedSel->setDateTime(datetime); d->dateCreatedCheck->setChecked(true); } } d->dateCreatedSel->setEnabled(d->dateCreatedCheck->isChecked()); d->syncHOSTDateCheck->setEnabled(d->dateCreatedCheck->isChecked()); d->syncIPTCDateCheck->setEnabled(d->dateCreatedCheck->isChecked()); d->dateCreatedSubSecEdit->setValue(0); d->dateCreatedSubSecCheck->setChecked(false); data = exiv2Iface.getExifTagString("Exif.Photo.SubSecTime", false); if (!data.isNull()) { bool ok = false; int subsec = data.toInt(&ok); if (ok) { d->dateCreatedSubSecEdit->setValue(subsec); d->dateCreatedSubSecCheck->setChecked(true); } } d->dateCreatedSubSecEdit->setEnabled(d->dateCreatedSubSecCheck->isChecked()); d->dateOriginalSel->setDateTime(TQDateTime::currentDateTime()); d->dateOriginalCheck->setChecked(false); datetimeStr = exiv2Iface.getExifTagString("Exif.Photo.DateTimeOriginal", false); if (!datetimeStr.isEmpty()) { datetime = TQDateTime::fromString(datetimeStr, Qt::ISODate); if (datetime.isValid()) { d->dateOriginalSel->setDateTime(datetime); d->dateOriginalCheck->setChecked(true); } } d->dateOriginalSel->setEnabled(d->dateOriginalCheck->isChecked()); d->dateOriginalSubSecEdit->setValue(0); d->dateOriginalSubSecCheck->setChecked(false); data = exiv2Iface.getExifTagString("Exif.Photo.SubSecTimeOriginal", false); if (!data.isNull()) { bool ok = false; int subsec = data.toInt(&ok); if (ok) { d->dateOriginalSubSecEdit->setValue(subsec); d->dateOriginalSubSecCheck->setChecked(true); } } d->dateOriginalSubSecEdit->setEnabled(d->dateOriginalSubSecCheck->isChecked()); d->dateDigitalizedSel->setDateTime(TQDateTime::currentDateTime()); d->dateDigitalizedCheck->setChecked(false); datetimeStr = exiv2Iface.getExifTagString("Exif.Photo.DateTimeDigitized", false); if (!datetimeStr.isEmpty()) { datetime = TQDateTime::fromString(datetimeStr, Qt::ISODate); if (datetime.isValid()) { d->dateDigitalizedSel->setDateTime(datetime); d->dateDigitalizedCheck->setChecked(true); } } d->dateDigitalizedSel->setEnabled(d->dateDigitalizedCheck->isChecked()); d->dateDigitalizedSubSecEdit->setValue(0); d->dateDigitalizedSubSecCheck->setChecked(false); data = exiv2Iface.getExifTagString("Exif.Photo.SubSecTimeDigitized", false); if (!data.isNull()) { bool ok = false; int subsec = data.toInt(&ok); if (ok) { d->dateDigitalizedSubSecEdit->setValue(subsec); d->dateDigitalizedSubSecCheck->setChecked(true); } } d->dateDigitalizedSubSecEdit->setEnabled(d->dateDigitalizedSubSecCheck->isChecked()); blockSignals(false); } void EXIFDateTime::applyMetadata(TQByteArray& exifData, TQByteArray& iptcData) { KExiv2Iface::KExiv2 exiv2Iface; exiv2Iface.setExif(exifData); exiv2Iface.setIptc(iptcData); if (d->dateCreatedCheck->isChecked()) { exiv2Iface.setExifTagString("Exif.Image.DateTime", d->dateCreatedSel->dateTime().toString(TQString("yyyy:MM:dd hh:mm:ss")).ascii()); if (syncIPTCDateIsChecked()) { exiv2Iface.setIptcTagString("Iptc.Application2.DateCreated", d->dateCreatedSel->dateTime().date().toString(Qt::ISODate)); exiv2Iface.setIptcTagString("Iptc.Application2.TimeCreated", d->dateCreatedSel->dateTime().time().toString(Qt::ISODate)); } } else exiv2Iface.removeExifTag("Exif.Image.DateTime"); if (d->dateCreatedSubSecCheck->isChecked()) exiv2Iface.setExifTagString("Exif.Photo.SubSecTime", TQString::number(d->dateCreatedSubSecEdit->value()).ascii()); else exiv2Iface.removeExifTag("Exif.Photo.SubSecTime"); if (d->dateOriginalCheck->isChecked()) exiv2Iface.setExifTagString("Exif.Photo.DateTimeOriginal", d->dateOriginalSel->dateTime().toString(TQString("yyyy:MM:dd hh:mm:ss")).ascii()); else exiv2Iface.removeExifTag("Exif.Photo.DateTimeOriginal"); if (d->dateOriginalSubSecCheck->isChecked()) exiv2Iface.setExifTagString("Exif.Photo.SubSecTimeOriginal", TQString::number(d->dateOriginalSubSecEdit->value()).ascii()); else exiv2Iface.removeExifTag("Exif.Photo.SubSecTimeOriginal"); if (d->dateDigitalizedCheck->isChecked()) exiv2Iface.setExifTagString("Exif.Photo.DateTimeDigitized", d->dateDigitalizedSel->dateTime().toString(TQString("yyyy:MM:dd hh:mm:ss")).ascii()); else exiv2Iface.removeExifTag("Exif.Photo.DateTimeDigitized"); if (d->dateDigitalizedSubSecCheck->isChecked()) exiv2Iface.setExifTagString("Exif.Photo.SubSecTimeDigitized", TQString::number(d->dateDigitalizedSubSecEdit->value()).ascii()); else exiv2Iface.removeExifTag("Exif.Photo.SubSecTimeDigitized"); exifData = exiv2Iface.getExif(); iptcData = exiv2Iface.getIptc(); } } // namespace KIPIMetadataEditPlugin