]> git.sur5r.net Git - minitube/blobdiff - src/downloaditem.cpp
Imported Upstream version 1.7
[minitube] / src / downloaditem.cpp
index 1219fb489944ca9800af9aae1075e03cc648d544..fe8b3b654a8f0869016a670bbd58c2b8028f432b 100644 (file)
@@ -3,6 +3,11 @@
 #include "video.h"
 
 #include <QDesktopServices>
+#include <QDebug>
+
+#ifdef APP_MAC
+#include "macutils.h"
+#endif
 
 namespace The {
     NetworkAccess* http();
@@ -18,7 +23,23 @@ DownloadItem::DownloadItem(Video *video, QUrl url, QString filename, QObject *pa
     , m_reply(0)
     , video(video)
     , m_status(Idle)
-{ }
+{
+    speedCheckTimer = new QTimer(this);
+    speedCheckTimer->setInterval(2000);
+    speedCheckTimer->setSingleShot(true);
+    connect(speedCheckTimer, SIGNAL(timeout()), SLOT(speedCheck()));
+}
+
+DownloadItem::~DownloadItem() {
+    if (m_reply) {
+        delete m_reply;
+        m_reply = 0;
+    }
+    if (video) {
+        delete video;
+        video = 0;
+    }
+}
 
 void DownloadItem::start() {
     m_reply = The::http()->simpleGet(m_url);
@@ -29,6 +50,9 @@ void DownloadItem::init() {
     if (!m_reply)
         return;
 
+    if (m_file.exists())
+        m_file.remove();
+
     m_status = Starting;
 
     m_startedSaving = false;
@@ -48,6 +72,7 @@ void DownloadItem::init() {
 
     // start timer for the download estimation
     m_downloadTime.start();
+    speedCheckTimer->start();
 
     if (m_reply->error() != QNetworkReply::NoError) {
         error(m_reply->error());
@@ -71,8 +96,12 @@ void DownloadItem::open() {
 
 void DownloadItem::openFolder() {
     QFileInfo info(m_file);
+#ifdef APP_MAC
+    mac::showInFinder(info.absoluteFilePath());
+#else
     QUrl url = QUrl::fromLocalFile(info.absolutePath());
     QDesktopServices::openUrl(url);
+#endif
 }
 
 void DownloadItem::tryAgain() {
@@ -88,9 +117,10 @@ void DownloadItem::tryAgain() {
 }
 
 void DownloadItem::downloadReadyRead() {
+    if (!m_reply) return;
 
     if (!m_file.isOpen()) {
-        if (!m_file.open(QIODevice::WriteOnly)) {
+        if (!m_file.open(QIODevice::ReadWrite)) {
             qDebug() << QString("Error opening output file: %1").arg(m_file.errorString());
             stop();
             emit statusChanged();
@@ -117,11 +147,11 @@ void DownloadItem::downloadReadyRead() {
 
 void DownloadItem::error(QNetworkReply::NetworkError) {
 
-#ifdef DOWNLOADMANAGER_DEBUG
-    qDebug() << "DownloadItem::" << __FUNCTION__ << m_reply->errorString() << m_url;
-#endif
+    if (m_reply) {
+        qWarning() << m_reply->errorString() << m_reply->url().toEncoded();
+        m_errorMessage = m_reply->errorString();
+    }
 
-    m_errorMessage = m_reply->errorString();
     m_reply = 0;
     m_status = Failed;
 
@@ -133,9 +163,11 @@ QString DownloadItem::errorMessage() const {
 }
 
 void DownloadItem::metaDataChanged() {
+    if (!m_reply) return;
     QVariant locationHeader = m_reply->header(QNetworkRequest::LocationHeader);
     if (locationHeader.isValid()) {
         m_url = locationHeader.toUrl();
+        // qDebug() << "Redirecting to" << m_url;
         m_reply->deleteLater();
         m_reply = The::http()->simpleGet(m_url);
         init();
@@ -147,28 +179,83 @@ void DownloadItem::metaDataChanged() {
 #endif
 }
 
+int DownloadItem::initialBufferSize() {
+    // qDebug() << video->getDefinitionCode();
+    switch (video->getDefinitionCode()) {
+    case 18:
+        return 1024*192;
+    case 22:
+        return 1024*512;
+    case 37:
+        return 1024*768;
+    }
+    return 1024*128;
+}
+
 void DownloadItem::downloadProgress(qint64 bytesReceived, qint64 bytesTotal) {
-    QTime now = QTime::currentTime();
-    if (m_lastProgressTime.msecsTo(now) < 200)
-        return;
 
-    m_lastProgressTime = now;
+    // qDebug() << bytesReceived << bytesTotal << m_downloadTime.elapsed();
+
+    if (m_lastProgressTime.elapsed() < 150) return;
+    m_lastProgressTime.start();
 
     m_bytesReceived = bytesReceived;
-    if (bytesTotal > 0) {
-        percent = bytesReceived * 100 / bytesTotal;
+
+    if (m_status != Downloading) {
+
+        int neededBytes = (int) (bytesTotal * .001);
+        // qDebug() << bytesReceived << bytesTotal << neededBytes << m_downloadTime.elapsed();
+        int bufferSize = initialBufferSize();
+        if (bytesReceived > bufferSize
+            && bytesReceived > neededBytes
+            && (m_downloadTime.elapsed() > 1000)) {
+            emit bufferProgress(100);
+            m_status = Downloading;
+            emit statusChanged();
+        } else {
+            int bufferPercent = bytesReceived * 100 / qMax(bufferSize, neededBytes);
+            emit bufferProgress(bufferPercent);
+        }
+
+    } else {
+
+        if (bytesTotal > 0) {
+            int percent = bytesReceived * 100 / bytesTotal;
+            if (percent != this->percent) {
+                this->percent = percent;
+                emit progress(percent);
+            }
+        }
+
     }
+}
 
-    // qDebug() << bytesReceived << bytesTotal;
-    if (m_status != Downloading
-        && bytesReceived > 1024 * 512
-        && bytesReceived > bytesTotal * .01) {
-        m_status = Downloading;
-        emit statusChanged();
+void DownloadItem::speedCheck() {
+    if (!m_reply) return;
+    if (m_bytesReceived < initialBufferSize() / 3) {
+        m_reply->disconnect();
+        m_reply->abort();
+        m_reply->deleteLater();
+        m_reply = 0;
+
+        // too slow! retry
+        qDebug() << "Retrying...";
+        connect(video, SIGNAL(gotStreamUrl(QUrl)), SLOT(gotStreamUrl(QUrl)));
+        video->loadStreamUrl();
+    }
+}
+
+void DownloadItem::gotStreamUrl(QUrl streamUrl) {
+
+    Video *video = static_cast<Video *>(sender());
+    if (!video) {
+        qDebug() << "Cannot get sender";
+        return;
     }
+    video->disconnect(this);
 
-    emit progress(percent);
-    // emit statusChanged();
+    m_reply = The::http()->simpleGet(video->getStreamUrl());
+    init();
 }
 
 qint64 DownloadItem::bytesTotal() const {
@@ -204,8 +291,13 @@ void DownloadItem::requestFinished() {
     m_reply = 0;
     m_finishedDownloading = true;
     if (!m_startedSaving) {
+        qDebug() << "Request finished but never started saving";
         return;
     }
+    if (m_status == Starting) {
+        m_status = Downloading;
+        emit statusChanged();
+    }
     m_file.close();
     m_status = Finished;
     emit statusChanged();