1
0
Fork 0

[Backend+UI] Made alot of appearance changes and added RoosterTeeth theme.

This commit is contained in:
NamedKitten 2018-12-03 08:17:57 +00:00
parent 56564c0247
commit f5581ab895
37 changed files with 390 additions and 54 deletions

View file

@ -111,6 +111,7 @@ DirectMpvPlayerBackend::DirectMpvPlayerBackend(QQuickItem* parent)
mpv_observe_property(mpv, 0, "demuxer-cache-duration", MPV_FORMAT_DOUBLE); mpv_observe_property(mpv, 0, "demuxer-cache-duration", MPV_FORMAT_DOUBLE);
mpv_observe_property(mpv, 0, "pause", MPV_FORMAT_NODE); mpv_observe_property(mpv, 0, "pause", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "playlist", MPV_FORMAT_NODE); mpv_observe_property(mpv, 0, "playlist", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "speed", MPV_FORMAT_DOUBLE);
mpv_set_wakeup_callback(mpv, wakeup, this); mpv_set_wakeup_callback(mpv, wakeup, this);
if (mpv_initialize(mpv) < 0) if (mpv_initialize(mpv) < 0)
@ -494,8 +495,11 @@ DirectMpvPlayerBackend::updateDurationString(int numTime)
durationString += " / "; durationString += " / ";
durationString += totalDurationString; durationString += totalDurationString;
if (lastSpeed != 1) { if (lastSpeed != 1) {
if (settings.value("Appearance/themeName", "").toString() !=
"RoosterTeeth") {
durationString += " (" + speed.toString() + "x)"; durationString += " (" + speed.toString() + "x)";
} }
}
emit durationStringChanged(durationString); emit durationStringChanged(durationString);
} }
@ -598,6 +602,9 @@ DirectMpvPlayerBackend::handle_mpv_event(mpv_event* event)
} else if (strcmp(prop->name, "chapter-list") == 0) { } else if (strcmp(prop->name, "chapter-list") == 0) {
mpv_node* nod = (mpv_node*)prop->data; mpv_node* nod = (mpv_node*)prop->data;
emit chaptersChanged(mpv::qt::node_to_variant(nod).toList()); emit chaptersChanged(mpv::qt::node_to_variant(nod).toList());
} else if (strcmp(prop->name, "speed") == 0) {
double speed = *(double*)prop->data;
emit speedChanged(speed);
} }
#ifdef DISCORD #ifdef DISCORD
updateDiscord(); updateDiscord();

View file

@ -8,6 +8,7 @@
#include <QObject> #include <QObject>
#include <QOpenGLContext> #include <QOpenGLContext>
#include <QQuickFramebufferObject> #include <QQuickFramebufferObject>
#include <QSettings>
#include <QWidget> #include <QWidget>
#include "backendinterface.hpp" #include "backendinterface.hpp"
@ -46,6 +47,7 @@ class DirectMpvPlayerBackend
double lastSpeed = 0; double lastSpeed = 0;
QString totalDurationString; QString totalDurationString;
QString lastPositionString; QString lastPositionString;
QSettings settings;
public: public:
static void on_update(void* ctx); static void on_update(void* ctx);
@ -91,6 +93,7 @@ signals:
void audioDevicesChanged(const QVariantMap& devices); void audioDevicesChanged(const QVariantMap& devices);
void playlistChanged(const QVariantList& devices); void playlistChanged(const QVariantList& devices);
void chaptersChanged(const QVariantList& devices); void chaptersChanged(const QVariantList& devices);
void speedChanged(const double& speed);
private slots: private slots:
void doUpdate(); void doUpdate();

View file

@ -1,10 +1,11 @@
#include "MpvPlayerBackend.h"
#include <clocale> #include <clocale>
#include <stdbool.h> #include <stdbool.h>
#include <stdexcept> #include <stdexcept>
#include "MpvPlayerBackend.h"
#include "utils.hpp" #include "utils.hpp"
#include <QApplication> #include <QApplication>
#include <QElapsedTimer>
#include <QOpenGLContext> #include <QOpenGLContext>
#include <QOpenGLFramebufferObject> #include <QOpenGLFramebufferObject>
#include <QQuickWindow> #include <QQuickWindow>
@ -17,9 +18,9 @@
#ifdef __linux__ #ifdef __linux__
#include <QX11Info> #include <QX11Info>
#include <QtX11Extras/QX11Info>
#include <X11/Xlib.h> #include <X11/Xlib.h>
#include <X11/Xutil.h> #include <X11/Xutil.h>
#include <QtX11Extras/QX11Info>
#include <qpa/qplatformnativeinterface.h> #include <qpa/qplatformnativeinterface.h>
#endif #endif
@ -34,7 +35,8 @@ wakeup(void* ctx)
void void
on_mpv_redraw(void* ctx) on_mpv_redraw(void* ctx)
{ {
QMetaObject::invokeMethod(reinterpret_cast<MpvPlayerBackend*>(ctx), "update"); QMetaObject::invokeMethod(
reinterpret_cast<MpvPlayerBackend*>(ctx), "update", Qt::QueuedConnection);
} }
static void* static void*
@ -84,7 +86,8 @@ public:
params[2].data = QX11Info::display(); params[2].data = QX11Info::display();
qDebug() << "On Xorg."; qDebug() << "On Xorg.";
} else if (QGuiApplication::platformName().contains("wayland")) { } else if (QGuiApplication::platformName().contains("wayland")) {
QPlatformNativeInterface *native = QGuiApplication::platformNativeInterface(); QPlatformNativeInterface* native =
QGuiApplication::platformNativeInterface();
params[2].type = MPV_RENDER_PARAM_WL_DISPLAY; params[2].type = MPV_RENDER_PARAM_WL_DISPLAY;
params[2].data = native->nativeResourceForWindow("display", nullptr); params[2].data = native->nativeResourceForWindow("display", nullptr);
qDebug() << "On wayland."; qDebug() << "On wayland.";
@ -118,7 +121,6 @@ public:
{ MPV_RENDER_PARAM_INVALID, nullptr } { MPV_RENDER_PARAM_INVALID, nullptr }
}; };
// See render_gl.h on what OpenGL environment mpv expects, and // See render_gl.h on what OpenGL environment mpv expects, and
// other API details. // other API details.
mpv_render_context_render(obj->mpv_gl, params); mpv_render_context_render(obj->mpv_gl, params);
@ -157,7 +159,7 @@ MpvPlayerBackend::MpvPlayerBackend(QQuickItem* parent)
mpv_observe_property(mpv, 0, "playback-abort", MPV_FORMAT_NONE); mpv_observe_property(mpv, 0, "playback-abort", MPV_FORMAT_NONE);
mpv_observe_property(mpv, 0, "chapter-list", MPV_FORMAT_NODE); mpv_observe_property(mpv, 0, "chapter-list", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "track-list", MPV_FORMAT_NODE); mpv_observe_property(mpv, 0, "track-list", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "audio-device-list", MPV_FORMAT_NONE); mpv_observe_property(mpv, 0, "audio-device-list", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "playlist-pos", MPV_FORMAT_DOUBLE); mpv_observe_property(mpv, 0, "playlist-pos", MPV_FORMAT_DOUBLE);
mpv_observe_property(mpv, 0, "volume", MPV_FORMAT_NONE); mpv_observe_property(mpv, 0, "volume", MPV_FORMAT_NONE);
mpv_observe_property(mpv, 0, "mute", MPV_FORMAT_NONE); mpv_observe_property(mpv, 0, "mute", MPV_FORMAT_NONE);
@ -168,6 +170,7 @@ MpvPlayerBackend::MpvPlayerBackend(QQuickItem* parent)
mpv_observe_property(mpv, 0, "demuxer-cache-duration", MPV_FORMAT_DOUBLE); mpv_observe_property(mpv, 0, "demuxer-cache-duration", MPV_FORMAT_DOUBLE);
mpv_observe_property(mpv, 0, "pause", MPV_FORMAT_NODE); mpv_observe_property(mpv, 0, "pause", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "playlist", MPV_FORMAT_NODE); mpv_observe_property(mpv, 0, "playlist", MPV_FORMAT_NODE);
mpv_observe_property(mpv, 0, "speed", MPV_FORMAT_DOUBLE);
mpv_set_wakeup_callback(mpv, wakeup, this); mpv_set_wakeup_callback(mpv, wakeup, this);
if (mpv_initialize(mpv) < 0) if (mpv_initialize(mpv) < 0)
@ -180,10 +183,14 @@ MpvPlayerBackend::MpvPlayerBackend(QQuickItem* parent)
Qt::QueuedConnection); Qt::QueuedConnection);
connect(this, connect(this,
&MpvPlayerBackend::positionChanged, &MpvPlayerBackend::positionChanged,
&MpvPlayerBackend::updateDurationString); this,
&MpvPlayerBackend::updateDurationString,
Qt::QueuedConnection);
connect(this, connect(this,
&MpvPlayerBackend::durationChanged, &MpvPlayerBackend::durationChanged,
&MpvPlayerBackend::updateDurationString); this,
&MpvPlayerBackend::updateDurationString,
Qt::QueuedConnection);
} }
MpvPlayerBackend::~MpvPlayerBackend() MpvPlayerBackend::~MpvPlayerBackend()
@ -218,13 +225,16 @@ MpvPlayerBackend::getProperty(const QString& name) const
void void
MpvPlayerBackend::command(const QVariant& params) MpvPlayerBackend::command(const QVariant& params)
{ {
mpv::qt::command_variant(mpv, params); mpv::qt::node_builder node(params);
mpv_command_node(mpv, node.node(), nullptr);
} }
void void
MpvPlayerBackend::setProperty(const QString& name, const QVariant& value) MpvPlayerBackend::setProperty(const QString& name, const QVariant& value)
{ {
mpv::qt::set_property_variant(mpv, name, value); mpv::qt::node_builder node(value);
qDebug() << "Setting property" << name << "to" << value;
mpv_set_property(mpv, name.toUtf8().data(), MPV_FORMAT_NODE, node.node());
} }
void void
@ -478,8 +488,11 @@ MpvPlayerBackend::updateDurationString(int numTime)
durationString += " / "; durationString += " / ";
durationString += totalDurationString; durationString += totalDurationString;
if (lastSpeed != 1) { if (lastSpeed != 1) {
if (settings.value("Appearance/themeName", "").toString() !=
"RoosterTeeth") {
durationString += " (" + speed.toString() + "x)"; durationString += " (" + speed.toString() + "x)";
} }
}
emit durationStringChanged(durationString); emit durationStringChanged(durationString);
} }
@ -490,24 +503,15 @@ MpvPlayerBackend::updateAppImage()
} }
QVariantMap QVariantMap
MpvPlayerBackend::getAudioDevices() const MpvPlayerBackend::getAudioDevices(const QVariant& drivers) const
{ {
QVariant drivers = getProperty("audio-device-list");
QVariant currentDevice = getProperty("audio-device");
QVariantMap newDrivers; QVariantMap newDrivers;
QSequentialIterable iterable = drivers.value<QSequentialIterable>(); QSequentialIterable iterable = drivers.value<QSequentialIterable>();
foreach (const QVariant& v, iterable) { foreach (const QVariant& v, iterable) {
QVariantMap item = v.toMap(); QVariantMap item = v.toMap();
item["selected"] = currentDevice == item["name"];
newDrivers[item["description"].toString()] = item; newDrivers[item["description"].toString()] = item;
} }
QMap<QString, QVariant> pulseItem;
pulseItem["name"] = "pulse";
pulseItem["description"] = "Default (pulseaudio)";
pulseItem["selected"] = currentDevice == "pulse";
newDrivers[pulseItem["description"].toString()] = pulseItem;
return newDrivers; return newDrivers;
} }
@ -566,22 +570,27 @@ MpvPlayerBackend::handle_mpv_event(mpv_event* event)
mpv_node* nod = (mpv_node*)prop->data; mpv_node* nod = (mpv_node*)prop->data;
if (mpv::qt::node_to_variant(nod).toBool()) { if (mpv::qt::node_to_variant(nod).toBool()) {
emit playStatusChanged(Enums::PlayStatus::Paused); emit playStatusChanged(Enums::PlayStatus::Paused);
Utils::SetScreensaver(window()->winId(), true); // Utils::SetScreensaver(window()->winId(), true);
} else { } else {
emit playStatusChanged(Enums::PlayStatus::Playing); emit playStatusChanged(Enums::PlayStatus::Playing);
Utils::SetScreensaver(window()->winId(), false); // Utils::SetScreensaver(window()->winId(), false);
} }
} else if (strcmp(prop->name, "track-list") == 0) { } else if (strcmp(prop->name, "track-list") == 0) {
mpv_node* nod = (mpv_node*)prop->data; mpv_node* nod = (mpv_node*)prop->data;
emit tracksChanged(mpv::qt::node_to_variant(nod).toList()); emit tracksChanged(mpv::qt::node_to_variant(nod).toList());
} else if (strcmp(prop->name, "audio-device-list") == 0) { } else if (strcmp(prop->name, "audio-device-list") == 0) {
emit audioDevicesChanged(getAudioDevices()); mpv_node* nod = (mpv_node*)prop->data;
emit audioDevicesChanged(
getAudioDevices(mpv::qt::node_to_variant(nod)));
} else if (strcmp(prop->name, "playlist") == 0) { } else if (strcmp(prop->name, "playlist") == 0) {
mpv_node* nod = (mpv_node*)prop->data; mpv_node* nod = (mpv_node*)prop->data;
emit playlistChanged(mpv::qt::node_to_variant(nod).toList()); emit playlistChanged(mpv::qt::node_to_variant(nod).toList());
} else if (strcmp(prop->name, "chapter-list") == 0) { } else if (strcmp(prop->name, "chapter-list") == 0) {
mpv_node* nod = (mpv_node*)prop->data; mpv_node* nod = (mpv_node*)prop->data;
emit chaptersChanged(mpv::qt::node_to_variant(nod).toList()); emit chaptersChanged(mpv::qt::node_to_variant(nod).toList());
} else if (strcmp(prop->name, "speed") == 0) {
double speed = *(double*)prop->data;
emit speedChanged(speed);
} }
#ifdef DISCORD #ifdef DISCORD
updateDiscord(); updateDiscord();

View file

@ -9,6 +9,7 @@
#include <QObject> #include <QObject>
#include <QOpenGLContext> #include <QOpenGLContext>
#include <QQuickFramebufferObject> #include <QQuickFramebufferObject>
#include <QSettings>
#include "backendinterface.hpp" #include "backendinterface.hpp"
#include "enums.hpp" #include "enums.hpp"
@ -26,6 +27,7 @@ class MpvPlayerBackend
mpv_handle* mpv; mpv_handle* mpv;
mpv_render_context* mpv_gl; mpv_render_context* mpv_gl;
QSettings settings;
bool onTop = false; bool onTop = false;
int lastTime = 0; int lastTime = 0;
double lastSpeed = 0; double lastSpeed = 0;
@ -53,7 +55,7 @@ public slots:
void setOption(const QString& name, const QVariant& value); void setOption(const QString& name, const QVariant& value);
QVariant getProperty(const QString& name) const; QVariant getProperty(const QString& name) const;
// Just used for adding missing audio devices to list. // Just used for adding missing audio devices to list.
QVariantMap getAudioDevices() const; QVariantMap getAudioDevices(const QVariant& drivers) const;
bool event(QEvent* event); bool event(QEvent* event);
signals: signals:
@ -76,6 +78,7 @@ signals:
void audioDevicesChanged(const QVariantMap& devices); void audioDevicesChanged(const QVariantMap& devices);
void playlistChanged(const QVariantList& devices); void playlistChanged(const QVariantList& devices);
void chaptersChanged(const QVariantList& devices); void chaptersChanged(const QVariantList& devices);
void speedChanged(const double& speed);
private slots: private slots:
void doUpdate(); void doUpdate();

View file

@ -42,6 +42,7 @@ signals:
virtual void audioDevicesChanged(const QVariantMap& devices) = 0; virtual void audioDevicesChanged(const QVariantMap& devices) = 0;
virtual void playlistChanged(const QVariantList& devices) = 0; virtual void playlistChanged(const QVariantList& devices) = 0;
virtual void chaptersChanged(const QVariantList& devices) = 0; virtual void chaptersChanged(const QVariantList& devices) = 0;
virtual void speedChanged(const double& speed) = 0;
}; };
Q_DECLARE_INTERFACE(BackendInterface, "NamedKitten.BackendInterface"); Q_DECLARE_INTERFACE(BackendInterface, "NamedKitten.BackendInterface");

View file

@ -30,6 +30,9 @@ Item {
} }
var component = Qt.createComponent(themeName + "ButtonLayout.qml") var component = Qt.createComponent(themeName + "ButtonLayout.qml")
if (component.status == Component.Error) {
console.log("Error loading component:", component.errorString())
}
component.createObject(controlsBar, { component.createObject(controlsBar, {
}) })
@ -100,8 +103,7 @@ Item {
Rectangle { Rectangle {
id: controlsBackground id: controlsBackground
height: controlsBar.visible ? controlsBar.height + progressBar.topPadding height: controlsBar.visible ? controlsBar.height + (appearance.themeName == "RoosterTeeth" ? 0 : progressBar.topPadding + (fun.nyanCat ? 0 : 1)) : 0
+ (fun.nyanCat ? 0 : 1) : 0
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right
@ -124,6 +126,7 @@ Item {
visible: controlsOverlay.controlsShowing visible: controlsOverlay.controlsShowing
VideoProgress { VideoProgress {
id: progressBar id: progressBar
visible: appearance.themeName == "RoosterTeeth" ? false : true
anchors.bottom: parent.top anchors.bottom: parent.top
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right

View file

@ -6,7 +6,7 @@ import player 1.0
Action { Action {
id: audioDeviceItem id: audioDeviceItem
property string deviceID: "none" property string deviceID: "none"
checkable: true checkable: false
checked: false checked: false
onTriggered: { onTriggered: {

View file

@ -47,7 +47,8 @@ MenuBar {
var trackType = track["type"] var trackType = track["type"]
var trackLang = LanguageCodes.localeCodeToEnglish( var trackLang = LanguageCodes.localeCodeToEnglish(
String(track["lang"])) String(track["lang"]))
var trackTitle = track["title"] trackLang = trackLang == undefined ? "" : trackLang
var trackTitle = track["title"] == undefined ? "" : track["title"] + " "
var component = Qt.createComponent("TrackItem.qml") var component = Qt.createComponent("TrackItem.qml")
if (trackType == "sub") { if (trackType == "sub") {
var action = component.createObject(subMenu, { var action = component.createObject(subMenu, {
@ -61,7 +62,7 @@ MenuBar {
subMenu.addAction(action) subMenu.addAction(action)
} else if (trackType == "audio") { } else if (trackType == "audio") {
var action = component.createObject(audioMenu, { var action = component.createObject(audioMenu, {
text: (trackTitle == undefined ? "" : trackTitle + " ") + (trackLang == "undefined" ? "" : trackLang), text: trackTitle + trackLang,
trackID: String( trackID: String(
trackID), trackID),
trackType: "aid", trackType: "aid",
@ -71,7 +72,7 @@ MenuBar {
audioMenu.addAction(action) audioMenu.addAction(action)
} else if (trackType == "video") { } else if (trackType == "video") {
var action = component.createObject(videoMenu, { var action = component.createObject(videoMenu, {
text: "Video " + trackID, text: "Video " + trackID + trackTitle,
trackID: String( trackID: String(
trackID), trackID),
trackType: "vid", trackType: "vid",
@ -358,15 +359,11 @@ MenuBar {
} }
for (var thing in audioDevices) { for (var thing in audioDevices) {
var audioDevice = audioDevices[thing] var audioDevice = audioDevices[thing]
var name = audioDevice["name"]
var description = audioDevice["description"]
var selected = audioDevice["selected"]
var component = Qt.createComponent("AudioDeviceItem.qml") var component = Qt.createComponent("AudioDeviceItem.qml")
var action = component.createObject(audioDeviceMenu, { var action = component.createObject(audioDeviceMenu, {
text: description, text: audioDevices[thing]["description"],
deviceID: String( deviceID: String(
name), audioDevices[thing]["name"])
checked: audioDevice["selected"]
}) })
action.ActionGroup.group = audioDeviceMenuGroup action.ActionGroup.group = audioDeviceMenuGroup
audioDeviceMenu.addAction(action) audioDeviceMenu.addAction(action)

View file

@ -14,6 +14,7 @@ Item {
PlayPauseButton { PlayPauseButton {
id: playPauseButton id: playPauseButton
anchors.left: owo.right
anchors.top: parent.top anchors.top: parent.top
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
icon.height: parent.height / 2 icon.height: parent.height / 2

View file

@ -0,0 +1,111 @@
import QtQuick 2.11
import QtQuick.Controls 2.4
import QtQuick.Dialogs 1.3
import QtQuick.Layouts 1.11
import QtQuick.Window 2.11
import Qt.labs.settings 1.0
import Qt.labs.platform 1.0 as LabsPlatform
import player 1.0
Item {
objectName: "buttonLayout"
id: layout
anchors.fill: controlsBar
PlayPauseButton {
id: playPauseButton
anchors.top: parent.top
anchors.bottom: parent.bottom
icon.height: parent.height / 2
icon.width: parent.height / 2
}
MouseArea {
id: mouseAreaVolumeArea
anchors.bottom: volumeButton.bottom
anchors.left: volumeSliderArea.left
anchors.right: volumeSliderArea.right
anchors.top: volumeSliderArea.top
height: layout.height + volumeButton.height
+ (volumeSliderArea.visible ? volumeSliderArea.height : 0)
hoverEnabled: true
propagateComposedEvents: true
acceptedButtons: Qt.NoButton
onEntered: {
volumeSliderArea.visible = true
mouseAreaPlayerTimer.stop()
}
onExited: {
volumeSliderArea.visible = false
mouseAreaPlayerTimer.restart()
}
}
VolumeButton {
id: volumeButton
anchors.left: playPauseButton.right
anchors.top: parent.top
anchors.bottom: parent.bottom
icon.height: parent.height / 2
icon.width: parent.height / 2
icon.color: hovered
|| mouseAreaVolumeArea.containsMouse ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName,
"buttonColor")
}
VerticalVolume {
id: volumeSliderArea
anchors.bottom: volumeButton.top
anchors.left: volumeButton.left
anchors.right: volumeButton.right
width: volumeButton.width
visible: mouseAreaVolumeArea.containsMouse || volumeButton.hovered
}
TimeLabel {
id: timeLabel
anchors.left: volumeButton.right
anchors.top: parent.top
anchors.bottom: parent.bottom
}
VideoProgress {
id: videoProgressRoosterTeeth
anchors.left: timeLabel.right
anchors.right: speedText.left
anchors.top: parent.top
anchors.bottom: parent.bottom
height: parent.height
to: progressBar.to
value: progressBar.value
}
SpeedText {
id: speedText
anchors.top: parent.top
anchors.bottom: parent.bottom
anchors.right: fullscreenButton.left
}
FullscreenButton {
id: fullscreenButton
anchors.right: settingsButton.left
anchors.top: parent.top
anchors.bottom: parent.bottom
icon.height: parent.height / 2
icon.width: parent.height / 2
}
SettingsButton {
id: settingsButton
anchors.right: parent.right
anchors.top: parent.top
anchors.bottom: parent.bottom
icon.height: parent.height / 2
icon.width: parent.height / 2
}
}

View file

@ -10,7 +10,12 @@ import player 1.0
Button { Button {
id: backwardButton id: backwardButton
icon.source: "icons/" + appearance.themeName + "/backward.svg" icon.source: "icons/" + appearance.themeName + "/backward.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor")
hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
onClicked: { onClicked: {
player.playerCommand(Enums.Commands.Seek, "-10") player.playerCommand(Enums.Commands.Seek, "-10")

View file

@ -10,7 +10,11 @@ import player 1.0
Button { Button {
id: forwardButton id: forwardButton
icon.source: "icons/" + appearance.themeName + "/forward.svg" icon.source: "icons/" + appearance.themeName + "/forward.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
onClicked: { onClicked: {
player.playerCommand(Enums.Commands.Seek, "10") player.playerCommand(Enums.Commands.Seek, "10")

View file

@ -10,7 +10,11 @@ import player 1.0
Button { Button {
id: fullscreenButton id: fullscreenButton
icon.source: "icons/" + appearance.themeName + "/fullscreen.svg" icon.source: "icons/" + appearance.themeName + "/fullscreen.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
Layout.alignment: Qt.AlignVCenter | Qt.AlignRight Layout.alignment: Qt.AlignVCenter | Qt.AlignRight
display: AbstractButton.IconOnly display: AbstractButton.IconOnly

View file

@ -10,7 +10,11 @@ import player 1.0
Button { Button {
id: playPauseButton id: playPauseButton
icon.source: "icons/" + appearance.themeName + "/pause.svg" icon.source: "icons/" + appearance.themeName + "/pause.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
onClicked: { onClicked: {
player.playerCommand(Enums.Commands.TogglePlayPause) player.playerCommand(Enums.Commands.TogglePlayPause)

View file

@ -11,7 +11,11 @@ Button {
id: playlistNextButton id: playlistNextButton
//icon.name: "next" //icon.name: "next"
icon.source: "icons/" + appearance.themeName + "/next.svg" icon.source: "icons/" + appearance.themeName + "/next.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
onClicked: { onClicked: {
player.playerCommand(Enums.Commands.NextPlaylistItem) player.playerCommand(Enums.Commands.NextPlaylistItem)

View file

@ -11,7 +11,11 @@ Button {
id: playlistPrevButton id: playlistPrevButton
objectName: "playlistPrevButton" objectName: "playlistPrevButton"
icon.source: "icons/" + appearance.themeName + "/prev.svg" icon.source: "icons/" + appearance.themeName + "/prev.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
visible: appearance.themeName == "Youtube" ? false : true visible: appearance.themeName == "Youtube" ? false : true
onClicked: { onClicked: {

View file

@ -11,11 +11,17 @@ Button {
id: settingsButton id: settingsButton
//icon.name: "settings" //icon.name: "settings"
icon.source: "icons/" + appearance.themeName + "/settings.svg" icon.source: "icons/" + appearance.themeName + "/settings.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
Layout.alignment: Qt.AlignVCenter | Qt.AlignRight Layout.alignment: Qt.AlignVCenter | Qt.AlignRight
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
onClicked: { onClicked: {
appearance.themeName = appearance.themeName == "YouTube" ? "Niconico" : "YouTube" var aptn = appearance.themeName
appearance.themeName = aptn == "YouTube" ? "RoosterTeeth" : aptn
== "RoosterTeeth" ? "Niconico" : "YouTube"
controlsBarItem.setControlsTheme(appearance.themeName) controlsBarItem.setControlsTheme(appearance.themeName)
console.log("Settings Menu Not Yet Implemented.") console.log("Settings Menu Not Yet Implemented.")
} }

View file

@ -0,0 +1,38 @@
import QtQuick 2.11
import QtQuick.Controls 2.4
import QtQuick.Dialogs 1.3
import QtQuick.Layouts 1.11
import QtQuick.Window 2.11
import Qt.labs.settings 1.0
import Qt.labs.platform 1.0 as LabsPlatform
import player 1.0
Text {
id: speedText
leftPadding: 0
rightPadding: 0
text: "1x"
font.family: appearance.fontName
font.pixelSize: layout.height / 2.5
color: speedStatusMouseArea.containsMouse ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName,
"buttonColor")
verticalAlignment: Text.AlignVCenter
Connections {
target: player
enabled: true
onSpeedChanged: function (speed) {
speedText.text = String(speed) + "x"
}
}
MouseArea {
id: speedStatusMouseArea
anchors.fill: parent
height: parent.height
hoverEnabled: true
propagateComposedEvents: false
acceptedButtons: Qt.NoButton
}
}

View file

@ -0,0 +1,78 @@
import QtQuick 2.11
import QtQuick.Controls 2.4
import QtQuick.Dialogs 1.3
import QtQuick.Layouts 1.11
import QtQuick.Window 2.11
import Qt.labs.settings 1.0
import Qt.labs.platform 1.0 as LabsPlatform
import player 1.0
Rectangle {
id: volumeSliderArea
height: 70
color: getAppearanceValueForTheme(appearance.themeName, "mainBackground")
visible: false
Slider {
id: volumeSlider
anchors.fill: parent
to: 100
value: 100
orientation: Qt.Vertical
implicitWidth: Math.max(background ? background.implicitWidth : 0,
(handle ? handle.implicitWidth : 0)
+ leftPadding + rightPadding)
implicitHeight: Math.max(
background.implicitHeight,
handle.implicitHeight + topPadding + bottomPadding)
padding: 6
Connections {
target: player
enabled: true
onVolumeChanged: function (volume) {
volumeSlider.value = volume
}
}
onMoved: {
player.playerCommand(Enums.Commands.SetVolume,
Math.round(volumeSlider.value).toString())
}
handle: Rectangle {
x: volumeSlider.leftPadding + ((volumeSlider.availableWidth - width) / 2)
y: volumeSlider.topPadding + (volumeSlider.visualPosition
* (volumeSlider.availableHeight - height))
implicitWidth: 10
implicitHeight: 10
radius: width / 2
color: "white"
border.width: 0
}
background: Rectangle {
x: volumeSlider.leftPadding + ((volumeSlider.availableWidth - width) / 2)
y: volumeSlider.topPadding
implicitWidth: 4
implicitHeight: 70
width: implicitWidth
height: volumeSlider.availableHeight
radius: 3
color: getAppearanceValueForTheme(appearance.themeName,
"progressBackgroundColor")
Rectangle {
y: volumeSlider.visualPosition * parent.height
width: 4
height: volumeSlider.position * parent.height
radius: 3
color: getAppearanceValueForTheme(appearance.themeName,
"volumeSliderBackground")
}
}
}
}

View file

@ -164,8 +164,10 @@ Slider {
implicitHeight: radius implicitHeight: radius
implicitWidth: radius implicitWidth: radius
radius: 12 + (progressBackground.height / 2) radius: 12 + (progressBackground.height / 2)
color: fun.nyanCat ? "transparent" : getAppearanceValueForTheme( color: appearance.themeName
appearance.themeName, "progressSliderColor") == "RoosterTeeth" ? "white" : fun.nyanCat ? "transparent" : getAppearanceValueForTheme(
appearance.themeName,
"progressSliderColor")
visible: getHandleVisibility(appearance.themeName, visible: getHandleVisibility(appearance.themeName,
mouseAreaProgressBar.containsMouse) mouseAreaProgressBar.containsMouse)
AnimatedImage { AnimatedImage {

View file

@ -11,7 +11,11 @@ Button {
id: volumeButton id: volumeButton
objectName: "volumeButton" objectName: "volumeButton"
icon.source: "icons/" + appearance.themeName + "/volume-up.svg" icon.source: "icons/" + appearance.themeName + "/volume-up.svg"
icon.color: getAppearanceValueForTheme(appearance.themeName, "buttonColor") hoverEnabled: true
icon.color: hovered ? getAppearanceValueForTheme(
appearance.themeName,
"buttonHoverColor") : getAppearanceValueForTheme(
appearance.themeName, "buttonColor")
display: AbstractButton.IconOnly display: AbstractButton.IconOnly
onClicked: { onClicked: {
player.playerCommand(Enums.Commands.ToggleMute) player.playerCommand(Enums.Commands.ToggleMute)

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M24 10V2L14 12l10 10v-8c6.6 0 12 5.4 12 12s-5.4 12-12 12-12-5.4-12-12H8c0 8.8 7.2 16 16 16s16-7.2 16-16-7.2-16-16-16zm-2.2 22h-1.7v-6.5l-2 .6v-1.4l3.5-1.3h.2V32zm8.5-3.5c0 .6-.1 1.2-.2 1.6s-.3.8-.6 1.1-.6.5-.9.7-.7.2-1.2.2-.8-.1-1.2-.2-.7-.4-.9-.7-.5-.7-.6-1.1-.2-1-.2-1.6V27c0-.6.1-1.2.2-1.6s.3-.8.6-1.1.6-.5.9-.7.7-.2 1.2-.2.8.1 1.2.2.7.4.9.7.5.7.6 1.1.2 1 .2 1.6v1.5zm-1.6-1.7c0-.4 0-.7-.1-1s-.1-.5-.2-.6-.2-.3-.4-.3-.3-.1-.5-.1-.4 0-.5.1-.3.2-.4.3-.2.4-.2.6-.1.6-.1 1v1.9c0 .4 0 .7.1 1s.1.5.2.6.2.3.4.3.3.1.5.1.4 0 .5-.1.3-.2.4-.3.2-.4.2-.6.1-.6.1-1v-1.9z"/></svg>

After

Width:  |  Height:  |  Size: 640 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M8 26c0 8.8 7.2 16 16 16s16-7.2 16-16h-4c0 6.6-5.4 12-12 12s-12-5.4-12-12 5.4-12 12-12v8l10-10L24 2v8c-8.8 0-16 7.2-16 16zm13.7 6H20v-6.5l-2 .6v-1.4l3.5-1.3h.2V32zm8.5-3.5c0 .6-.1 1.2-.2 1.6s-.3.8-.6 1.1-.6.5-.9.7-.7.2-1.2.2-.8-.1-1.2-.2-.7-.4-.9-.7-.5-.7-.6-1.1-.2-1-.2-1.6V27c0-.6.1-1.2.2-1.6s.3-.8.6-1.1.6-.5.9-.7.7-.2 1.2-.2.8.1 1.2.2.7.4.9.7.5.7.6 1.1.2 1 .2 1.6v1.5zm-1.7-1.7c0-.4 0-.7-.1-1s-.1-.5-.2-.6-.2-.3-.4-.3-.3-.1-.5-.1-.4 0-.5.1-.3.2-.4.3-.2.4-.2.6-.1.6-.1 1v1.9c0 .4 0 .7.1 1s.1.5.2.6.2.3.4.3.3.1.5.1.4 0 .5-.1.3-.2.4-.3.2-.4.2-.6.1-.6.1-1v-1.9z"/></svg>

After

Width:  |  Height:  |  Size: 642 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M14 28h-4v10h10v-4h-6v-6zm-4-8h4v-6h6v-4H10v10zm24 14h-6v4h10V28h-4v6zm-6-24v4h6v6h4V10H28z"/></svg>

After

Width:  |  Height:  |  Size: 172 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M12 36l17-12-17-12v24zm20-24v24h4V12h-4z"/></svg>

After

Width:  |  Height:  |  Size: 121 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M12 38h8V10h-8v28zm16-28v28h8V10h-8z"/></svg>

After

Width:  |  Height:  |  Size: 117 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M16 10v28l22-14z"/></svg>

After

Width:  |  Height:  |  Size: 97 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48" viewBox="-12 -12 48 48"><path d="M26 6H-8v4h34V6zm0-8H-8v4h34v-4zM-8 18h26v-4H-8v4zm30-4v12l10-6-10-6z"/></svg>

After

Width:  |  Height:  |  Size: 174 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M12 12h4v24h-4zm7 12l17 12V12z"/></svg>

After

Width:  |  Height:  |  Size: 111 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M38.86 25.95c.08-.64.14-1.29.14-1.95s-.06-1.31-.14-1.95l4.23-3.31c.38-.3.49-.84.24-1.28l-4-6.93c-.25-.43-.77-.61-1.22-.43l-4.98 2.01c-1.03-.79-2.16-1.46-3.38-1.97L29 4.84c-.09-.47-.5-.84-1-.84h-8c-.5 0-.91.37-.99.84l-.75 5.3a14.8 14.8 0 0 0-3.38 1.97L9.9 10.1a1 1 0 0 0-1.22.43l-4 6.93c-.25.43-.14.97.24 1.28l4.22 3.31C9.06 22.69 9 23.34 9 24s.06 1.31.14 1.95l-4.22 3.31c-.38.3-.49.84-.24 1.28l4 6.93c.25.43.77.61 1.22.43l4.98-2.01c1.03.79 2.16 1.46 3.38 1.97l.75 5.3c.08.47.49.84.99.84h8c.5 0 .91-.37.99-.84l.75-5.3a14.8 14.8 0 0 0 3.38-1.97l4.98 2.01a1 1 0 0 0 1.22-.43l4-6.93c.25-.43.14-.97-.24-1.28l-4.22-3.31zM24 31c-3.87 0-7-3.13-7-7s3.13-7 7-7 7 3.13 7 7-3.13 7-7 7z"/></svg>

After

Width:  |  Height:  |  Size: 754 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M40 8H8c-2.21 0-4 1.79-4 4v24c0 2.21 1.79 4 4 4h32c2.21 0 4-1.79 4-4V12c0-2.21-1.79-4-4-4zM8 24h8v4H8v-4zm20 12H8v-4h20v4zm12 0h-8v-4h8v4zm0-8H20v-4h20v4z"/></svg>

After

Width:  |  Height:  |  Size: 235 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M37 24c0-3.53-2.04-6.58-5-8.05v16.11c2.96-1.48 5-4.53 5-8.06zm-27-6v12h8l10 10V8L18 18h-8z"/></svg>

After

Width:  |  Height:  |  Size: 171 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M33 24c0-3.53-2.04-6.58-5-8.05v4.42l4.91 4.91c.06-.42.09-.85.09-1.28zm5 0c0 1.88-.41 3.65-1.08 5.28l3.03 3.03C41.25 29.82 42 27 42 24c0-8.56-5.99-15.72-14-17.54v4.13c5.78 1.72 10 7.07 10 13.41zM8.55 6L6 8.55 15.45 18H6v12h8l10 10V26.55l8.51 8.51c-1.34 1.03-2.85 1.86-4.51 2.36v4.13a17.94 17.94 0 0 0 7.37-3.62L39.45 42 42 39.45l-18-18L8.55 6zM24 8l-4.18 4.18L24 16.36V8z"/></svg>

After

Width:  |  Height:  |  Size: 451 B

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48"><path d="M6 18v12h8l10 10V8L14 18H6zm27 6c0-3.53-2.04-6.58-5-8.05v16.11c2.96-1.48 5-4.53 5-8.06zM28 6.46v4.13c5.78 1.72 10 7.07 10 13.41s-4.22 11.69-10 13.41v4.13c8.01-1.82 14-8.97 14-17.54S36.01 8.28 28 6.46z"/></svg>

After

Width:  |  Height:  |  Size: 281 B

View file

@ -25,6 +25,8 @@ Window {
return youTubeAppearance[name] return youTubeAppearance[name]
} else if (themeName == "Niconico") { } else if (themeName == "Niconico") {
return nicoNicoAppearance[name] return nicoNicoAppearance[name]
} else if (themeName == "RoosterTeeth") {
return roosterTeethAppearance[name]
} }
} }
@ -56,6 +58,7 @@ Window {
property string progressBackgroundColor: "#3CFFFFFF" property string progressBackgroundColor: "#3CFFFFFF"
property string progressCachedColor: "white" property string progressCachedColor: "white"
property string buttonColor: "white" property string buttonColor: "white"
property string buttonHoverColor: "white"
property string progressSliderColor: "red" property string progressSliderColor: "red"
property string chapterMarkerColor: "#fc0" property string chapterMarkerColor: "#fc0"
property string volumeSliderBackground: "white" property string volumeSliderBackground: "white"
@ -68,11 +71,25 @@ Window {
property string progressBackgroundColor: "#444" property string progressBackgroundColor: "#444"
property string progressCachedColor: "white" property string progressCachedColor: "white"
property string buttonColor: "white" property string buttonColor: "white"
property string buttonHoverColor: "white"
property string progressSliderColor: "#007cff" property string progressSliderColor: "#007cff"
property string chapterMarkerColor: "#fc0" property string chapterMarkerColor: "#fc0"
property string volumeSliderBackground: "#007cff" property string volumeSliderBackground: "#007cff"
} }
Settings {
id: roosterTeethAppearance
category: "RoosterTeethAppearance"
property string mainBackground: "#CC2B333F"
property string progressBackgroundColor: "#444"
property string progressCachedColor: "white"
property string buttonColor: "white"
property string buttonHoverColor: "#c9373f"
property string progressSliderColor: "#c9373f"
property string chapterMarkerColor: "#fc0"
property string volumeSliderBackground: "#c9373f"
}
Settings { Settings {
id: i18n id: i18n
category: "I18N" category: "I18N"

View file

@ -7,6 +7,9 @@
<file>MainMenu.qml</file> <file>MainMenu.qml</file>
<file>YouTubeButtonLayout.qml</file> <file>YouTubeButtonLayout.qml</file>
<file>NiconicoButtonLayout.qml</file> <file>NiconicoButtonLayout.qml</file>
<file>RoosterTeethButtonLayout.qml</file>
<file alias="VerticalVolume.qml">UIComponents/VerticalVolume.qml</file>
<file alias="SpeedText.qml">UIComponents/SpeedText.qml</file>
<file alias="ForwardButton.qml">UIComponents/ForwardButton.qml</file> <file alias="ForwardButton.qml">UIComponents/ForwardButton.qml</file>
<file alias="BackwardButton.qml">UIComponents/BackwardButton.qml</file> <file alias="BackwardButton.qml">UIComponents/BackwardButton.qml</file>
<file alias="PlaylistPrevButton.qml">UIComponents/PlaylistPrevButton.qml</file> <file alias="PlaylistPrevButton.qml">UIComponents/PlaylistPrevButton.qml</file>
@ -39,6 +42,21 @@
<file>icons/YouTube/prev.svg</file> <file>icons/YouTube/prev.svg</file>
<file>icons/YouTube/subtitles.svg</file> <file>icons/YouTube/subtitles.svg</file>
<file>icons/YouTube/playlist.svg</file> <file>icons/YouTube/playlist.svg</file>
<file>icons/RoosterTeeth/play.svg</file>
<file>icons/RoosterTeeth/pause.svg</file>
<file>icons/RoosterTeeth/forward.svg</file>
<file>icons/RoosterTeeth/backward.svg</file>
<file>icons/RoosterTeeth/settings.svg</file>
<file>icons/RoosterTeeth/fullscreen.svg</file>
<file>icons/RoosterTeeth/volume-up.svg</file>
<file>icons/RoosterTeeth/volume-mute.svg</file>
<file>icons/RoosterTeeth/volume-down.svg</file>
<file>icons/RoosterTeeth/next.svg</file>
<file>icons/RoosterTeeth/prev.svg</file>
<file>icons/RoosterTeeth/subtitles.svg</file>
<file>icons/RoosterTeeth/playlist.svg</file>
<file>icons/Niconico/play.svg</file> <file>icons/Niconico/play.svg</file>
<file>icons/Niconico/pause.svg</file> <file>icons/Niconico/pause.svg</file>
<file>icons/Niconico/settings.svg</file> <file>icons/Niconico/settings.svg</file>