#include "videosource.h"
#include "ytchannel.h"
#include "ytsearch.h"
-#include "ytsinglevideosource.h"
#ifdef APP_SNAPSHOT
#include "snapshotsettings.h"
#endif
#include "idle.h"
#include "videodefinition.h"
+#include "searchvideosource.h"
+#include "singlevideosource.h"
+#include "videoapi.h"
+
MediaView *MediaView::instance() {
static MediaView *i = new MediaView();
return i;
QAction *leftAction = new QAction(tr("Rewind %1 seconds").arg(10));
leftAction->setShortcut(Qt::Key_Left);
leftAction->setAutoRepeat(false);
- connect(leftAction, &QAction::triggered, this, [this] {
- qint64 position = media->position();
- position -= 10000;
- if (position < 0) position = 0;
- media->seek(position);
- });
+ connect(leftAction, &QAction::triggered, this, [this] { media->relativeSeek(-10000); });
addAction(leftAction);
playingVideoActions << leftAction;
QAction *rightAction = new QAction(tr("Fast forward %1 seconds").arg(10));
rightAction->setShortcut(Qt::Key_Right);
rightAction->setAutoRepeat(false);
- connect(rightAction, &QAction::triggered, this, [this] {
- qint64 position = media->position();
- position += 10000;
- qint64 duration = media->duration();
- if (position > duration) position = duration;
- media->seek(position);
- });
+ connect(rightAction, &QAction::triggered, this, [this] { media->relativeSeek(10000); });
addAction(rightAction);
playingVideoActions << rightAction;
}
SearchParams *MediaView::getSearchParams() {
VideoSource *videoSource = playlistModel->getVideoSource();
- if (videoSource && videoSource->metaObject()->className() == QLatin1String("YTSearch")) {
- YTSearch *search = qobject_cast<YTSearch *>(videoSource);
- return search->getSearchParams();
+ if (!videoSource) return nullptr;
+ auto clazz = videoSource->metaObject()->className();
+ if (clazz == QLatin1String("SearchVideoSource")) {
+ auto search = qobject_cast<SearchVideoSource *>(videoSource);
+ if (search) return search->getSearchParams();
}
return nullptr;
}
searchParams->keywords().startsWith("https://")) {
QString videoId = YTSearch::videoIdFromUrl(searchParams->keywords());
if (!videoId.isEmpty()) {
- YTSingleVideoSource *singleVideoSource = new YTSingleVideoSource(this);
- singleVideoSource->setVideoId(videoId);
- setVideoSource(singleVideoSource);
+ auto source = new SingleVideoSource(this);
+ source->setVideoId(videoId);
+ setVideoSource(source);
+
QTime tstamp = YTSearch::videoTimestampFromUrl(searchParams->keywords());
pauseTime = QTime(0, 0).msecsTo(tstamp);
return;
}
}
}
- YTSearch *ytSearch = new YTSearch(searchParams);
- ytSearch->setAsyncDetails(true);
- connect(ytSearch, SIGNAL(gotDetails()), playlistModel, SLOT(emitDataChanged()));
- setVideoSource(ytSearch);
+
+ VideoSource *search = new SearchVideoSource(searchParams);
+ setVideoSource(search);
}
void MediaView::setVideoSource(VideoSource *videoSource, bool addToHistory, bool back) {
// qDebug() << "Adding VideoSource" << videoSource->getName() << videoSource;
- YTSearch * ytSearch = qobject_cast<YTSearch *>(videoSource);
- if (nullptr != ytSearch) {
- if (!ytSearch->getSearchParams()->channelId().isEmpty()) {
- updateSubscriptionActionForChannel(ytSearch->getSearchParams()->channelId());
- }
- }
-
if (addToHistory) {
int currentIndex = getHistoryIndex();
if (currentIndex >= 0 && currentIndex < history.size() - 1) {
VideoSource *vs = history.takeLast();
if (!vs->parent()) {
qDebug() << "Deleting VideoSource" << vs->getName() << vs;
+ vs->abort();
vs->deleteLater();
}
}
}
}
+ SearchParams *searchParams = getSearchParams();
+
sidebar->showPlaylist();
- sidebar->getRefineSearchWidget()->setSearchParams(getSearchParams());
+ sidebar->getRefineSearchWidget()->setSearchParams(searchParams);
sidebar->hideSuggestions();
sidebar->getHeader()->updateInfo();
- SearchParams *searchParams = getSearchParams();
bool isChannel = searchParams && !searchParams->channelId().isEmpty();
+ if (isChannel) {
+ updateSubscriptionActionForChannel(searchParams->channelId());
+ }
playlistView->setClickableAuthors(!isChannel);
}
if (pauseTime > 0 && (state == Media::PlayingState || state == Media::BufferingState)) {
qDebug() << "Seeking to" << pauseTime;
media->seek(pauseTime);
+ media->play();
pauseTime = 0;
}
if (state == Media::PlayingState) {
handleError(media->errorString());
}
- bool enablePlayingVideoActions = state == Media::PlayingState || state == Media::PausedState;
+ bool enablePlayingVideoActions = state != Media::StoppedState;
for (QAction *action : qAsConst(playingVideoActions))
action->setEnabled(enablePlayingVideoActions);
void MediaView::pause() {
switch (media->state()) {
case Media::PlayingState:
+ qDebug() << "Pausing";
media->pause();
pauseTimer.start();
break;
default:
- if (pauseTimer.hasExpired(60000)) {
+ if (pauseTimer.isValid() && pauseTimer.hasExpired(60000)) {
+ qDebug() << "Pause timer expired";
pauseTimer.invalidate();
- connect(playlistModel->activeVideo(), &Video::gotStreamUrl, this,
- &MediaView::resumeWithNewStreamUrl);
- playlistModel->activeVideo()->loadStreamUrl();
- } else
+ auto activeVideo = playlistModel->activeVideo();
+ if (activeVideo) {
+ connect(activeVideo, &Video::gotStreamUrl, this,
+ &MediaView::resumeWithNewStreamUrl);
+ activeVideo->loadStreamUrl();
+ } else
+ qDebug() << "No active video";
+ } else {
+ qDebug() << "Playing" << media->file();
media->play();
+ }
break;
}
}
VideoSource *videoSource = history.takeFirst();
// Don't delete videoSource in the Browse view
if (!videoSource->parent()) {
+ videoSource->abort();
videoSource->deleteLater();
}
}
demoTimer->stop();
#endif
- for (QAction *action : currentVideoActions)
+ for (QAction *action : qAsConst(currentVideoActions))
action->setEnabled(false);
QAction *a = MainWindow::instance()->getAction("download");
}
void MediaView::onAboutToFinish() {
- qint64 currentTime = media->position();
- qint64 totalTime = media->duration();
- // qDebug() << __PRETTY_FUNCTION__ << currentTime << totalTime;
- if (totalTime < 1 || currentTime + 10000 < totalTime) {
- // QTimer::singleShot(500, this, SLOT(playbackResume()));
- media->seek(currentTime);
- media->play();
- }
+
}
void MediaView::onPlaybackFinished() {
if (!playlistView->selectionModel()->hasSelection()) return;
QModelIndexList indexes = playlistView->selectionModel()->selectedIndexes();
- qStableSort(indexes.begin(), indexes.end());
+ std::stable_sort(indexes.begin(), indexes.end());
playlistModel->move(indexes, true);
// set current index after row moves to something more intuitive
if (!playlistView->selectionModel()->hasSelection()) return;
QModelIndexList indexes = playlistView->selectionModel()->selectedIndexes();
- qStableSort(indexes.begin(), indexes.end(), qGreater<QModelIndex>());
+ std::stable_sort(indexes.begin(), indexes.end(),
+ [](const QModelIndex &a, const QModelIndex &b) { return b < a; });
playlistModel->move(indexes, false);
// set current index after row moves to something more intuitive
void MediaView::relatedVideos() {
Video *video = playlistModel->activeVideo();
if (!video) return;
- YTSingleVideoSource *singleVideoSource = new YTSingleVideoSource();
- singleVideoSource->setVideo(video->clone());
- singleVideoSource->setAsyncDetails(true);
- setVideoSource(singleVideoSource);
+
+ auto source = new SingleVideoSource(this);
+ source->setVideo(video->clone());
+ setVideoSource(source);
+
MainWindow::instance()->getAction("relatedVideos")->setEnabled(false);
}