[Digikam-devel] extragear/graphics/digikam/kioslave
Marcel Wiesweg
marcel.wiesweg at gmx.de
Sat Jan 13 16:13:18 GMT 2007
SVN commit 622969 by mwiesweg:
Always read metadata from added images. Previously, this worked only when
the image was added and then digikam started. Now, it works as well when
the file is copied while digikam is running, from inside or
outside digikam.
The code is duplicated from ScanLib and AlbumDB, with the promise to remove code
duplication in the future.
Added several code duplication comments to digikamalbums.cpp.
CCMAIL: digikam-devel at kde.org
M +219 -3 digikamalbums.cpp
--- trunk/extragear/graphics/digikam/kioslave/digikamalbums.cpp #622968:622969
@@ -249,6 +249,7 @@
void kio_digikamalbums::get( const KURL& url )
{
+// Code duplication from file:// ioslave
kdDebug() << k_funcinfo << " : " << url << endl;
// get the libraryPath
@@ -334,6 +335,7 @@
void kio_digikamalbums::put(const KURL& url, int permissions, bool overwrite, bool /*resume*/)
{
+// Code duplication from file:// ioslave
kdDebug() << k_funcinfo << " : " << url.url() << endl;
// get the libraryPath
@@ -487,6 +489,7 @@
void kio_digikamalbums::copy( const KURL &src, const KURL &dst, int mode, bool overwrite )
{
+// Code duplication from file:// ioslave?
kdDebug() << k_funcinfo << "Src: " << src.path() << ", Dst: " << dst.path() << endl;
// get the album library path
@@ -541,6 +544,7 @@
// metadata of the src album to the dst album
if (src.fileName() == ".digikam_properties")
{
+ // no duplication in AlbumDB?
// copy metadata of album to destination album
m_sqlDB.execSql( QString("UPDATE Albums SET date='%1', caption='%2', "
"collection='%3', icon=%4 ")
@@ -730,6 +734,7 @@
void kio_digikamalbums::rename( const KURL& src, const KURL& dst, bool overwrite )
{
+// Code duplication from file:// ioslave?
kdDebug() << k_funcinfo << "Src: " << src << ", Dst: " << dst << endl;
// if the filename is .digikam_properties fake that we renamed it
@@ -900,6 +905,7 @@
void kio_digikamalbums::listDir( const KURL& url )
{
+// Code duplication from file:// ioslave?
kdDebug() << k_funcinfo << " : " << url.path() << endl;
QString libraryPath = url.user();
@@ -949,6 +955,7 @@
void kio_digikamalbums::mkdir( const KURL& url, int permissions )
{
+// Code duplication from file:// ioslave?
kdDebug() << k_funcinfo << " : " << url.url() << endl;
QString libraryPath = url.user();
@@ -991,6 +998,7 @@
}
else
{
+ // code similar to AlbumDB::addAlbum
m_sqlDB.execSql( QString("REPLACE INTO Albums (url, date) "
"VALUES('%1','%2')")
.arg(escapeString(url.path()),
@@ -1020,7 +1028,8 @@
void kio_digikamalbums::chmod( const KURL& url, int permissions )
{
- kdDebug() << k_funcinfo << " : " << url.url() << endl;
+// Code duplication from file:// ioslave?
+ kdDebug() << k_funcinfo << " : " << url.url() << endl;
// get the album library path
QString libraryPath = url.user();
@@ -1039,6 +1048,7 @@
void kio_digikamalbums::del( const KURL& url, bool isfile)
{
+// Code duplication from file:// ioslave?
kdDebug() << k_funcinfo << " : " << url.url() << endl;
// get the album library path
@@ -1218,6 +1228,7 @@
void kio_digikamalbums::buildAlbumList()
{
+// simplified from AlbumDB::scanAlbums()
m_albumList.clear();
QStringList values;
@@ -1247,6 +1258,7 @@
AlbumInfo kio_digikamalbums::findAlbum(const QString& url, bool addIfNotExists)
{
+// similar to AlbumDB::getOrCreateAlbumId
AlbumInfo album;
for (QValueList<AlbumInfo>::const_iterator it = m_albumList.begin();
it != m_albumList.end(); ++it)
@@ -1284,12 +1296,14 @@
void kio_digikamalbums::delAlbum(int albumID)
{
+// code duplication from AlbumDB::deleteAlbum
m_sqlDB.execSql(QString("DELETE FROM Albums WHERE id='%1'")
.arg(albumID));
}
void kio_digikamalbums::renameAlbum(const QString& oldURL, const QString& newURL)
{
+// similar to AlbumDB::setAlbumURL, but why more extended?
// first update the url of the album which was renamed
m_sqlDB.execSql( QString("UPDATE Albums SET url='%1' WHERE url='%2'")
@@ -1315,6 +1329,7 @@
bool kio_digikamalbums::findImage(int albumID, const QString& name) const
{
+// no similar method in AlbumDB?
QStringList values;
m_sqlDB.execSql( QString("SELECT name FROM Images "
@@ -1326,8 +1341,25 @@
return !(values.isEmpty());
}
+// from albuminfo.h
+class TagInfo
+{
+public:
+
+ typedef QValueList<TagInfo> List;
+
+ int id;
+ int pid;
+ QString name;
+ QString icon;
+};
+
void kio_digikamalbums::addImage(int albumID, const QString& filePath)
{
+// Code duplication: ScanLib::storeItemInDatabase, AlbumDB::addItem,
+// AlbumDB::setItemRating, AlbumDB::addItemTag, AlbumDB::addTag
+
+ // from ScanLib::storeItemInDatabase
QString comment;
QDateTime datetime;
int rating = 0;
@@ -1356,6 +1388,10 @@
datetime = info.lastModified();
}
+ // Try to get image tags from IPTC keywords tags.
+ QStringList keywordsList = metadata.getImageKeywords();
+
+ // from AlbumDB::addItem
m_sqlDB.execSql(QString("REPLACE INTO Images "
"(dirid, name, datetime, caption) "
"VALUES(%1, '%2', '%3', '%4')")
@@ -1366,6 +1402,7 @@
Q_LLONG imageID = m_sqlDB.lastInsertedRow();
+ // from AlbumDB::setItemRating
if (imageID != -1 && rating != -1)
{
m_sqlDB.execSql(QString("REPLACE INTO ImageProperties "
@@ -1373,12 +1410,189 @@
"VALUES(%1, '%2', '%3');")
.arg(imageID)
.arg("Rating")
- .arg(rating) );
- }
+ .arg(rating) );
+ }
+
+ // Set existing tags in database or create new tags if not exist.
+
+ if ( imageID != -1 && !keywordsList.isEmpty() )
+ {
+ QStringList keywordsList2Create;
+
+ // Create a list of the tags currently in database
+
+ TagInfo::List tagsList;
+
+ QStringList values;
+ m_sqlDB.execSql( "SELECT id, pid, name FROM Tags;", &values );
+
+ for (QStringList::iterator it = values.begin(); it != values.end();)
+ {
+ TagInfo info;
+
+ info.id = (*it).toInt();
+ ++it;
+ info.pid = (*it).toInt();
+ ++it;
+ info.name = *it;
+ ++it;
+ tagsList.append(info);
+ }
+
+ // For every tag in keywordsList, scan taglist to check if tag already exists.
+
+ for (QStringList::iterator kwd = keywordsList.begin();
+ kwd != keywordsList.end(); ++kwd )
+ {
+ // split full tag "url" into list of single tag names
+ QStringList tagHierarchy = QStringList::split('/', *kwd);
+ if (tagHierarchy.isEmpty())
+ continue;
+
+ // last entry in list is the actual tag name
+ bool foundTag = false;
+ QString tagName = tagHierarchy.back();
+ tagHierarchy.pop_back();
+
+ for (TagInfo::List::iterator tag = tagsList.begin();
+ tag != tagsList.end(); ++tag )
+ {
+ // There might be multiple tags with the same name, but in different
+ // hierarchies. We must check them all until we find the correct hierarchy
+ if ((*tag).name == tagName)
+ {
+ int parentID = (*tag).pid;
+
+ // Check hierarchy, from bottom to top
+ bool foundParentTag = true;
+ QStringList::iterator parentTagName = tagHierarchy.end();
+
+ while (foundParentTag && parentTagName != tagHierarchy.begin())
+ {
+ --parentTagName;
+
+ foundParentTag = false;
+
+ for (TagInfo::List::iterator parentTag = tagsList.begin();
+ parentTag != tagsList.end(); ++parentTag )
+ {
+ // check if name is the same, and if ID is identical
+ // to the parent ID we got from the child tag
+ if ( (*parentTag).id == parentID &&
+ (*parentTag).name == (*parentTagName) )
+ {
+ parentID = (*parentTag).pid;
+ foundParentTag = true;
+ break;
+ }
+ }
+
+ // If we traversed the list without a match,
+ // foundParentTag will be false, the while loop breaks.
+ }
+
+ // If we managed to traverse the full hierarchy,
+ // we have our tag.
+ if (foundParentTag)
+ {
+ // from AlbumDB::addItemTag
+ m_sqlDB.execSql( QString("REPLACE INTO ImageTags (imageid, tagid) "
+ "VALUES(%1, %2);")
+ .arg(imageID)
+ .arg((*tag).id) );
+ foundTag = true;
+ break;
+ }
+ }
+ }
+
+ if (!foundTag)
+ keywordsList2Create.append(*kwd);
+ }
+
+ // If tags do not exist in database, create them.
+
+ if (!keywordsList2Create.isEmpty())
+ {
+ for (QStringList::iterator kwd = keywordsList2Create.begin();
+ kwd != keywordsList2Create.end(); ++kwd )
+ {
+ // split full tag "url" into list of single tag names
+ QStringList tagHierarchy = QStringList::split('/', *kwd);
+
+ if (tagHierarchy.isEmpty())
+ continue;
+
+ int parentTagID = 0;
+ int tagID = 0;
+ bool parentTagExisted = true;
+
+ // Traverse hierarchy from top to bottom
+ for (QStringList::iterator tagName = tagHierarchy.begin();
+ tagName != tagHierarchy.end(); ++tagName)
+ {
+ tagID = 0;
+
+ // if the parent tag did not exist, we need not check if the child exists
+ if (parentTagExisted)
+ {
+ for (TagInfo::List::iterator tag = tagsList.begin();
+ tag != tagsList.end(); ++tag )
+ {
+ // find the tag with tag name according to tagHierarchy,
+ // and parent ID identical to the ID of the tag we found in
+ // the previous run.
+ if ((*tag).name == (*tagName) && (*tag).pid == parentTagID)
+ {
+ tagID = (*tag).id;
+ break;
+ }
+ }
+ }
+
+ if (tagID != 0)
+ {
+ // tag already found in DB
+ parentTagID = tagID;
+ continue;
+ }
+
+ // Tag does not yet exist in DB, add it
+ // from AlbumDB::addTag
+ m_sqlDB.execSql( QString("INSERT INTO Tags (pid, name, icon) "
+ "VALUES( %1, '%2', 0)")
+ .arg(parentTagID)
+ .arg(escapeString(*tagName)));
+ if (tagID == -1)
+ {
+ // Something is wrong in database. Abort.
+ break;
+ }
+
+ // append to our list of existing tags (for following keywords)
+ TagInfo info;
+ info.id = tagID;
+ info.pid = parentTagID;
+ info.name = (*tagName);
+ tagsList.append(info);
+
+ parentTagID = tagID;
+ parentTagExisted = false;
+ }
+
+ // from AlbumDB::addItemTag
+ m_sqlDB.execSql( QString("REPLACE INTO ImageTags (imageid, tagid) "
+ "VALUES(%1, %2);")
+ .arg(imageID)
+ .arg(tagID) );
+ }
+ }
+ }
}
void kio_digikamalbums::delImage(int albumID, const QString& name)
{
+// code duplication from AlbumDB::deleteItem
m_sqlDB.execSql( QString("DELETE FROM Images "
"WHERE dirid=%1 AND name='%2';")
.arg(albumID)
@@ -1388,6 +1602,7 @@
void kio_digikamalbums::renameImage(int oldAlbumID, const QString& oldName,
int newAlbumID, const QString& newName)
{
+// code duplication from AlbumDB::deleteItem, AlbumDB::moveItem
// first delete any stale entries for the destination file
m_sqlDB.execSql( QString("DELETE FROM Images "
"WHERE dirid=%1 AND name='%2';")
@@ -1406,6 +1621,7 @@
void kio_digikamalbums::copyImage(int srcAlbumID, const QString& srcName,
int dstAlbumID, const QString& dstName)
{
+// code duplication from AlbumDB::copyItem
// check for src == dest
if (srcAlbumID == dstAlbumID && srcName == dstName)
{
More information about the Digikam-devel
mailing list