diff options
author | am <am@f440f766-f032-0410-8965-dc7d17de2ca0> | 2009-07-11 16:32:41 +0000 |
---|---|---|
committer | am <am@f440f766-f032-0410-8965-dc7d17de2ca0> | 2009-07-11 16:32:41 +0000 |
commit | b6fbec29ad08a0607adf4b5d3fe5d8a237d1a970 (patch) | |
tree | 640ae442854672b279828bcd0fd39721bdc42835 | |
parent | b700071a54e9ce9e9097a704fb1d71dc2a795bfb (diff) | |
download | SheMov-b6fbec29ad08a0607adf4b5d3fe5d8a237d1a970.tar.gz SheMov-b6fbec29ad08a0607adf4b5d3fe5d8a237d1a970.tar.bz2 SheMov-b6fbec29ad08a0607adf4b5d3fe5d8a237d1a970.zip |
-implemented deleteFiles
-implemented refresh
-implemented copyFiles
-implemented moveFiles
-implemented renameFiles
git-svn-id: file:///var/svn/repos2/shemov/trunk@384 f440f766-f032-0410-8965-dc7d17de2ca0
-rw-r--r-- | filesystemwidget.cpp | 214 | ||||
-rw-r--r-- | filesystemwidget.h | 18 | ||||
-rw-r--r-- | fileview.cpp | 34 | ||||
-rw-r--r-- | fileview.h | 4 | ||||
-rw-r--r-- | messagedialog.cpp | 8 | ||||
-rw-r--r-- | messagedialog.h | 8 | ||||
-rw-r--r-- | shemov.cpp | 41 | ||||
-rw-r--r-- | shemov.h | 7 |
8 files changed, 324 insertions, 10 deletions
diff --git a/filesystemwidget.cpp b/filesystemwidget.cpp index c424eaa..aafcd6d 100644 --- a/filesystemwidget.cpp +++ b/filesystemwidget.cpp @@ -17,6 +17,11 @@ #include <QCompleter> #include <QProcess> #include <QApplication> +#include <QMessageBox> +#include <QFile> +#include <QAction> +#include <QRegExp> + #include <QDebug> #include "filesystemwidget.h" @@ -25,6 +30,7 @@ #include "shemoviconprovider.h" #include "filesystemfileproxy.h" #include "helper.h" +#include "messagedialog.h" FilesystemWidget::FilesystemWidget(QWidget *parent) : QWidget(parent) { mModel = new QDirModel; @@ -53,6 +59,10 @@ FilesystemWidget::FilesystemWidget(QWidget *parent) : QWidget(parent) { mFileView->setItemsExpandable(false); mFileView->setSelectionMode(QAbstractItemView::MultiSelection); + QString title = QString(tr("%1 - Rename file")).arg(qApp->applicationName()); + mRenameDialog = new MessageDialog(tr("Rename dummy to:"), title, this); + connect(mRenameDialog, SIGNAL(accepted()), this, SLOT(doRenameFile())); + QWidget *fileWidget = new QWidget; QHBoxLayout *directoryEdit = new QHBoxLayout; QLabel *dirLabel = new QLabel(tr("&Directory")); @@ -155,7 +165,145 @@ void FilesystemWidget::parentDir(){ if(idx.parent().isValid()){ mDirView->setCurrentIndex(idx.parent()); } - mFileView->selectionModel()->clearSelection(); +} + +void FilesystemWidget::deleteFiles(){ + QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(mFileView->model()); + QModelIndexList selected = mFileView->selectionModel()->selectedRows(); + int count(0); + if(!selected.isEmpty()){ + count = selected.count(); + QAction *refresh = action(mFileView, "RE"); + if(refresh){ + // a refresh would invalidate selection + refresh->setEnabled(false); + } + QString message = QString(tr("Really delete %1 files?")).arg(QString::number(selected.count())); + int retval = QMessageBox::question(this, tr("Question"), message, QMessageBox::Yes | QMessageBox::No); + if(retval == QMessageBox::Yes){ + foreach(QModelIndex idx, selected){ + QModelIndex real = proxy->mapToSource(idx); + deleteRecursive(mModel->fileInfo(real)); + } + } + mFileView->selectionModel()->clearSelection(); + mModel->refresh(QModelIndex()); + if(refresh){ + refresh->setEnabled(true); + } + }else{ + count = 1; + QModelIndex cur = mFileView->currentIndex(); + QModelIndex real = proxy->mapToSource(cur); + QString message = QString(tr("Really delete %1?")).arg(mModel->fileName(real)); + int retval = QMessageBox::question(this, tr("Question"), message, QMessageBox::Yes | QMessageBox::No); + if(retval == QMessageBox::Yes){ + deleteRecursive(mModel->fileInfo(real)); + mModel->refresh(real.parent()); + } + } + QString message = QString(tr("Deleted %1 file(s)")).arg(count); + emit statusbarMessage(message); +} + +void FilesystemWidget::copyFiles(){ + QModelIndexList selected = mFileView->selectionModel()->selectedRows(); + if(selected.isEmpty()){ + emit statusbarMessage(tr("No files selected!")); + return; + } + QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(mFileView->model()); + QModelIndex rootIndex = proxy->mapToSource(mFileView->rootIndex()); + QFileInfo root = mModel->fileInfo(rootIndex); + QString message = QString(tr("Really copy %1 files to %2?")).arg(selected.count()).arg(root.absoluteFilePath()); + int retval = QMessageBox::question(this, tr("Question"), message, QMessageBox::Yes | QMessageBox::No); + if(retval == QMessageBox::Yes){ + QAction *refresh = action(mFileView, "RE"); + if(refresh){ + refresh->setEnabled(false); + } + int files(0), dirs(0), failed(0); + foreach(QModelIndex idx, selected){ + QModelIndex real = proxy->mapToSource(idx); + QFileInfo info = mModel->fileInfo(real); + if(info.isDir()){ + ++dirs; + copyRecursive(info, root.absoluteFilePath()); + }else{ + QString newFile = QString("%1/%2").arg(root.absoluteFilePath()).arg(info.fileName()); + if(QFile::copy(info.absoluteFilePath(), newFile)){ + ++files; + }else{ + ++failed; + } + } + } + QString message = QString(tr("Successfully copied %1 files and %2 directories, %3 errors")).arg(files).arg(dirs).arg(failed); + statusbarMessage(message); + mFileView->selectionModel()->clearSelection(); + mModel->refresh(rootIndex); + if(refresh){ + refresh->setEnabled(true); + } + } +} + +void FilesystemWidget::moveFiles(){ + QModelIndexList selected = mFileView->selectionModel()->selectedRows(); + if(selected.isEmpty()){ + emit statusbarMessage(tr("No files selected!")); + return; + } + QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(mFileView->model()); + QModelIndex rootIndex = proxy->mapToSource(mFileView->rootIndex()); + QFileInfo root = mModel->fileInfo(rootIndex); + QString message = QString(tr("Really move %1 file(s) to %2?")).arg(selected.count()).arg(root.absoluteFilePath()); + int retval = QMessageBox::question(this, tr("Question"), message, QMessageBox::Yes | QMessageBox::No); + if(retval == QMessageBox::Yes){ + QAction *refresh = action(mFileView, "RE"); + if(refresh){ + refresh->setEnabled(false); + } + int success(0), failed(0); + foreach(QModelIndex cur, selected){ + QModelIndex real = proxy->mapToSource(cur); + QFileInfo info = mModel->fileInfo(real); + QString dest = QString("%1/%2").arg(root.absoluteFilePath()).arg(info.fileName()); + if(QFile::rename(info.absoluteFilePath(), dest)){ + ++success; + }else{ + ++failed; + } + } + QString message = QString(tr("Successfully moved %1 file(s), %2 errors")).arg(success).arg(failed); + emit statusbarMessage(message); + if(refresh){ + refresh->setEnabled(true); + } + mFileView->selectionModel()->clearSelection(); + mModel->refresh(QModelIndex()); + } +} + +void FilesystemWidget::renameFile(){ + QModelIndex cur = mFileView->currentIndex(); + if(!cur.isValid()){ + emit statusbarMessage(tr("Nothing to rename!")); + return; + } + QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(mFileView->model()); + QModelIndex source = proxy->mapToSource(cur); + QFileInfo info = mModel->fileInfo(source); + QString text = QString(tr("Rename %1 to:")).arg(info.fileName()); + mRenameDialog->setMessage(text); + QString newFilename = info.fileName().toLower(); + QRegExp re2("['#()&%!]+"); + newFilename.replace(re2, " "); + QRegExp re1("\\s{2,}"); + newFilename.replace(re1, " "); + newFilename.replace(' ', '.'); + mRenameDialog->setText(newFilename); + mRenameDialog->exec(); } void FilesystemWidget::setWindowTitle(const QString &dir){ @@ -163,3 +311,67 @@ void FilesystemWidget::setWindowTitle(const QString &dir){ emit windowTitle(mWindowTitle); } +void FilesystemWidget::deleteRecursive(const QFileInfo &start){ + if(start.isDir()){ + QDir curDir = QDir(start.absoluteFilePath());; + foreach(QFileInfo info, curDir.entryInfoList(QDir::AllEntries | QDir::NoDotAndDotDot)){ + if(info.isDir()){ + deleteRecursive(info); + }else{ + QFile::remove(info.absoluteFilePath()); + } + } + QDir dir = start.absoluteDir(); + dir.rmdir(start.fileName()); + }else{ + QFile::remove(start.absoluteFilePath()); + } +} + +void FilesystemWidget::copyRecursive(const QFileInfo &start, const QString &destdir){ + if(!start.isDir()){ + return; + } + QDir source(start.absoluteFilePath()); + QDir dest = QDir(destdir); + if(!dest.exists(source.dirName())){ + dest.mkdir(source.dirName()); + } + QString d = QString("%1/%2").arg(destdir).arg(source.dirName()); + foreach(QFileInfo cur, source.entryInfoList(QDir::AllEntries | QDir::NoDotAndDotDot)){ + if(cur.isDir()){ + copyRecursive(cur, d); + }else{ + QString destPath = QString("%1/%2").arg(d).arg(cur.fileName()); + QFile::copy(cur.absoluteFilePath(), destPath); + } + } +} + +void FilesystemWidget::doRenameFile(){ + QString name = mRenameDialog->text(); + QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(mFileView->model()); + QModelIndex cur = mFileView->currentIndex(); + QModelIndex real = proxy->mapToSource(cur); + QFileInfo info = mModel->fileInfo(real); + QString newName = QString("%1/%2").arg(info.absolutePath()).arg(name); + if(QFile::rename(info.absoluteFilePath(), newName)){ + QString message = QString(tr("Renamed %1 to %2")).arg(info.absoluteFilePath()).arg(newName); + emit statusbarMessage(message); + mModel->refresh(real.parent()); + } + QFileInfo n(newName); + mTemplate = n.completeBaseName(); + emit newTemplate(mTemplate); +} + +QAction * FilesystemWidget::action(QWidget *widget, const QVariant &data) const{ + QAction *retval = 0; + foreach(QAction *a, widget->actions()){ + if(a->data() == data){ + retval = a; + break; + } + } + return retval; +} diff --git a/filesystemwidget.h b/filesystemwidget.h index a5d89d7..18cc17a 100644 --- a/filesystemwidget.h +++ b/filesystemwidget.h @@ -17,6 +17,10 @@ class FileView; class QModelIndex; class FilesystemFileProxy; class QLineEdit; +class QFileInfo; +class QAction; +class QVariant; +class MessageDialog; class FilesystemWidget : public QWidget { Q_OBJECT @@ -28,15 +32,27 @@ class FilesystemWidget : public QWidget { signals: void windowTitle(const QString &); + void statusbarMessage(const QString &); + void newTemplate(const QString &); public slots: void directoryChanged(const QModelIndex &selected, const QModelIndex &); void directoryEdited(); void fileViewActivated(const QModelIndex &index); void parentDir(); + void deleteFiles(); + void copyFiles(); + void moveFiles(); + void renameFile(); + + private slots: + void doRenameFile(); private: void setWindowTitle(const QString &dir); + void deleteRecursive(const QFileInfo &start); + void copyRecursive(const QFileInfo &start, const QString &destdir); + QAction *action(QWidget *widget, const QVariant &data) const; QDirModel *mModel; QTreeView *mDirView; FileView *mFileView; @@ -44,6 +60,8 @@ class FilesystemWidget : public QWidget { FilesystemFileProxy *mFileProxy; QLineEdit *mDirEdit; QString mWindowTitle; + MessageDialog *mRenameDialog; + QString mTemplate; }; #endif diff --git a/fileview.cpp b/fileview.cpp index 5995d60..adc8eeb 100644 --- a/fileview.cpp +++ b/fileview.cpp @@ -13,19 +13,33 @@ #include <QRegExp> #include <QDirModel> #include <QSortFilterProxyModel> +#include <QAction> +#include <QApplication> #include <QDebug> #include "fileview.h" #include "messagedialog.h" -FileView::FileView(QWidget *parent) : QTreeView(parent) { +FileView::FileView(QWidget *parent) : QTreeView(parent), mDeleteA(0) { setRootIsDecorated(false); - mMarkDialog = new MessageDialog(tr("Enter pattern to mark"), this); + QString title = QString("%1 - %2"); + QString markTitle = title.arg(qApp->applicationName(), tr("Mark files")); + mMarkDialog = new MessageDialog(tr("Enter pattern to mark"), markTitle, this); connect(mMarkDialog, SIGNAL(accepted()), this, SLOT(doMark())); - mCreateFolderDialog = new MessageDialog(tr("Enter folder name"), this); + QString folderTitle = title.arg(qApp->applicationName(), tr("Create folder")); + mCreateFolderDialog = new MessageDialog(tr("Enter folder name"), folderTitle, this); connect(mCreateFolderDialog, SIGNAL(accepted()), this, SLOT(doCreateFolder())); } +void FileView::findActions(){ + foreach(QAction *a, actions()){ + if(a->data().toString() == "DA"){ + mDeleteA = a; + } + } + Q_ASSERT(mDeleteA != 0); +} + void FileView::markFiles(){ mMarkDialog->show(); } @@ -38,6 +52,14 @@ void FileView::createFolder(){ mCreateFolderDialog->show(); } +void FileView::refresh(){ + QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(model()); + QDirModel *model = static_cast<QDirModel*>(proxy->sourceModel()); + QModelIndex root = rootIndex(); + QModelIndex real = proxy->mapToSource(root); + model->refresh(root); +} + void FileView::doMark(){ int rowCount = model()->rowCount(rootIndex()); QString sRegex = mMarkDialog->text(); @@ -91,7 +113,7 @@ void FileView::contextMenuEvent(QContextMenuEvent *e){ int ctr(0); foreach(QAction *a, actions()){ contextMenu.addAction(a); - if((ctr == 1)){ + if((ctr == 1) || (ctr == 2)){ contextMenu.addSeparator(); } ++ctr; @@ -110,6 +132,10 @@ void FileView::keyPressEvent(QKeyEvent *e){ emit enterPressed(currentIndex()); e->accept(); break; + case Qt::Key_Delete: + mDeleteA->trigger(); + e->accept(); + break; default: QTreeView::keyPressEvent(e); } @@ -15,12 +15,14 @@ class QKeyEvent; class QResizeEvent; class MessageDialog; class QModelIndex; +class QAction; class FileView : public QTreeView { Q_OBJECT public: FileView(QWidget *parent = 0); ~FileView() {}; + void findActions(); signals: void upDir(); @@ -31,6 +33,7 @@ class FileView : public QTreeView { void markFiles(); void unmarkFiles(); void createFolder(); + void refresh(); private slots: void doMark(); @@ -44,6 +47,7 @@ class FileView : public QTreeView { private: MessageDialog *mMarkDialog; MessageDialog *mCreateFolderDialog; + QAction *mDeleteA; }; #endif diff --git a/messagedialog.cpp b/messagedialog.cpp index c3261aa..241a2cc 100644 --- a/messagedialog.cpp +++ b/messagedialog.cpp @@ -13,11 +13,11 @@ #include "messagedialog.h" -MessageDialog::MessageDialog(const QString &message, QWidget *parent, Qt::WindowFlags f) : QDialog(parent, f){ +MessageDialog::MessageDialog(const QString &message, const QString &title, QWidget *parent, Qt::WindowFlags f) : QDialog(parent, f){ mEdit = new QLineEdit; mOk = new QPushButton(tr("Ok")); mCancel = new QPushButton(tr("Cancel")); - QLabel *m = new QLabel(message); + mMessage = new QLabel(message); QHBoxLayout *buttonLayout = new QHBoxLayout; buttonLayout->addStretch(); @@ -25,7 +25,7 @@ MessageDialog::MessageDialog(const QString &message, QWidget *parent, Qt::Window buttonLayout->addWidget(mCancel); QVBoxLayout *mainLayout = new QVBoxLayout; - mainLayout->addWidget(m); + mainLayout->addWidget(mMessage); mainLayout->addWidget(mEdit); mainLayout->addLayout(buttonLayout); @@ -34,7 +34,7 @@ MessageDialog::MessageDialog(const QString &message, QWidget *parent, Qt::Window connect(mCancel, SIGNAL(clicked()), this, SLOT(reject())); setLayout(mainLayout); - setWindowTitle(tr("SheMov - Mark files")); + setWindowTitle(title); } void MessageDialog::accept(){ diff --git a/messagedialog.h b/messagedialog.h index 217feef..efb7303 100644 --- a/messagedialog.h +++ b/messagedialog.h @@ -10,6 +10,7 @@ #include <QDialog> #include <QLineEdit> +#include <QLabel> class QPushButton; class QString; @@ -17,9 +18,12 @@ class QString; class MessageDialog : public QDialog { Q_OBJECT public: - MessageDialog(const QString &message, QWidget *parent = 0, Qt::WindowFlags f = 0); + MessageDialog(const QString &message, const QString &title, QWidget *parent = 0, Qt::WindowFlags f = 0); ~MessageDialog() {}; const QString text() const { return mEdit->text(); }; + void setMessage(const QString &message) { mMessage->setText(message); }; + void setTitle(const QString &title) { mTitle = title; }; + void setText(const QString &text) { mEdit->setText(text); }; public slots: void accept(); @@ -28,6 +32,8 @@ class MessageDialog : public QDialog { QLineEdit *mEdit; QPushButton *mOk; QPushButton *mCancel; + QLabel *mMessage; + QString mTitle; }; #endif @@ -34,9 +34,13 @@ SheMov::SheMov(QWidget *parent, Qt::WindowFlags flags) : QMainWindow(parent, fla createActions(); createMenus(); + mFSWidget->fileView()->findActions(); + connect(mFSWidget->fileView()->selectionModel(), SIGNAL(selectionChanged(const QItemSelection &, const QItemSelection &)), this, SLOT(updateSelectionCount(const QItemSelection &, const QItemSelection &))); connect(mFSWidget, SIGNAL(windowTitle(const QString &)), this, SLOT(newWindowTitle(const QString &))); connect(mFSWidget->fileView(), SIGNAL(statusbarMessage(const QString &)), this, SLOT(statusbarMessage(const QString &))); + connect(mFSWidget, SIGNAL(statusbarMessage(const QString &)), this, SLOT(statusbarMessage(const QString &))); + connect(mFSWidget, SIGNAL(newTemplate(const QString &)), this, SLOT(setTemplate(const QString &))); QWidget *centralWidget = new QWidget; centralWidget->setLayout(mainLayout); @@ -57,12 +61,21 @@ void SheMov::statusbarMessage(const QString &message){ statusBar()->showMessage(message); } +void SheMov::setTemplate(const QString &newTemplate){ + mTemplate->setText(newTemplate); +} + void SheMov::createStatusbar(){ QLabel *selCountL = new QLabel(tr("Sel. Items")); mSelectedItems = new QLabel("0"); mSelectedItems->setFrameStyle(QFrame::Panel | QFrame::Sunken); statusBar()->addPermanentWidget(selCountL); statusBar()->addPermanentWidget(mSelectedItems); + QLabel *templateL = new QLabel(tr("Template")); + mTemplate = new QLabel(tr("No template set")); + mTemplate->setFrameStyle(QFrame::Panel | QFrame::Sunken); + statusBar()->addPermanentWidget(templateL); + statusBar()->addPermanentWidget(mTemplate); } void SheMov::createActions(){ @@ -81,6 +94,28 @@ void SheMov::createActions(){ mCreateFolderA->setShortcut(tr("CTRL+n")); connect(mCreateFolderA, SIGNAL(triggered()), mFSWidget->fileView(), SLOT(createFolder())); mFSWidget->fileView()->addAction(mCreateFolderA); + mDeleteFilesA = new QAction(tr("Delete selected..."), this); + mDeleteFilesA->setShortcut(tr("CTRL+d")); + mDeleteFilesA->setData("DA"); + connect(mDeleteFilesA, SIGNAL(triggered()), mFSWidget, SLOT(deleteFiles())); + mFSWidget->fileView()->addAction(mDeleteFilesA); + mRefreshA = new QAction(tr("Refresh"), this); + mRefreshA->setShortcut(Qt::Key_F4); + mRefreshA->setData("RE"); + connect(mRefreshA, SIGNAL(triggered()), mFSWidget->fileView(), SLOT(refresh())); + mFSWidget->fileView()->addAction(mRefreshA); + mCopyA = new QAction(tr("Copy file(s)..."), this); + mCopyA->setShortcut(tr("CTRL+v")); + connect(mCopyA, SIGNAL(triggered()), mFSWidget, SLOT(copyFiles())); + mFSWidget->fileView()->addAction(mCopyA); + mMoveA = new QAction(tr("Move file(s)..."), this); + mMoveA->setShortcut(tr("CTRL+m")); + connect(mMoveA, SIGNAL(triggered()), mFSWidget, SLOT(moveFiles())); + mFSWidget->fileView()->addAction(mMoveA); + mRenameA = new QAction(tr("Rename file..."), this); + mRenameA->setShortcut(tr("CTRL+r")); + connect(mRenameA, SIGNAL(triggered()), mFSWidget, SLOT(renameFile())); + mFSWidget->fileView()->addAction(mRenameA); } void SheMov::createMenus(){ @@ -91,7 +126,13 @@ void SheMov::createMenus(){ editMenu->addAction(mUnmarkFilesA); editMenu->addSeparator(); editMenu->addAction(mCreateFolderA); + editMenu->addAction(mDeleteFilesA); + editMenu->addSeparator(); + editMenu->addAction(mCopyA); + editMenu->addAction(mMoveA); + editMenu->addAction(mRenameA); editMenu->addSeparator(); + editMenu->addAction(mRefreshA); menuBar()->addMenu(fileMenu); menuBar()->addMenu(editMenu); @@ -26,6 +26,7 @@ class SheMov : public QMainWindow { void updateSelectionCount(const QItemSelection &sel, const QItemSelection &prev); void newWindowTitle(const QString &title); void statusbarMessage(const QString &message); + void setTemplate(const QString &newTemplate); private: void createStatusbar(); @@ -34,12 +35,18 @@ class SheMov : public QMainWindow { //Statusbar Items QLabel *mSelectedItems; + QLabel *mTemplate; //Actions QAction *mQuitA; QAction *mMarkFilesA; QAction *mUnmarkFilesA; QAction *mCreateFolderA; + QAction *mDeleteFilesA; + QAction *mRefreshA; + QAction *mCopyA; + QAction *mMoveA; + QAction *mRenameA; //EndActions QTabWidget *mTab; |