mirror of
https://invent.kde.org/network/falkon.git
synced 2024-12-24 12:46:35 +01:00
Merge pull request #1889 from trnkava1/downloadScripts
Greasemonkey: add script updating
This commit is contained in:
commit
80ad43ba42
@ -16,7 +16,6 @@
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
* ============================================================ */
|
||||
#include "gm_downloader.h"
|
||||
#include "gm_addscriptdialog.h"
|
||||
#include "gm_manager.h"
|
||||
#include "gm_script.h"
|
||||
|
||||
@ -38,6 +37,11 @@ GM_Downloader::GM_Downloader(const QUrl &url, GM_Manager* manager)
|
||||
connect(m_reply, SIGNAL(finished()), this, SLOT(scriptDownloaded()));
|
||||
}
|
||||
|
||||
void GM_Downloader::updateScript(const QString &fileName)
|
||||
{
|
||||
m_fileName = fileName;
|
||||
}
|
||||
|
||||
void GM_Downloader::scriptDownloaded()
|
||||
{
|
||||
if (m_reply != qobject_cast<FollowRedirectReply*>(sender())) {
|
||||
@ -52,13 +56,15 @@ void GM_Downloader::scriptDownloaded()
|
||||
const QByteArray response = QString::fromUtf8(m_reply->readAll()).toUtf8();
|
||||
|
||||
if (response.contains(QByteArray("// ==UserScript=="))) {
|
||||
const QString filePath = QString("%1/%2").arg(m_manager->scriptsDirectory(), QzTools::getFileNameFromUrl(m_reply->url()));
|
||||
m_fileName = QzTools::ensureUniqueFilename(filePath);
|
||||
|
||||
if (m_fileName.isEmpty()) {
|
||||
const QString filePath = QString("%1/%2").arg(m_manager->scriptsDirectory(), QzTools::getFileNameFromUrl(m_reply->url()));
|
||||
m_fileName = QzTools::ensureUniqueFilename(filePath);
|
||||
}
|
||||
QFile file(m_fileName);
|
||||
|
||||
if (!file.open(QFile::WriteOnly)) {
|
||||
qWarning() << "GreaseMonkey: Cannot open file for writing" << m_fileName;
|
||||
emit error();
|
||||
deleteLater();
|
||||
return;
|
||||
}
|
||||
@ -91,6 +97,7 @@ void GM_Downloader::scriptDownloaded()
|
||||
void GM_Downloader::requireDownloaded()
|
||||
{
|
||||
if (m_reply != qobject_cast<FollowRedirectReply*>(sender())) {
|
||||
emit error();
|
||||
deleteLater();
|
||||
return;
|
||||
}
|
||||
@ -109,6 +116,7 @@ void GM_Downloader::requireDownloaded()
|
||||
|
||||
if (!file.open(QFile::WriteOnly)) {
|
||||
qWarning() << "GreaseMonkey: Cannot open file for writing" << fileName;
|
||||
emit error();
|
||||
deleteLater();
|
||||
return;
|
||||
}
|
||||
@ -135,24 +143,7 @@ void GM_Downloader::downloadRequires()
|
||||
connect(m_reply, SIGNAL(finished()), this, SLOT(requireDownloaded()));
|
||||
}
|
||||
else {
|
||||
bool deleteScript = true;
|
||||
GM_Script* script = new GM_Script(m_manager, m_fileName);
|
||||
|
||||
if (script->isValid()) {
|
||||
if (!m_manager->containsScript(script->fullName())) {
|
||||
GM_AddScriptDialog dialog(m_manager, script);
|
||||
deleteScript = dialog.exec() != QDialog::Accepted;
|
||||
}
|
||||
else {
|
||||
m_manager->showNotification(tr("'%1' is already installed").arg(script->name()));
|
||||
}
|
||||
}
|
||||
|
||||
if (deleteScript) {
|
||||
delete script;
|
||||
QFile(m_fileName).remove();
|
||||
}
|
||||
|
||||
emit finished(m_fileName);
|
||||
deleteLater();
|
||||
}
|
||||
}
|
||||
|
@ -32,6 +32,12 @@ class GM_Downloader : public QObject
|
||||
public:
|
||||
explicit GM_Downloader(const QUrl &url, GM_Manager* manager);
|
||||
|
||||
void updateScript(const QString& fileName);
|
||||
|
||||
signals:
|
||||
void finished(const QString& fileName);
|
||||
void error();
|
||||
|
||||
private slots:
|
||||
void scriptDownloaded();
|
||||
void requireDownloaded();
|
||||
|
@ -20,6 +20,7 @@
|
||||
#include "gm_downloader.h"
|
||||
#include "gm_icon.h"
|
||||
#include "gm_urlinterceptor.h"
|
||||
#include "gm_addscriptdialog.h"
|
||||
#include "settings/gm_settings.h"
|
||||
|
||||
#include "browserwindow.h"
|
||||
@ -256,7 +257,25 @@ void GM_Manager::scriptChanged()
|
||||
|
||||
void GM_Manager::doDownloadScript(const QUrl &url)
|
||||
{
|
||||
new GM_Downloader(url, this);
|
||||
GM_Downloader *downloader = new GM_Downloader(url, this);
|
||||
connect(downloader, &GM_Downloader::finished, this, [=](const QString &fileName) {
|
||||
bool deleteScript = true;
|
||||
GM_Script *script = new GM_Script(this, fileName);
|
||||
if (script->isValid()) {
|
||||
if (!containsScript(script->fullName())) {
|
||||
GM_AddScriptDialog dialog(this, script);
|
||||
deleteScript = dialog.exec() != QDialog::Accepted;
|
||||
}
|
||||
else {
|
||||
showNotification(tr("'%1' is already installed").arg(script->name()));
|
||||
}
|
||||
}
|
||||
|
||||
if (deleteScript) {
|
||||
delete script;
|
||||
QFile(fileName).remove();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
bool GM_Manager::canRunOnScheme(const QString &scheme)
|
||||
|
@ -17,9 +17,12 @@
|
||||
* ============================================================ */
|
||||
#include "gm_script.h"
|
||||
#include "gm_manager.h"
|
||||
#include "gm_downloader.h"
|
||||
|
||||
#include "qzregexp.h"
|
||||
#include "delayedfilewatcher.h"
|
||||
#include "followredirectreply.h"
|
||||
#include "mainapplication.h"
|
||||
|
||||
#include <QFile>
|
||||
#include <QStringList>
|
||||
@ -36,6 +39,7 @@ GM_Script::GM_Script(GM_Manager* manager, const QString &filePath)
|
||||
, m_fileName(filePath)
|
||||
, m_enabled(true)
|
||||
, m_valid(false)
|
||||
, m_updating(false)
|
||||
{
|
||||
parseScript();
|
||||
|
||||
@ -148,6 +152,31 @@ QWebEngineScript GM_Script::webScript() const
|
||||
return script;
|
||||
}
|
||||
|
||||
bool GM_Script::isUpdating()
|
||||
{
|
||||
return m_updating;
|
||||
}
|
||||
|
||||
void GM_Script::updateScript()
|
||||
{
|
||||
if (!m_downloadUrl.isValid() || m_updating)
|
||||
return;
|
||||
|
||||
m_updating = true;
|
||||
emit updatingChanged(m_updating);
|
||||
|
||||
GM_Downloader *downloader = new GM_Downloader(m_downloadUrl, m_manager);
|
||||
downloader->updateScript(m_fileName);
|
||||
connect(downloader, &GM_Downloader::finished, this, [this]() {
|
||||
m_updating = false;
|
||||
emit updatingChanged(m_updating);
|
||||
});
|
||||
connect(downloader, &GM_Downloader::error, this, [this]() {
|
||||
m_updating = false;
|
||||
emit updatingChanged(m_updating);
|
||||
});
|
||||
}
|
||||
|
||||
void GM_Script::watchedFileChanged(const QString &file)
|
||||
{
|
||||
if (m_fileName == file) {
|
||||
@ -254,6 +283,9 @@ void GM_Script::parseScript()
|
||||
m_version = value;
|
||||
}
|
||||
else if (key == QLatin1String("@updateURL")) {
|
||||
m_updateUrl = QUrl(value);
|
||||
}
|
||||
else if (key == QLatin1String("@downloadURL")) {
|
||||
m_downloadUrl = QUrl(value);
|
||||
}
|
||||
else if (key == QLatin1String("@include") || key == QLatin1String("@match")) {
|
||||
@ -276,12 +308,6 @@ void GM_Script::parseScript()
|
||||
m_startAt = DocumentIdle;
|
||||
}
|
||||
}
|
||||
else if (key == QLatin1String("@downloadURL") && m_downloadUrl.isEmpty()) {
|
||||
m_downloadUrl = QUrl(value);
|
||||
}
|
||||
else if (key == QLatin1String("@updateURL") && m_updateUrl.isEmpty()) {
|
||||
m_updateUrl = QUrl(value);
|
||||
}
|
||||
}
|
||||
|
||||
if (m_include.isEmpty()) {
|
||||
|
@ -62,8 +62,12 @@ public:
|
||||
|
||||
QWebEngineScript webScript() const;
|
||||
|
||||
bool isUpdating();
|
||||
void updateScript();
|
||||
|
||||
signals:
|
||||
void scriptChanged();
|
||||
void updatingChanged(bool updating);
|
||||
|
||||
private slots:
|
||||
void watchedFileChanged(const QString &file);
|
||||
@ -91,6 +95,7 @@ private:
|
||||
QString m_fileName;
|
||||
bool m_enabled;
|
||||
bool m_valid;
|
||||
bool m_updating;
|
||||
};
|
||||
|
||||
#endif // GM_SCRIPT_H
|
||||
|
@ -38,6 +38,8 @@ GM_Settings::GM_Settings(GM_Manager* manager, QWidget* parent)
|
||||
|
||||
connect(ui->listWidget, SIGNAL(itemDoubleClicked(QListWidgetItem*)),
|
||||
this, SLOT(showItemInfo(QListWidgetItem*)));
|
||||
connect(ui->listWidget, SIGNAL(updateItemRequested(QListWidgetItem*)),
|
||||
this, SLOT(updateItem(QListWidgetItem*)));
|
||||
connect(ui->listWidget, SIGNAL(removeItemRequested(QListWidgetItem*)),
|
||||
this, SLOT(removeItem(QListWidgetItem*)));
|
||||
connect(ui->openDirectory, SIGNAL(clicked()),
|
||||
@ -69,6 +71,15 @@ void GM_Settings::showItemInfo(QListWidgetItem* item)
|
||||
dialog->open();
|
||||
}
|
||||
|
||||
void GM_Settings::updateItem(QListWidgetItem* item)
|
||||
{
|
||||
GM_Script *script = getScript(item);
|
||||
if (!script) {
|
||||
return;
|
||||
}
|
||||
script->updateScript();
|
||||
}
|
||||
|
||||
void GM_Settings::removeItem(QListWidgetItem* item)
|
||||
{
|
||||
GM_Script* script = getScript(item);
|
||||
@ -148,6 +159,8 @@ void GM_Settings::loadScripts()
|
||||
item->setText(script->name());
|
||||
item->setData(Qt::UserRole, script->version());
|
||||
item->setData(Qt::UserRole + 1, script->description());
|
||||
item->setData(Qt::UserRole + 2, !script->downloadUrl().isEmpty());
|
||||
item->setData(Qt::UserRole + 3, script->isUpdating());
|
||||
|
||||
item->setFlags(item->flags() | Qt::ItemIsUserCheckable);
|
||||
item->setCheckState(script->isEnabled() ? Qt::Checked : Qt::Unchecked);
|
||||
|
@ -40,6 +40,7 @@ public:
|
||||
|
||||
private slots:
|
||||
void showItemInfo(QListWidgetItem* item);
|
||||
void updateItem(QListWidgetItem* item);
|
||||
void removeItem(QListWidgetItem* item);
|
||||
|
||||
void itemChanged(QListWidgetItem* item);
|
||||
|
@ -29,6 +29,7 @@ GM_SettingsListDelegate::GM_SettingsListDelegate(QObject* parent)
|
||||
, m_padding(0)
|
||||
{
|
||||
m_removePixmap = IconProvider::standardIcon(QStyle::SP_DialogCloseButton).pixmap(16);
|
||||
m_updateIcon = IconProvider::standardIcon(QStyle::SP_BrowserReload);
|
||||
}
|
||||
|
||||
int GM_SettingsListDelegate::padding() const
|
||||
@ -63,6 +64,8 @@ void GM_SettingsListDelegate::paint(QPainter* painter, const QStyleOptionViewIte
|
||||
|
||||
int leftPosition = m_padding;
|
||||
int rightPosition = opt.rect.right() - m_padding - 16; // 16 for remove button
|
||||
if (index.data(Qt::UserRole + 2).toBool())
|
||||
rightPosition -= m_padding + 16; // 16 for update button
|
||||
|
||||
// Draw background
|
||||
style->drawPrimitive(QStyle::PE_PanelItemViewItem, &opt, painter, w);
|
||||
@ -109,6 +112,16 @@ void GM_SettingsListDelegate::paint(QPainter* painter, const QStyleOptionViewIte
|
||||
painter->setFont(opt.font);
|
||||
style->drawItemText(painter, infoRect, Qt::TextSingleLine | Qt::AlignLeft, opt.palette, true, info, colorRole);
|
||||
|
||||
// Draw update button
|
||||
if (index.data(Qt::UserRole + 2).toBool()) {
|
||||
const int updateIconSize = 16;
|
||||
const int updateIconYPos = center - (updateIconSize / 2);
|
||||
const QPixmap updatePixmap = m_updateIcon.pixmap(16, index.data(Qt::UserRole + 3).toBool() ? QIcon::Disabled : QIcon::Normal);
|
||||
QRect updateIconRect(rightPosition, updateIconYPos, updateIconSize, updateIconSize);
|
||||
painter->drawPixmap(updateIconRect, updatePixmap);
|
||||
rightPosition += m_padding + 16;
|
||||
}
|
||||
|
||||
// Draw remove button
|
||||
const int removeIconSize = 16;
|
||||
const int removeIconYPos = center - (removeIconSize / 2);
|
||||
|
@ -32,6 +32,7 @@ public:
|
||||
|
||||
private:
|
||||
QPixmap m_removePixmap;
|
||||
QIcon m_updateIcon;
|
||||
|
||||
mutable int m_rowHeight;
|
||||
mutable int m_padding;
|
||||
|
@ -36,15 +36,18 @@ void GM_SettingsListWidget::mousePressEvent(QMouseEvent* event)
|
||||
return;
|
||||
}
|
||||
|
||||
if (containsUpdateIcon(event->pos())) {
|
||||
emit updateItemRequested(itemAt(event->pos()));
|
||||
return;
|
||||
}
|
||||
|
||||
QListWidget::mousePressEvent(event);
|
||||
}
|
||||
|
||||
void GM_SettingsListWidget::mouseDoubleClickEvent(QMouseEvent* event)
|
||||
{
|
||||
if (containsRemoveIcon(event->pos())) {
|
||||
emit removeItemRequested(itemAt(event->pos()));
|
||||
if (containsRemoveIcon(event->pos()) || containsUpdateIcon(event->pos()))
|
||||
return;
|
||||
}
|
||||
|
||||
QListWidget::mouseDoubleClickEvent(event);
|
||||
}
|
||||
@ -65,3 +68,19 @@ bool GM_SettingsListWidget::containsRemoveIcon(const QPoint &pos) const
|
||||
|
||||
return removeIconRect.contains(pos);
|
||||
}
|
||||
|
||||
bool GM_SettingsListWidget::containsUpdateIcon(const QPoint &pos) const
|
||||
{
|
||||
QListWidgetItem *item = itemAt(pos);
|
||||
if (!item || !item->data(Qt::UserRole + 2).toBool())
|
||||
return false;
|
||||
|
||||
const QRect rect = visualItemRect(item);
|
||||
const int updateIconPosition = rect.right() - m_delegate->padding() * 2 - 16 * 2;
|
||||
const int center = rect.height() / 2 + rect.top();
|
||||
const int updateIconYPos = center - (16 / 2);
|
||||
|
||||
QRect updateIconRect(updateIconPosition, updateIconYPos, 16, 16);
|
||||
|
||||
return updateIconRect.contains(pos);
|
||||
}
|
||||
|
@ -30,11 +30,13 @@ public:
|
||||
|
||||
signals:
|
||||
void removeItemRequested(QListWidgetItem* item);
|
||||
void updateItemRequested(QListWidgetItem* item);
|
||||
|
||||
public slots:
|
||||
|
||||
private:
|
||||
bool containsRemoveIcon(const QPoint &pos) const;
|
||||
bool containsUpdateIcon(const QPoint &pos) const;
|
||||
|
||||
void mousePressEvent(QMouseEvent* event);
|
||||
void mouseDoubleClickEvent(QMouseEvent* event);
|
||||
|
Loading…
Reference in New Issue
Block a user