/* 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 of the License, or (at your option) any later version. */ #include #include #include #include "smdirmodel.h" #include "smdirwatcher.h" #include "smtreeitem.h" #include "smglobals.h" #include "helper.h" SmDirModel::SmDirModel(const QStringList &headers, QObject *parent) : SmTreeModel(headers, parent), mHeaders(headers){ mWatch = new SmDirWatcher(this); connect(mWatch, SIGNAL(needRefresh()), this, SLOT(refresh())); mRunTimer = new QTimer(this); mRunTimer->setInterval(2000); connect(mRunTimer, SIGNAL(timeout()), mWatch, SLOT(start())); mRunTimer->start(); readSettings(); mCollector = mWatch->collector(); connect(mCollector, SIGNAL(population(SmTreeItem*)), this, SLOT(populate(SmTreeItem*))); connect(mCollector, SIGNAL(newData(QList,int)), this, SLOT(dirEvent(QList,int)), Qt::BlockingQueuedConnection); } SmDirModel::~SmDirModel(){ delete mWatch; delete mRunTimer; } QVariant SmDirModel::data(const QModelIndex &index, int role) const{ if(!index.isValid()){ return QVariant(); } SmTreeItem *i = itemAt(index); switch (role){ case NameRole: return i->data(Name); case SizeRole: return i->data(Size); case TypeRole: return i->data(Type); case CreatedRole: return i->data(Created); case Md5sumRole: return i->data(Md5sum); case DurationRole: return i->data(Duration); case BitrateRole: return i->data(Bitrate); case FullPathRole: return i->data(FullPath); case Qt::DecorationRole: { if(index.column() == 0){ QStringList mime = i->data(Type).toString().split('/'); if(mime.at(0) == "inode"){ return mIcons.value("folder"); } if(!mIcons.contains(mime.at(0))){ return mIcons.value("other"); } return mIcons.value(mime.at(0).toLower()); } } default: return SmTreeModel::data(index, role); } } bool SmDirModel::setData(const QModelIndex &index, const QVariant &value, int role){ if(!index.isValid()){ return false; } if(role == Qt::EditRole && index.column() == Name){ //this is a rename QString newName = value.toString(); if(newName.contains(QDir::separator())){ return false; } SmTreeItem *i = itemAt(index); QString old = i->data(FullPath).toString(); QString dir = fileInfo(index).absolutePath(); QString newPath = QString("%1/%2").arg(dir).arg(newName); QFile::rename(old, newPath); emit needResize(); // watcher->collector will do the rest return true; } return SmTreeModel::setData(index, value, role); } bool SmDirModel::isDir(const QModelIndex &idx) const { if(!idx.isValid()){ return false; } SmTreeItem *i = itemAt(idx); QFileInfo fi(i->data(FullPath).toString()); return fi.isDir(); } QDir SmDirModel::dir() const{ return QDir(mCurrentDir); } QFileInfo SmDirModel::fileInfo(const QModelIndex &idx) const { if(!idx.isValid()){ return QFileInfo(); } SmTreeItem *i = itemAt(idx); return QFileInfo(i->data(FullPath).toString()); } void SmDirModel::setDir(const QString &dir){ mCurrentDir = dir; mCollector->start(); mWatch->setDir(mCurrentDir); } void SmDirModel::dirEvent(const QList &data, int e){ if(e == SmDirWatcher::Added){ /* for some reason SmTreeModel::addRow() doesn't work, * couldn't figure it out in 5 hours, so customize it * and reset the model */ addFile(data); } QModelIndex idx = find(data.at(Name), Name, rootIndex()); if(e == SmDirWatcher::Deleted){ removeRow(idx.row()); } if(e == SmDirWatcher::Modified){ for(int i = 0; i < mHeaders.count(); ++i){ QModelIndex c = index(idx.row(), i, QModelIndex()); setData(c, data.at(i), Qt::EditRole); } } emit needResize(); } void SmDirModel::readSettings(){ const QHash icons = SmGlobals::instance()->icons(); QSettings s; QString iconName = s.value("ui/foldericon").toString(); mIcons.insert("folder", QIcon(icons.value(iconName))); iconName = s.value("ui/movieicon").toString(); mIcons.insert("video", QIcon(icons.value(iconName))); iconName = s.value("ui/pictureicon").toString(); mIcons.insert("image", QIcon(icons.value(iconName))); iconName = s.value("ui/othericon").toString(); mIcons.insert("other", QIcon(icons.value(iconName))); } void SmDirModel::refresh(){ } void SmDirModel::populate(SmTreeItem *root){ setRoot(root); emit needResize(); } void SmDirModel::addFile(const QList &data){ SmTreeItem *newItem = new SmTreeItem(data, root()); int w = root()->childCount(); int i = 0; while(i < root()->childCount()){ if(newItem->data(Name).toString().toLower() < root()->child(i)->data(Name).toString().toLower()){ w = i; break; } ++i; } beginResetModel(); root()->insertChild(w, newItem); endResetModel(); return; } const QList SmDirModel::fileData(const QFileInfo &fi) const{ QList data; data << fi.fileName() << fi.size(); QString mime = Helper::mimeType(fi.absoluteFilePath()); data << mime; data << fi.lastModified(); QList si = QList() << QVariant() << QVariant(); if(mime.startsWith("video")){ si = Helper::duration(fi.absoluteFilePath()); } data << Helper::md5Sum(fi.absoluteFilePath()); data << si << fi.absoluteFilePath(); return data; }