Work on downloader.
This commit is contained in:
parent
30ef010bf8
commit
c3aeb0e9db
@ -398,6 +398,9 @@ set(APP_SOURCES
|
||||
src/network-web/webview.cpp
|
||||
src/network-web/downloader.cpp
|
||||
src/network-web/downloadmanager.cpp
|
||||
src/network-web/edittableview.cpp
|
||||
src/network-web/autosaver.cpp
|
||||
src/network-web/squeezelabel.cpp
|
||||
|
||||
# MAIN sources.
|
||||
src/main.cpp
|
||||
@ -476,6 +479,9 @@ set(APP_HEADERS
|
||||
src/network-web/webview.h
|
||||
src/network-web/downloader.h
|
||||
src/network-web/downloadmanager.h
|
||||
src/network-web/edittableview.h
|
||||
src/network-web/autosaver.h
|
||||
src/network-web/squeezelabel.h
|
||||
)
|
||||
|
||||
# APP form files.
|
||||
@ -491,6 +497,7 @@ set(APP_FORMS
|
||||
src/gui/formbackupdatabasesettings.ui
|
||||
src/gui/formrestoredatabasesettings.ui
|
||||
src/network-web/downloadmanager.ui
|
||||
src/network-web/downloaditem.ui
|
||||
)
|
||||
|
||||
# APP translations.
|
||||
|
119
src/network-web/autosaver.cpp
Normal file
119
src/network-web/autosaver.cpp
Normal file
@ -0,0 +1,119 @@
|
||||
/*
|
||||
* Copyright 2008 Benjamin C. Meyer <ben@meyerhome.net>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program 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 General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2007-2008 Trolltech ASA. All rights reserved.
|
||||
**
|
||||
** This file is part of the demonstration applications of the Qt Toolkit.
|
||||
**
|
||||
** This file may be used under the terms of the GNU General Public
|
||||
** License versions 2.0 or 3.0 as published by the Free Software
|
||||
** Foundation and appearing in the files LICENSE.GPL2 and LICENSE.GPL3
|
||||
** included in the packaging of this file. Alternatively you may (at
|
||||
** your option) use any later version of the GNU General Public
|
||||
** License if such license has been publicly approved by Trolltech ASA
|
||||
** (or its successors, if any) and the KDE Free Qt Foundation. In
|
||||
** addition, as a special exception, Trolltech gives you certain
|
||||
** additional rights. These rights are described in the Trolltech GPL
|
||||
** Exception version 1.2, which can be found at
|
||||
** http://www.trolltech.com/products/qt/gplexception/ and in the file
|
||||
** GPL_EXCEPTION.txt in this package.
|
||||
**
|
||||
** Please review the following information to ensure GNU General
|
||||
** Public Licensing requirements will be met:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/opensource/. If
|
||||
** you are unsure which license is appropriate for your use, please
|
||||
** review the following information:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/licensingoverview
|
||||
** or contact the sales department at sales@trolltech.com.
|
||||
**
|
||||
** In addition, as a special exception, Trolltech, as the sole
|
||||
** copyright holder for Qt Designer, grants users of the Qt/Eclipse
|
||||
** Integration plug-in the right for the Qt/Eclipse Integration to
|
||||
** link to functionality provided by Qt Designer and its related
|
||||
** libraries.
|
||||
**
|
||||
** This file is provided "AS IS" with NO WARRANTY OF ANY KIND,
|
||||
** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR
|
||||
** A PARTICULAR PURPOSE. Trolltech reserves all rights not expressly
|
||||
** granted herein.
|
||||
**
|
||||
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
|
||||
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include "autosaver.h"
|
||||
|
||||
#include <qdir.h>
|
||||
#include <qcoreapplication.h>
|
||||
#include <qmetaobject.h>
|
||||
|
||||
#include <qdebug.h>
|
||||
|
||||
#define AUTOSAVE_IN 1000 * 3 // seconds
|
||||
#define MAXWAIT 1000 * 15 // seconds
|
||||
|
||||
AutoSaver::AutoSaver(QObject *parent) : QObject(parent)
|
||||
{
|
||||
Q_ASSERT(parent);
|
||||
}
|
||||
|
||||
AutoSaver::~AutoSaver()
|
||||
{
|
||||
if (m_timer.isActive()) {
|
||||
qWarning() << "AutoSaver: still active when destroyed, changes not saved.";
|
||||
if (parent() && parent()->metaObject())
|
||||
qWarning() << parent() << parent()->metaObject()->className() << "should call saveIfNeccessary";
|
||||
}
|
||||
}
|
||||
|
||||
void AutoSaver::changeOccurred()
|
||||
{
|
||||
if (m_firstChange.isNull())
|
||||
m_firstChange.start();
|
||||
|
||||
if (m_firstChange.elapsed() > MAXWAIT) {
|
||||
saveIfNeccessary();
|
||||
} else {
|
||||
m_timer.start(AUTOSAVE_IN, this);
|
||||
}
|
||||
}
|
||||
|
||||
void AutoSaver::timerEvent(QTimerEvent *event)
|
||||
{
|
||||
if (event->timerId() == m_timer.timerId()) {
|
||||
saveIfNeccessary();
|
||||
} else {
|
||||
QObject::timerEvent(event);
|
||||
}
|
||||
}
|
||||
|
||||
void AutoSaver::saveIfNeccessary()
|
||||
{
|
||||
if (!m_timer.isActive())
|
||||
return;
|
||||
m_timer.stop();
|
||||
m_firstChange = QTime();
|
||||
if (!QMetaObject::invokeMethod(parent(), "save", Qt::DirectConnection)) {
|
||||
qWarning() << "AutoSaver: error invoking slot save() on parent";
|
||||
}
|
||||
}
|
||||
|
98
src/network-web/autosaver.h
Normal file
98
src/network-web/autosaver.h
Normal file
@ -0,0 +1,98 @@
|
||||
/*
|
||||
* Copyright 2008 Benjamin C. Meyer <ben@meyerhome.net>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program 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 General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2007-2008 Trolltech ASA. All rights reserved.
|
||||
**
|
||||
** This file is part of the demonstration applications of the Qt Toolkit.
|
||||
**
|
||||
** This file may be used under the terms of the GNU General Public
|
||||
** License versions 2.0 or 3.0 as published by the Free Software
|
||||
** Foundation and appearing in the files LICENSE.GPL2 and LICENSE.GPL3
|
||||
** included in the packaging of this file. Alternatively you may (at
|
||||
** your option) use any later version of the GNU General Public
|
||||
** License if such license has been publicly approved by Trolltech ASA
|
||||
** (or its successors, if any) and the KDE Free Qt Foundation. In
|
||||
** addition, as a special exception, Trolltech gives you certain
|
||||
** additional rights. These rights are described in the Trolltech GPL
|
||||
** Exception version 1.2, which can be found at
|
||||
** http://www.trolltech.com/products/qt/gplexception/ and in the file
|
||||
** GPL_EXCEPTION.txt in this package.
|
||||
**
|
||||
** Please review the following information to ensure GNU General
|
||||
** Public Licensing requirements will be met:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/opensource/. If
|
||||
** you are unsure which license is appropriate for your use, please
|
||||
** review the following information:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/licensingoverview
|
||||
** or contact the sales department at sales@trolltech.com.
|
||||
**
|
||||
** In addition, as a special exception, Trolltech, as the sole
|
||||
** copyright holder for Qt Designer, grants users of the Qt/Eclipse
|
||||
** Integration plug-in the right for the Qt/Eclipse Integration to
|
||||
** link to functionality provided by Qt Designer and its related
|
||||
** libraries.
|
||||
**
|
||||
** This file is provided "AS IS" with NO WARRANTY OF ANY KIND,
|
||||
** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR
|
||||
** A PARTICULAR PURPOSE. Trolltech reserves all rights not expressly
|
||||
** granted herein.
|
||||
**
|
||||
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
|
||||
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef AUTOSAVER_H
|
||||
#define AUTOSAVER_H
|
||||
|
||||
#include <qobject.h>
|
||||
#include <qbasictimer.h>
|
||||
#include <qdatetime.h>
|
||||
|
||||
/*
|
||||
This class will call the save() slot on the parent object when the parent changes.
|
||||
It will wait several seconds after changed() to combining multiple changes and
|
||||
prevent continuous writing to disk.
|
||||
*/
|
||||
class AutoSaver : public QObject
|
||||
{
|
||||
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
AutoSaver(QObject *parent);
|
||||
~AutoSaver();
|
||||
void saveIfNeccessary();
|
||||
|
||||
public slots:
|
||||
void changeOccurred();
|
||||
|
||||
protected:
|
||||
void timerEvent(QTimerEvent *event);
|
||||
|
||||
private:
|
||||
QBasicTimer m_timer;
|
||||
QTime m_firstChange;
|
||||
|
||||
};
|
||||
|
||||
#endif // AUTOSAVER_H
|
||||
|
131
src/network-web/downloaditem.ui
Normal file
131
src/network-web/downloaditem.ui
Normal file
@ -0,0 +1,131 @@
|
||||
<ui version="4.0" >
|
||||
<class>DownloadItem</class>
|
||||
<widget class="QWidget" name="DownloadItem" >
|
||||
<property name="geometry" >
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>423</width>
|
||||
<height>110</height>
|
||||
</rect>
|
||||
</property>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout" >
|
||||
<property name="margin" >
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QLabel" name="fileIcon" >
|
||||
<property name="sizePolicy" >
|
||||
<sizepolicy vsizetype="Minimum" hsizetype="Minimum" >
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text" >
|
||||
<string>Ico</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout_2" >
|
||||
<item>
|
||||
<widget class="SqueezeLabel" native="1" name="fileNameLabel" >
|
||||
<property name="sizePolicy" >
|
||||
<sizepolicy vsizetype="Preferred" hsizetype="Expanding" >
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text" stdset="0" >
|
||||
<string>Filename</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QProgressBar" name="progressBar" >
|
||||
<property name="value" >
|
||||
<number>0</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="SqueezeLabel" native="1" name="downloadInfoLabel" >
|
||||
<property name="sizePolicy" >
|
||||
<sizepolicy vsizetype="Preferred" hsizetype="Minimum" >
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text" stdset="0" >
|
||||
<string/>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout" >
|
||||
<item>
|
||||
<spacer name="verticalSpacer" >
|
||||
<property name="orientation" >
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0" >
|
||||
<size>
|
||||
<width>17</width>
|
||||
<height>1</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="tryAgainButton" >
|
||||
<property name="enabled" >
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="text" >
|
||||
<string>Try Again</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="stopButton" >
|
||||
<property name="text" >
|
||||
<string>Stop</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="openButton" >
|
||||
<property name="text" >
|
||||
<string>Open</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="verticalSpacer_2" >
|
||||
<property name="orientation" >
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0" >
|
||||
<size>
|
||||
<width>17</width>
|
||||
<height>5</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>SqueezeLabel</class>
|
||||
<extends>QWidget</extends>
|
||||
<header>squeezelabel.h</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
@ -1,37 +1,858 @@
|
||||
// This file is part of RSS Guard.
|
||||
//
|
||||
// Copyright (C) 2011-2015 by Martin Rotter <rotter.martinos@gmail.com>
|
||||
//
|
||||
// RSS Guard is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// RSS Guard 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 General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with RSS Guard. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include "network-web/downloadmanager.h"
|
||||
|
||||
|
||||
DownloadManager::DownloadManager(QWidget *parent) : TabContent(parent), m_ui(new Ui::DownloadManager) {
|
||||
m_ui->setupUi(this);
|
||||
}
|
||||
|
||||
DownloadManager::~DownloadManager() {
|
||||
qDebug("Destroying DownloadManager.");
|
||||
delete m_ui;
|
||||
}
|
||||
|
||||
// TODO: pokračovat, převzít downloaditem, edittableview z arory
|
||||
// přistup k downloadmanageru bude z qApp->downloadManager(),
|
||||
// bude se využívat pro stahování skrze webview
|
||||
|
||||
|
||||
WebBrowser *DownloadManager::webBrowser() {
|
||||
return NULL;
|
||||
}
|
||||
/*
|
||||
* Copyright 2008-2009 Benjamin C. Meyer <ben@meyerhome.net>
|
||||
* Copyright 2008 Jason A. Donenfeld <Jason@zx2c4.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program 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 General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2008-2008 Trolltech ASA. All rights reserved.
|
||||
**
|
||||
** This file is part of the demonstration applications of the Qt Toolkit.
|
||||
**
|
||||
** This file may be used under the terms of the GNU General Public
|
||||
** License versions 2.0 or 3.0 as published by the Free Software
|
||||
** Foundation and appearing in the files LICENSE.GPL2 and LICENSE.GPL3
|
||||
** included in the packaging of this file. Alternatively you may (at
|
||||
** your option) use any later version of the GNU General Public
|
||||
** License if such license has been publicly approved by Trolltech ASA
|
||||
** (or its successors, if any) and the KDE Free Qt Foundation. In
|
||||
** addition, as a special exception, Trolltech gives you certain
|
||||
** additional rights. These rights are described in the Trolltech GPL
|
||||
** Exception version 1.2, which can be found at
|
||||
** http://www.trolltech.com/products/qt/gplexception/ and in the file
|
||||
** GPL_EXCEPTION.txt in this package.
|
||||
**
|
||||
** Please review the following information to ensure GNU General
|
||||
** Public Licensing requirements will be met:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/opensource/. If
|
||||
** you are unsure which license is appropriate for your use, please
|
||||
** review the following information:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/licensingoverview
|
||||
** or contact the sales department at sales@trolltech.com.
|
||||
**
|
||||
** In addition, as a special exception, Trolltech, as the sole
|
||||
** copyright holder for Qt Designer, grants users of the Qt/Eclipse
|
||||
** Integration plug-in the right for the Qt/Eclipse Integration to
|
||||
** link to functionality provided by Qt Designer and its related
|
||||
** libraries.
|
||||
**
|
||||
** This file is provided "AS IS" with NO WARRANTY OF ANY KIND,
|
||||
** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR
|
||||
** A PARTICULAR PURPOSE. Trolltech reserves all rights not expressly
|
||||
** granted herein.
|
||||
**
|
||||
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
|
||||
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#include "downloadmanager.h"
|
||||
|
||||
#include "autosaver.h"
|
||||
|
||||
#include "miscellaneous/application.h"
|
||||
|
||||
#include "network-web/silentnetworkaccessmanager.h"
|
||||
|
||||
#include <math.h>
|
||||
|
||||
#include <qdesktopservices.h>
|
||||
#include <qfiledialog.h>
|
||||
#include <qfileiconprovider.h>
|
||||
#include <qheaderview.h>
|
||||
#include <qmessagebox.h>
|
||||
#include <qmetaobject.h>
|
||||
#include <qmimedata.h>
|
||||
#include <qprocess.h>
|
||||
#include <qsettings.h>
|
||||
|
||||
#include <qdebug.h>
|
||||
|
||||
#include <qwebsettings.h>
|
||||
|
||||
//#define DOWNLOADMANAGER_DEBUG
|
||||
|
||||
/*!
|
||||
DownloadItem is a widget that is displayed in the download manager list.
|
||||
It moves the data from the QNetworkReply into the QFile as well
|
||||
as update the information/progressbar and report errors.
|
||||
*/
|
||||
DownloadItem::DownloadItem(QNetworkReply *reply, bool requestFileName, QWidget *parent)
|
||||
: QWidget(parent)
|
||||
, m_reply(reply)
|
||||
, m_requestFileName(requestFileName)
|
||||
, m_bytesReceived(0)
|
||||
, m_startedSaving(false)
|
||||
, m_finishedDownloading(false)
|
||||
, m_gettingFileName(false)
|
||||
, m_canceledFileSelect(false)
|
||||
{
|
||||
setupUi(this);
|
||||
QPalette p = downloadInfoLabel->palette();
|
||||
p.setColor(QPalette::Text, Qt::darkGray);
|
||||
downloadInfoLabel->setPalette(p);
|
||||
progressBar->setMaximum(0);
|
||||
tryAgainButton->hide();
|
||||
connect(stopButton, SIGNAL(clicked()), this, SLOT(stop()));
|
||||
connect(openButton, SIGNAL(clicked()), this, SLOT(open()));
|
||||
connect(tryAgainButton, SIGNAL(clicked()), this, SLOT(tryAgain()));
|
||||
|
||||
if (!requestFileName) {
|
||||
QSettings settings;
|
||||
settings.beginGroup(QLatin1String("downloadmanager"));
|
||||
m_requestFileName = settings.value(QLatin1String("alwaysPromptForFileName"), false).toBool();
|
||||
}
|
||||
|
||||
init();
|
||||
}
|
||||
|
||||
void DownloadItem::init()
|
||||
{
|
||||
if (!m_reply)
|
||||
return;
|
||||
|
||||
m_startedSaving = false;
|
||||
m_finishedDownloading = false;
|
||||
|
||||
openButton->setEnabled(false);
|
||||
|
||||
// attach to the m_reply
|
||||
m_url = m_reply->url();
|
||||
m_reply->setParent(this);
|
||||
connect(m_reply, SIGNAL(readyRead()), this, SLOT(downloadReadyRead()));
|
||||
connect(m_reply, SIGNAL(error(QNetworkReply::NetworkError)),
|
||||
this, SLOT(error(QNetworkReply::NetworkError)));
|
||||
connect(m_reply, SIGNAL(downloadProgress(qint64, qint64)),
|
||||
this, SLOT(downloadProgress(qint64, qint64)));
|
||||
connect(m_reply, SIGNAL(metaDataChanged()),
|
||||
this, SLOT(metaDataChanged()));
|
||||
connect(m_reply, SIGNAL(finished()),
|
||||
this, SLOT(finished()));
|
||||
|
||||
// reset info
|
||||
downloadInfoLabel->clear();
|
||||
progressBar->setValue(0);
|
||||
getFileName();
|
||||
|
||||
// start timer for the download estimation
|
||||
m_downloadTime.start();
|
||||
|
||||
if (m_reply->error() != QNetworkReply::NoError) {
|
||||
error(m_reply->error());
|
||||
finished();
|
||||
}
|
||||
}
|
||||
|
||||
void DownloadItem::getFileName()
|
||||
{
|
||||
if (m_gettingFileName)
|
||||
return;
|
||||
|
||||
QString downloadDirectory = qApp->downloadManager()->downloadDirectory();
|
||||
|
||||
QString defaultFileName = saveFileName(downloadDirectory);
|
||||
QString fileName = defaultFileName;
|
||||
if (m_requestFileName) {
|
||||
m_gettingFileName = true;
|
||||
fileName = QFileDialog::getSaveFileName(this, tr("Save File"), defaultFileName);
|
||||
m_gettingFileName = false;
|
||||
if (fileName.isEmpty()) {
|
||||
progressBar->setVisible(false);
|
||||
stop();
|
||||
fileNameLabel->setText(tr("Download canceled: %1").arg(QFileInfo(defaultFileName).fileName()));
|
||||
m_canceledFileSelect = true;
|
||||
return;
|
||||
}
|
||||
QFileInfo fileInfo = QFileInfo(fileName);
|
||||
qApp->downloadManager()->setDownloadDirectory(fileInfo.absoluteDir().absolutePath());
|
||||
fileNameLabel->setText(fileInfo.fileName());
|
||||
}
|
||||
m_output.setFileName(fileName);
|
||||
|
||||
// Check file path for saving.
|
||||
QDir saveDirPath = QFileInfo(m_output.fileName()).dir();
|
||||
if (!saveDirPath.exists()) {
|
||||
if (!saveDirPath.mkpath(saveDirPath.absolutePath())) {
|
||||
progressBar->setVisible(false);
|
||||
stop();
|
||||
downloadInfoLabel->setText(tr("Download directory (%1) couldn't be created.").arg(saveDirPath.absolutePath()));
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
fileNameLabel->setText(QFileInfo(m_output.fileName()).fileName());
|
||||
if (m_requestFileName)
|
||||
downloadReadyRead();
|
||||
}
|
||||
|
||||
QString DownloadItem::saveFileName(const QString &directory) const
|
||||
{
|
||||
// Move this function into QNetworkReply to also get file name sent from the server
|
||||
QString path;
|
||||
if (m_reply->hasRawHeader("Content-Disposition")) {
|
||||
QString value = QLatin1String(m_reply->rawHeader("Content-Disposition"));
|
||||
int pos = value.indexOf(QLatin1String("filename="));
|
||||
if (pos != -1) {
|
||||
QString name = value.mid(pos + 9);
|
||||
if (name.startsWith(QLatin1Char('"')) && name.endsWith(QLatin1Char('"')))
|
||||
name = name.mid(1, name.size() - 2);
|
||||
path = name;
|
||||
}
|
||||
}
|
||||
if (path.isEmpty())
|
||||
path = m_url.path();
|
||||
|
||||
QFileInfo info(path);
|
||||
QString baseName = info.completeBaseName();
|
||||
QString endName = info.suffix();
|
||||
|
||||
if (baseName.isEmpty()) {
|
||||
baseName = QLatin1String("unnamed_download");
|
||||
|
||||
#ifdef DOWNLOADMANAGER_DEBUG
|
||||
qDebug() << "DownloadItem::" << __FUNCTION__ << "downloading unknown file:" << m_url;
|
||||
#endif
|
||||
}
|
||||
|
||||
if (!endName.isEmpty())
|
||||
endName = QLatin1Char('.') + endName;
|
||||
|
||||
QString name = directory + baseName + endName;
|
||||
if (!m_requestFileName && QFile::exists(name)) {
|
||||
// already exists, don't overwrite
|
||||
int i = 1;
|
||||
do {
|
||||
name = directory + baseName + QLatin1Char('-') + QString::number(i++) + endName;
|
||||
} while (QFile::exists(name));
|
||||
}
|
||||
return name;
|
||||
}
|
||||
|
||||
void DownloadItem::stop()
|
||||
{
|
||||
setUpdatesEnabled(false);
|
||||
stopButton->setEnabled(false);
|
||||
stopButton->hide();
|
||||
tryAgainButton->setEnabled(true);
|
||||
tryAgainButton->show();
|
||||
setUpdatesEnabled(true);
|
||||
m_reply->abort();
|
||||
emit downloadFinished();
|
||||
}
|
||||
|
||||
void DownloadItem::open()
|
||||
{
|
||||
QFileInfo info(m_output);
|
||||
QUrl url = QUrl::fromLocalFile(info.absoluteFilePath());
|
||||
QDesktopServices::openUrl(url);
|
||||
}
|
||||
|
||||
void DownloadItem::tryAgain()
|
||||
{
|
||||
if (!tryAgainButton->isEnabled())
|
||||
return;
|
||||
|
||||
tryAgainButton->setEnabled(false);
|
||||
tryAgainButton->setVisible(false);
|
||||
stopButton->setEnabled(true);
|
||||
stopButton->setVisible(true);
|
||||
progressBar->setVisible(true);
|
||||
|
||||
QNetworkReply *r = qApp->downloadManager()->networkManager()->get(QNetworkRequest(m_url));
|
||||
if (m_reply)
|
||||
m_reply->deleteLater();
|
||||
if (m_output.exists())
|
||||
m_output.remove();
|
||||
m_reply = r;
|
||||
init();
|
||||
emit statusChanged();
|
||||
}
|
||||
|
||||
void DownloadItem::downloadReadyRead()
|
||||
{
|
||||
if (m_requestFileName && m_output.fileName().isEmpty())
|
||||
return;
|
||||
if (!m_output.isOpen()) {
|
||||
// in case someone else has already put a file there
|
||||
if (!m_requestFileName)
|
||||
getFileName();
|
||||
if (!m_output.open(QIODevice::WriteOnly)) {
|
||||
downloadInfoLabel->setText(tr("Error opening output file: %1")
|
||||
.arg(m_output.errorString()));
|
||||
stop();
|
||||
emit statusChanged();
|
||||
return;
|
||||
}
|
||||
emit statusChanged();
|
||||
}
|
||||
if (-1 == m_output.write(m_reply->readAll())) {
|
||||
downloadInfoLabel->setText(tr("Error saving: %1")
|
||||
.arg(m_output.errorString()));
|
||||
stopButton->click();
|
||||
} else {
|
||||
m_startedSaving = true;
|
||||
if (m_finishedDownloading)
|
||||
finished();
|
||||
}
|
||||
}
|
||||
|
||||
void DownloadItem::error(QNetworkReply::NetworkError)
|
||||
{
|
||||
#ifdef DOWNLOADMANAGER_DEBUG
|
||||
qDebug() << "DownloadItem::" << __FUNCTION__ << m_reply->errorString() << m_url;
|
||||
#endif
|
||||
|
||||
downloadInfoLabel->setText(tr("Network Error: %1").arg(m_reply->errorString()));
|
||||
tryAgainButton->setEnabled(true);
|
||||
tryAgainButton->setVisible(true);
|
||||
emit downloadFinished();
|
||||
}
|
||||
|
||||
void DownloadItem::metaDataChanged()
|
||||
{
|
||||
QVariant locationHeader = m_reply->header(QNetworkRequest::LocationHeader);
|
||||
if (locationHeader.isValid()) {
|
||||
m_url = locationHeader.toUrl();
|
||||
m_reply->deleteLater();
|
||||
m_reply = qApp->downloadManager()->networkManager()->get(QNetworkRequest(m_url));
|
||||
init();
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef DOWNLOADMANAGER_DEBUG
|
||||
qDebug() << "DownloadItem::" << __FUNCTION__ << "not handled.";
|
||||
#endif
|
||||
}
|
||||
|
||||
void DownloadItem::downloadProgress(qint64 bytesReceived, qint64 bytesTotal)
|
||||
{
|
||||
QTime now = QTime::currentTime();
|
||||
if (m_lastProgressTime.msecsTo(now) < 200)
|
||||
return;
|
||||
|
||||
m_lastProgressTime = now;
|
||||
|
||||
m_bytesReceived = bytesReceived;
|
||||
qint64 currentValue = 0;
|
||||
qint64 totalValue = 0;
|
||||
if (bytesTotal > 0) {
|
||||
currentValue = bytesReceived * 100 / bytesTotal;
|
||||
totalValue = 100;
|
||||
}
|
||||
progressBar->setValue(currentValue);
|
||||
progressBar->setMaximum(totalValue);
|
||||
|
||||
emit progress(currentValue, totalValue);
|
||||
updateInfoLabel();
|
||||
}
|
||||
|
||||
qint64 DownloadItem::bytesTotal() const
|
||||
{
|
||||
return m_reply->header(QNetworkRequest::ContentLengthHeader).toULongLong();
|
||||
}
|
||||
|
||||
qint64 DownloadItem::bytesReceived() const
|
||||
{
|
||||
return m_bytesReceived;
|
||||
}
|
||||
|
||||
double DownloadItem::remainingTime() const
|
||||
{
|
||||
if (!downloading())
|
||||
return -1.0;
|
||||
|
||||
double timeRemaining = ((double)(bytesTotal() - bytesReceived())) / currentSpeed();
|
||||
|
||||
// When downloading the eta should never be 0
|
||||
if (timeRemaining == 0)
|
||||
timeRemaining = 1;
|
||||
|
||||
return timeRemaining;
|
||||
}
|
||||
|
||||
double DownloadItem::currentSpeed() const
|
||||
{
|
||||
if (!downloading())
|
||||
return -1.0;
|
||||
|
||||
return m_bytesReceived * 1000.0 / m_downloadTime.elapsed();
|
||||
}
|
||||
|
||||
void DownloadItem::updateInfoLabel()
|
||||
{
|
||||
if (m_reply->error() != QNetworkReply::NoError)
|
||||
return;
|
||||
|
||||
qint64 bytesTotal = m_reply->header(QNetworkRequest::ContentLengthHeader).toULongLong();
|
||||
bool running = !downloadedSuccessfully();
|
||||
|
||||
// update info label
|
||||
double speed = currentSpeed();
|
||||
double timeRemaining = remainingTime();
|
||||
|
||||
QString info;
|
||||
if (running) {
|
||||
QString remaining;
|
||||
|
||||
if (bytesTotal != 0) {
|
||||
remaining = DownloadManager::timeString(timeRemaining);
|
||||
}
|
||||
|
||||
info = QString(tr("%1 of %2 (%3/sec) - %4"))
|
||||
.arg(DownloadManager::dataString(m_bytesReceived))
|
||||
.arg(bytesTotal == 0 ? tr("?") : DownloadManager::dataString(bytesTotal))
|
||||
.arg(DownloadManager::dataString((int)speed))
|
||||
.arg(remaining);
|
||||
} else {
|
||||
if (m_bytesReceived == bytesTotal)
|
||||
info = DownloadManager::dataString(m_output.size());
|
||||
else
|
||||
info = tr("%1 of %2 - Download Complete")
|
||||
.arg(DownloadManager::dataString(m_bytesReceived))
|
||||
.arg(DownloadManager::dataString(bytesTotal));
|
||||
}
|
||||
downloadInfoLabel->setText(info);
|
||||
}
|
||||
|
||||
bool DownloadItem::downloading() const
|
||||
{
|
||||
return (progressBar->isVisible());
|
||||
}
|
||||
|
||||
bool DownloadItem::downloadedSuccessfully() const
|
||||
{
|
||||
return (stopButton->isHidden() && tryAgainButton->isHidden());
|
||||
}
|
||||
|
||||
void DownloadItem::finished()
|
||||
{
|
||||
m_finishedDownloading = true;
|
||||
if (!m_startedSaving) {
|
||||
return;
|
||||
}
|
||||
progressBar->hide();
|
||||
stopButton->setEnabled(false);
|
||||
stopButton->hide();
|
||||
openButton->setEnabled(true);
|
||||
m_output.close();
|
||||
updateInfoLabel();
|
||||
emit statusChanged();
|
||||
emit downloadFinished();
|
||||
}
|
||||
|
||||
/*!
|
||||
DownloadManager is a Dialog that contains a list of DownloadItems
|
||||
|
||||
It is a basic download manager. It only downloads the file, doesn't do BitTorrent,
|
||||
extract zipped files or anything fancy.
|
||||
*/
|
||||
DownloadManager::DownloadManager(QWidget *parent)
|
||||
: TabContent(parent)
|
||||
, m_autoSaver(new AutoSaver(this))
|
||||
, m_model(new DownloadModel(this))
|
||||
, m_networkManager(new SilentNetworkAccessManager(this))
|
||||
, m_iconProvider(0)
|
||||
, m_removePolicy(Never)
|
||||
{
|
||||
setupUi(this);
|
||||
|
||||
QSettings settings;
|
||||
settings.beginGroup(QLatin1String("downloadmanager"));
|
||||
QString defaultLocation = QDesktopServices::storageLocation(QDesktopServices::DesktopLocation);
|
||||
setDownloadDirectory(settings.value(QLatin1String("downloadDirectory"), defaultLocation).toString());
|
||||
|
||||
downloadsView->setShowGrid(false);
|
||||
downloadsView->verticalHeader()->hide();
|
||||
downloadsView->horizontalHeader()->hide();
|
||||
downloadsView->setAlternatingRowColors(true);
|
||||
downloadsView->horizontalHeader()->setStretchLastSection(true);
|
||||
downloadsView->setModel(m_model);
|
||||
connect(cleanupButton, SIGNAL(clicked()), this, SLOT(cleanup()));
|
||||
connect(buttonBox, SIGNAL(rejected()), this, SLOT(close()));
|
||||
load();
|
||||
}
|
||||
|
||||
DownloadManager::~DownloadManager()
|
||||
{
|
||||
m_autoSaver->changeOccurred();
|
||||
m_autoSaver->saveIfNeccessary();
|
||||
if (m_iconProvider)
|
||||
delete m_iconProvider;
|
||||
}
|
||||
|
||||
int DownloadManager::activeDownloads() const
|
||||
{
|
||||
int count = 0;
|
||||
for (int i = 0; i < m_downloads.count(); ++i) {
|
||||
if (m_downloads.at(i)->stopButton->isEnabled())
|
||||
++count;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
bool DownloadManager::allowQuit()
|
||||
{
|
||||
if (activeDownloads() >= 1) {
|
||||
int choice = QMessageBox::warning(this, QString(),
|
||||
tr("There are %1 downloads in progress\n"
|
||||
"Do you want to quit anyway?").arg(activeDownloads()),
|
||||
QMessageBox::Yes | QMessageBox::No,
|
||||
QMessageBox::No);
|
||||
if (choice == QMessageBox::No) {
|
||||
show();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void DownloadManager::download(const QNetworkRequest &request, bool requestFileName)
|
||||
{
|
||||
if (request.url().isEmpty())
|
||||
return;
|
||||
|
||||
handleUnsupportedContent(m_networkManager->get(request), requestFileName);
|
||||
}
|
||||
|
||||
void DownloadManager::download(const QUrl &url, bool requestFileName) {
|
||||
download(QNetworkRequest(url), requestFileName);
|
||||
}
|
||||
|
||||
void DownloadManager::handleUnsupportedContent(QNetworkReply *reply, bool requestFileName)
|
||||
{
|
||||
if (!reply || reply->url().isEmpty())
|
||||
return;
|
||||
|
||||
QVariant header = reply->header(QNetworkRequest::ContentLengthHeader);
|
||||
bool ok;
|
||||
int size = header.toInt(&ok);
|
||||
if (ok && size == 0)
|
||||
return;
|
||||
|
||||
#ifdef DOWNLOADMANAGER_DEBUG
|
||||
qDebug() << "DownloadManager::" << __FUNCTION__ << reply->url() << "requestFileName" << requestFileName;
|
||||
#endif
|
||||
|
||||
DownloadItem *item = new DownloadItem(reply, requestFileName, this);
|
||||
addItem(item);
|
||||
|
||||
if (item->m_canceledFileSelect)
|
||||
return;
|
||||
/*
|
||||
if (!isVisible())
|
||||
show();
|
||||
|
||||
activateWindow();
|
||||
raise();*/
|
||||
}
|
||||
|
||||
void DownloadManager::addItem(DownloadItem *item)
|
||||
{
|
||||
connect(item, SIGNAL(statusChanged()), this, SLOT(updateRow()));
|
||||
connect(item, SIGNAL(downloadFinished()), this, SLOT(finished()));
|
||||
int row = m_downloads.count();
|
||||
m_model->beginInsertRows(QModelIndex(), row, row);
|
||||
m_downloads.append(item);
|
||||
m_model->endInsertRows();
|
||||
updateItemCount();
|
||||
downloadsView->setIndexWidget(m_model->index(row, 0), item);
|
||||
QIcon icon = style()->standardIcon(QStyle::SP_FileIcon);
|
||||
item->fileIcon->setPixmap(icon.pixmap(48, 48));
|
||||
downloadsView->setRowHeight(row, item->sizeHint().height());
|
||||
updateRow(item); //incase download finishes before the constructor returns
|
||||
updateActiveItemCount();
|
||||
}
|
||||
|
||||
void DownloadManager::updateActiveItemCount()
|
||||
{
|
||||
int acCount = activeDownloads();
|
||||
if (acCount > 0) {
|
||||
setWindowTitle(QApplication::translate("DownloadDialog", "Downloading %1", 0, QApplication::UnicodeUTF8).arg(acCount));
|
||||
} else {
|
||||
setWindowTitle(QApplication::translate("DownloadDialog", "Downloads", 0, QApplication::UnicodeUTF8));
|
||||
}
|
||||
}
|
||||
QNetworkAccessManager *DownloadManager::networkManager() const
|
||||
{
|
||||
return m_networkManager;
|
||||
}
|
||||
|
||||
void DownloadManager::finished()
|
||||
{
|
||||
updateActiveItemCount();
|
||||
if (isVisible()) {
|
||||
QApplication::alert(this);
|
||||
}
|
||||
}
|
||||
|
||||
void DownloadManager::updateRow()
|
||||
{
|
||||
if (DownloadItem *item = qobject_cast<DownloadItem*>(sender()))
|
||||
updateRow(item);
|
||||
}
|
||||
|
||||
void DownloadManager::updateRow(DownloadItem *item)
|
||||
{
|
||||
int row = m_downloads.indexOf(item);
|
||||
if (-1 == row)
|
||||
return;
|
||||
if (!m_iconProvider)
|
||||
m_iconProvider = new QFileIconProvider();
|
||||
QIcon icon = m_iconProvider->icon(item->m_output.fileName());
|
||||
if (icon.isNull())
|
||||
icon = style()->standardIcon(QStyle::SP_FileIcon);
|
||||
item->fileIcon->setPixmap(icon.pixmap(48, 48));
|
||||
|
||||
int oldHeight = downloadsView->rowHeight(row);
|
||||
downloadsView->setRowHeight(row, qMax(oldHeight, item->minimumSizeHint().height()));
|
||||
|
||||
bool remove = false;
|
||||
QWebSettings *globalSettings = QWebSettings::globalSettings();
|
||||
if (!item->downloading()
|
||||
&& globalSettings->testAttribute(QWebSettings::PrivateBrowsingEnabled))
|
||||
remove = true;
|
||||
|
||||
if (item->downloadedSuccessfully()
|
||||
&& removePolicy() == DownloadManager::SuccessFullDownload) {
|
||||
remove = true;
|
||||
}
|
||||
if (remove)
|
||||
m_model->removeRow(row);
|
||||
|
||||
cleanupButton->setEnabled(m_downloads.count() - activeDownloads() > 0);
|
||||
}
|
||||
|
||||
DownloadManager::RemovePolicy DownloadManager::removePolicy() const
|
||||
{
|
||||
return m_removePolicy;
|
||||
}
|
||||
|
||||
void DownloadManager::setRemovePolicy(RemovePolicy policy)
|
||||
{
|
||||
if (policy == m_removePolicy)
|
||||
return;
|
||||
m_removePolicy = policy;
|
||||
m_autoSaver->changeOccurred();
|
||||
}
|
||||
|
||||
void DownloadManager::save() const
|
||||
{
|
||||
QSettings settings;
|
||||
settings.beginGroup(QLatin1String("downloadmanager"));
|
||||
QMetaEnum removePolicyEnum = staticMetaObject.enumerator(staticMetaObject.indexOfEnumerator("RemovePolicy"));
|
||||
settings.setValue(QLatin1String("removeDownloadsPolicy"), QLatin1String(removePolicyEnum.valueToKey(m_removePolicy)));
|
||||
settings.setValue(QLatin1String("size"), size());
|
||||
if (m_removePolicy == Exit)
|
||||
return;
|
||||
|
||||
for (int i = 0; i < m_downloads.count(); ++i) {
|
||||
QString key = QString(QLatin1String("download_%1_")).arg(i);
|
||||
settings.setValue(key + QLatin1String("url"), m_downloads[i]->m_url);
|
||||
settings.setValue(key + QLatin1String("location"), QFileInfo(m_downloads[i]->m_output).filePath());
|
||||
settings.setValue(key + QLatin1String("done"), m_downloads[i]->downloadedSuccessfully());
|
||||
}
|
||||
int i = m_downloads.count();
|
||||
QString key = QString(QLatin1String("download_%1_")).arg(i);
|
||||
while (settings.contains(key + QLatin1String("url"))) {
|
||||
settings.remove(key + QLatin1String("url"));
|
||||
settings.remove(key + QLatin1String("location"));
|
||||
settings.remove(key + QLatin1String("done"));
|
||||
key = QString(QLatin1String("download_%1_")).arg(++i);
|
||||
}
|
||||
}
|
||||
|
||||
void DownloadManager::load()
|
||||
{
|
||||
QSettings settings;
|
||||
settings.beginGroup(QLatin1String("downloadmanager"));
|
||||
QSize size = settings.value(QLatin1String("size")).toSize();
|
||||
if (size.isValid())
|
||||
resize(size);
|
||||
QByteArray value = settings.value(QLatin1String("removeDownloadsPolicy"), QLatin1String("Never")).toByteArray();
|
||||
QMetaEnum removePolicyEnum = staticMetaObject.enumerator(staticMetaObject.indexOfEnumerator("RemovePolicy"));
|
||||
m_removePolicy = removePolicyEnum.keyToValue(value) == -1 ?
|
||||
Never :
|
||||
static_cast<RemovePolicy>(removePolicyEnum.keyToValue(value));
|
||||
|
||||
int i = 0;
|
||||
QString key = QString(QLatin1String("download_%1_")).arg(i);
|
||||
while (settings.contains(key + QLatin1String("url"))) {
|
||||
QUrl url = settings.value(key + QLatin1String("url")).toUrl();
|
||||
QString fileName = settings.value(key + QLatin1String("location")).toString();
|
||||
bool done = settings.value(key + QLatin1String("done"), true).toBool();
|
||||
if (!url.isEmpty() && !fileName.isEmpty()) {
|
||||
DownloadItem *item = new DownloadItem(0, this);
|
||||
item->m_output.setFileName(fileName);
|
||||
item->fileNameLabel->setText(QFileInfo(item->m_output.fileName()).fileName());
|
||||
item->m_url = url;
|
||||
item->stopButton->setVisible(false);
|
||||
item->stopButton->setEnabled(false);
|
||||
item->tryAgainButton->setVisible(!done);
|
||||
item->tryAgainButton->setEnabled(!done);
|
||||
item->progressBar->setVisible(false);
|
||||
addItem(item);
|
||||
}
|
||||
key = QString(QLatin1String("download_%1_")).arg(++i);
|
||||
}
|
||||
cleanupButton->setEnabled(m_downloads.count() - activeDownloads() > 0);
|
||||
updateActiveItemCount();
|
||||
}
|
||||
|
||||
void DownloadManager::cleanup()
|
||||
{
|
||||
if (m_downloads.isEmpty())
|
||||
return;
|
||||
m_model->removeRows(0, m_downloads.count());
|
||||
updateItemCount();
|
||||
updateActiveItemCount();
|
||||
if (m_downloads.isEmpty() && m_iconProvider) {
|
||||
delete m_iconProvider;
|
||||
m_iconProvider = 0;
|
||||
}
|
||||
m_autoSaver->changeOccurred();
|
||||
}
|
||||
|
||||
void DownloadManager::updateItemCount()
|
||||
{
|
||||
int count = m_downloads.count();
|
||||
itemCount->setText(tr("%n Download(s)", "", count));
|
||||
}
|
||||
|
||||
void DownloadManager::setDownloadDirectory(const QString &directory)
|
||||
{
|
||||
m_downloadDirectory = directory;
|
||||
if (!m_downloadDirectory.isEmpty())
|
||||
m_downloadDirectory += QLatin1Char('/');
|
||||
}
|
||||
|
||||
QString DownloadManager::downloadDirectory()
|
||||
{
|
||||
return m_downloadDirectory;
|
||||
}
|
||||
|
||||
QString DownloadManager::timeString(double timeRemaining)
|
||||
{
|
||||
QString remaining;
|
||||
|
||||
if (timeRemaining > 60) {
|
||||
timeRemaining = timeRemaining / 60;
|
||||
timeRemaining = floor(timeRemaining);
|
||||
remaining = tr("%n minutes remaining", "", int(timeRemaining));
|
||||
}
|
||||
else {
|
||||
timeRemaining = floor(timeRemaining);
|
||||
remaining = tr("%n seconds remaining", "", int(timeRemaining));
|
||||
}
|
||||
|
||||
return remaining;
|
||||
}
|
||||
|
||||
QString DownloadManager::dataString(qint64 size)
|
||||
{
|
||||
QString unit;
|
||||
double newSize;
|
||||
|
||||
if (size < 1024) {
|
||||
newSize = size;
|
||||
unit = tr("bytes");
|
||||
} else if (size < 1024 * 1024) {
|
||||
newSize = (double)size / (double)1024;
|
||||
unit = tr("kB");
|
||||
} else if (size < 1024 * 1024 * 1024) {
|
||||
newSize = (double)size / (double)(1024 * 1024);
|
||||
unit = tr("MB");
|
||||
} else {
|
||||
newSize = (double)size / (double)(1024 * 1024 * 1024);
|
||||
unit = tr("GB");
|
||||
}
|
||||
|
||||
return QString(QLatin1String("%1 %2")).arg(newSize, 0, 'f', 1).arg(unit);
|
||||
}
|
||||
|
||||
DownloadModel::DownloadModel(DownloadManager *downloadManager, QObject *parent)
|
||||
: QAbstractListModel(parent)
|
||||
, m_downloadManager(downloadManager)
|
||||
{
|
||||
}
|
||||
|
||||
QVariant DownloadModel::data(const QModelIndex &index, int role) const
|
||||
{
|
||||
if (index.row() < 0 || index.row() >= rowCount(index.parent()))
|
||||
return QVariant();
|
||||
if (role == Qt::ToolTipRole)
|
||||
if (!m_downloadManager->m_downloads.at(index.row())->downloadedSuccessfully())
|
||||
return m_downloadManager->m_downloads.at(index.row())->downloadInfoLabel->text();
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
int DownloadModel::rowCount(const QModelIndex &parent) const
|
||||
{
|
||||
return (parent.isValid()) ? 0 : m_downloadManager->m_downloads.count();
|
||||
}
|
||||
|
||||
bool DownloadModel::removeRows(int row, int count, const QModelIndex &parent)
|
||||
{
|
||||
if (parent.isValid())
|
||||
return false;
|
||||
|
||||
int lastRow = row + count - 1;
|
||||
for (int i = lastRow; i >= row; --i) {
|
||||
if (m_downloadManager->m_downloads.at(i)->downloadedSuccessfully()
|
||||
|| m_downloadManager->m_downloads.at(i)->tryAgainButton->isEnabled()) {
|
||||
beginRemoveRows(parent, i, i);
|
||||
m_downloadManager->m_downloads.takeAt(i)->deleteLater();
|
||||
endRemoveRows();
|
||||
}
|
||||
}
|
||||
m_downloadManager->m_autoSaver->changeOccurred();
|
||||
m_downloadManager->updateItemCount();
|
||||
return true;
|
||||
}
|
||||
|
||||
Qt::ItemFlags DownloadModel::flags(const QModelIndex &index) const
|
||||
{
|
||||
if (index.row() < 0 || index.row() >= rowCount(index.parent()))
|
||||
return 0;
|
||||
|
||||
Qt::ItemFlags defaultFlags = QAbstractItemModel::flags(index);
|
||||
|
||||
DownloadItem *item = m_downloadManager->m_downloads.at(index.row());
|
||||
if (item->downloadedSuccessfully())
|
||||
return defaultFlags | Qt::ItemIsDragEnabled;
|
||||
|
||||
return defaultFlags;
|
||||
}
|
||||
|
||||
QMimeData *DownloadModel::mimeData(const QModelIndexList &indexes) const
|
||||
{
|
||||
QMimeData *mimeData = new QMimeData();
|
||||
QList<QUrl> urls;
|
||||
foreach (const QModelIndex &index, indexes) {
|
||||
if (!index.isValid())
|
||||
continue;
|
||||
DownloadItem *item = m_downloadManager->m_downloads.at(index.row());
|
||||
urls.append(QUrl::fromLocalFile(QFileInfo(item->m_output).absoluteFilePath()));
|
||||
}
|
||||
mimeData->setUrls(urls);
|
||||
return mimeData;
|
||||
}
|
||||
|
||||
WebBrowser *DownloadManager::webBrowser() {
|
||||
return NULL;
|
||||
}
|
||||
|
@ -1,43 +1,213 @@
|
||||
// This file is part of RSS Guard.
|
||||
//
|
||||
// Copyright (C) 2011-2015 by Martin Rotter <rotter.martinos@gmail.com>
|
||||
//
|
||||
// RSS Guard is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// RSS Guard 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 General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with RSS Guard. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef DOWNLOADMANAGER_H
|
||||
#define DOWNLOADMANAGER_H
|
||||
|
||||
#include "gui/tabcontent.h"
|
||||
|
||||
#include "ui_downloadmanager.h"
|
||||
|
||||
|
||||
namespace Ui {
|
||||
class DownloadManager;
|
||||
}
|
||||
|
||||
class DownloadManager : public TabContent {
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit DownloadManager(QWidget *parent = 0);
|
||||
virtual ~DownloadManager();
|
||||
|
||||
WebBrowser *webBrowser();
|
||||
|
||||
private:
|
||||
Ui::DownloadManager *m_ui;
|
||||
};
|
||||
|
||||
#endif // DOWNLOADMANAGER_H
|
||||
/*
|
||||
* Copyright 2008-2009 Benjamin C. Meyer <ben@meyerhome.net>
|
||||
* Copyright 2008 Jason A. Donenfeld <Jason@zx2c4.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program 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 General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 2008-2008 Trolltech ASA. All rights reserved.
|
||||
**
|
||||
** This file is part of the demonstration applications of the Qt Toolkit.
|
||||
**
|
||||
** This file may be used under the terms of the GNU General Public
|
||||
** License versions 2.0 or 3.0 as published by the Free Software
|
||||
** Foundation and appearing in the files LICENSE.GPL2 and LICENSE.GPL3
|
||||
** included in the packaging of this file. Alternatively you may (at
|
||||
** your option) use any later version of the GNU General Public
|
||||
** License if such license has been publicly approved by Trolltech ASA
|
||||
** (or its successors, if any) and the KDE Free Qt Foundation. In
|
||||
** addition, as a special exception, Trolltech gives you certain
|
||||
** additional rights. These rights are described in the Trolltech GPL
|
||||
** Exception version 1.2, which can be found at
|
||||
** http://www.trolltech.com/products/qt/gplexception/ and in the file
|
||||
** GPL_EXCEPTION.txt in this package.
|
||||
**
|
||||
** Please review the following information to ensure GNU General
|
||||
** Public Licensing requirements will be met:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/opensource/. If
|
||||
** you are unsure which license is appropriate for your use, please
|
||||
** review the following information:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/licensingoverview
|
||||
** or contact the sales department at sales@trolltech.com.
|
||||
**
|
||||
** In addition, as a special exception, Trolltech, as the sole
|
||||
** copyright holder for Qt Designer, grants users of the Qt/Eclipse
|
||||
** Integration plug-in the right for the Qt/Eclipse Integration to
|
||||
** link to functionality provided by Qt Designer and its related
|
||||
** libraries.
|
||||
**
|
||||
** This file is provided "AS IS" with NO WARRANTY OF ANY KIND,
|
||||
** INCLUDING THE WARRANTIES OF DESIGN, MERCHANTABILITY AND FITNESS FOR
|
||||
** A PARTICULAR PURPOSE. Trolltech reserves all rights not expressly
|
||||
** granted herein.
|
||||
**
|
||||
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
|
||||
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
**
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef DOWNLOADMANAGER_H
|
||||
#define DOWNLOADMANAGER_H
|
||||
|
||||
#include "ui_downloadmanager.h"
|
||||
#include "ui_downloaditem.h"
|
||||
|
||||
#include "gui/tabcontent.h"
|
||||
|
||||
#include <qnetworkreply.h>
|
||||
|
||||
#include <qfile.h>
|
||||
#include <qdatetime.h>
|
||||
|
||||
class DownloadItem : public QWidget, public Ui_DownloadItem {
|
||||
Q_OBJECT
|
||||
|
||||
friend class DownloadManager;
|
||||
|
||||
signals:
|
||||
void statusChanged();
|
||||
void progress(qint64 bytesReceived = 0, qint64 bytesTotal = 0);
|
||||
void downloadFinished();
|
||||
|
||||
public:
|
||||
DownloadItem(QNetworkReply *reply = 0, bool requestFileName = false, QWidget *parent = 0);
|
||||
bool downloading() const;
|
||||
bool downloadedSuccessfully() const;
|
||||
|
||||
qint64 bytesTotal() const;
|
||||
qint64 bytesReceived() const;
|
||||
double remainingTime() const;
|
||||
double currentSpeed() const;
|
||||
|
||||
QUrl m_url;
|
||||
|
||||
QFile m_output;
|
||||
QNetworkReply *m_reply;
|
||||
|
||||
private slots:
|
||||
void stop();
|
||||
void tryAgain();
|
||||
void open();
|
||||
|
||||
void downloadReadyRead();
|
||||
void error(QNetworkReply::NetworkError code);
|
||||
void downloadProgress(qint64 bytesReceived, qint64 bytesTotal);
|
||||
void metaDataChanged();
|
||||
void finished();
|
||||
|
||||
private:
|
||||
void getFileName();
|
||||
void init();
|
||||
void updateInfoLabel();
|
||||
|
||||
QString saveFileName(const QString &directory) const;
|
||||
|
||||
bool m_requestFileName;
|
||||
qint64 m_bytesReceived;
|
||||
QTime m_downloadTime;
|
||||
bool m_startedSaving;
|
||||
bool m_finishedDownloading;
|
||||
bool m_gettingFileName;
|
||||
bool m_canceledFileSelect;
|
||||
QTime m_lastProgressTime;
|
||||
};
|
||||
|
||||
class AutoSaver;
|
||||
class DownloadModel;
|
||||
QT_BEGIN_NAMESPACE
|
||||
class QFileIconProvider;
|
||||
class QMimeData;
|
||||
QT_END_NAMESPACE
|
||||
|
||||
class DownloadManager : public TabContent, public Ui_DownloadManager {
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(RemovePolicy removePolicy READ removePolicy WRITE setRemovePolicy)
|
||||
Q_ENUMS(RemovePolicy)
|
||||
|
||||
friend class DownloadModel;
|
||||
|
||||
public:
|
||||
enum RemovePolicy {
|
||||
Never,
|
||||
Exit,
|
||||
SuccessFullDownload
|
||||
};
|
||||
|
||||
DownloadManager(QWidget *parent = 0);
|
||||
~DownloadManager();
|
||||
|
||||
WebBrowser *webBrowser();
|
||||
QNetworkAccessManager *networkManager() const;
|
||||
|
||||
int activeDownloads() const;
|
||||
bool allowQuit();
|
||||
|
||||
RemovePolicy removePolicy() const;
|
||||
void setRemovePolicy(RemovePolicy policy);
|
||||
|
||||
static QString timeString(double timeRemaining);
|
||||
static QString dataString(qint64 size);
|
||||
|
||||
void setDownloadDirectory(const QString &directory);
|
||||
QString downloadDirectory();
|
||||
|
||||
public slots:
|
||||
void download(const QNetworkRequest &request, bool requestFileName = false);
|
||||
void download(const QUrl &url, bool requestFileName = false);
|
||||
void handleUnsupportedContent(QNetworkReply *reply, bool requestFileName = false);
|
||||
void cleanup();
|
||||
|
||||
private slots:
|
||||
void save() const;
|
||||
void updateRow(DownloadItem *item);
|
||||
void updateRow();
|
||||
void finished();
|
||||
|
||||
private:
|
||||
void addItem(DownloadItem *item);
|
||||
void updateItemCount();
|
||||
void load();
|
||||
void updateActiveItemCount();
|
||||
|
||||
AutoSaver *m_autoSaver;
|
||||
DownloadModel *m_model;
|
||||
QNetworkAccessManager *m_networkManager;
|
||||
QFileIconProvider *m_iconProvider;
|
||||
QList<DownloadItem*> m_downloads;
|
||||
RemovePolicy m_removePolicy;
|
||||
QString m_downloadDirectory;
|
||||
};
|
||||
|
||||
class DownloadModel : public QAbstractListModel {
|
||||
Q_OBJECT
|
||||
|
||||
friend class DownloadManager;
|
||||
|
||||
public:
|
||||
DownloadModel(DownloadManager *downloadManager, QObject *parent = 0);
|
||||
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
|
||||
int rowCount(const QModelIndex &parent = QModelIndex()) const;
|
||||
bool removeRows(int row, int count, const QModelIndex &parent = QModelIndex());
|
||||
Qt::ItemFlags flags(const QModelIndex &index) const;
|
||||
QMimeData *mimeData(const QModelIndexList &indexes) const;
|
||||
|
||||
private:
|
||||
DownloadManager *m_downloadManager;
|
||||
};
|
||||
|
||||
#endif // DOWNLOADMANAGER_H
|
||||
|
@ -13,11 +13,21 @@
|
||||
<property name="windowTitle">
|
||||
<string>Form</string>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<item>
|
||||
<widget class="QTableView" name="tableView"/>
|
||||
<layout class="QGridLayout" name="gridLayout">
|
||||
<item row="0" column="0" colspan="2">
|
||||
<widget class="EditTableView" name="downloadsView">
|
||||
<property name="frameShape">
|
||||
<enum>QFrame::NoFrame</enum>
|
||||
</property>
|
||||
<property name="dragEnabled">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="dragDropMode">
|
||||
<enum>QAbstractItemView::DragOnly</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<item row="1" column="0">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
||||
<item>
|
||||
<widget class="QPushButton" name="cleanupButton">
|
||||
@ -42,17 +52,56 @@
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLabel" name="itemCount">
|
||||
<property name="text">
|
||||
<string>0 Items</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<widget class="QLabel" name="itemCount">
|
||||
<property name="text">
|
||||
<string>0 Items</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
<widget class="QWidget" name="layoutWidget">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>30</x>
|
||||
<y>10</y>
|
||||
<width>133</width>
|
||||
<height>25</height>
|
||||
</rect>
|
||||
</property>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_2">
|
||||
<item>
|
||||
<spacer name="horizontalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>50</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QDialogButtonBox" name="buttonBox">
|
||||
<property name="standardButtons">
|
||||
<set>QDialogButtonBox::Close</set>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>EditTableView</class>
|
||||
<extends>QTableView</extends>
|
||||
<header>edittableview.h</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
|
81
src/network-web/edittableview.cpp
Normal file
81
src/network-web/edittableview.cpp
Normal file
@ -0,0 +1,81 @@
|
||||
/**
|
||||
* Copyright (c) 2008, Benjamin C. Meyer <ben@meyerhome.net>
|
||||
* Copyright (c) 2009, Jakub Wieczorek <faw217@gmail.com>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the Benjamin Meyer nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "edittableview.h"
|
||||
|
||||
#include <qevent.h>
|
||||
|
||||
EditTableView::EditTableView(QWidget *parent)
|
||||
: QTableView(parent)
|
||||
{
|
||||
}
|
||||
|
||||
void EditTableView::keyPressEvent(QKeyEvent *event)
|
||||
{
|
||||
if (model() && event->key() == Qt::Key_Delete) {
|
||||
removeSelected();
|
||||
event->setAccepted(true);
|
||||
} else {
|
||||
QAbstractItemView::keyPressEvent(event);
|
||||
}
|
||||
}
|
||||
|
||||
void EditTableView::removeSelected()
|
||||
{
|
||||
if (!model() || !selectionModel() || !selectionModel()->hasSelection())
|
||||
return;
|
||||
|
||||
QModelIndexList selectedRows = selectionModel()->selectedRows();
|
||||
if (selectedRows.isEmpty())
|
||||
return;
|
||||
|
||||
int newSelectedRow = selectedRows.at(0).row();
|
||||
for (int i = selectedRows.count() - 1; i >= 0; --i) {
|
||||
QModelIndex idx = selectedRows.at(i);
|
||||
model()->removeRow(idx.row(), rootIndex());
|
||||
}
|
||||
|
||||
// select the item at the same position
|
||||
QModelIndex newSelectedIndex = model()->index(newSelectedRow, 0, rootIndex());
|
||||
// if that was the last item
|
||||
if (!newSelectedIndex.isValid())
|
||||
newSelectedIndex = model()->index(newSelectedRow - 1, 0, rootIndex());
|
||||
|
||||
selectionModel()->select(newSelectedIndex, QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
|
||||
setCurrentIndex(newSelectedIndex);
|
||||
}
|
||||
|
||||
void EditTableView::removeAll()
|
||||
{
|
||||
if (!model())
|
||||
return;
|
||||
|
||||
model()->removeRows(0, model()->rowCount(rootIndex()), rootIndex());
|
||||
}
|
||||
|
49
src/network-web/edittableview.h
Normal file
49
src/network-web/edittableview.h
Normal file
@ -0,0 +1,49 @@
|
||||
/**
|
||||
* Copyright (c) 2008, Benjamin C. Meyer <ben@meyerhome.net>
|
||||
* Copyright (c) 2009, Jakub Wieczorek <faw217@gmail.com>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the Benjamin Meyer nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef EDITTABLEVIEW_H
|
||||
#define EDITTABLEVIEW_H
|
||||
|
||||
#include <qtableview.h>
|
||||
|
||||
class EditTableView : public QTableView
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
EditTableView(QWidget *parent = 0);
|
||||
void keyPressEvent(QKeyEvent *event);
|
||||
|
||||
public slots:
|
||||
void removeSelected();
|
||||
void removeAll();
|
||||
};
|
||||
|
||||
#endif // EDITTABLEVIEW_H
|
||||
|
48
src/network-web/squeezelabel.cpp
Normal file
48
src/network-web/squeezelabel.cpp
Normal file
@ -0,0 +1,48 @@
|
||||
/**
|
||||
* Copyright (c) 2009, Benjamin C. Meyer <ben@meyerhome.net>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the Benjamin Meyer nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "squeezelabel.h"
|
||||
|
||||
SqueezeLabel::SqueezeLabel(QWidget *parent)
|
||||
: QLabel(parent)
|
||||
{
|
||||
}
|
||||
|
||||
void SqueezeLabel::paintEvent(QPaintEvent *event)
|
||||
{
|
||||
if (m_SqueezedTextCache != text()) {
|
||||
m_SqueezedTextCache = text();
|
||||
QFontMetrics fm = fontMetrics();
|
||||
if (fm.width(m_SqueezedTextCache) > contentsRect().width()) {
|
||||
QString elided = fm.elidedText(text(), Qt::ElideMiddle, width());
|
||||
setText(elided);
|
||||
}
|
||||
}
|
||||
QLabel::paintEvent(event);
|
||||
}
|
||||
|
53
src/network-web/squeezelabel.h
Normal file
53
src/network-web/squeezelabel.h
Normal file
@ -0,0 +1,53 @@
|
||||
/**
|
||||
* Copyright (c) 2009, Benjamin C. Meyer <ben@meyerhome.net>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. Neither the name of the Benjamin Meyer nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef SQUEEZELABEL_H
|
||||
#define SQUEEZELABEL_H
|
||||
|
||||
#include <qlabel.h>
|
||||
|
||||
/*
|
||||
A label that will squeeze the set text to fit within the size of the
|
||||
widget. The text will be elided in the middle.
|
||||
*/
|
||||
class SqueezeLabel : public QLabel
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
SqueezeLabel(QWidget *parent = 0);
|
||||
|
||||
protected:
|
||||
void paintEvent(QPaintEvent *event);
|
||||
|
||||
private:
|
||||
QString m_SqueezedTextCache;
|
||||
};
|
||||
|
||||
#endif // SQUEEZELABEL_H
|
||||
|
@ -24,6 +24,7 @@
|
||||
#include "network-web/webpage.h"
|
||||
#include "network-web/webfactory.h"
|
||||
#include "gui/messagebox.h"
|
||||
#include "gui/formmain.h"
|
||||
|
||||
#include <QStyleOptionFrameV3>
|
||||
#include <QAction>
|
||||
|
Loading…
x
Reference in New Issue
Block a user