|
1 /* borrowed from https://github.com/skhaz/qt-physfs-wrapper |
|
2 * TODO: add copyright header, determine license |
|
3 */ |
|
4 |
|
5 #include "FileEngine.h" |
|
6 |
|
7 FileEngine::FileEngine(const QString& filename) |
|
8 : _handler(NULL) |
|
9 , _flags(0) |
|
10 { |
|
11 setFileName(filename); |
|
12 } |
|
13 |
|
14 FileEngine::~FileEngine() |
|
15 { |
|
16 close(); |
|
17 } |
|
18 |
|
19 bool FileEngine::open(QIODevice::OpenMode openMode) |
|
20 { |
|
21 close(); |
|
22 |
|
23 if (openMode & QIODevice::WriteOnly) { |
|
24 _handler = PHYSFS_openWrite(_filename.toUtf8().constData()); |
|
25 _flags = QAbstractFileEngine::WriteOwnerPerm | QAbstractFileEngine::WriteUserPerm | QAbstractFileEngine::FileType; |
|
26 } |
|
27 |
|
28 else if (openMode & QIODevice::ReadOnly) { |
|
29 _handler = PHYSFS_openRead(_filename.toUtf8().constData()); |
|
30 } |
|
31 |
|
32 else if (openMode & QIODevice::Append) { |
|
33 _handler = PHYSFS_openAppend(_filename.toUtf8().constData()); |
|
34 } |
|
35 |
|
36 else { |
|
37 qWarning("Bad file open mode: %d", (int)openMode); |
|
38 } |
|
39 |
|
40 if (!_handler) { |
|
41 qWarning("Failed to open %s, reason: %s", _filename.toUtf8().constData(), PHYSFS_getLastError()); |
|
42 return false; |
|
43 } |
|
44 |
|
45 return true; |
|
46 } |
|
47 |
|
48 bool FileEngine::close() |
|
49 { |
|
50 if (isOpened()) { |
|
51 int result = PHYSFS_close(_handler); |
|
52 _handler = NULL; |
|
53 return result != 0; |
|
54 } |
|
55 |
|
56 return true; |
|
57 } |
|
58 |
|
59 bool FileEngine::flush() |
|
60 { |
|
61 return PHYSFS_flush(_handler) != 0; |
|
62 } |
|
63 |
|
64 qint64 FileEngine::size() const |
|
65 { |
|
66 return _size; |
|
67 } |
|
68 |
|
69 qint64 FileEngine::pos() const |
|
70 { |
|
71 return PHYSFS_tell(_handler); |
|
72 } |
|
73 |
|
74 bool FileEngine::seek(qint64 pos) |
|
75 { |
|
76 return PHYSFS_seek(_handler, pos) != 0; |
|
77 } |
|
78 |
|
79 bool FileEngine::isSequential() const |
|
80 { |
|
81 return true; |
|
82 } |
|
83 |
|
84 bool FileEngine::remove() |
|
85 { |
|
86 return PHYSFS_delete(_filename.toUtf8().constData()) != 0; |
|
87 } |
|
88 |
|
89 bool FileEngine::mkdir(const QString &dirName, bool createParentDirectories) const |
|
90 { |
|
91 Q_UNUSED(createParentDirectories); |
|
92 return PHYSFS_mkdir(dirName.toUtf8().constData()) != 0; |
|
93 } |
|
94 |
|
95 bool FileEngine::rmdir(const QString &dirName, bool recurseParentDirectories) const |
|
96 { |
|
97 Q_UNUSED(recurseParentDirectories); |
|
98 return PHYSFS_delete(dirName.toUtf8().constData()) != 0; |
|
99 } |
|
100 |
|
101 bool FileEngine::caseSensitive() const |
|
102 { |
|
103 return true; |
|
104 } |
|
105 |
|
106 bool FileEngine::isRelativePath() const |
|
107 { |
|
108 return true; |
|
109 } |
|
110 |
|
111 QStringList FileEngine::entryList(QDir::Filters filters, const QStringList &filterNames) const |
|
112 { |
|
113 Q_UNUSED(filters); |
|
114 |
|
115 QString file; |
|
116 QStringList result; |
|
117 char **files = PHYSFS_enumerateFiles(""); |
|
118 |
|
119 for (char **i = files; *i != NULL; i++) { |
|
120 file = QString::fromAscii(*i); |
|
121 if (QDir::match(filterNames, file)) { |
|
122 result << file; |
|
123 } |
|
124 } |
|
125 |
|
126 PHYSFS_freeList(files); |
|
127 return result; |
|
128 } |
|
129 |
|
130 QAbstractFileEngine::FileFlags FileEngine::fileFlags(FileFlags type) const |
|
131 { |
|
132 return type & _flags; |
|
133 } |
|
134 |
|
135 QString FileEngine::fileName(FileName file) const |
|
136 { |
|
137 if (file == QAbstractFileEngine::AbsolutePathName) |
|
138 return PHYSFS_getWriteDir(); |
|
139 |
|
140 return _filename; |
|
141 } |
|
142 |
|
143 QDateTime FileEngine::fileTime(FileTime time) const |
|
144 { |
|
145 switch (time) |
|
146 { |
|
147 case QAbstractFileEngine::ModificationTime: |
|
148 default: |
|
149 return _datetime; |
|
150 break; |
|
151 }; |
|
152 } |
|
153 |
|
154 void FileEngine::setFileName(const QString &file) |
|
155 { |
|
156 _filename = file; |
|
157 PHYSFS_Stat stat; |
|
158 if (PHYSFS_stat(_filename.toUtf8().constData(), &stat) != 0) { |
|
159 _size = stat.filesize; |
|
160 _datetime = QDateTime::fromTime_t(stat.modtime); |
|
161 _flags |= QAbstractFileEngine::ExistsFlag; |
|
162 |
|
163 switch (stat.filetype) |
|
164 { |
|
165 case PHYSFS_FILETYPE_REGULAR: |
|
166 _flags |= QAbstractFileEngine::FileType; |
|
167 break; |
|
168 |
|
169 case PHYSFS_FILETYPE_DIRECTORY: |
|
170 _flags |= QAbstractFileEngine::DirectoryType; |
|
171 break; |
|
172 case PHYSFS_FILETYPE_SYMLINK: |
|
173 _flags |= QAbstractFileEngine::LinkType; |
|
174 break; |
|
175 default: ; |
|
176 }; |
|
177 } |
|
178 } |
|
179 |
|
180 bool FileEngine::atEnd() const |
|
181 { |
|
182 return PHYSFS_eof(_handler) != 0; |
|
183 } |
|
184 |
|
185 qint64 FileEngine::read(char *data, qint64 maxlen) |
|
186 { |
|
187 return PHYSFS_readBytes(_handler, data, maxlen); |
|
188 } |
|
189 |
|
190 qint64 FileEngine::readLine(char *data, qint64 maxlen) |
|
191 { |
|
192 Q_UNUSED(data); |
|
193 Q_UNUSED(maxlen); |
|
194 // TODO |
|
195 return 0; |
|
196 } |
|
197 |
|
198 qint64 FileEngine::write(const char *data, qint64 len) |
|
199 { |
|
200 return PHYSFS_writeBytes(_handler, data, len); |
|
201 } |
|
202 |
|
203 bool FileEngine::isOpened() const |
|
204 { |
|
205 return _handler != NULL; |
|
206 } |
|
207 |
|
208 QFile::FileError FileEngine::error() const |
|
209 { |
|
210 return QFile::UnspecifiedError; |
|
211 } |
|
212 |
|
213 QString FileEngine::errorString() const |
|
214 { |
|
215 return PHYSFS_getLastError(); |
|
216 } |
|
217 |
|
218 bool FileEngine::supportsExtension(Extension extension) const |
|
219 { |
|
220 return extension == QAbstractFileEngine::AtEndExtension; |
|
221 } |
|
222 |
|
223 QAbstractFileEngine* FileEngineHandler::create(const QString &filename) const |
|
224 { |
|
225 return new FileEngine(filename); |
|
226 } |