option to enter new name in overwrite dialog
[case] / src / fileoperator.h
1 // case - file manager for N900
2 // Copyright (C) 2010 Lukas Hrazky <lukkash@email.cz>
3 // 
4 // This program is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU General Public License as published by
6 // the Free Software Foundation, either version 3 of the License, or
7 // (at your option) any later version.
8 // 
9 // This program is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU General Public License for more details.
13 // 
14 // You should have received a copy of the GNU General Public License
15 // along with this program. If not, see <http://www.gnu.org/licenses/>.
16
17
18 #ifndef FILEOPERATOR_H
19 #define FILEOPERATOR_H
20
21 #include <QWidget>
22 #include <QProgressBar>
23 #include <QFileInfo>
24 #include <QThread>
25 #include <QMutex>
26 #include <QWaitCondition>
27 #include <QDir>
28 #include <QMap>
29 #include <QSet>
30
31
32 class FileManipulatorThread;
33
34
35 class FileOperator : public QWidget {
36     Q_OBJECT
37
38 public:
39     // DONT_ASK_ONCE is a hackish way to avoid asking twice to overwrite the same directory when moving
40     enum Response{NONE, ABORT, RETRY, IGNORE, KEEP, OVERWRITE, SKIP_DIR, ASK, DONT_ASK_ONCE};
41
42     FileOperator(QWidget *parent = 0);
43
44     static QString shortenPath(const QString &path);
45
46     void deleteFiles(const QFileInfoList &files);
47     void copyFiles(const QFileInfoList &files, QDir &destination);
48     void moveFiles(const QFileInfoList &files, QDir &destination);
49
50 public slots:
51     void showErrorPrompt(FileManipulatorThread* manipulator,
52         const QString &message,
53         const QString &fileName,
54         const int err);
55     void showOverwritePrompt(FileManipulatorThread* manipulator,
56         const QString &fileName,
57         const bool dirOverDir);
58     void showInputFilenamePrompt(FileManipulatorThread* manipulator,
59         const QFileInfo &fileName,
60         const bool dirOverDir);
61
62     void remove(FileManipulatorThread* manipulator);
63     void setBarSize(FileManipulatorThread* manipulator, unsigned int size);
64     void updateProgress(FileManipulatorThread* manipulator, int value);
65
66 protected:
67     void caterNewThread(FileManipulatorThread *thread);
68
69     QList<FileManipulatorThread*> manipulatorList;
70 };
71
72
73 class FileManipulatorThread : public QThread {
74     Q_OBJECT
75
76 public:
77     explicit FileManipulatorThread(const QFileInfoList files, QDir dest = QDir());
78     ~FileManipulatorThread();
79     void setResponse(const FileOperator::Response response, const bool appyToAll = false, const int err = 0);
80
81     void setText(int value);
82
83     QProgressBar *progressBar;
84
85     time_t startTime;
86     QMutex mutex;
87     QWaitCondition waitCond;
88     // the new name entered from the overwrite dialog
89     QString newNameFromDialog;
90
91 protected:
92     void processFiles(const QFileInfoList &files);
93     virtual void perform(const QFileInfo &file) = 0;
94
95     bool remove(QString &fileName, const bool doUpdates = false);
96     bool remove(const QFileInfoList &files, const bool doUpdates = false);
97     bool remove(const QFileInfo &file, const bool doUpdates = false);
98
99     void copy(const QFileInfo &file);
100
101     unsigned int calculateFileSize(const QFileInfoList &files,
102         const bool count = false,
103         const bool addSize = false);
104
105     QFileInfoList listDirFiles(const QString &dirPath);
106
107     void setBarSize(unsigned int size);
108     void updateProgress(int value);
109     void updateFile(const QString &name);
110
111     // files to process by the operation
112     const QFileInfoList files;
113     // destination for files - changes as the operation recurses into directories
114     QDir dest;
115
116     // responses from the dialog prompts (error and overwrite)
117     FileOperator::Response response;
118     FileOperator::Response overwriteAll;
119     // a flag to abort the operation
120     bool abort;
121     // an array indicating whether to always ignore the error of index errno
122     bool ignoreAll[256];
123
124     // set of files that won't be deleted by the remove(...) functions
125     // used when move(...) would not overwrite target file to ensure the source file doesn't get deleted
126     QSet<QString> removeExcludeFiles;
127
128     // A map of file paths to their size. Not the actual size, but what is calculated for the
129     // purpose of the progressbar for the given operation. So either fileSize/BLOCK_SIZE or simply
130     // 1 for a file and file count for dirs (or both for copy&delete)
131     QMap<QString, qint64> fileSizeMap;
132
133     // the name of the file thats being processed (for progressBar) and the text of the progressBar (the format)
134     QString fileName, barText;
135     // stamp of the last ETA recalculation - done every second
136     time_t lastTimeUpdate;
137     char timeBuf[10];
138     // progress information of the bar and for the current file
139     unsigned int barSize, barValue, fileSize, fileValue;
140
141 signals:
142     void showErrorPrompt(FileManipulatorThread*, const QString&, const QString&, const int);
143     void showOverwritePrompt(FileManipulatorThread*, const QString&, const bool);
144     void showInputFilenamePrompt(FileManipulatorThread*, const QFileInfo&, const bool);
145     void finished(FileManipulatorThread*);
146     void setBarSize(FileManipulatorThread*, unsigned int);
147     void updateProgress(FileManipulatorThread*, int);
148 };
149
150
151 class DeleteThread : public FileManipulatorThread {
152     Q_OBJECT
153
154 public:
155     explicit DeleteThread(const QFileInfoList &files);
156
157 protected:
158     void run();
159     virtual void perform(const QFileInfo &file);
160 };
161
162
163 class CopyThread : public FileManipulatorThread {
164     Q_OBJECT
165
166 public:
167     explicit CopyThread(const QFileInfoList &files, QDir &dest);
168
169 protected:
170     void run();
171     virtual void perform(const QFileInfo &file);
172 };
173
174
175 class MoveThread : public FileManipulatorThread {
176     Q_OBJECT
177
178 public:
179     explicit MoveThread(const QFileInfoList &files, QDir &dest);
180
181 protected:
182     void run();
183     virtual void perform(const QFileInfo &file);
184     void rename(const QFileInfoList &files, const QDir &dest);
185 };
186
187
188 #endif // FILEOPERATOR_H