More fixes

This commit is contained in:
WardPearce
2025-09-19 17:49:27 +12:00
parent 37cb1e85ad
commit e786451ac4
6 changed files with 93 additions and 386 deletions
+5 -14
View File
@@ -31,7 +31,7 @@
"media-captions": "^1.0.4",
"mousetrap": "^1.6.5",
"peerjs": "^1.5.5",
"shaka-player": "^4.11.7",
"shaka-player": "^4.16.2",
"sponsorblock-api": "^0.2.4",
"svelte-infinite-loading": "^1.4.0",
"svelte-persisted-store": "^0.12.0",
@@ -5750,12 +5750,6 @@
"node": ">= 0.4.0"
}
},
"node_modules/eme-encryption-scheme-polyfill": {
"version": "2.2.1",
"resolved": "https://registry.npmjs.org/eme-encryption-scheme-polyfill/-/eme-encryption-scheme-polyfill-2.2.1.tgz",
"integrity": "sha512-GzgrLuZPYGijd8oaKuBqYv3Tc2oruDZM3V2982KOuy/PA1N3zwMe+/oIXJYfZ3BH3PwW5nONdBBE+VY6jlwbrw==",
"license": "Apache-2.0"
},
"node_modules/emoji-regex": {
"version": "8.0.0",
"resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz",
@@ -11124,15 +11118,12 @@
}
},
"node_modules/shaka-player": {
"version": "4.11.7",
"resolved": "https://registry.npmjs.org/shaka-player/-/shaka-player-4.11.7.tgz",
"integrity": "sha512-jNsdQd4pa24w2QwXHGNBs8MQ33YajYiZclWaSuGt+dLJ7/D9+NG1LJQGnTrGd0G1aDdbEzmEpppG3ic4OsGpyw==",
"version": "4.16.2",
"resolved": "https://registry.npmjs.org/shaka-player/-/shaka-player-4.16.2.tgz",
"integrity": "sha512-AFswL7ZXT37UceDAsovQXQ3BRGLmPcmdgXgLVJdmHN2mnrYCvTrl7CGg2jeIPxUOHipAeeq33LrDM9uGBlQRVA==",
"license": "Apache-2.0",
"dependencies": {
"eme-encryption-scheme-polyfill": "^2.1.5"
},
"engines": {
"node": ">=14"
"node": ">=18"
}
},
"node_modules/sharp": {
+4 -3
View File
@@ -10,7 +10,8 @@
"check:watch": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json --watch",
"lint": "prettier --check . && eslint .",
"format": "prettier --write .",
"postinstall": "patch-package"
"patch:shaka": "node ./scripts/patchShaka.mjs",
"postinstall": "npm run patch:shaka"
},
"devDependencies": {
"@capacitor/assets": "^3.0.5",
@@ -63,10 +64,10 @@
"media-captions": "^1.0.4",
"mousetrap": "^1.6.5",
"peerjs": "^1.5.5",
"shaka-player": "^4.11.7",
"shaka-player": "^4.16.2",
"sponsorblock-api": "^0.2.4",
"svelte-infinite-loading": "^1.4.0",
"svelte-persisted-store": "^0.12.0",
"youtubei.js": "^15.1.1"
}
}
}
+37
View File
@@ -0,0 +1,37 @@
import { readFile, appendFile } from "node:fs/promises";
import path from "node:path";
import * as url from "node:url";
const __dirname = path.dirname(url.fileURLToPath(import.meta.url));
async function main() {
const fileNames = ["shaka-player.ui.d.ts", "shaka-player.ui.debug.d.ts"];
for (const filename of fileNames) {
await fixTypes(filename);
}
}
async function fixTypes(filename) {
const filePath = path.join(
__dirname,
"..",
"node_modules",
"shaka-player",
"dist",
filename,
);
const shakaTs = await readFile(filePath, "utf-8");
if (!shakaTs.includes("export default shaka")) {
await appendFile(filePath, "export default shaka;");
console.log(`[PatchShaka] Fixed types in ${filename}`);
} else {
console.log(`[PatchShaka] No changes needed in ${filename}`);
}
}
main().catch(() => {
console.error("[PatchShaka]", "Failed to patch shaka-player");
});
+47 -89
View File
@@ -1,6 +1,5 @@
<script lang="ts">
import { page } from '$app/stores';
import '$lib/css/shaka-player-theme.css';
import { getBestThumbnail } from '$lib/images';
import { padTime, videoLength } from '$lib/numbers';
import { type PhasedDescription } from '$lib/timestamps';
@@ -13,6 +12,7 @@
import ISO6391 from 'iso-639-1';
import Mousetrap from 'mousetrap';
import 'shaka-player/dist/controls.css';
import '$lib/css/shaka-player-theme.css';
import shaka from 'shaka-player/dist/shaka-player.ui';
import { SponsorBlock, type Category, type Segment } from 'sponsorblock-api';
import { onDestroy, onMount, tick } from 'svelte';
@@ -91,62 +91,16 @@
played: (await getDynamicTheme())['--primary']
}
});
setChapterMarkers();
const overflowMenuButton = document.querySelector('.shaka-overflow-menu-button');
if (overflowMenuButton) {
overflowMenuButton.innerHTML = 'settings';
}
const backToOverflowButton = document.querySelector('.shaka-back-to-overflow-button');
if (backToOverflowButton) {
backToOverflowButton.innerHTML = 'arrow_back_ios_new';
}
}
themeColorStore.subscribe(updateSeekBarTheme);
darkModeStore.subscribe(updateSeekBarTheme);
function setChapterMarkers() {
const shakaControls = shakaUi.getControls();
if (data.content.timestamps && shakaControls) {
const seekBar = shakaControls
.getControlsContainer()
.querySelector('.shaka-seek-bar-container');
data.content.timestamps.forEach((chapter, index) => {
const nextChapter = data.content.timestamps[index + 1];
const marker = document.createElement('div');
marker.classList.add('chapter-marker');
const startPercent = (chapter.time / data.video.lengthSeconds) * 100;
let widthPercent: number;
if (nextChapter) {
widthPercent = ((nextChapter.time - chapter.time) / data.video.lengthSeconds) * 100;
} else {
widthPercent = 100 - startPercent;
}
marker.style.left = `${startPercent}%`;
marker.style.width = `${widthPercent}%`;
const tooltip = document.createElement('div');
tooltip.classList.add('tooltip');
tooltip.textContent = chapter.title;
marker.appendChild(tooltip);
if (seekBar) seekBar.appendChild(marker);
});
}
}
function restoreDefaultLanguage() {
if (!$playerDefaultLanguage || $playerDefaultLanguage === "original") {
const languageAndRole = player.getAudioLanguagesAndRoles().find(({ role }) => role === "main");
if (!$playerDefaultLanguage || $playerDefaultLanguage === 'original') {
const languageAndRole = player
.getAudioLanguagesAndRoles()
.find(({ role }) => role === 'main');
if (languageAndRole !== undefined) {
player.selectAudioLanguage(languageAndRole.language);
return;
@@ -343,45 +297,11 @@
// Will inject requirements for SABR if SABR is required.
playerElementResizeObserver = injectSABR(player, playerElement as HTMLMediaElement, data.video);
try {
document.getElementsByClassName('shaka-ad-info')[0].remove();
} catch {}
if (!data.video.liveNow) {
if (data.video.captions) {
data.video.captions.forEach(async (caption) => {
player.addTextTrackAsync(
caption.url.startsWith('http') ? caption.url : `${get(instanceStore)}${caption.url}`,
caption.language_code,
'captions',
undefined,
undefined,
caption.label
);
});
}
if (data.content.timestamps) {
let chapterWebVTT = 'WEBVTT\n\n';
let timestampIndex = 0;
data.content.timestamps.forEach((timestamp) => {
let endTime: string;
if (timestampIndex === data.content.timestamps.length - 1) {
endTime = videoLength(data.video.lengthSeconds);
} else {
endTime = data.content.timestamps[timestampIndex + 1].timePretty;
}
chapterWebVTT += `${padTime(timestamp.timePretty)} --> ${padTime(endTime)}\n${timestamp.title.replaceAll('-', '').trim()}\n\n`;
timestampIndex += 1;
});
if (timestampIndex > 0) {
player.addChaptersTrack(
`data:text/vtt;base64,${btoa(chapterWebVTT)}`,
get(playerDefaultLanguage)
);
}
}
if (watchProgressTimeout) {
clearInterval(watchProgressTimeout);
}
@@ -418,6 +338,44 @@
} else {
await player.load(dashUrl, await getLastPlayPos());
}
if (data.video.captions) {
data.video.captions.forEach(async (caption) => {
player.addTextTrackAsync(
caption.url.startsWith('http') ? caption.url : `${get(instanceStore)}${caption.url}`,
caption.language_code,
'captions',
undefined,
undefined,
caption.label
);
});
}
if (data.content.timestamps) {
let chapterWebVTT = 'WEBVTT\n\n';
let timestampIndex = 0;
data.content.timestamps.forEach((timestamp) => {
let endTime: string;
if (timestampIndex === data.content.timestamps.length - 1) {
endTime = videoLength(data.video.lengthSeconds);
} else {
endTime = data.content.timestamps[timestampIndex + 1].timePretty;
}
chapterWebVTT += `${padTime(timestamp.timePretty)}.000 --> ${padTime(endTime)}.000\n${timestamp.title.replaceAll('-', '').trim()}\n\n`;
timestampIndex += 1;
});
if (timestampIndex > 0) {
player.addChaptersTrack(
`data:text/vtt;base64,${btoa(chapterWebVTT)}`,
get(playerDefaultLanguage)
);
}
}
} else {
if (data.video.fallbackPatch === 'youtubejs') {
if (!data.video.dashUrl) {
@@ -8,285 +8,6 @@
color: var(--on-surface);
}
.player-theme .shaka-bottom-controls {
width: 100%;
padding: 0;
padding-bottom: 0;
z-index: 1;
display: flex;
flex-direction: column;
}
.player-theme .shaka-ad-controls {
order: 1;
}
.player-theme .shaka-controls-button-panel {
order: 2;
height: 2.5rem; /* 40px */
padding: 0 0.625rem; /* 10px */
}
.player-theme .shaka-range-container {
margin: 0.25rem 0.625rem; /* 4px 10px */
top: 0;
}
.player-theme .shaka-small-play-button {
order: -3;
}
.player-theme .shaka-mute-button {
order: -2;
}
.player-theme .shaka-controls-button-panel > * {
margin: 0;
padding: 0.1875rem 0.5rem; /* 3px 8px */
color: #fff;
height: 2.5rem; /* 40px */
font-size: 2rem; /* 32px */
}
.player-theme .shaka-controls-button-panel > *:hover {
color: var(--primary);
}
.player-theme .shaka-controls-button-panel > *:focus {
outline: none;
box-shadow: inset 0 0 0 2px var(--primary);
color: var(--primary);
}
.player-theme .shaka-controls-button-panel .shaka-volume-bar-container {
height: 0.1875rem; /* 3px */
padding: 0;
}
.player-theme .shaka-controls-button-panel .shaka-volume-bar-container:hover,
.player-theme .shaka-controls-button-panel .shaka-volume-bar-container:focus {
display: block;
opacity: 1;
padding: 0 0.375rem; /* 6px */
}
.player-theme .shaka-mute-button:hover + div {
opacity: 1;
width: 3.125rem; /* 50px */
padding: 0 0.375rem; /* 6px */
}
.player-theme .shaka-current-time {
padding: 0 0.625rem; /* 10px */
font-size: 1rem; /* 16px */
color: #fff !important;
}
.player-theme .shaka-seek-bar-container {
height: 0.1875rem; /* 3px */
position: relative;
top: -0.0625rem; /* -1px */
margin-bottom: 0;
border-radius: 0;
}
.player-theme .shaka-seek-bar-container .shaka-range-element {
opacity: 0;
}
.player-theme .shaka-seek-bar-container:hover {
height: 0.3125rem; /* 5px */
top: 0;
cursor: pointer;
}
.player-theme .shaka-seek-bar-container:hover .shaka-range-element {
opacity: 1;
cursor: pointer;
}
.player-theme .shaka-seek-bar-container input[type='range']::-webkit-slider-thumb,
.player-theme .shaka-seek-bar-container input[type='range']::-moz-range-thumb,
.player-theme .shaka-seek-bar-container input[type='range']::-ms-thumb {
background: var(--primary);
cursor: pointer;
}
.player-theme .shaka-overflow-menu,
.player-theme .shaka-settings-menu {
border-radius: 0.25rem;
background: var(--surface-container-low);
right: 0.625rem; /* 10px */
bottom: 3.125rem; /* 50px */
min-width: 12.5rem; /* 200px */
animation: none !important;
transition: none !important;
opacity: 1 !important;
visibility: visible !important;
z-index: 99999999 !important;
pointer-events: auto !important;
pointer-events: auto !important;
}
.player-theme .shaka-settings-menu {
padding-bottom: 0.5rem; /* 8px */
}
.player-theme .shaka-settings-menu button {
font-size: 1rem; /* 16px */
border: none;
margin: 0;
}
.player-theme .shaka-settings-menu button span {
margin-left: 2.0625rem; /* 33px */
font-size: 1rem; /* 16px */
}
.player-theme .shaka-settings-menu button[aria-selected='true'] {
display: flex;
}
.player-theme .shaka-settings-menu button[aria-selected='true'] span {
order: 2;
margin-left: 0;
}
.player-theme .shaka-settings-menu button[aria-selected='true'] i {
order: 1;
font-size: 1rem; /* 16px */
padding-left: 0.3125rem; /* 5px */
}
.shaka-overflow-menu * {
z-index: 99999999 !important;
pointer-events: auto !important;
}
.player-theme .shaka-overflow-menu button,
.player-theme .shaka-settings-menu button {
padding: 0;
margin-bottom: 0.5em;
visibility: visible !important;
z-index: 99999999 !important;
pointer-events: auto !important;
}
.player-theme .shaka-overflow-menu button i {
display: none;
}
.player-theme .shaka-overflow-menu button .shaka-overflow-button-label {
display: flex;
align-items: start;
cursor: default;
outline: none;
height: 2.5rem; /* 40px */
flex: 0 0 100%;
visibility: visible !important;
z-index: 99999999 !important;
pointer-events: auto !important;
pointer-events: auto !important;
}
.shaka-settings-menu {
padding: 0.5em;
}
.shaka-settings-menu button {
gap: 0;
justify-content: start;
}
.player-theme .shaka-overflow-menu button .shaka-overflow-button-label span {
flex-shrink: 0;
padding-left: 0.9375rem; /* 15px */
font-size: 1rem; /* 16px */
display: flex;
align-items: center;
}
.shaka-overflow-button-label span:not(.shaka-current-selection-span) {
font-weight: 200 !important;
}
.player-theme .shaka-overflow-menu span + span {
color: var(--primary-text);
font-weight: 400 !important;
font-size: 1rem !important;
padding-right: 0.5rem; /* 8px */
}
.player-theme .shaka-overflow-menu .shaka-pip-button span + span {
padding-right: 0.9375rem !important; /* 15px */
}
.player-theme .shaka-overflow-menu .shaka-pip-button span + span:after {
content: '';
}
.player-theme .shaka-back-to-overflow-button {
padding: 0.5rem 0;
border-bottom: 1px solid rgba(255, 255, 255, 0.2);
font-size: 1rem; /* 16px */
color: var(--primary-text);
height: 2.5rem; /* 40px */
}
.player-theme .shaka-back-to-overflow-button .material-icons-round {
font-size: 1rem; /* 16px */
padding-right: 0.625rem; /* 10px */
}
.player-theme .shaka-back-to-overflow-button span {
margin-left: 0.1875rem !important; /* 3px */
}
.player-theme .shaka-overflow-menu button:hover,
.player-theme .shaka-settings-menu button:hover {
background-color: var(--surface-bright);
cursor: pointer;
}
.player-theme .shaka-overflow-menu button:hover label,
.player-theme .shaka-settings-menu button:hover label {
cursor: pointer;
}
.player-theme .shaka-overflow-menu button:focus,
.player-theme .shaka-settings-menu button:focus {
background-color: var(--surface-bright);
border: none;
outline: none;
}
.player-theme .shaka-overflow-menu button,
.player-theme .shaka-settings-menu button {
color: var(--primary-text);
}
.player-theme .shaka-captions-off {
color: var(--surface-bright);
}
.player-theme .shaka-overflow-menu-button {
font-size: 1rem; /* 16px */
margin-right: 0.3125rem; /* 5px */
}
.player-theme .chapter-marker {
bottom: 100%;
height: 4px;
margin-bottom: 8px;
position: absolute;
background: linear-gradient(
to right,
var(--primary-container) 0%,
var(--primary-container) calc(100% - 10px),
transparent 100%
);
}
@media screen and (max-width: 650px) {
.player-theme .shaka-end-time {
display: none;
-1
View File
@@ -2,7 +2,6 @@ import { sveltekit } from '@sveltejs/kit/vite';
import { SvelteKitPWA } from '@vite-pwa/sveltekit';
import { defineConfig } from 'vite';
export default defineConfig({
plugins: [
SvelteKitPWA({