Gui: allow to configure the checks of the cache directory
This commit is contained in:
@@ -93,6 +93,7 @@
|
||||
#include "SpaceballEvent.h"
|
||||
#include "Control.h"
|
||||
#include "DocumentRecovery.h"
|
||||
#include "DlgSettingsCacheDirectory.h"
|
||||
#include "TransactionObject.h"
|
||||
#include "FileDialog.h"
|
||||
#include "ExpressionBindingPy.h"
|
||||
@@ -2422,6 +2423,7 @@ void Application::checkForPreviousCrashes()
|
||||
|
||||
// If the recovery dialog wasn't shown check the cache size periodically
|
||||
Gui::Dialog::ApplicationCache cache;
|
||||
cache.applyUserSettings();
|
||||
if (cache.periodicCheckOfSize()) {
|
||||
qint64 total = cache.size();
|
||||
cache.performAction(total);
|
||||
|
||||
@@ -328,6 +328,7 @@ SET(Gui_UIC_SRCS
|
||||
DlgPropertyLink.ui
|
||||
DlgReportView.ui
|
||||
DlgSettings3DView.ui
|
||||
DlgSettingsCacheDirectory.ui
|
||||
DlgSettingsNavigation.ui
|
||||
DlgSettingsSelection.ui
|
||||
DlgSettingsUnits.ui
|
||||
@@ -563,6 +564,7 @@ SET(Dialog_Settings_CPP_SRCS
|
||||
DlgPreferencesImp.cpp
|
||||
DlgReportViewImp.cpp
|
||||
DlgSettings3DViewImp.cpp
|
||||
DlgSettingsCacheDirectory.cpp
|
||||
DlgSettingsNavigation.cpp
|
||||
DlgSettingsSelection.cpp
|
||||
DlgSettingsUnitsImp.cpp
|
||||
@@ -580,6 +582,7 @@ SET(Dialog_Settings_HPP_SRCS
|
||||
DlgPreferencesImp.h
|
||||
DlgReportViewImp.h
|
||||
DlgSettings3DViewImp.h
|
||||
DlgSettingsCacheDirectory.h
|
||||
DlgSettingsNavigation.h
|
||||
DlgSettingsSelection.h
|
||||
DlgSettingsUnitsImp.h
|
||||
@@ -599,6 +602,7 @@ SET(Dialog_Settings_SRCS
|
||||
DlgPreferences.ui
|
||||
DlgReportView.ui
|
||||
DlgSettings3DView.ui
|
||||
DlgSettingsCacheDirectory.ui
|
||||
DlgSettingsNavigation.ui
|
||||
DlgSettingsSelection.ui
|
||||
DlgSettingsUnits.ui
|
||||
|
||||
391
src/Gui/DlgSettingsCacheDirectory.cpp
Normal file
391
src/Gui/DlgSettingsCacheDirectory.cpp
Normal file
@@ -0,0 +1,391 @@
|
||||
/***************************************************************************
|
||||
* Copyright (c) 2021 Werner Mayer <wmayer[at]users.sourceforge.net> *
|
||||
* *
|
||||
* This file is part of the FreeCAD CAx development system. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Library General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
|
||||
* GNU Library General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Library General Public *
|
||||
* License along with this library; see the file COPYING.LIB. If not, *
|
||||
* write to the Free Software Foundation, Inc., 59 Temple Place, *
|
||||
* Suite 330, Boston, MA 02111-1307, USA *
|
||||
* *
|
||||
***************************************************************************/
|
||||
|
||||
|
||||
#include "PreCompiled.h"
|
||||
|
||||
#ifndef _PreComp_
|
||||
# include <QCoreApplication>
|
||||
# include <QDate>
|
||||
# include <QDesktopServices>
|
||||
# include <QDir>
|
||||
# include <QLocale>
|
||||
# include <QMessageBox>
|
||||
# include <QSettings>
|
||||
# include <QUrl>
|
||||
# include <climits>
|
||||
# include <cmath>
|
||||
#endif
|
||||
|
||||
#include "DlgSettingsCacheDirectory.h"
|
||||
#include "ui_DlgSettingsCacheDirectory.h"
|
||||
#include "DocumentRecovery.h"
|
||||
#include "MainWindow.h"
|
||||
#include <App/Application.h>
|
||||
#include <App/Document.h>
|
||||
|
||||
using namespace Gui::Dialog;
|
||||
|
||||
/* TRANSLATOR Gui::Dialog::DlgSettingsCacheDirectory */
|
||||
|
||||
QString DlgSettingsCacheDirectory::currentSize;
|
||||
|
||||
DlgSettingsCacheDirectory::DlgSettingsCacheDirectory(QWidget* parent)
|
||||
: PreferencePage(parent)
|
||||
, ui(new Ui_DlgSettingsCacheDirectory)
|
||||
{
|
||||
ui->setupUi(this);
|
||||
ui->labelCache->setToolTip(tr("Notify the user if the cache size exceeds the specified limit"));
|
||||
if (currentSize.isEmpty())
|
||||
currentSize = tr("Unknown");
|
||||
setCurrentCacheSize(currentSize);
|
||||
|
||||
QString path = QString::fromStdString(App::Application::getUserCachePath());
|
||||
ui->cacheLocation->setText(path);
|
||||
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("100 MB"), 100);
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("300 MB"), 300);
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("500 MB"), 500);
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("1 GB"), 1024);
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("2 GB"), 2048);
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("3 GB"), 3072);
|
||||
|
||||
connect(ui->pushButtonCheck, &QPushButton::clicked, this, &DlgSettingsCacheDirectory::runCheck);
|
||||
connect(ui->openButton, &QPushButton::clicked, this, &DlgSettingsCacheDirectory::openDirectory);
|
||||
}
|
||||
|
||||
DlgSettingsCacheDirectory::~DlgSettingsCacheDirectory()
|
||||
{
|
||||
}
|
||||
|
||||
void DlgSettingsCacheDirectory::saveSettings()
|
||||
{
|
||||
ApplicationCacheSettings::setCheckPeriod(ui->comboBoxPeriod->currentIndex());
|
||||
ApplicationCacheSettings::setCacheSizeLimit(ui->comboBoxLimit->currentData().toUInt());
|
||||
}
|
||||
|
||||
void DlgSettingsCacheDirectory::loadSettings()
|
||||
{
|
||||
int period = ApplicationCacheSettings::getCheckPeriod();
|
||||
if (period >= 0 && period < ui->comboBoxPeriod->count())
|
||||
ui->comboBoxPeriod->setCurrentIndex(period);
|
||||
unsigned int limit = ApplicationCacheSettings::getCacheSizeLimit();
|
||||
int index = ui->comboBoxLimit->findData(limit);
|
||||
|
||||
// if not found then add a new item with this value
|
||||
if (index < 0) {
|
||||
ui->comboBoxLimit->addItem(QString::fromLatin1("%1 MB").arg(limit), limit);
|
||||
index = ui->comboBoxLimit->count() - 1;
|
||||
}
|
||||
ui->comboBoxLimit->setCurrentIndex(index);
|
||||
}
|
||||
|
||||
void DlgSettingsCacheDirectory::changeEvent(QEvent *e)
|
||||
{
|
||||
if (e->type() == QEvent::LanguageChange) {
|
||||
int period = ui->comboBoxPeriod->currentIndex();
|
||||
ui->retranslateUi(this);
|
||||
ui->comboBoxPeriod->setCurrentIndex(period);
|
||||
setCurrentCacheSize(currentSize);
|
||||
}
|
||||
QWidget::changeEvent(e);
|
||||
}
|
||||
|
||||
void DlgSettingsCacheDirectory::setCurrentCacheSize(const QString& str)
|
||||
{
|
||||
currentSize = str;
|
||||
ui->labelCurrentCache->setText(tr("Current cache size: %1").arg(str));
|
||||
}
|
||||
|
||||
void DlgSettingsCacheDirectory::runCheck()
|
||||
{
|
||||
Gui::Dialog::ApplicationCache cache;
|
||||
unsigned int sizeInMB = ui->comboBoxLimit->currentData().toUInt();
|
||||
cache.setLimit(ApplicationCache::toBytes(sizeInMB));
|
||||
qint64 total = cache.size();
|
||||
setCurrentCacheSize(ApplicationCache::toString(total));
|
||||
|
||||
// When performing the clean-up then recompute the new cache size
|
||||
if (cache.performAction(total)) {
|
||||
total = cache.size();
|
||||
setCurrentCacheSize(ApplicationCache::toString(total));
|
||||
}
|
||||
}
|
||||
|
||||
void DlgSettingsCacheDirectory::openDirectory()
|
||||
{
|
||||
QString path = QString::fromStdString(App::Application::getUserCachePath());
|
||||
QUrl url = QUrl::fromLocalFile(path);
|
||||
QDesktopServices::openUrl(url);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
ApplicationCache::ApplicationCache()
|
||||
{
|
||||
limit = std::pow(1024, 3);
|
||||
setPeriod(Period::Weekly);
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::setPeriod
|
||||
* Set the period to check for the cache size
|
||||
* \param period
|
||||
*/
|
||||
void ApplicationCache::setPeriod(ApplicationCache::Period period)
|
||||
{
|
||||
switch (period) {
|
||||
case Period::Always:
|
||||
numDays = -1;
|
||||
break;
|
||||
case Period::Daily:
|
||||
numDays = 1;
|
||||
break;
|
||||
case Period::Weekly:
|
||||
numDays = 7;
|
||||
break;
|
||||
case Period::Monthly:
|
||||
numDays = 31;
|
||||
break;
|
||||
case Period::Yearly:
|
||||
numDays = 365;
|
||||
break;
|
||||
case Period::Never:
|
||||
numDays = INT_MAX;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::setLimit
|
||||
* Set the limit in bytes to perform a check
|
||||
* \param value
|
||||
*/
|
||||
void ApplicationCache::setLimit(qint64 value)
|
||||
{
|
||||
limit = value;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::periodicCheckOfSize
|
||||
* Checks if the periodic check should be performed now
|
||||
* \return
|
||||
*/
|
||||
bool ApplicationCache::periodicCheckOfSize() const
|
||||
{
|
||||
QString vendor = QString::fromLatin1(App::Application::Config()["ExeVendor"].c_str());
|
||||
QString application = QString::fromStdString(App::Application::getExecutableName());
|
||||
|
||||
QSettings settings(vendor, application);
|
||||
QString key = QString::fromLatin1("LastCacheCheck");
|
||||
QDate date = settings.value(key).toDate();
|
||||
QDate now = QDate::currentDate();
|
||||
|
||||
// get the days since the last check
|
||||
int days = date.daysTo(now);
|
||||
if (date.isNull()) {
|
||||
days = 1000;
|
||||
}
|
||||
|
||||
if (days >= numDays) {
|
||||
settings.setValue(key, now);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::performAction
|
||||
* If the cache size \a total is higher than the limit then show a dialog to the user
|
||||
* \param total
|
||||
*/
|
||||
bool ApplicationCache::performAction(qint64 total)
|
||||
{
|
||||
bool performed = false;
|
||||
if (total > limit) {
|
||||
QString path = QString::fromStdString(App::Application::getUserCachePath());
|
||||
QMessageBox msgBox(Gui::getMainWindow());
|
||||
msgBox.setIcon(QMessageBox::Warning);
|
||||
msgBox.setWindowTitle(tr("Cache directory"));
|
||||
|
||||
QString hint = tr("The cache directory %1 exceeds the size of %2.").arg(path, ApplicationCache::toString(limit));
|
||||
QString ask = tr("Do you want to clear it now?");
|
||||
QString warn = tr("Warning: Please make sure that this is the only running %1 instance "
|
||||
"and that no documents are opened as this may result into data loss!").arg(QCoreApplication::applicationName());
|
||||
|
||||
msgBox.setText(QString::fromLatin1("%1 %2\n\n\n%3").arg(hint, ask, warn));
|
||||
msgBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No | QMessageBox::Open);
|
||||
msgBox.setDefaultButton(QMessageBox::No);
|
||||
|
||||
while (true) {
|
||||
int ret = msgBox.exec();
|
||||
if (ret == QMessageBox::Open) {
|
||||
QUrl url = QUrl::fromLocalFile(path);
|
||||
QDesktopServices::openUrl(url);
|
||||
}
|
||||
else {
|
||||
if (ret == QMessageBox::Yes) {
|
||||
clearDirectory(path);
|
||||
performed = true;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return performed;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::size
|
||||
* Determines the size of the cache.
|
||||
* \return
|
||||
*/
|
||||
qint64 ApplicationCache::size() const
|
||||
{
|
||||
// QDirIterator lists some directories twice
|
||||
#if 0
|
||||
QDir cache = QString::fromStdString(App::Application::getUserCachePath());
|
||||
QDirIterator it(cache, QDirIterator::Subdirectories);
|
||||
qint64 total = 0;
|
||||
while (it.hasNext()) {
|
||||
it.next();
|
||||
total += it.fileInfo().size();
|
||||
}
|
||||
|
||||
return total;
|
||||
#else
|
||||
qint64 total = dirSize(QString::fromStdString(App::Application::getUserCachePath()));
|
||||
return total;
|
||||
#endif
|
||||
}
|
||||
|
||||
/*!
|
||||
* \internal
|
||||
*/
|
||||
void ApplicationCache::clearDirectory(const QString& path)
|
||||
{
|
||||
// Add the transient directories and the lock files to the ignore list
|
||||
QDir tmp = QString::fromUtf8(App::Application::getUserCachePath().c_str());
|
||||
tmp.setNameFilters(QStringList() << QString::fromLatin1("*.lock"));
|
||||
tmp.setFilter(QDir::Files);
|
||||
|
||||
QList<QFileInfo> dirs;
|
||||
std::vector<App::Document*> docs = App::GetApplication().getDocuments();
|
||||
for (auto it : docs) {
|
||||
QDir dir(QString::fromStdString(it->TransientDir.getStrValue()));
|
||||
QFileInfo fi(dir.absolutePath());
|
||||
dirs.append(fi);
|
||||
}
|
||||
|
||||
DocumentRecoveryCleaner cleaner;
|
||||
cleaner.setIgnoreFiles(tmp.entryList());
|
||||
cleaner.setIgnoreDirectories(dirs);
|
||||
cleaner.clearDirectory(QFileInfo(path));
|
||||
}
|
||||
|
||||
/*!
|
||||
* \internal
|
||||
*/
|
||||
qint64 ApplicationCache::dirSize(QString dirPath) const
|
||||
{
|
||||
qint64 total = 0;
|
||||
QDir dir(dirPath);
|
||||
|
||||
QDir::Filters fileFilters = QDir::Files;
|
||||
for (QString filePath : dir.entryList(fileFilters)) {
|
||||
QFileInfo fi(dir, filePath);
|
||||
total += fi.size();
|
||||
}
|
||||
|
||||
// traverse sub-directories recursively
|
||||
QDir::Filters dirFilters = QDir::Dirs | QDir::NoDotAndDotDot;
|
||||
for (QString subDirPath : dir.entryList(dirFilters))
|
||||
total += dirSize(dirPath + QDir::separator() + subDirPath);
|
||||
return total;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::applyUserSettings
|
||||
* Set period and limit according to user settings
|
||||
*/
|
||||
void ApplicationCache::applyUserSettings()
|
||||
{
|
||||
int period = ApplicationCacheSettings::getCheckPeriod();
|
||||
setPeriod(static_cast<Period>(period));
|
||||
|
||||
unsigned int sizeInMB = ApplicationCacheSettings::getCacheSizeLimit();
|
||||
setLimit(ApplicationCache::toBytes(sizeInMB));
|
||||
}
|
||||
|
||||
qint64 ApplicationCache::toBytes(unsigned int sizeInMB)
|
||||
{
|
||||
qint64 value = static_cast<qint64>(sizeInMB) * 1024 * 1024;
|
||||
return value;
|
||||
}
|
||||
|
||||
QString ApplicationCache::toString(qint64 size)
|
||||
{
|
||||
QStringList units = {QString::fromLatin1("Bytes"),
|
||||
QString::fromLatin1("KB"),
|
||||
QString::fromLatin1("MB"),
|
||||
QString::fromLatin1("GB")};
|
||||
int i;
|
||||
double outputSize = size;
|
||||
for (i=0; i<units.size()-1; i++) {
|
||||
if (outputSize < 1024)
|
||||
break;
|
||||
outputSize /= 1024;
|
||||
}
|
||||
|
||||
return QString::fromLatin1("%1 %2").arg(QLocale().toString(outputSize, 'f', 2), units[i]);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
unsigned int ApplicationCacheSettings::getCacheSizeLimit()
|
||||
{
|
||||
ParameterGrp::handle hGrp = WindowParameter::getDefaultParameter()->GetGroup("CacheDirectory");
|
||||
return hGrp->GetUnsigned("Limit", 500);
|
||||
}
|
||||
|
||||
void ApplicationCacheSettings::setCacheSizeLimit(unsigned int limit)
|
||||
{
|
||||
ParameterGrp::handle hGrp = WindowParameter::getDefaultParameter()->GetGroup("CacheDirectory");
|
||||
hGrp->SetUnsigned("Limit", limit);
|
||||
}
|
||||
|
||||
int ApplicationCacheSettings::getCheckPeriod()
|
||||
{
|
||||
ParameterGrp::handle hGrp = WindowParameter::getDefaultParameter()->GetGroup("CacheDirectory");
|
||||
return hGrp->GetInt("Period", static_cast<int>(ApplicationCache::Period::Weekly));
|
||||
}
|
||||
|
||||
void ApplicationCacheSettings::setCheckPeriod(int period)
|
||||
{
|
||||
ParameterGrp::handle hGrp = WindowParameter::getDefaultParameter()->GetGroup("CacheDirectory");
|
||||
hGrp->SetInt("Period", period);
|
||||
}
|
||||
|
||||
|
||||
#include "moc_DlgSettingsCacheDirectory.cpp"
|
||||
109
src/Gui/DlgSettingsCacheDirectory.h
Normal file
109
src/Gui/DlgSettingsCacheDirectory.h
Normal file
@@ -0,0 +1,109 @@
|
||||
/***************************************************************************
|
||||
* Copyright (c) 2021 Werner Mayer <wmayer[at]users.sourceforge.net> *
|
||||
* *
|
||||
* This file is part of the FreeCAD CAx development system. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Library General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
|
||||
* GNU Library General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Library General Public *
|
||||
* License along with this library; see the file COPYING.LIB. If not, *
|
||||
* write to the Free Software Foundation, Inc., 59 Temple Place, *
|
||||
* Suite 330, Boston, MA 02111-1307, USA *
|
||||
* *
|
||||
***************************************************************************/
|
||||
|
||||
|
||||
#ifndef GUI_DIALOG_DLGSETTINGSCACHEDIRECTORY_H
|
||||
#define GUI_DIALOG_DLGSETTINGSCACHEDIRECTORY_H
|
||||
|
||||
#include "PropertyPage.h"
|
||||
#include <memory>
|
||||
|
||||
namespace Gui {
|
||||
namespace Dialog {
|
||||
class Ui_DlgSettingsCacheDirectory;
|
||||
|
||||
/**
|
||||
* The DlgSettingsCacheDirectory class implements a preference page to change settings
|
||||
* for the cache directory handling.
|
||||
* @author Werner Mayer
|
||||
*/
|
||||
class DlgSettingsCacheDirectory : public PreferencePage
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
DlgSettingsCacheDirectory(QWidget* parent = nullptr);
|
||||
~DlgSettingsCacheDirectory();
|
||||
|
||||
void saveSettings();
|
||||
void loadSettings();
|
||||
|
||||
protected:
|
||||
void changeEvent(QEvent *e);
|
||||
|
||||
private:
|
||||
void runCheck();
|
||||
void openDirectory();
|
||||
void setCurrentCacheSize(const QString&);
|
||||
|
||||
private:
|
||||
static QString currentSize;
|
||||
std::unique_ptr<Ui_DlgSettingsCacheDirectory> ui;
|
||||
};
|
||||
|
||||
class ApplicationCache : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum class Period {
|
||||
Always,
|
||||
Daily,
|
||||
Weekly,
|
||||
Monthly,
|
||||
Yearly,
|
||||
Never
|
||||
};
|
||||
|
||||
ApplicationCache();
|
||||
void applyUserSettings();
|
||||
void setPeriod(Period);
|
||||
void setLimit(qint64);
|
||||
bool periodicCheckOfSize() const;
|
||||
qint64 size() const;
|
||||
bool performAction(qint64);
|
||||
|
||||
static QString toString(qint64 size);
|
||||
static qint64 toBytes(unsigned int);
|
||||
|
||||
private:
|
||||
void clearDirectory(const QString& path);
|
||||
qint64 dirSize(QString dirPath) const;
|
||||
|
||||
private:
|
||||
qint64 limit;
|
||||
int numDays;
|
||||
};
|
||||
|
||||
class ApplicationCacheSettings
|
||||
{
|
||||
public:
|
||||
static unsigned int getCacheSizeLimit();
|
||||
static void setCacheSizeLimit(unsigned int);
|
||||
static int getCheckPeriod();
|
||||
static void setCheckPeriod(int);
|
||||
};
|
||||
|
||||
} // namespace Dialog
|
||||
} // namespace Gui
|
||||
|
||||
#endif // GUI_DIALOG_DLGSETTINGSCACHEDIRECTORY_H
|
||||
201
src/Gui/DlgSettingsCacheDirectory.ui
Normal file
201
src/Gui/DlgSettingsCacheDirectory.ui
Normal file
@@ -0,0 +1,201 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>Gui::Dialog::DlgSettingsCacheDirectory</class>
|
||||
<widget class="QWidget" name="Gui::Dialog::DlgSettingsCacheDirectory">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>488</width>
|
||||
<height>360</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Cache</string>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout_2">
|
||||
<item row="0" column="0">
|
||||
<widget class="QGroupBox" name="GroupBox5">
|
||||
<property name="title">
|
||||
<string>Cache directory</string>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout_3">
|
||||
<item row="0" column="0" colspan="3">
|
||||
<layout class="QGridLayout" name="gridLayout">
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="label">
|
||||
<property name="text">
|
||||
<string>Location:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1" colspan="2">
|
||||
<widget class="QLineEdit" name="cacheLocation">
|
||||
<property name="readOnly">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="3">
|
||||
<widget class="QPushButton" name="openButton">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Fixed" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="icon">
|
||||
<iconset resource="Icons/resource.qrc">
|
||||
<normaloff>:/icons/document-open.svg</normaloff>:/icons/document-open.svg</iconset>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="labelPeriod">
|
||||
<property name="text">
|
||||
<string>Check periodically at program start:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<spacer name="horizontalSpacer_3">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>118</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="1" column="2" colspan="2">
|
||||
<widget class="QComboBox" name="comboBoxPeriod">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Always</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Daily</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Weekly</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Monthly</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Yearly</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Never</string>
|
||||
</property>
|
||||
</item>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="labelCache">
|
||||
<property name="text">
|
||||
<string>Cache size limit:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<spacer name="horizontalSpacer_4">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>118</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="2" column="2" colspan="2">
|
||||
<widget class="QComboBox" name="comboBoxLimit">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="labelCurrentCache">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string notr="true">Current cache size:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<widget class="QPushButton" name="pushButtonCheck">
|
||||
<property name="text">
|
||||
<string>Check now...</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="2">
|
||||
<spacer name="horizontalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>150</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<spacer name="verticalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>169</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<layoutdefault spacing="6" margin="11"/>
|
||||
<resources>
|
||||
<include location="Icons/resource.qrc"/>
|
||||
</resources>
|
||||
<connections/>
|
||||
</ui>
|
||||
@@ -30,10 +30,8 @@
|
||||
#ifndef _PreComp_
|
||||
# include <QApplication>
|
||||
# include <QCloseEvent>
|
||||
# include <QDate>
|
||||
# include <QDateTime>
|
||||
# include <QDebug>
|
||||
# include <QDesktopServices>
|
||||
# include <QDir>
|
||||
# include <QFile>
|
||||
# include <QFileInfo>
|
||||
@@ -41,14 +39,12 @@
|
||||
# include <QMenu>
|
||||
# include <QMessageBox>
|
||||
# include <QPushButton>
|
||||
# include <QSettings>
|
||||
# include <QTextStream>
|
||||
# include <QTreeWidgetItem>
|
||||
# include <QMap>
|
||||
# include <QSet>
|
||||
# include <QList>
|
||||
# include <QVector>
|
||||
# include <climits>
|
||||
# include <cmath>
|
||||
# include <sstream>
|
||||
#endif
|
||||
|
||||
@@ -341,7 +337,7 @@ void DocumentRecovery::accept()
|
||||
<< docs[i]->Label.getValue() << "'");
|
||||
}
|
||||
else {
|
||||
DocumentRecoveryCleaner::clearDirectory(xfi.absolutePath());
|
||||
DocumentRecoveryCleaner().clearDirectory(xfi.absolutePath());
|
||||
QDir().rmdir(xfi.absolutePath());
|
||||
}
|
||||
|
||||
@@ -531,7 +527,7 @@ void DocumentRecovery::onDeleteSection()
|
||||
QTreeWidgetItem* item = d_ptr->ui.treeWidget->takeTopLevelItem(index);
|
||||
|
||||
QString projectFile = item->toolTip(0);
|
||||
DocumentRecoveryCleaner::clearDirectory(QFileInfo(tmp.filePath(projectFile)));
|
||||
DocumentRecoveryCleaner().clearDirectory(QFileInfo(tmp.filePath(projectFile)));
|
||||
tmp.rmdir(projectFile);
|
||||
delete item;
|
||||
}
|
||||
@@ -570,7 +566,7 @@ void DocumentRecovery::cleanup(QDir& tmp, const QList<QFileInfo>& dirs, const QS
|
||||
{
|
||||
if (!dirs.isEmpty()) {
|
||||
for (QList<QFileInfo>::const_iterator jt = dirs.cbegin(); jt != dirs.cend(); ++jt) {
|
||||
DocumentRecoveryCleaner::clearDirectory(*jt);
|
||||
DocumentRecoveryCleaner().clearDirectory(*jt);
|
||||
tmp.rmdir(jt->fileName());
|
||||
}
|
||||
}
|
||||
@@ -691,6 +687,7 @@ void DocumentRecoveryCleaner::clearDirectory(const QFileInfo& dir)
|
||||
// Remove all files in this directory
|
||||
qThisDir.setFilter(QDir::Files);
|
||||
QStringList files = qThisDir.entryList();
|
||||
subtractFiles(files);
|
||||
for (QStringList::iterator it = files.begin(); it != files.end(); ++it) {
|
||||
QString file = *it;
|
||||
qThisDir.remove(file);
|
||||
@@ -699,164 +696,40 @@ void DocumentRecoveryCleaner::clearDirectory(const QFileInfo& dir)
|
||||
// Clear this directory of any sub-directories
|
||||
qThisDir.setFilter(QDir::Dirs | QDir::NoDotAndDotDot);
|
||||
QFileInfoList subdirs = qThisDir.entryInfoList();
|
||||
subtractDirs(subdirs);
|
||||
for (QFileInfoList::iterator it = subdirs.begin(); it != subdirs.end(); ++it) {
|
||||
clearDirectory(*it);
|
||||
qThisDir.rmdir(it->fileName());
|
||||
}
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
ApplicationCache::ApplicationCache()
|
||||
void DocumentRecoveryCleaner::subtractFiles(QStringList& files)
|
||||
{
|
||||
limit = std::pow(1024, 3);
|
||||
setPeriod(Period::Weekly);
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::setPeriod
|
||||
* Set the period to check for the cache size
|
||||
* \param period
|
||||
*/
|
||||
void ApplicationCache::setPeriod(ApplicationCache::Period period)
|
||||
{
|
||||
switch (period) {
|
||||
case Period::Always:
|
||||
numDays = -1;
|
||||
break;
|
||||
case Period::Daily:
|
||||
numDays = 1;
|
||||
break;
|
||||
case Period::Weekly:
|
||||
numDays = 7;
|
||||
break;
|
||||
case Period::Monthly:
|
||||
numDays = 31;
|
||||
break;
|
||||
case Period::Yearly:
|
||||
numDays = 365;
|
||||
break;
|
||||
case Period::Never:
|
||||
numDays = INT_MAX;
|
||||
break;
|
||||
if (!ignoreFiles.isEmpty() && !files.isEmpty()) {
|
||||
QSet<QString> set1 = files.toSet();
|
||||
QSet<QString> set2 = ignoreFiles.toSet();
|
||||
set1.subtract(set2);
|
||||
files = set1.toList();
|
||||
}
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::setLimit
|
||||
* Set the limit in bytes to perform a check
|
||||
* \param value
|
||||
*/
|
||||
void ApplicationCache::setLimit(qint64 value)
|
||||
void DocumentRecoveryCleaner::subtractDirs(QFileInfoList& dirs)
|
||||
{
|
||||
limit = value;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::periodicCheckOfSize
|
||||
* Checks if the periodic check should be performed now
|
||||
* \return
|
||||
*/
|
||||
bool ApplicationCache::periodicCheckOfSize() const
|
||||
{
|
||||
QString vendor = QString::fromLatin1(App::Application::Config()["ExeVendor"].c_str());
|
||||
QString application = QString::fromStdString(App::Application::getExecutableName());
|
||||
|
||||
QSettings settings(vendor, application);
|
||||
QString key = QString::fromLatin1("LastCacheCheck");
|
||||
QDate date = settings.value(key).toDate();
|
||||
QDate now = QDate::currentDate();
|
||||
|
||||
// get the days since the last check
|
||||
int days = date.daysTo(now);
|
||||
if (date.isNull()) {
|
||||
days = 1000;
|
||||
}
|
||||
|
||||
if (days >= numDays) {
|
||||
settings.setValue(key, now);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::performAction
|
||||
* If the cache size \a total is higher than the limit then show a dialog to the user
|
||||
* \param total
|
||||
*/
|
||||
void ApplicationCache::performAction(qint64 total)
|
||||
{
|
||||
if (total > limit) {
|
||||
QString path = QString::fromStdString(App::Application::getUserCachePath());
|
||||
QMessageBox msgBox(Gui::getMainWindow());
|
||||
msgBox.setIcon(QMessageBox::Warning);
|
||||
msgBox.setWindowTitle(tr("Cache directory"));
|
||||
msgBox.setText(tr("The cache directory %1 exceeds the size of %2 GB.\n"
|
||||
"Do you want to clear it now?").arg(path).arg(1));
|
||||
msgBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No | QMessageBox::Open);
|
||||
msgBox.setDefaultButton(QMessageBox::No);
|
||||
|
||||
while (true) {
|
||||
int ret = msgBox.exec();
|
||||
if (ret == QMessageBox::Open) {
|
||||
QUrl url = QUrl::fromLocalFile(path);
|
||||
QDesktopServices::openUrl(url);
|
||||
}
|
||||
else {
|
||||
if (ret == QMessageBox::Yes) {
|
||||
DocumentRecoveryCleaner::clearDirectory(QFileInfo(path));
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (!ignoreDirs.isEmpty() && !dirs.isEmpty()) {
|
||||
for (const auto& it : ignoreDirs) {
|
||||
dirs.removeOne(it);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief ApplicationCache::size
|
||||
* Determines the size of the cache.
|
||||
* \return
|
||||
*/
|
||||
qint64 ApplicationCache::size() const
|
||||
void DocumentRecoveryCleaner::setIgnoreFiles(const QStringList& list)
|
||||
{
|
||||
// QDirIterator lists some directories twice
|
||||
#if 0
|
||||
QDir cache = QString::fromStdString(App::Application::getUserCachePath());
|
||||
QDirIterator it(cache, QDirIterator::Subdirectories);
|
||||
qint64 total = 0;
|
||||
while (it.hasNext()) {
|
||||
it.next();
|
||||
total += it.fileInfo().size();
|
||||
}
|
||||
|
||||
return total;
|
||||
#else
|
||||
qint64 total = dirSize(QString::fromStdString(App::Application::getUserCachePath()));
|
||||
return total;
|
||||
#endif
|
||||
ignoreFiles = list;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \internal
|
||||
*/
|
||||
qint64 ApplicationCache::dirSize(QString dirPath) const
|
||||
void DocumentRecoveryCleaner::setIgnoreDirectories(const QFileInfoList& list)
|
||||
{
|
||||
qint64 total = 0;
|
||||
QDir dir(dirPath);
|
||||
|
||||
QDir::Filters fileFilters = QDir::Files;
|
||||
for (QString filePath : dir.entryList(fileFilters)) {
|
||||
QFileInfo fi(dir, filePath);
|
||||
total += fi.size();
|
||||
}
|
||||
|
||||
// traverse sub-directories recursively
|
||||
QDir::Filters dirFilters = QDir::Dirs | QDir::NoDotAndDotDot;
|
||||
for (QString subDirPath : dir.entryList(dirFilters))
|
||||
total += dirSize(dirPath + QDir::separator() + subDirPath);
|
||||
return total;
|
||||
ignoreDirs = list;
|
||||
}
|
||||
|
||||
#include "moc_DocumentRecovery.cpp"
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <QScopedPointer>
|
||||
#include <QList>
|
||||
#include <QFileInfo>
|
||||
#include <QFileInfoList>
|
||||
#include <string>
|
||||
#include <functional>
|
||||
|
||||
@@ -85,35 +86,17 @@ public:
|
||||
|
||||
class DocumentRecoveryCleaner {
|
||||
public:
|
||||
static void clearDirectory(const QFileInfo& dir);
|
||||
};
|
||||
|
||||
class ApplicationCache : public QObject {
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum class Period {
|
||||
Always,
|
||||
Daily,
|
||||
Weekly,
|
||||
Monthly,
|
||||
Yearly,
|
||||
Never
|
||||
};
|
||||
|
||||
ApplicationCache();
|
||||
void setPeriod(Period);
|
||||
void setLimit(qint64);
|
||||
bool periodicCheckOfSize() const;
|
||||
qint64 size() const;
|
||||
void performAction(qint64);
|
||||
void clearDirectory(const QFileInfo& dir);
|
||||
void setIgnoreFiles(const QStringList&);
|
||||
void setIgnoreDirectories(const QFileInfoList&);
|
||||
|
||||
private:
|
||||
qint64 dirSize(QString dirPath) const;
|
||||
void subtractFiles(QStringList&);
|
||||
void subtractDirs(QFileInfoList&);
|
||||
|
||||
private:
|
||||
qint64 limit;
|
||||
int numDays;
|
||||
QStringList ignoreFiles;
|
||||
QFileInfoList ignoreDirs;
|
||||
};
|
||||
|
||||
} //namespace Dialog
|
||||
|
||||
@@ -50,6 +50,7 @@
|
||||
#include "DlgKeyboardImp.h"
|
||||
#include "DlgCustomizeSpaceball.h"
|
||||
#include "DlgCustomizeSpNavSettings.h"
|
||||
#include "DlgSettingsCacheDirectory.h"
|
||||
#include "InputField.h"
|
||||
#include "QuantitySpinBox.h"
|
||||
#include "PrefWidgets.h"
|
||||
@@ -69,6 +70,7 @@ WidgetFactorySupplier::WidgetFactorySupplier()
|
||||
//new PrefPageProducer<DlgOnlineHelpImp> ( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
new PrefPageProducer<DlgSettingsDocumentImp> ( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
new PrefPageProducer<DlgSettingsSelection> ( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
new PrefPageProducer<DlgSettingsCacheDirectory>( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
new PrefPageProducer<DlgSettingsEditorImp> ( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
new PrefPageProducer<DlgReportViewImp> ( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
new PrefPageProducer<DlgSettingsMacroImp> ( QT_TRANSLATE_NOOP("QObject","General") );
|
||||
|
||||
Reference in New Issue
Block a user