This commit is contained in:
Malte Jürgens 2022-10-14 23:16:34 +02:00
parent 1eda9d75b0
commit 100f9bf58e
No known key found for this signature in database
GPG Key ID: D29FBD5F93C0CFC3
13 changed files with 224 additions and 58 deletions

1
.gitignore vendored
View File

@ -1,2 +1,3 @@
/build /build
.vscode .vscode
/submodules/Vencord

View File

@ -40,6 +40,7 @@ set(discord-screenaudio_SRC
src/discordpage.cpp src/discordpage.cpp
src/streamdialog.cpp src/streamdialog.cpp
src/log.cpp src/log.cpp
src/webclass.cpp
resources.qrc resources.qrc
) )

View File

@ -131,28 +131,28 @@ setInterval(() => {
} }
// Add about text in settings // Add about text in settings
if ( // if (
document.getElementsByClassName("dirscordScreenaudioAboutText").length == 0 // document.getElementsByClassName("dirscordScreenaudioAboutText").length == 0
) { // ) {
for (const el of document.getElementsByClassName("info-3pQQBb")) { // for (const el of document.getElementsByClassName("info-3pQQBb")) {
let aboutEl; // let aboutEl;
if (window.discordScreenaudioKXMLGUI) { // if (window.discordScreenaudioKXMLGUI) {
aboutEl = document.createElement("a"); // aboutEl = document.createElement("a");
aboutEl.addEventListener("click", () => { // aboutEl.addEventListener("click", () => {
console.log("!discord-screenaudio-about"); // console.log("!discord-screenaudio-about");
}); // });
} else { // } else {
aboutEl = document.createElement("div"); // aboutEl = document.createElement("div");
} // }
aboutEl.innerText = `discord-screenaudio ${window.discordScreenaudioVersion}`; // aboutEl.innerText = `discord-screenaudio ${window.discordScreenaudioVersion}`;
aboutEl.style.fontSize = "12px"; // aboutEl.style.fontSize = "12px";
aboutEl.style.color = "var(--text-muted)"; // aboutEl.style.color = "var(--text-muted)";
aboutEl.style.textTransform = "none"; // aboutEl.style.textTransform = "none";
aboutEl.classList.add("dirscordScreenaudioAboutText"); // aboutEl.classList.add("dirscordScreenaudioAboutText");
aboutEl.style.cursor = "pointer"; // aboutEl.style.cursor = "pointer";
el.appendChild(aboutEl); // el.appendChild(aboutEl);
} // }
} // }
// Remove stream settings if stream is active // Remove stream settings if stream is active
document.getElementById("manage-streams-change-windows")?.remove(); document.getElementById("manage-streams-change-windows")?.remove();

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,40 @@
let webclass;
const promise = new Promise((resolve) => {
setTimeout(() => {
new QWebChannel(qt.webChannelTransport, function (channel) {
webclass = channel.objects.webclass;
resolve();
});
});
});
async function prepareWebclass() {
if (!webclass) await promise;
}
window.VencordNative = {
getVersions: () => ({}),
ipc: {
send: async (event: string, ...args: any[]) => {
await prepareWebclass();
webclass.vencordSend(event, args);
},
sendSync: (event: string, ...args: any[]) => {
if (event === "VencordGetSettings") return "{}";
else throw new Error("Synchroneous IPC not implemented");
},
on(event: string, listener: () => {}) {
// TODO quickCss
},
off(event: string, listener: () => {}) {
// not used for now
},
invoke:
(event: string, ...args: any[]) =>
async () => {
await prepareWebclass();
return webclass.vencordSend(event, args);
},
},
};

14
assets/vencord/plugin.js Normal file
View File

@ -0,0 +1,14 @@
import definePlugin from "../utils/types";
export default definePlugin({
name: "discord-screenaudio",
authors: [
{
name: "maltejur",
id: 205966226709676032n,
},
],
required: true,
description: "UI patches for discord-screenaudio.",
patches: [],
});

36
assets/vencord/vencord.js Normal file

File diff suppressed because one or more lines are too long

View File

@ -2,7 +2,7 @@
<RCC> <RCC>
<qresource> <qresource>
<file>assets/userscript.js</file> <file>assets/userscript.js</file>
<file>assets/vencord.js</file> <file>assets/vencord/vencord.js</file>
<file>assets/de.shorsh.discord-screenaudio.png</file> <file>assets/de.shorsh.discord-screenaudio.png</file>
</qresource> </qresource>
</RCC> </RCC>

38
scripts/build_vencord.sh Executable file
View File

@ -0,0 +1,38 @@
#!/usr/bin/bash
set -e
cd "$(dirname "$0")/../submodules"
echo_status() {
echo
echo
echo "-> $1..."
}
if [ ! -d "Vencord" ]; then
echo_status "Cloning Vencord"
git clone https://github.com/Vendicated/Vencord.git
cd Vencord
else
echo_status "Pulling Vencord changes"
cd Vencord
git pull
fi
echo_status "Checking out latest commit"
git reset --hard HEAD
git checkout main
git reset --hard origin/main
echo_status "Installing dependencies"
pnpm i
echo_status "Patching Vencord"
cp -v ../../assets/vencord/plugin.js ./src/plugins/discord-screenaudio.js
cp -v ../../assets/vencord/VencordNativeStub.ts ./browser/VencordNativeStub.ts
echo_status "Building Vencord"
pnpm run buildWeb
echo_status "Copying built file"
cp -v ./dist/browser.js ../../assets/vencord/vencord.js

View File

@ -51,10 +51,15 @@ DiscordPage::DiscordPage(QWidget *parent) : QWebEnginePage(parent) {
settings()->setAttribute(QWebEngineSettings::JavascriptCanOpenWindows, false); settings()->setAttribute(QWebEngineSettings::JavascriptCanOpenWindows, false);
settings()->setAttribute(QWebEngineSettings::ScrollAnimatorEnabled, true); settings()->setAttribute(QWebEngineSettings::ScrollAnimatorEnabled, true);
injectScriptFile("qwebchannel.js", ":/qtwebchannel/qwebchannel.js");
setUrl(QUrl("https://discord.com/app")); setUrl(QUrl("https://discord.com/app"));
setWebChannel(new QWebChannel(this));
webChannel()->registerObject("webclass", &m_webClass);
injectScriptFile("userscript.js", ":/assets/userscript.js"); injectScriptFile("userscript.js", ":/assets/userscript.js");
injectScriptFile("vencord.js", ":/assets/vencord.js"); injectScriptFile("vencord.js", ":/assets/vencord/vencord.js");
injectScriptText("version.js", injectScriptText("version.js",
QString("window.discordScreenaudioVersion = '%1';") QString("window.discordScreenaudioVersion = '%1';")
@ -115,7 +120,9 @@ DiscordPage::DiscordPage(QWidget *parent) : QWebEnginePage(parent) {
&DiscordPage::startStream); &DiscordPage::startStream);
} }
void DiscordPage::injectScriptText(QString name, QString content) { void DiscordPage::injectScriptText(
QString name, QString content,
QWebEngineScript::InjectionPoint injectionPoint) {
qDebug(mainLog) << "Injecting " << name; qDebug(mainLog) << "Injecting " << name;
QWebEngineScript script; QWebEngineScript script;
@ -123,20 +130,22 @@ void DiscordPage::injectScriptText(QString name, QString content) {
script.setSourceCode(content); script.setSourceCode(content);
script.setName(name); script.setName(name);
script.setWorldId(QWebEngineScript::MainWorld); script.setWorldId(QWebEngineScript::MainWorld);
script.setInjectionPoint(QWebEngineScript::DocumentCreation); script.setInjectionPoint(injectionPoint);
script.setRunsOnSubFrames(false); script.setRunsOnSubFrames(false);
scripts().insert(script); scripts().insert(script);
} }
void DiscordPage::injectScriptFile(QString name, QString source) { void DiscordPage::injectScriptFile(
QString name, QString source,
QWebEngineScript::InjectionPoint injectionPoint) {
QFile file(source); QFile file(source);
if (!file.open(QIODevice::ReadOnly)) { if (!file.open(QIODevice::ReadOnly)) {
qFatal("Failed to load %s with error: %s", source.toLatin1().constData(), qFatal("Failed to load %s with error: %s", source.toLatin1().constData(),
file.errorString().toLatin1().constData()); file.errorString().toLatin1().constData());
} else { } else {
injectScriptText(name, file.readAll()); injectScriptText(name, file.readAll(), injectionPoint);
} }
} }

View File

@ -2,6 +2,7 @@
#include "streamdialog.h" #include "streamdialog.h"
#include "virtmic.h" #include "virtmic.h"
#include "webclass.h"
#ifdef KXMLGUI #ifdef KXMLGUI
#include <KActionCollection> #include <KActionCollection>
@ -12,6 +13,7 @@
#include <QProcess> #include <QProcess>
#include <QWebEngineFullScreenRequest> #include <QWebEngineFullScreenRequest>
#include <QWebEnginePage> #include <QWebEnginePage>
#include <QWebEngineScript>
class DiscordPage : public QWebEnginePage { class DiscordPage : public QWebEnginePage {
Q_OBJECT Q_OBJECT
@ -22,6 +24,7 @@ public:
private: private:
StreamDialog m_streamDialog; StreamDialog m_streamDialog;
QProcess m_virtmicProcess; QProcess m_virtmicProcess;
WebClass m_webClass;
#ifdef KXMLGUI #ifdef KXMLGUI
KHelpMenu *m_helpMenu; KHelpMenu *m_helpMenu;
#ifdef KGLOBALACCEL #ifdef KGLOBALACCEL
@ -37,8 +40,12 @@ private:
javaScriptConsoleMessage(QWebEnginePage::JavaScriptConsoleMessageLevel level, javaScriptConsoleMessage(QWebEnginePage::JavaScriptConsoleMessageLevel level,
const QString &message, int lineNumber, const QString &message, int lineNumber,
const QString &sourceID) override; const QString &sourceID) override;
void injectScriptText(QString name, QString content); void injectScriptText(QString name, QString content,
void injectScriptFile(QString name, QString source); QWebEngineScript::InjectionPoint injectionPoint =
QWebEngineScript::DocumentCreation);
void injectScriptFile(QString name, QString source,
QWebEngineScript::InjectionPoint injectionPoint =
QWebEngineScript::DocumentCreation);
void stopVirtmic(); void stopVirtmic();
void startVirtmic(QString target); void startVirtmic(QString target);
void toggleMute(); void toggleMute();

35
src/webclass.cpp Normal file
View File

@ -0,0 +1,35 @@
#include "webclass.h"
#include <QDesktopServices>
#include <QUrl>
QVariant WebClass::vencordSend(QString event, QVariantList args) {
if (event == "VencordGetRepo") {
return true;
}
if (event == "VencordGetSettingsDir") {
return "~/.config/discord-screenaudio/vencord";
}
if (event == "VencordGetQuickCss") {
// TODO
return "";
}
if (event == "VencordGetSettings") {
return m_vencordSettings;
}
if (event == "VencordSetSettings") {
m_vencordSettings = args[0].toString();
return true;
}
if (event == "VencordGetUpdates") {
return QVariantMap{{"ok", true}, {"value", QVariantList()}};
}
if (event == "VencordOpenExternal") {
QDesktopServices::openUrl(QUrl(args[0].toString()));
return true;
}
if (event == "VencordOpenQuickCss") {
return true;
}
assert(false);
}

13
src/webclass.h Normal file
View File

@ -0,0 +1,13 @@
#pragma once
#include <QObject>
#include <QVariant>
class WebClass : public QObject {
Q_OBJECT
public slots:
QVariant vencordSend(QString event, QVariantList args);
private:
QString m_vencordSettings;
};