|
|
|
/*! @file
|
|
|
|
|
|
|
|
@id $Id$
|
|
|
|
*/
|
|
|
|
// 1 2 3 4 5 6 7 8
|
|
|
|
// 45678901234567890123456789012345678901234567890123456789012345678901234567890
|
|
|
|
|
|
|
|
#include <QtCore/QFile>
|
|
|
|
#include <QtCore/QDir>
|
|
|
|
#include <QtCore/QFileInfo>
|
|
|
|
#include <QtCore/QFileSystemWatcher>
|
|
|
|
#include <QtCore/QString>
|
|
|
|
#include <QtCore/QStringList>
|
|
|
|
|
|
|
|
#include <cassert>
|
|
|
|
|
|
|
|
//! Store string lists.
|
|
|
|
/** Abstract storage interface to string lists, such as bookmarks. */
|
|
|
|
class Storage: public QObject {
|
|
|
|
Q_OBJECT;
|
|
|
|
Q_SIGNALS:
|
|
|
|
//! Emitted if file content has changed.
|
|
|
|
void changed();
|
|
|
|
public:
|
|
|
|
Storage() {}
|
|
|
|
/*! @return true if readable or writable */
|
|
|
|
bool valid() {
|
|
|
|
return readable() || writeable();
|
|
|
|
}
|
|
|
|
/*! @return true if valid */
|
|
|
|
operator bool() {
|
|
|
|
return valid();
|
|
|
|
}
|
|
|
|
/*! @return true if storage object already exists */
|
|
|
|
virtual bool readable() = 0;
|
|
|
|
/*! @return true if storage object exists or could be created */
|
|
|
|
virtual bool writeable() = 0;
|
|
|
|
/*! @return storage content as string list */
|
|
|
|
virtual QStringList read() = 0;
|
|
|
|
//! Writes storage content from string list.
|
|
|
|
virtual bool write(const QStringList& out) = 0;
|
|
|
|
};
|
|
|
|
|
|
|
|
//! Implement @ref Storage for files.
|
|
|
|
class FileStorage: public Storage {
|
|
|
|
Q_OBJECT;
|
|
|
|
public:
|
|
|
|
/*! @param file full path to storage file */
|
|
|
|
FileStorage(QString file): _file(file) {
|
|
|
|
_watcher.addPath(QFileInfo(_file).absolutePath());
|
|
|
|
assert(connect(&_watcher, SIGNAL(directoryChanged(const QString&)),
|
|
|
|
SLOT(setupWatcher())));
|
|
|
|
assert(connect(&_watcher, SIGNAL(fileChanged(const QString&)),
|
|
|
|
SIGNAL(changed())));
|
|
|
|
}
|
|
|
|
bool readable() {
|
|
|
|
return QFileInfo(_file).exists();
|
|
|
|
}
|
|
|
|
bool writeable() {
|
|
|
|
return readable() ||
|
|
|
|
(!_file.fileName().isEmpty() &&
|
|
|
|
QFileInfo(_file).absoluteDir().exists());
|
|
|
|
}
|
|
|
|
QStringList read() {
|
|
|
|
QStringList res;
|
|
|
|
if (readable()) {
|
|
|
|
if (_file.open(QIODevice::ReadOnly))
|
|
|
|
res=QString::fromUtf8(_file.readAll()).split("\n");
|
|
|
|
_file.close();
|
|
|
|
}
|
|
|
|
return res;
|
|
|
|
}
|
|
|
|
bool write(const QStringList& out) {
|
|
|
|
bool res(false);
|
|
|
|
if (writeable()) {
|
|
|
|
if (_file.open(QIODevice::WriteOnly))
|
|
|
|
if (_file.write(out.join("\n").toUtf8())>=0) res=true;
|
|
|
|
_file.close();
|
|
|
|
}
|
|
|
|
return res;
|
|
|
|
}
|
|
|
|
private Q_SLOTS:
|
|
|
|
void setupWatcher() {
|
|
|
|
bool watching(_watcher.files().size());
|
|
|
|
if (watching) // remove watchlist if already existent
|
|
|
|
_watcher.removePaths(_watcher.files());
|
|
|
|
if (readable()) { // add file to watchlist
|
|
|
|
_watcher.addPath(_file.fileName());
|
|
|
|
if (!watching) // send change event if file is initially created
|
|
|
|
changed();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
private:
|
|
|
|
QFile _file;
|
|
|
|
QFileSystemWatcher _watcher;
|
|
|
|
};
|