File indexing completed on 2024-05-12 15:59:59
0001 /* This file is part of the KDE project 0002 SPDX-FileCopyrightText: 1998, 1999 David Faure <faure@kde.org> 0003 SPDX-FileCopyrightText: 2010 C. Boemann <cbo@boemann.dk> 0004 0005 SPDX-License-Identifier: LGPL-2.0-or-later 0006 */ 0007 0008 #ifndef __koStore_h_ 0009 #define __koStore_h_ 0010 0011 #include <QByteArray> 0012 #include <QIODevice> 0013 #include "kritastore_export.h" 0014 0015 class QWidget; 0016 class QUrl; 0017 class KoStorePrivate; 0018 0019 /** 0020 * Saves and loads Krita documents using various backends. Currently supported 0021 * backends are zip and directory. 0022 * We call a "store" the file on the hard disk (the one the users sees) 0023 * and call a "file" a file inside the store. 0024 */ 0025 class KRITASTORE_EXPORT KoStore 0026 { 0027 public: 0028 0029 enum Mode { Read, Write }; 0030 enum Backend { Auto, Zip, Directory }; 0031 0032 /** 0033 * Open a store (i.e. the representation on disk of a Krita document). 0034 * 0035 * @param fileName the name of the file to open 0036 * @param mode if KoStore::Read, open an existing store to read it. 0037 * if KoStore::Write, create or replace a store. 0038 * @param backend the backend to use for the data storage. 0039 * Auto means automatically-determined for reading, 0040 * and the current format (now Zip) for writing. 0041 * 0042 * @param appIdentification the application's mimetype, 0043 * to be written in the file for "mime-magic" identification. 0044 * Only meaningful if mode is Write, and if backend!=Directory. 0045 * 0046 * @param writeMimetype If true, some backends (notably the Zip 0047 * store) will write a file called 'mimetype' automatically and 0048 * fill it with data from the appIdentification. This is only 0049 * applicable if Mode is set to Write. 0050 */ 0051 static KoStore *createStore(const QString &fileName, Mode mode, 0052 const QByteArray &appIdentification = QByteArray(), 0053 Backend backend = Auto, bool writeMimetype = true); 0054 0055 /** 0056 * Create a store for any kind of QIODevice: file, memory buffer... 0057 * KoStore will take care of opening the QIODevice. 0058 * This method doesn't support the Directory store! 0059 */ 0060 static KoStore *createStore(QIODevice *device, Mode mode, 0061 const QByteArray &appIdentification = QByteArray(), 0062 Backend backend = Auto, bool writeMimetype = true); 0063 0064 0065 /** 0066 * Destroys the store (i.e. closes the file on the hard disk) 0067 */ 0068 virtual ~KoStore(); 0069 0070 /** 0071 * Open a new file inside the store 0072 * @param name The filename, internal representation ("root", "tar:/0"... ). 0073 * If the tar:/ prefix is missing it's assumed to be a relative URI. 0074 * @return true on success. 0075 */ 0076 bool open(const QString &name); 0077 0078 /** 0079 * Check whether a file inside the store is currently opened with open(), 0080 * ready to be read or written. 0081 * @return true if a file is currently opened. 0082 */ 0083 bool isOpen() const; 0084 0085 /** 0086 * Close the file inside the store 0087 * @return true on success. 0088 */ 0089 bool close(); 0090 0091 /** 0092 * Get a device for reading a file from the store directly 0093 * (slightly faster than read() calls) 0094 * You need to call @ref open first, and @ref close afterwards. 0095 */ 0096 QIODevice *device() const; 0097 0098 /** 0099 * Read data from the currently opened file. You can also use the streams 0100 * for this. 0101 */ 0102 QByteArray read(qint64 max); 0103 0104 /** 0105 * Write data into the currently opened file. You can also use the streams 0106 * for this. 0107 */ 0108 qint64 write(const QByteArray &data); 0109 0110 /** 0111 * Read data from the currently opened file. You can also use the streams 0112 * for this. 0113 * @return size of data read, -1 on error 0114 */ 0115 qint64 read(char *buffer, qint64 length); 0116 0117 /** 0118 * Write data into the currently opened file. You can also use the streams 0119 * for this. 0120 */ 0121 virtual qint64 write(const char* data, qint64 length); 0122 0123 /** 0124 * @return the size of the currently opened file, -1 on error. 0125 * Can be used as an argument for the read methods, for instance 0126 */ 0127 qint64 size() const; 0128 0129 /** 0130 * @return true if an error occurred 0131 */ 0132 bool bad() const; 0133 0134 /** 0135 * @return the mode used when opening, read or write 0136 */ 0137 Mode mode() const; 0138 0139 /** 0140 * If an store is opened for reading, then the directories 0141 * of the store can be accessed via this function. 0142 * 0143 * @return a stringlist with all directories found 0144 */ 0145 virtual QStringList directoryList() const; 0146 0147 /** 0148 * Enters one or multiple directories. In Read mode this actually 0149 * checks whether the specified directories exist and returns false 0150 * if they don't. In Write mode we don't create the directory, we 0151 * just use the "current directory" to generate the absolute path 0152 * if you pass a relative path (one not starting with tar:/) when 0153 * opening a stream. 0154 * Note: Operates on internal names 0155 */ 0156 virtual bool enterDirectory(const QString &directory); 0157 0158 /** 0159 * Leaves a directory. Equivalent to "cd .." 0160 * @return true on success, false if we were at the root already to 0161 * make it possible to "loop to the root" 0162 */ 0163 bool leaveDirectory(); 0164 0165 /** 0166 * Returns the current path including a trailing slash. 0167 * Note: Returns a path in "internal name" style 0168 */ 0169 QString currentPath() const; 0170 0171 /** 0172 * Stacks the current directory. Restore the current path using 0173 * @ref popDirectory . 0174 */ 0175 void pushDirectory(); 0176 0177 /** 0178 * Restores the previously pushed directory. No-op if the stack is 0179 * empty. 0180 */ 0181 void popDirectory(); 0182 0183 /** 0184 * @return true if the given file exists in the current directory, 0185 * i.e. if open(fileName) will work. 0186 */ 0187 bool hasFile(const QString &fileName) const; 0188 0189 /** 0190 *@return true if the given directory exists in the archive 0191 */ 0192 bool hasDirectory(const QString &directoryName); 0193 0194 /** 0195 * Extracts a file out of the store to a buffer 0196 * @param sourceName file in the store 0197 * @param data memory buffer 0198 */ 0199 bool extractFile(const QString &sourceName, QByteArray &data); 0200 0201 //@{ 0202 /// See QIODevice 0203 bool seek(qint64 pos); 0204 qint64 pos() const; 0205 bool atEnd() const; 0206 //@} 0207 0208 /** 0209 * Call this before destroying the store, to be able to catch errors 0210 * (e.g. from ksavefile) 0211 */ 0212 bool finalize(); 0213 0214 /** 0215 * Allow to enable or disable compression of the files. Only supported by the 0216 * ZIP backend. 0217 */ 0218 virtual void setCompressionEnabled(bool e); 0219 0220 /// When reading, in the paths in the store where name occurs, substitution is used. 0221 void setSubstitution(const QString &name, const QString &substitution); 0222 0223 protected: 0224 KoStore(Mode mode, bool writeMimetype = true); 0225 0226 /** 0227 * Finalize store - called by finalize. 0228 * @return true on success 0229 */ 0230 virtual bool doFinalize() { 0231 return true; 0232 } 0233 0234 /** 0235 * Open the file @p name in the store, for writing 0236 * On success, this method must set m_stream to a stream in which we can write. 0237 * @param name "absolute path" (in the archive) to the file to open 0238 * @return true on success 0239 */ 0240 virtual bool openWrite(const QString &name) = 0; 0241 /** 0242 * Open the file @p name in the store, for reading. 0243 * On success, this method must set m_stream to a stream from which we can read, 0244 * as well as setting m_iSize to the size of the file. 0245 * @param name "absolute path" (in the archive) to the file to open 0246 * @return true on success 0247 */ 0248 virtual bool openRead(const QString &name) = 0; 0249 0250 /** 0251 * @return true on success 0252 */ 0253 virtual bool closeRead() = 0; 0254 /** 0255 * @return true on success 0256 */ 0257 virtual bool closeWrite() = 0; 0258 0259 /** 0260 * Enter a subdirectory of the current directory. 0261 * The directory might not exist yet in Write mode. 0262 */ 0263 virtual bool enterRelativeDirectory(const QString &dirName) = 0; 0264 0265 /** 0266 * Enter a directory where we've been before. 0267 * It is guaranteed to always exist. 0268 */ 0269 virtual bool enterAbsoluteDirectory(const QString &path) = 0; 0270 0271 /** 0272 * Check if a file exists inside the store. 0273 * @param absPath the absolute path inside the store, i.e. not relative to the current directory 0274 */ 0275 virtual bool fileExists(const QString &absPath) const = 0; 0276 0277 protected: 0278 KoStorePrivate *d_ptr; 0279 0280 private: 0281 Q_DECLARE_PRIVATE(KoStore) 0282 0283 private: 0284 KoStore(const KoStore& store); ///< don't copy 0285 KoStore& operator=(const KoStore& store); ///< don't assign 0286 }; 0287 0288 #endif