diff -r -N ./extra/kipi-plugins/metadataedit/CMakeLists.txt ../../digikam/extra/kipi-plugins/metadataedit/CMakeLists.txt
15a16,19
>                                       common/exifeditwidget.cpp
>                                       common/iptceditwidget.cpp
>                                       common/xmpeditwidget.cpp
>                                       common/metadataedit.cpp
diff -r -N ./extra/kipi-plugins/metadataedit/common/exifeditwidget.cpp ../../digikam/extra/kipi-plugins/metadataedit/common/exifeditwidget.cpp
0a1,383
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a KPageWidget to edit EXIF metadata
>  *
>  * Copyright (C) 2006-2010 by Gilles Caulier <caulier dot gilles at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #include "exifeditwidget.moc"
> 
> // Qt includes
> 
> #include <QCloseEvent>
> #include <QKeyEvent>
> 
> // KDE includes
> 
> #include <kapplication.h>
> #include <kconfig.h>
> #include <kdebug.h>
> #include <kguiitem.h>
> #include <khelpmenu.h>
> #include <kiconloader.h>
> #include <klocale.h>
> #include <kmenu.h>
> #include <kmessagebox.h>
> #include <kpushbutton.h>
> #include <ktoolinvocation.h>
> #include <KConfigGroup>
> 
> // LibKIPI includes
> 
> #include <libkipi/imagecollection.h>
> #include <libkipi/imageinfo.h>
> #include <libkipi/interface.h>
> #include <libkipi/plugin.h>
> 
> // LibKExiv2 includes
> 
> #include <libkexiv2/version.h>
> #include <libkexiv2/kexiv2.h>
> 
> // Local includes
> 
> #include "exifadjust.h"
> #include "exifcaption.h"
> #include "exifdatetime.h"
> #include "exifdevice.h"
> #include "exiflens.h"
> #include "exiflight.h"
> #include "kpaboutdata.h"
> #include "pluginsversion.h"
> 
> using namespace KExiv2Iface;
> using namespace KIPIPlugins;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class allEXIFEditWidgetPrivate
> {
> 
> public:
> 
>     allEXIFEditWidgetPrivate()
>     {
>         modified      = false;
>         isReadOnly    = false;
>         interface     = 0;
> 
>         about         = 0;
> 
>         page_caption  = 0;
>         page_datetime = 0;
>         page_lens     = 0;
>         page_device   = 0;
>         page_light    = 0;
>         page_adjust   = 0;
> 
>         captionPage   = 0;
>         datetimePage  = 0;
>         lensPage      = 0;
>         devicePage    = 0;
>         lightPage     = 0;
>         adjustPage    = 0;
>     }
> 
>     bool                      modified;
>     bool                      isReadOnly;
> 
>     QByteArray                exifData;
>     QByteArray                iptcData;
>     QByteArray                xmpData;
> 
>     KPageWidgetItem          *page_caption;
>     KPageWidgetItem          *page_datetime;
>     KPageWidgetItem          *page_lens;
>     KPageWidgetItem          *page_device;
>     KPageWidgetItem          *page_light;
>     KPageWidgetItem          *page_adjust;
> 
>     KUrl::List                urls;
> 
>     KUrl::List::iterator      currItem;
> 
>     EXIFCaption              *captionPage;
>     EXIFDateTime             *datetimePage;
>     EXIFLens                 *lensPage;
>     EXIFDevice               *devicePage;
>     EXIFLight                *lightPage;
>     EXIFAdjust               *adjustPage;
> 
>     Interface                *interface;
> 
>     KPAboutData              *about;
> };
> 
> allEXIFEditWidget::allEXIFEditWidget(QWidget* parent, KUrl::List urls, Interface *iface)
>               : KPageWidget(parent), d(new allEXIFEditWidgetPrivate)
> {
>     d->urls      = urls;
>     d->interface = iface;
>     d->currItem  = d->urls.begin();
> 
>     // ---------------------------------------------------------------
> 
>     d->captionPage   = new EXIFCaption(this);
>     d->page_caption  = addPage(d->captionPage, i18nc("image caption", "Caption"));
>     d->page_caption->setHeader(i18n("Caption Information"));
>     d->page_caption->setIcon(KIcon("edit-rename"));
> 
>     d->datetimePage  = new EXIFDateTime(this);
>     d->page_datetime = addPage(d->datetimePage, i18n("Date & Time"));
>     d->page_datetime->setHeader(i18n("Date and Time Information"));
>     d->page_datetime->setIcon(KIcon("view-calendar-day"));
> 
>     d->lensPage      = new EXIFLens(this);
>     d->page_lens     = addPage(d->lensPage, i18n("Lens"));
>     d->page_lens->setHeader(i18n("Lens Settings"));
>     d->page_lens->setIcon(KIcon("camera-photo"));
> 
>     d->devicePage    = new EXIFDevice(this);
>     d->page_device   = addPage(d->devicePage, i18n("Device"));
>     d->page_device->setHeader(i18n("Capture Device Settings"));
>     d->page_device->setIcon(KIcon("scanner"));
> 
>     d->lightPage     = new EXIFLight(this);
>     d->page_light    = addPage(d->lightPage, i18n("Light"));
>     d->page_light->setHeader(i18n("Light Source Information"));
>     d->page_light->setIcon(KIcon("image-x-generic"));
> 
>     d->adjustPage    = new EXIFAdjust(this);
>     d->page_adjust   = addPage(d->adjustPage, i18nc("Picture adjustments", "Adjustments"));
>     d->page_adjust->setHeader(i18n("Pictures Adjustments"));
>     d->page_adjust->setIcon(KIcon("fill-color"));
> 
>     // ------------------------------------------------------------
> 
>     connect(d->captionPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->datetimePage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->lensPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->devicePage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->lightPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->adjustPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     // ------------------------------------------------------------
> 
>     readSettings();
>     slotItemChanged();
> }
> 
> allEXIFEditWidget::~allEXIFEditWidget()
> {
>     delete d->about;
>     delete d;
> }
> 
> void allEXIFEditWidget::slotClose()
> {
>     saveSettings();
> }
> 
> void allEXIFEditWidget::readSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group("All Metadata Edit Settings");
>     showPage(group.readEntry("All EXIF Edit Page", 0));
>     d->captionPage->setCheckedSyncJFIFComment(group.readEntry("All Sync JFIF Comment", true));
>     d->captionPage->setCheckedSyncHOSTComment(group.readEntry("All Sync Host Comment", true));
>     d->captionPage->setCheckedSyncXMPCaption(group.readEntry("All Sync XMP Caption", true));
>     d->captionPage->setCheckedSyncIPTCCaption(group.readEntry("All Sync IPTC Caption", true));
>     d->datetimePage->setCheckedSyncHOSTDate(group.readEntry("All Sync Host Date", true));
>     d->datetimePage->setCheckedSyncXMPDate(group.readEntry("All Sync XMP Date", true));
>     d->datetimePage->setCheckedSyncIPTCDate(group.readEntry("All Sync IPTC Date", true));
> }
> 
> void allEXIFEditWidget::saveSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group("All Metadata Edit Settings");
>     group.writeEntry("All EXIF Edit Page", activePageIndex());
>     group.writeEntry("All Sync JFIF Comment", d->captionPage->syncJFIFCommentIsChecked());
>     group.writeEntry("All Sync Host Comment", d->captionPage->syncHOSTCommentIsChecked());
>     group.writeEntry("All Sync XMP Caption", d->captionPage->syncXMPCaptionIsChecked());
>     group.writeEntry("All Sync IPTC Caption", d->captionPage->syncIPTCCaptionIsChecked());
>     group.writeEntry("All Sync Host Date", d->datetimePage->syncHOSTDateIsChecked());
>     group.writeEntry("All Sync XMP Date", d->datetimePage->syncXMPDateIsChecked());
>     group.writeEntry("All Sync IPTC Date", d->datetimePage->syncIPTCDateIsChecked());
>     config.sync();
> }
> 
> void allEXIFEditWidget::slotItemChanged()
> {
>     KExiv2 exiv2Iface;
>     exiv2Iface.load((*d->currItem).path());
> 
> #if KEXIV2_VERSION >= 0x010000
>     d->exifData = exiv2Iface.getExifEncoded();
> #else
>     d->exifData = exiv2Iface.getExif();
> #endif
> 
>     d->iptcData = exiv2Iface.getIptc();
>     d->xmpData  = exiv2Iface.getXmp();
>     d->captionPage->readMetadata(d->exifData);
>     d->datetimePage->readMetadata(d->exifData);
>     d->lensPage->readMetadata(d->exifData);
>     d->devicePage->readMetadata(d->exifData);
>     d->lightPage->readMetadata(d->exifData);
>     d->adjustPage->readMetadata(d->exifData);
> 
>     d->isReadOnly = !KExiv2::canWriteExif((*d->currItem).path());
>     emit signalSetReadOnly(d->isReadOnly);
>     d->page_caption->setEnabled(!d->isReadOnly);
>     d->page_datetime->setEnabled(!d->isReadOnly);
>     d->page_lens->setEnabled(!d->isReadOnly);
>     d->page_device->setEnabled(!d->isReadOnly);
>     d->page_light->setEnabled(!d->isReadOnly);
>     d->page_adjust->setEnabled(!d->isReadOnly);
> }
> 
> void allEXIFEditWidget::slotApply()
> {
>     if (d->modified && !d->isReadOnly)
>     {
>         ImageInfo info = d->interface->info(*d->currItem);
> 
>         if (d->captionPage->syncHOSTCommentIsChecked())
>         {
>             info.setDescription(d->captionPage->getEXIFUserComments());
>         }
>         d->captionPage->applyMetadata(d->exifData, d->iptcData, d->xmpData);
> 
>         if (d->datetimePage->syncHOSTDateIsChecked())
>         {
>             info.setTime(d->datetimePage->getEXIFCreationDate());
>         }
>         d->datetimePage->applyMetadata(d->exifData, d->iptcData, d->xmpData);
> 
>         d->lensPage->applyMetadata(d->exifData);
>         d->devicePage->applyMetadata(d->exifData);
>         d->lightPage->applyMetadata(d->exifData);
>         d->adjustPage->applyMetadata(d->exifData);
> 
>         KExiv2 exiv2Iface;
>         exiv2Iface.setWriteRawFiles(d->interface->hostSetting("WriteMetadataToRAW").toBool());
> 
> #if KEXIV2_VERSION >= 0x000600
>         exiv2Iface.setUpdateFileTimeStamp(d->interface->hostSetting("WriteMetadataUpdateFiletimeStamp").toBool());
> #endif
> 
>         exiv2Iface.load((*d->currItem).path());
>         exiv2Iface.setExif(d->exifData);
>         exiv2Iface.setIptc(d->iptcData);
>         exiv2Iface.setXmp(d->xmpData);
>         exiv2Iface.save((*d->currItem).path());
> 
>         d->modified = false;
>     }
> }
> 
> void allEXIFEditWidget::slotUser1()
> {
>     slotApply();
>     d->currItem++;
>     slotItemChanged();
> }
> 
> void allEXIFEditWidget::slotUser2()
> {
>     slotApply();
>     d->currItem--;
>     slotItemChanged();
> }
> 
> void allEXIFEditWidget::slotModified()
> {
>     if (!d->isReadOnly)
>     {
>         d->modified = true;
>         emit signalModified();
>     }
> }
> 
> void allEXIFEditWidget::slotOk()
> {
>     slotApply();
>     saveSettings();
> }
> 
> void allEXIFEditWidget::showPage(int page)
> {
>     switch(page)
>     {
>         case 0:
>             setCurrentPage(d->page_caption);
>             break;
>         case 1:
>             setCurrentPage(d->page_datetime);
>             break;
>         case 2:
>             setCurrentPage(d->page_lens);
>             break;
>         case 3:
>             setCurrentPage(d->page_device);
>             break;
>         case 4:
>             setCurrentPage(d->page_light);
>             break;
>         case 5:
>             setCurrentPage(d->page_adjust);
>             break;
>         default:
>             setCurrentPage(d->page_caption);
>             break;
>     }
> }
> 
> int allEXIFEditWidget::activePageIndex()
> {
>     KPageWidgetItem *cur = currentPage();
> 
>     if (cur == d->page_caption)  return 0;
>     if (cur == d->page_datetime) return 1;
>     if (cur == d->page_lens)     return 2;
>     if (cur == d->page_device)   return 3;
>     if (cur == d->page_light)    return 4;
>     if (cur == d->page_adjust)   return 5;
> 
>     return 0;
> }
> 
> bool allEXIFEditWidget::isModified()
> {
>     return d->modified;
> }
> 
> }  // namespace KIPIMetadataEditPlugin
diff -r -N ./extra/kipi-plugins/metadataedit/common/exifeditwidget.h ../../digikam/extra/kipi-plugins/metadataedit/common/exifeditwidget.h
0a1,91
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a KPageWidget to edit EXIF metadata
>  *
>  * Copyright (C) 2006-2010 by Gilles Caulier <caulier dot gilles at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #ifndef EXIFEDITWIDGET_H
> #define EXIFEDITWIDGET_H
> 
> // KDE includes
> 
> #include <kpagewidget.h>
> #include <kurl.h>
> 
> class QCloseEvent;
> class QEvent;
> class QObject;
> 
> namespace KIPI
> {
>     class Interface;
> }
> 
> using namespace KIPI;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class allEXIFEditWidgetPrivate;
> 
> class allEXIFEditWidget : public KPageWidget
> {
>     Q_OBJECT
> 
> public:
> 
>     allEXIFEditWidget(QWidget* parent, KUrl::List urls, Interface* iface);
>     ~allEXIFEditWidget();
>     
>     bool isModified();
> 
> Q_SIGNALS:
>     void signalSetReadOnly( bool );
>     void signalModified();
> 
> public Q_SLOTS:
> 
>     void slotModified();
> 
> protected Q_SLOTS:
> 
>     void slotOk();
> 
> private Q_SLOTS:
>     void slotClose();
>     void slotItemChanged();
>     void slotApply();
>     void slotUser1();
>     void slotUser2();
> 
> private:
>     void readSettings();
>     void saveSettings();
> 
>     int  activePageIndex();
>     void showPage(int page);
> 
> private:
> 
>     allEXIFEditWidgetPrivate* const d;
> };
> 
> }  // namespace KIPIMetadataEditPlugin
> 
> #endif /* EXIFEDITDIALOG_H */
diff -r -N ./extra/kipi-plugins/metadataedit/common/iptceditwidget.cpp ../../digikam/extra/kipi-plugins/metadataedit/common/iptceditwidget.cpp
0a1,440
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a KPageWidget to edit IPTC metadata
>  *
>  * Copyright (C) 2006-2010 by Gilles Caulier <caulier dot gilles at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #include "iptceditwidget.moc"
> 
> // Qt includes
> 
> #include <QCloseEvent>
> #include <QKeyEvent>
> 
> // KDE includes
> 
> #include <kapplication.h>
> #include <kconfig.h>
> #include <kdebug.h>
> #include <kguiitem.h>
> #include <khelpmenu.h>
> #include <kiconloader.h>
> #include <klocale.h>
> #include <kmenu.h>
> #include <kmessagebox.h>
> #include <kpushbutton.h>
> #include <ktoolinvocation.h>
> 
> // LibKIPI includes
> 
> #include <libkipi/imagecollection.h>
> #include <libkipi/imageinfo.h>
> #include <libkipi/interface.h>
> #include <libkipi/plugin.h>
> 
> // LibKExiv2 includes
> 
> #include <libkexiv2/version.h>
> #include <libkexiv2/kexiv2.h>
> 
> // Local includes
> 
> #include "iptccategories.h"
> #include "iptccontent.h"
> #include "iptccredits.h"
> #include "iptcenvelope.h"
> #include "iptckeywords.h"
> #include "iptcorigin.h"
> #include "iptcproperties.h"
> #include "iptcstatus.h"
> #include "iptcsubjects.h"
> #include "kpaboutdata.h"
> #include "pluginsversion.h"
> 
> using namespace KExiv2Iface;
> using namespace KIPIPlugins;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class allIPTCEditWidgetPrivate
> {
> 
> public:
> 
>     allIPTCEditWidgetPrivate()
>     {
>         modified        = false;
>         isReadOnly      = false;
>         page_content    = 0;
>         page_properties = 0;
>         page_subjects   = 0;
>         page_keywords   = 0;
>         page_categories = 0;
>         page_credits    = 0;
>         page_status     = 0;
>         page_origin     = 0;
>         page_envelope   = 0;
>         about           = 0;
>         contentPage     = 0;
>         propertiesPage  = 0;
>         subjectsPage    = 0;
>         keywordsPage    = 0;
>         categoriesPage  = 0;
>         creditsPage     = 0;
>         statusPage      = 0;
>         originPage      = 0;
>         envelopePage    = 0;
>     }
> 
>     bool                  modified;
>     bool                  isReadOnly;
> 
>     QByteArray            exifData;
>     QByteArray            iptcData;
> 
>     KPageWidgetItem      *page_content;
>     KPageWidgetItem      *page_properties;
>     KPageWidgetItem      *page_subjects;
>     KPageWidgetItem      *page_keywords;
>     KPageWidgetItem      *page_categories;
>     KPageWidgetItem      *page_credits;
>     KPageWidgetItem      *page_status;
>     KPageWidgetItem      *page_origin;
>     KPageWidgetItem      *page_envelope;
> 
>     KUrl::List            urls;
> 
>     KUrl::List::iterator  currItem;
> 
>     IPTCContent          *contentPage;
>     IPTCProperties       *propertiesPage;
>     IPTCSubjects         *subjectsPage;
>     IPTCKeywords         *keywordsPage;
>     IPTCCategories       *categoriesPage;
>     IPTCCredits          *creditsPage;
>     IPTCStatus           *statusPage;
>     IPTCOrigin           *originPage;
>     IPTCEnvelope         *envelopePage;
> 
>     Interface            *interface;
> 
>     KPAboutData          *about;
> };
> 
> allIPTCEditWidget::allIPTCEditWidget(QWidget* parent, KUrl::List urls, Interface* iface)
>               : KPageWidget(parent), d(new allIPTCEditWidgetPrivate)
> {
>     d->urls      = urls;
>     d->interface = iface;
>     d->currItem  = d->urls.begin();
>  
>     // ---------------------------------------------------------------
> 
>     d->contentPage   = new IPTCContent(this);
>     d->page_content  = addPage(d->contentPage, i18n("Content"));
>     d->page_content->setHeader(i18n("<qt>Content Information<br/>"
>                      "<i>Use this panel to describe the visual content of the image</i></qt>"));
>     d->page_content->setIcon(KIcon("help-contents"));
> 
>     d->originPage  = new IPTCOrigin(this);
>     d->page_origin = addPage(d->originPage, i18n("Origin"));
>     d->page_origin->setHeader(i18n("<qt>Origin Information<br/>"
>                     "<i>Use this panel for formal descriptive information about the image</i></qt>"));
>     d->page_origin->setIcon(KIcon("applications-internet"));
> 
>     d->creditsPage  = new IPTCCredits(this);
>     d->page_credits = addPage(d->creditsPage, i18n("Credits"));
>     d->page_credits->setHeader(i18n("<qt>Credit Information<br/>"
>                      "<i>Use this panel to record copyright information about the image</i></qt>"));
>     d->page_credits->setIcon(KIcon("view-pim-contacts"));
> 
>     d->subjectsPage  = new IPTCSubjects(this);
>     d->page_subjects = addPage(d->subjectsPage, i18n("Subjects"));
>     d->page_subjects->setHeader(i18n("<qt>Subject Information<br/>"
>                       "<i>Use this panel to record subject information about the image</i></qt>"));
>     d->page_subjects->setIcon(KIcon("feed-subscribe"));
> 
>     d->keywordsPage  = new IPTCKeywords(this);
>     d->page_keywords = addPage(d->keywordsPage, i18n("Keywords"));
>     d->page_keywords->setHeader(i18n("<qt>Keyword Information<br/>"
>                       "<i>Use this panel to record keywords relevant to the image</i></qt>"));
>     d->page_keywords->setIcon(KIcon("bookmarks"));
> 
>     d->categoriesPage  = new IPTCCategories(this);
>     d->page_categories = addPage(d->categoriesPage, i18n("Categories"));
>     d->page_categories->setHeader(i18n("<qt>Category Information<br/>"
>                         "<i>Use this panel to record categories relevant to the image</i></qt>"));
>     d->page_categories->setIcon(KIcon("folder-image"));
> 
>     d->statusPage  = new IPTCStatus(this);
>     d->page_status = addPage(d->statusPage, i18n("Status"));
>     d->page_status->setHeader(i18n("<qt>Status Information<br/>"
>                     "<i>Use this panel to record workflow information</i></qt>"));
>     d->page_status->setIcon(KIcon("view-pim-tasks"));
> 
>     d->propertiesPage  = new IPTCProperties(this);
>     d->page_properties = addPage(d->propertiesPage, i18n("Properties"));
>     d->page_properties->setHeader(i18n("<qt>Status Properties<br/>"
>                       "<i>Use this panel to record workflow properties</i></qt>"));
>     d->page_properties->setIcon(KIcon("draw-freehand"));
> 
>     d->envelopePage  = new IPTCEnvelope(this);
>     d->page_envelope = addPage(d->envelopePage, i18n("Envelope"));
>     d->page_envelope->setHeader(i18n("<qt>Envelope Information<br/>"
>                       "<i>Use this panel to record editorial details</i></qt>"));
>     d->page_envelope->setIcon(KIcon("view-pim-mail"));
> 
>     // ---------------------------------------------------------------
> 
>     connect(d->contentPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->propertiesPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->subjectsPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->keywordsPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->categoriesPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->creditsPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->statusPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->originPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->envelopePage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     // ------------------------------------------------------------
> 
>     readSettings();
>     slotItemChanged();
> }
> 
> allIPTCEditWidget::~allIPTCEditWidget()
> {
>     delete d->about;
>     delete d;
> }
> 
> void allIPTCEditWidget::slotClose()
> {
>     saveSettings();
> }
> 
> void allIPTCEditWidget::readSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group("All Metadata Edit Settings");
>     showPage(group.readEntry("All IPTC Edit Page", 0));
>     d->contentPage->setCheckedSyncJFIFComment(group.readEntry("All Sync JFIF Comment", true));
>     d->contentPage->setCheckedSyncHOSTComment(group.readEntry("All Sync Host Comment", true));
>     d->contentPage->setCheckedSyncEXIFComment(group.readEntry("All Sync EXIF Comment", true));
>     d->originPage->setCheckedSyncHOSTDate(group.readEntry("All Sync Host Date", true));
>     d->originPage->setCheckedSyncEXIFDate(group.readEntry("All Sync EXIF Date", true));
> }
> 
> void allIPTCEditWidget::saveSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group("All Metadata Edit Settings");
>     group.writeEntry("All IPTC Edit Page", activePageIndex());
>     group.writeEntry("All Sync JFIF Comment", d->contentPage->syncJFIFCommentIsChecked());
>     group.writeEntry("All Sync Host Comment", d->contentPage->syncHOSTCommentIsChecked());
>     group.writeEntry("All Sync EXIF Comment", d->contentPage->syncEXIFCommentIsChecked());
>     group.writeEntry("All Sync Host Date", d->originPage->syncHOSTDateIsChecked());
>     group.writeEntry("All Sync EXIF Date", d->originPage->syncEXIFDateIsChecked());
>     config.sync();
> }
> 
> void allIPTCEditWidget::slotItemChanged()
> {
>     KExiv2 exiv2Iface;
>     exiv2Iface.load((*d->currItem).path());
> 
> #if KEXIV2_VERSION >= 0x010000
>     d->exifData = exiv2Iface.getExifEncoded();
> #else
>     d->exifData = exiv2Iface.getExif();
> #endif
> 
>     d->iptcData = exiv2Iface.getIptc();
>     d->contentPage->readMetadata(d->iptcData);
>     d->originPage->readMetadata(d->iptcData);
>     d->creditsPage->readMetadata(d->iptcData);
>     d->subjectsPage->readMetadata(d->iptcData);
>     d->keywordsPage->readMetadata(d->iptcData);
>     d->categoriesPage->readMetadata(d->iptcData);
>     d->statusPage->readMetadata(d->iptcData);
>     d->propertiesPage->readMetadata(d->iptcData);
>     d->envelopePage->readMetadata(d->iptcData);
> 
>     d->isReadOnly = !KExiv2::canWriteIptc((*d->currItem).path());
>     emit signalSetReadOnly(d->isReadOnly);
>     
>     d->page_content->setEnabled(!d->isReadOnly);
>     d->page_origin->setEnabled(!d->isReadOnly);
>     d->page_credits->setEnabled(!d->isReadOnly);
>     d->page_subjects->setEnabled(!d->isReadOnly);
>     d->page_keywords->setEnabled(!d->isReadOnly);
>     d->page_categories->setEnabled(!d->isReadOnly);
>     d->page_status->setEnabled(!d->isReadOnly);
>     d->page_properties->setEnabled(!d->isReadOnly);
>     d->page_envelope->setEnabled(!d->isReadOnly);
> }
> 
> void allIPTCEditWidget::slotApply()
> {
>     if (d->modified && !d->isReadOnly)
>     {
>         ImageInfo info = d->interface->info(*d->currItem);
> 
>         if (d->contentPage->syncHOSTCommentIsChecked())
>         {
>             info.setDescription(d->contentPage->getIPTCCaption());
>         }
>         d->contentPage->applyMetadata(d->exifData, d->iptcData);
> 
>         if (d->originPage->syncHOSTDateIsChecked())
>         {
>             info.setTime(d->originPage->getIPTCCreationDate());
>         }
>         d->originPage->applyMetadata(d->exifData, d->iptcData);
> 
>         d->creditsPage->applyMetadata(d->iptcData);
>         d->subjectsPage->applyMetadata(d->iptcData);
>         d->keywordsPage->applyMetadata(d->iptcData);
>         d->categoriesPage->applyMetadata(d->iptcData);
>         d->statusPage->applyMetadata(d->iptcData);
>         d->propertiesPage->applyMetadata(d->iptcData);
>         d->envelopePage->applyMetadata(d->iptcData);
> 
>         KExiv2 exiv2Iface;
>         exiv2Iface.setWriteRawFiles(d->interface->hostSetting("WriteMetadataToRAW").toBool());
> 
> #if KEXIV2_VERSION >= 0x000600
>         exiv2Iface.setUpdateFileTimeStamp(d->interface->hostSetting("WriteMetadataUpdateFiletimeStamp").toBool());
> #endif
> 
>         exiv2Iface.load((*d->currItem).path());
>         exiv2Iface.setExif(d->exifData);
>         exiv2Iface.setIptc(d->iptcData);
>         exiv2Iface.save((*d->currItem).path());
>         d->modified = false;
>     }
> }
> 
> void allIPTCEditWidget::slotUser1()
> {
>     slotApply();
>     d->currItem++;
>     slotItemChanged();
> }
> 
> void allIPTCEditWidget::slotUser2()
> {
>     slotApply();
>     d->currItem--;
>     slotItemChanged();
> }
> 
> void allIPTCEditWidget::slotModified()
> {
>     if (!d->isReadOnly)
>     {
>         d->modified = true;
>         emit signalModified();
>     }
> }
> 
> void allIPTCEditWidget::slotOk()
> {
>     slotApply();
>     saveSettings();
> }
> 
> void allIPTCEditWidget::showPage(int page)
> {
>     switch(page)
>     {
>         case 0:
>             setCurrentPage(d->page_content);
>             break;
>         case 1:
>             setCurrentPage(d->page_origin);
>             break;
>         case 2:
>             setCurrentPage(d->page_credits);
>             break;
>         case 3:
>             setCurrentPage(d->page_subjects);
>             break;
>         case 4:
>             setCurrentPage(d->page_keywords);
>             break;
>         case 5:
>             setCurrentPage(d->page_categories);
>             break;
>         case 6:
>             setCurrentPage(d->page_status);
>             break;
>         case 7:
>             setCurrentPage(d->page_properties);
>             break;
>         case 8:
>             setCurrentPage(d->page_envelope);
>             break;
>         default:
>             setCurrentPage(d->page_content);
>             break;
>     }
> }
> 
> int allIPTCEditWidget::activePageIndex()
> {
>     KPageWidgetItem *cur = currentPage();
> 
>     if (cur == d->page_content)    return 0;
>     if (cur == d->page_origin)     return 1;
>     if (cur == d->page_credits)    return 2;
>     if (cur == d->page_subjects)   return 3;
>     if (cur == d->page_keywords)   return 4;
>     if (cur == d->page_categories) return 5;
>     if (cur == d->page_status)     return 6;
>     if (cur == d->page_properties) return 7;
>     if (cur == d->page_envelope)   return 8;
> 
>     return 0;
> }
> 
> bool allIPTCEditWidget::isModified()
> {
>     return d->modified;
> }
> 
> }  // namespace KIPIMetadataEditPlugin
diff -r -N ./extra/kipi-plugins/metadataedit/common/iptceditwidget.h ../../digikam/extra/kipi-plugins/metadataedit/common/iptceditwidget.h
0a1,91
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a KPageWidget to edit IPTC metadata
>  *
>  * Copyright (C) 2006-2010 by Gilles Caulier <caulier dot gilles at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #ifndef IPTCEDITWIDGET_H
> #define IPTCEDITWIDGET_H
> 
> // KDE includes
> 
> #include <kpagedialog.h>
> #include <kurl.h>
> 
> class QCloseEvent;
> class QEvent;
> class QObject;
> 
> namespace KIPI
> {
>     class Interface;
> }
> 
> using namespace KIPI;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class allIPTCEditWidgetPrivate;
> 
> class allIPTCEditWidget : public KPageWidget
> {
>     Q_OBJECT
> 
> public:
> 
>     allIPTCEditWidget(QWidget* parent, KUrl::List urls, Interface* iface);
>     ~allIPTCEditWidget();
>     
>     bool isModified();
> 
> Q_SIGNALS:
>     void signalModified();
>     void signalSetReadOnly( bool );
> 
> public Q_SLOTS:
> 
>     void slotModified();
> 
> protected Q_SLOTS:
> 
>     void slotOk();
>     void slotClose();
> 
> private Q_SLOTS:
>     void slotItemChanged();
>     void slotApply();
>     void slotUser1();
>     void slotUser2();
> 
> private:
>     void readSettings();
>     void saveSettings();
> 
>     int  activePageIndex();
>     void showPage(int page);
> 
> private:
> 
>     allIPTCEditWidgetPrivate* const d;
> };
> 
> }  // namespace KIPIMetadataEditPlugin
> 
> #endif /* IPTCEDITWIDGET_H */
diff -r -N ./extra/kipi-plugins/metadataedit/common/metadataedit.cpp ../../digikam/extra/kipi-plugins/metadataedit/common/metadataedit.cpp
0a1,403
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a dialog to edit EXIF,IPTC and XMP metadata
>  *
>  * Copyright (C) 2011 by Dodon Victor <dodonvictor at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #include "metadataedit.moc"
> 
> // Qt includes
> 
> #include <QCloseEvent>
> #include <QKeyEvent>
> #include <QPointer>
> #include <QObject>
> 
> // KDE includes
> 
> #include <kapplication.h>
> #include <kconfig.h>
> #include <kdebug.h>
> #include <kguiitem.h>
> #include <khelpmenu.h>
> #include <kiconloader.h>
> #include <klocale.h>
> #include <kmenu.h>
> #include <kmessagebox.h>
> #include <kpushbutton.h>
> #include <ktoolinvocation.h>
> #include <ktabwidget.h>
> 
> // LibKIPI includes
> 
> #include <libkipi/imagecollection.h>
> #include <libkipi/imageinfo.h>
> #include <libkipi/interface.h>
> #include <libkipi/plugin.h>
> 
> // LibKExiv2 includes
> 
> #include <libkexiv2/version.h>
> #include <libkexiv2/kexiv2.h>
> 
> // Local includes
> 
> #include "kpaboutdata.h"
> #include "pluginsversion.h"
> #include "exifeditwidget.h"
> #include "iptceditwidget.h"
> #include "xmpeditwidget.h"
> 
> using namespace KExiv2Iface;
> using namespace KIPIPlugins;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class MetadataEditDialogPrivate
> {
> public:
>     MetadataEditDialogPrivate()
>     {
>         isReadOnly = false;
>         about = 0;
>         tabWidget = 0;
>         tabExif = 0;
>         tabIptc = 0;
>         tabXmp = 0;
>     }
>     
>     bool isReadOnly;
>     
>     KUrl::List                            urls;
>     KUrl::List::iterator                  currItem;
>     
>     Interface                             *interface;
>     
>     KTabWidget                            *tabWidget;
>     allEXIFEditWidget                     *tabExif;
>     allIPTCEditWidget                     *tabIptc;
>     allXMPEditWidget                      *tabXmp;
>     KPAboutData                           *about;
>     QString                               tabName;
> };
> 
> MetadataEditDialog::MetadataEditDialog(QWidget *parent,KUrl::List urls,
>         Interface *iface): KDialog(parent),d(new MetadataEditDialogPrivate)
> {
>     d->urls      = urls;
>     d->interface = iface;
>     d->currItem  = d->urls.begin();
>     
>     this-> setCaption(tr("Metadata edit dialog"));
>     d->tabWidget = new KTabWidget(this);
>     d->tabExif = new allEXIFEditWidget(this, urls, iface);
>     d->tabIptc = new allIPTCEditWidget(this, urls, iface);
>     d->tabXmp = new allXMPEditWidget(this, urls, iface);
>     d->tabWidget->addTab(d->tabExif,QObject::tr("Edit EXIF"));
>     d->tabWidget->addTab(d->tabIptc,QObject::tr("Edit IPTC"));
>     d->tabWidget->addTab(d->tabXmp,QObject::tr("Edit XMP"));
>     
>     setMainWidget(d->tabWidget);
>     setButtons(urls.count() > 1 ? Help|User1|User2|Ok|Apply|Close
>                                    : Help|Ok|Apply|Close);
>     setDefaultButton(Ok);
>     setButtonIcon(User1, KIcon("go-next"));
>     setButtonIcon(User2, KIcon("go-previous"));
>     setButtonText(User1, i18n("Next"));
>     setButtonText(User2, i18n("Previous"));
>     setModal(true);
>     
>     //----------------------------------------------------------
>     
>     connect(d->tabExif,SIGNAL(signalModified()),
>         this,SLOT(slotModified()));
>     
>     connect(d->tabIptc,SIGNAL(signalModified()),
>         this,SLOT(slotModified()));
>     
>     connect(d->tabXmp,SIGNAL(signalModified()),
>         this,SLOT(slotModified()));    
>         
>     connect(this,SIGNAL(applyClicked()),
>         this,SLOT(slotApply()));
>         
>     connect(this,SIGNAL(signalApply()),
>         d->tabExif,SLOT(slotApply()));
>         
>     connect(this,SIGNAL(signalApply()),
>         d->tabIptc,SLOT(slotApply()));
>         
>     connect(this,SIGNAL(signalApply()),
>         d->tabXmp,SLOT(slotApply()));
>         
>     connect(this,SIGNAL(closeClicked()),
>         this,SLOT(slotClose()));
>         
>     connect(this,SIGNAL(signalClose()),
>         d->tabExif,SLOT(slotClose()));
>         
>     connect(this,SIGNAL(signalClose()),
>         d->tabIptc,SLOT(slotClose()));
>     
>     connect(this,SIGNAL(signalClose()),
>         d->tabXmp,SLOT(slotClose()));
>         
>     connect(this,SIGNAL(user1Clicked()),
>         this,SLOT(slotUser1()));
>         
>     connect(this,SIGNAL(signalUser1()),
>         d->tabExif,SLOT(slotUser1()));
>         
>     connect(this,SIGNAL(signalUser1()),
>         d->tabIptc,SLOT(slotUser1()));
>     
>     connect(this,SIGNAL(signalUser1()),
>         d->tabXmp,SLOT(slotUser1()));
>         
>     connect(this,SIGNAL(user2Clicked()),
>         this,SLOT(slotUser2()));
>         
>     connect(this,SIGNAL(signalUser2()),
>         d->tabExif,SLOT(slotUser2()));
>         
>     connect(this,SIGNAL(signalUser2()),
>         d->tabIptc,SLOT(slotUser2()));
>     
>     connect(this,SIGNAL(signalUser2()),
>         d->tabXmp,SLOT(slotUser2()));
>         
>     connect(this,SIGNAL(okClicked()),
>         this,SLOT(slotOk()));
>         
>     connect(this,SIGNAL(signalOk()),
>         d->tabExif,SLOT(slotOk()));
>         
>     connect(this,SIGNAL(signalOk()),
>         d->tabIptc,SLOT(slotOk()));
>     
>     connect(this,SIGNAL(signalOk()),
>         d->tabXmp,SLOT(slotOk()));
>         
>     connect(d->tabExif,SIGNAL(signalSetReadOnly(bool)),
>         this,SLOT(slotSetReadOnly(bool)));
>         
>     connect(d->tabIptc,SIGNAL(signalSetReadOnly(bool)),
>         this,SLOT(slotSetReadOnly(bool)));
>         
>     connect(d->tabXmp,SIGNAL(signalSetReadOnly(bool)),
>         this,SLOT(slotSetReadOnly(bool)));
>         
>     connect(d->tabWidget,SIGNAL(currentChanged(int)),
>         this,SLOT(setWindowTitle(int)));
>     
>     //----------------------------------------------------------
>     
>     enableButton(Apply,false);
>     
>     d->about = new KPAboutData(ki18n("Edit Metadata"),
>                                0,
>                                KAboutData::License_GPL,
>                                ki18n("A Plugin to edit pictures' metadata."),
>                                ki18n("(c) 2006-2010, Gilles Caulier"));
> 
>     d->about->addAuthor(ki18n("Gilles Caulier"), ki18n("Author and Maintainer"),
>                         "caulier dot gilles at gmail dot com");
> 
>     disconnect(this, SIGNAL(helpClicked()),
>                this, SLOT(slotHelp()));
> 
>     KHelpMenu* helpMenu = new KHelpMenu(this, d->about, false);
>     helpMenu->menu()->removeAction(helpMenu->menu()->actions().first());
>     QAction *handbook   = new QAction(i18n("Handbook"), this);
>     connect(handbook, SIGNAL(triggered(bool)),
>             this, SLOT(slotHelp()));
>     helpMenu->menu()->insertAction(helpMenu->menu()->actions().first(), handbook);
>     button(Help)->setMenu(helpMenu->menu());
>     
>     readSettings();
>     slotItemChanged();
> 
> }
> 
> MetadataEditDialog::~MetadataEditDialog()
> {
>     delete d->about;
>     delete d;
> };
> 
> void MetadataEditDialog::slotHelp()
> {
>     KToolInvocation::invokeHelp("metadataeditor", "kipi-plugins");
> }
> 
> void MetadataEditDialog::slotClose()
> {
>     emit signalClose();
>     saveSettings();
>     close();
> }
> 
> void MetadataEditDialog::slotModified()
> {
>     bool modified=false;
>     
>     switch (d->tabWidget->currentIndex()) {
>     
>         case 0:
>             modified = d->tabExif->isModified();
>             break;
>     
>         case 1:
>             modified = d->tabIptc->isModified();
>             break;
>     
>         case 2:
>             modified = d->tabXmp->isModified();
>             break;
>         }
>     
>     enableButton(Apply,modified);    
> }
> 
> void MetadataEditDialog::slotApply()
> {
>     emit signalApply();
>     slotItemChanged();
> }
> 
> void MetadataEditDialog::readSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group(QString("Metadata Edit Dialog"));
>     restoreDialogSize(group);
> }
> 
> void MetadataEditDialog::saveSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group(QString("Metadata Edit Dialog"));
>     saveDialogSize(group);
> }
> 
> void MetadataEditDialog::slotUser1()
> {
>     slotApply();
>     d->currItem++;
>     emit signalUser1();
>     slotItemChanged();
> }
> 
> void MetadataEditDialog::slotUser2()
> {
>     slotApply();
>     d->currItem--;
>     emit signalUser2();
>     slotItemChanged();
> }
> 
> void MetadataEditDialog::slotItemChanged()
> {
>     enableButton(Apply, !d->isReadOnly);
>     setWindowTitle(d->tabWidget->currentIndex());
>     enableButton(User1, *(d->currItem) != d->urls.last());
>     enableButton(User2, *(d->currItem) != d->urls.first());
>     enableButton(Apply, false);
> }
> 
> void MetadataEditDialog::slotOk()
> {
>     slotApply();
>     saveSettings();
>     emit signalOk();
>     accept();
> }
> 
> bool MetadataEditDialog::eventFilter(QObject *, QEvent *e)
> {
>     if ( e->type() == QEvent::KeyPress )
>     {
>         QKeyEvent *k = (QKeyEvent *)e;
> 
>         if (k->modifiers() == Qt::ControlModifier &&
>             (k->key() == Qt::Key_Enter || k->key() == Qt::Key_Return))
>         {
>             slotApply();
> 
>             if (isButtonEnabled(User1))
>                 slotUser1();
> 
>             return true;
>         }
>         else if (k->modifiers() == Qt::ShiftModifier &&
>                  (k->key() == Qt::Key_Enter || k->key() == Qt::Key_Return))
>         {
>             slotApply();
> 
>             if (isButtonEnabled(User2))
>                 slotUser2();
> 
>             return true;
>         }
> 
>         return false;
>     }
> 
>     return false;
> }
> 
> void MetadataEditDialog::closeEvent(QCloseEvent *e)
> {
>     if (!e) return;
>     saveSettings();
>     e->accept();
> }
> 
> void MetadataEditDialog::slotSetReadOnly(bool state)
> {
>     d->isReadOnly = state;
> }
> 
> void MetadataEditDialog::setWindowTitle(int tabIndex)
> {
>     switch (tabIndex) { 
>        
>         case 0:
>             d->tabName = "EXIF";
>             break;
>         
>         case 1:
>             d->tabName = "IPTC";
>             break;
>         
>         case 2:
>             d->tabName = "XMP";
>             break;
>     }
>     
>     setCaption(QString("%1 (%2/%3) - %4 %5 %6 ")
>         .arg((*d->currItem).fileName())
>         .arg(d->urls.indexOf(*(d->currItem))+1)
>         .arg(d->urls.count())
>         .arg(i18n("Edit"))
>         .arg(d->tabName)
>         .arg(i18n("Metadata")));
> }
> 
> }
diff -r -N ./extra/kipi-plugins/metadataedit/common/metadataedit.h ../../digikam/extra/kipi-plugins/metadataedit/common/metadataedit.h
0a1,95
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a dialog to edit EXIF,IPTC and XMP metadata
>  *
>  * Copyright (C) 2011 by Dodon Victor <dodonvictor at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #ifndef EDITALLMETADATA_H
> #define EDITALLMETADATA_H
> 
> #include <kpagedialog.h>
> #include <kurl.h>
> #include <QObject>
> 
> class QObject;
> class QCloseEvent;
> class Event;
> 
> namespace KIPI
> {
>     class Interface;
> }
> 
> using namespace KIPI;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class MetadataEditDialogPrivate;
> 
> class MetadataEditDialog : public KDialog
> {
>     Q_OBJECT
>         
> public:
>     MetadataEditDialog(QWidget *parent,KUrl::List urls,Interface *iface);
>     ~MetadataEditDialog();
>         
> public Q_SLOTS:
> 
>     void slotModified();
> 
> private Q_SLOTS:
> 
>     void slotHelp();
>     void slotOk();
>     void slotClose();
>     void slotItemChanged();
>     void slotApply();
>     void slotUser1();
>     void slotUser2();
>     void slotSetReadOnly(bool);
>     void setWindowTitle(int);
>     
> Q_SIGNALS:
> 
>     void signalApply();
>     void signalClose();
>     void signalUser1();
>     void signalUser2();    
>     void signalOk();
>     
> protected:
> 
>     void closeEvent(QCloseEvent*);
>     bool eventFilter(QObject*, QEvent*);
>         
> private:
> 
>     void saveSettings();
>     void readSettings();
> 
> private:
> 
>     MetadataEditDialogPrivate* const d;
> };
> 
> }  // namespace KIPIMetadataEditPlugin
> 
> #endif  /* EDITALLMETADATA_H */
diff -r -N ./extra/kipi-plugins/metadataedit/common/xmpeditwidget.cpp ../../digikam/extra/kipi-plugins/metadataedit/common/xmpeditwidget.cpp
0a1,429
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-10-11
>  * Description : a KPageWidget to edit XMP metadata
>  *
>  * Copyright (C) 2007-2010 by Gilles Caulier <caulier dot gilles at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #include "xmpeditwidget.moc"
> 
> // Qt includes
> 
> #include <QCloseEvent>
> #include <QKeyEvent>
> 
> // KDE includes
> 
> #include <kapplication.h>
> #include <kconfig.h>
> #include <kdebug.h>
> #include <kguiitem.h>
> #include <khelpmenu.h>
> #include <kiconloader.h>
> #include <klocale.h>
> #include <kmenu.h>
> #include <kmessagebox.h>
> #include <kpushbutton.h>
> #include <ktoolinvocation.h>
> 
> // LibKIPI includes
> 
> #include <libkipi/imagecollection.h>
> #include <libkipi/imageinfo.h>
> #include <libkipi/interface.h>
> #include <libkipi/plugin.h>
> 
> // LibKExiv2 includes
> 
> #include <libkexiv2/version.h>
> #include <libkexiv2/kexiv2.h>
> 
> // Local includes
> 
> #include "kpaboutdata.h"
> #include "pluginsversion.h"
> #include "xmpcategories.h"
> #include "xmpcontent.h"
> #include "xmpcredits.h"
> #include "xmpkeywords.h"
> #include "xmporigin.h"
> #include "xmpproperties.h"
> #include "xmpstatus.h"
> #include "xmpsubjects.h"
> 
> using namespace KExiv2Iface;
> using namespace KIPIPlugins;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class allXMPEditWidgetPrivate
> {
> 
> public:
> 
>     allXMPEditWidgetPrivate()
>     {
>         modified        = false;
>         isReadOnly      = false;
>         page_content    = 0;
>         page_properties = 0;
>         page_subjects   = 0;
>         page_keywords   = 0;
>         page_categories = 0;
>         page_credits    = 0;
>         page_status     = 0;
>         page_origin     = 0;
>         about           = 0;
>         keywordsPage    = 0;
>         categoriesPage  = 0;
>         contentPage     = 0;
>         subjectsPage    = 0;
>         originPage      = 0;
>         creditsPage     = 0;
>         statusPage      = 0;
>         propertiesPage  = 0;
>     }
> 
>     bool                  modified;
>     bool                  isReadOnly;
> 
>     QByteArray            exifData;
>     QByteArray            iptcData;
>     QByteArray            xmpData;
> 
>     KPageWidgetItem      *page_content;
>     KPageWidgetItem      *page_origin;
>     KPageWidgetItem      *page_subjects;
>     KPageWidgetItem      *page_keywords;
>     KPageWidgetItem      *page_categories;
>     KPageWidgetItem      *page_credits;
>     KPageWidgetItem      *page_status;
>     KPageWidgetItem      *page_properties;
> 
>     KUrl::List            urls;
> 
>     KUrl::List::iterator  currItem;
> 
>     XMPContent           *contentPage;
>     XMPKeywords          *keywordsPage;
>     XMPCategories        *categoriesPage;
>     XMPSubjects          *subjectsPage;
>     XMPOrigin            *originPage;
>     XMPCredits           *creditsPage;
>     XMPStatus            *statusPage;
>     XMPProperties        *propertiesPage;
> 
>     Interface            *interface;
> 
>     KPAboutData          *about;
> };
> 
> allXMPEditWidget::allXMPEditWidget(QWidget* parent, KUrl::List urls, Interface *iface)
>              : KPageWidget(parent), d(new allXMPEditWidgetPrivate)
> {
>     d->urls      = urls;
>     d->interface = iface;
>     d->currItem  = d->urls.begin();
> 
>     // ---------------------------------------------------------------
> 
>     d->contentPage   = new XMPContent(this);
>     d->page_content  = addPage(d->contentPage, i18n("Content"));
>     d->page_content->setHeader(i18n("<qt>Content Information<br/>"
>                      "<i>Use this panel to describe the visual content of the image</i></qt>"));
>     d->page_content->setIcon(KIcon("draw-text"));
> 
>     d->originPage  = new XMPOrigin(this);
>     d->page_origin = addPage(d->originPage, i18n("Origin"));
>     d->page_origin->setHeader(i18n("<qt>Origin Information<br/>"
>                     "<i>Use this panel for formal descriptive information about the image</i></qt>"));
>     d->page_origin->setIcon(KIcon("document-properties"));
> 
>     d->creditsPage  = new XMPCredits(this);
>     d->page_credits = addPage(d->creditsPage, i18n("Credits"));
>     d->page_credits->setHeader(i18n("<qt>Credit Information<br/>"
>                      "<i>Use this panel to record copyright information about the image</i></qt>"));
>     d->page_credits->setIcon(KIcon("view-pim-contacts"));
> 
>     d->subjectsPage  = new XMPSubjects(this);
>     d->page_subjects = addPage(d->subjectsPage, i18n("Subjects"));
>     d->page_subjects->setHeader(i18n("<qt>Subject Information<br/>"
>                       "<i>Use this panel to record subject information about the image</i></qt>"));
>     d->page_subjects->setIcon(KIcon("feed-subscribe"));
> 
>     d->keywordsPage  = new XMPKeywords(this);
>     d->page_keywords = addPage(d->keywordsPage, i18n("Keywords"));
>     d->page_keywords->setHeader(i18n("<qt>Keyword Information<br/>"
>                       "<i>Use this panel to record keywords relevant to the image</i></qt>"));
>     d->page_keywords->setIcon(KIcon("bookmarks"));
> 
>     d->categoriesPage  = new XMPCategories(this);
>     d->page_categories = addPage(d->categoriesPage, i18n("Categories"));
>     d->page_categories->setHeader(i18n("<qt>Category Information<br/>"
>                         "<i>Use this panel to record categories relevant to the image</i></qt>"));
>     d->page_categories->setIcon(KIcon("folder"));
> 
>     d->statusPage  = new XMPStatus(this);
>     d->page_status = addPage(d->statusPage, i18n("Status"));
>     d->page_status->setHeader(i18n("<qt>Status Information<br/>"
>                     "<i>Use this panel to record workflow information</i></qt>"));
>     d->page_status->setIcon(KIcon("view-pim-tasks"));
> 
>     d->propertiesPage  = new XMPProperties(this);
>     d->page_properties = addPage(d->propertiesPage, i18n("Properties"));
>     d->page_properties->setHeader(i18n("<qt>Status Properties<br/>"
>                       "<i>Use this panel to record workflow properties</i></qt>"));
>     d->page_properties->setIcon(KIcon("draw-freehand"));
> 
>     // ------------------------------------------------------------
> 
>     connect(d->contentPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->propertiesPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->originPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->subjectsPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->keywordsPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->categoriesPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->creditsPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     connect(d->statusPage, SIGNAL(signalModified()),
>             this, SLOT(slotModified()));
> 
>     // ------------------------------------------------------------
> 
>     readSettings();
>     slotItemChanged();
> }
> 
> allXMPEditWidget::~allXMPEditWidget()
> {
>     delete d->about;
>     delete d;
> }
> 
> void allXMPEditWidget::slotClose()
> {
>     saveSettings();
> }
> 
> void allXMPEditWidget::readSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group("All Metadata Edit Settings");
> 
>     showPage(group.readEntry("All XMP Edit Page", 0));
>     d->contentPage->setCheckedSyncJFIFComment(group.readEntry("All Sync JFIF Comment", true));
>     d->contentPage->setCheckedSyncHOSTComment(group.readEntry("All Sync Host Comment", true));
>     d->contentPage->setCheckedSyncEXIFComment(group.readEntry("All Sync EXIF Comment", true));
>     d->originPage->setCheckedSyncHOSTDate(group.readEntry("All Sync Host Date", true));
>     d->originPage->setCheckedSyncEXIFDate(group.readEntry("All Sync EXIF Date", true));
> 
>     KConfigGroup group2 = config.group(QString("All XMP Edit Dialog"));
> }
> 
> void allXMPEditWidget::saveSettings()
> {
>     KConfig config("kipirc");
>     KConfigGroup group = config.group("All Metadata Edit Settings");
> 
>     group.writeEntry("All XMP Edit Page", activePageIndex());
>     group.writeEntry("All Sync JFIF Comment", d->contentPage->syncJFIFCommentIsChecked());
>     group.writeEntry("All Sync Host Comment", d->contentPage->syncHOSTCommentIsChecked());
>     group.writeEntry("All Sync EXIF Comment", d->contentPage->syncEXIFCommentIsChecked());
>     group.writeEntry("All Sync Host Date", d->originPage->syncHOSTDateIsChecked());
>     group.writeEntry("All Sync EXIF Date", d->originPage->syncEXIFDateIsChecked());
> 
>     KConfigGroup group2 = config.group(QString("All XMP Edit Dialog"));
>     config.sync();
> }
> 
> void allXMPEditWidget::slotItemChanged()
> {
>     KExiv2 exiv2Iface;
>     exiv2Iface.load((*d->currItem).path());
> 
> #if KEXIV2_VERSION >= 0x010000
>     d->exifData = exiv2Iface.getExifEncoded();
> #else
>     d->exifData = exiv2Iface.getExif();
> #endif
> 
>     d->iptcData = exiv2Iface.getIptc();
>     d->xmpData  = exiv2Iface.getXmp();
> 
>     d->contentPage->readMetadata(d->xmpData);
>     d->originPage->readMetadata(d->xmpData);
>     d->subjectsPage->readMetadata(d->xmpData);
>     d->keywordsPage->readMetadata(d->xmpData);
>     d->categoriesPage->readMetadata(d->xmpData);
>     d->creditsPage->readMetadata(d->xmpData);
>     d->statusPage->readMetadata(d->xmpData);
>     d->propertiesPage->readMetadata(d->xmpData);
>     d->isReadOnly = !KExiv2::canWriteXmp((*d->currItem).path());
>     emit signalSetReadOnly(d->isReadOnly);
> 
>     d->page_content->setEnabled(!d->isReadOnly);
>     d->page_origin->setEnabled(!d->isReadOnly);
>     d->page_subjects->setEnabled(!d->isReadOnly);
>     d->page_keywords->setEnabled(!d->isReadOnly);
>     d->page_categories->setEnabled(!d->isReadOnly);
>     d->page_credits->setEnabled(!d->isReadOnly);
>     d->page_status->setEnabled(!d->isReadOnly);
>     d->page_properties->setEnabled(!d->isReadOnly);
> 
> }
> 
> void allXMPEditWidget::slotApply()
> {
>     if (d->modified && !d->isReadOnly)
>     {
>         ImageInfo info = d->interface->info(*d->currItem);
> 
>         if (d->contentPage->syncHOSTCommentIsChecked())
>         {
>             info.setDescription(d->contentPage->getXMPCaption());
>         }
>         d->contentPage->applyMetadata(d->exifData, d->xmpData);
> 
>         if (d->originPage->syncHOSTDateIsChecked())
>         {
>             info.setTime(d->originPage->getXMPCreationDate());
>         }
>         d->originPage->applyMetadata(d->exifData, d->xmpData);
> 
>         d->subjectsPage->applyMetadata(d->xmpData);
>         d->keywordsPage->applyMetadata(d->xmpData);
>         d->categoriesPage->applyMetadata(d->xmpData);
>         d->creditsPage->applyMetadata(d->xmpData);
>         d->statusPage->applyMetadata(d->xmpData);
>         d->propertiesPage->applyMetadata(d->xmpData);
> 
>         KExiv2 exiv2Iface;
>         exiv2Iface.setWriteRawFiles(d->interface->hostSetting("WriteMetadataToRAW").toBool());
> 
> #if KEXIV2_VERSION >= 0x000600
>         exiv2Iface.setUpdateFileTimeStamp(d->interface->hostSetting("WriteMetadataUpdateFiletimeStamp").toBool());
> #endif
> 
>         exiv2Iface.load((*d->currItem).path());
>         exiv2Iface.setExif(d->exifData);
>         exiv2Iface.setIptc(d->iptcData);
>         exiv2Iface.setXmp(d->xmpData);
>         exiv2Iface.save((*d->currItem).path());
>         d->modified = false;
>     }
> }
> 
> void allXMPEditWidget::slotUser1()
> {
>     slotApply();
>     d->currItem++;
>     slotItemChanged();
> }
> 
> void allXMPEditWidget::slotUser2()
> {
>     slotApply();
>     d->currItem--;
>     slotItemChanged();
> }
> 
> void allXMPEditWidget::slotModified()
> {
>     if (!d->isReadOnly)
>     {
>         d->modified = true;
>         emit signalModified();
>     }
> }
> 
> void allXMPEditWidget::slotOk()
> {
>     slotApply();
>     saveSettings();
> }
> 
> void allXMPEditWidget::showPage(int page)
> {
>     switch(page)
>     {
>         case 0:
>             setCurrentPage(d->page_content);
>             break;
>         case 1:
>             setCurrentPage(d->page_origin);
>             break;
>         case 2:
>             setCurrentPage(d->page_credits);
>             break;
>         case 3:
>             setCurrentPage(d->page_subjects);
>             break;
>         case 4:
>             setCurrentPage(d->page_keywords);
>             break;
>         case 5:
>             setCurrentPage(d->page_categories);
>             break;
>         case 6:
>             setCurrentPage(d->page_status);
>             break;
>         case 7:
>             setCurrentPage(d->page_properties);
>             break;
>         default:
>             setCurrentPage(d->page_content);
>             break;
>     }
> }
> 
> int allXMPEditWidget::activePageIndex()
> {
>     KPageWidgetItem *cur = currentPage();
> 
>     if (cur == d->page_content)    return 0;
>     if (cur == d->page_origin)     return 1;
>     if (cur == d->page_credits)    return 2;
>     if (cur == d->page_subjects)   return 3;
>     if (cur == d->page_keywords)   return 4;
>     if (cur == d->page_categories) return 5;
>     if (cur == d->page_status)     return 6;
>     if (cur == d->page_properties) return 7;
> 
>     return 0;
> }
> 
> bool allXMPEditWidget::isModified()
> {
>     return d->modified;
> }
> 
> }  // namespace KIPIMetadataEditPlugin
diff -r -N ./extra/kipi-plugins/metadataedit/common/xmpeditwidget.h ../../digikam/extra/kipi-plugins/metadataedit/common/xmpeditwidget.h
0a1,92
> /* ============================================================
>  *
>  * This file is a part of kipi-plugins project
>  * http://www.kipi-plugins.org
>  *
>  * Date        : 2011-03-14
>  * Description : a KPageWidget to edit XMP metadata
>  *
>  * Copyright (C) 2007-2010 by Gilles Caulier <caulier dot gilles at gmail dot com>
>  *
>  * 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.
>  *
>  * ============================================================ */
> 
> #ifndef ALLXMPEDITWIDGET_H
> #define ALLXMPEDITWIDGET_H
> 
> // KDE includes
> 
> #include <kpagedialog.h>
> #include <kurl.h>
> 
> class QCloseEvent;
> class QEvent;
> class QObject;
> 
> namespace KIPI
> {
>     class Interface;
> }
> 
> using namespace KIPI;
> 
> namespace KIPIMetadataEditPlugin
> {
> 
> class allXMPEditWidgetPrivate;
> 
> class allXMPEditWidget : public KPageWidget
> {
>     Q_OBJECT
> 
> public:
> 
>     allXMPEditWidget(QWidget* parent, KUrl::List urls, Interface *iface);
>     ~allXMPEditWidget();
>     
>     bool isModified();
> 
> Q_SIGNALS:
>     void signalModified();
>     void signalSetReadOnly( bool );
> 
> public Q_SLOTS:
> 
>     void slotModified();
> 
> protected Q_SLOTS:
> 
>     void slotOk();
>     void slotClose();
> 
> private Q_SLOTS:
> 
>     void slotItemChanged();
>     void slotApply();
>     void slotUser1();
>     void slotUser2();
> 
> private:
>     void readSettings();
>     void saveSettings();
> 
>     int  activePageIndex();
>     void showPage(int page);
> 
> private:
> 
>     allXMPEditWidgetPrivate* const d;
> };
> 
> }  // namespace KIPIMetadataEditPlugin
> 
> #endif /* ALLXMPEDITWIDGET_H */
diff -r -N ./extra/kipi-plugins/metadataedit/plugin_metadataedit.cpp ../../digikam/extra/kipi-plugins/metadataedit/plugin_metadataedit.cpp
61a62
> #include "metadataedit.h"
162a164,172
>     // ------------------------------------------------------
>     m_actionMetadataEdit->menu()->addSeparator();
> 
>     KAction* metadataEdit = actionCollection()->addAction("editallmetadata");
>     metadataEdit->setText(i18n("Edit &All Metadata"));
>     connect(metadataEdit, SIGNAL(triggered(bool)),
>             this,SLOT(slotEditAllMetadata()));
>     m_actionMetadataEdit->addAction(metadataEdit);
> 
178a189,202
> void Plugin_MetadataEdit::slotEditAllMetadata()
> {
>     ImageCollection images = m_interface->currentSelection();
> 
>     if ( !images.isValid() || images.images().isEmpty() )
>         return;
> 
>     QPointer<MetadataEditDialog> dialog = new MetadataEditDialog(kapp->activeWindow(), images.images(), m_interface);
>     dialog->exec();
>     m_interface->refreshImages(images.images());
> 
>     delete dialog;
> }
> 
diff -r -N ./extra/kipi-plugins/metadataedit/plugin_metadataedit.h ../../digikam/extra/kipi-plugins/metadataedit/plugin_metadataedit.h
32c32
< #include <kurl.h>
---
> #include <KUrl>
74a75,76
>     void slotEditAllMetadata();
> 
diff -r -N ./extra/kipi-plugins/metadataedit/TODO ../../digikam/extra/kipi-plugins/metadataedit/TODO
1c1
< Use shared widgets from libkexiv2 1.1.0 (KDE 4.5), already used in digiKam core :
---
> Use shared widgets from libkexiv2 1.1.0 (KDE 4.5), already used in digiKam core:
