Load segment description from hashparams

This commit is contained in:
mini-bomba
2022-09-01 23:10:03 +02:00
committed by Ajay
parent 59093cdf21
commit df2586e76d

View File

@@ -1,11 +1,26 @@
import Config from "./config"; import Config from "./config";
import { SponsorTime, CategorySkipOption, VideoID, SponsorHideType, VideoInfo, StorageChangesObject, ChannelIDInfo, ChannelIDStatus, SponsorSourceType, SegmentUUID, Category, SkipToTimeParams, ToggleSkippable, ActionType, ScheduledTime, HashedValue } from "./types"; import {
ActionType,
import { ContentContainer, Keybind } from "./types"; Category,
CategorySkipOption,
ChannelIDInfo,
ChannelIDStatus,
ContentContainer,
HashedValue,
Keybind,
ScheduledTime,
SegmentUUID,
SkipToTimeParams,
SponsorHideType,
SponsorSourceType,
SponsorTime,
StorageChangesObject,
ToggleSkippable,
VideoID,
VideoInfo,
} from "./types";
import Utils from "./utils"; import Utils from "./utils";
const utils = new Utils(); import PreviewBar, { PreviewBarSegment } from "./js-components/previewBar";
import PreviewBar, {PreviewBarSegment} from "./js-components/previewBar";
import SkipNotice from "./render/SkipNotice"; import SkipNotice from "./render/SkipNotice";
import SkipNoticeComponent from "./components/SkipNoticeComponent"; import SkipNoticeComponent from "./components/SkipNoticeComponent";
import SubmissionNotice from "./render/SubmissionNotice"; import SubmissionNotice from "./render/SubmissionNotice";
@@ -22,6 +37,8 @@ import { importTimes } from "./utils/exporter";
import { ChapterVote } from "./render/ChapterVote"; import { ChapterVote } from "./render/ChapterVote";
import { openWarningDialog } from "./utils/warnings"; import { openWarningDialog } from "./utils/warnings";
const utils = new Utils();
// Hack to get the CSS loaded on permission-based sites (Invidious) // Hack to get the CSS loaded on permission-based sites (Invidious)
utils.wait(() => Config.config !== null, 5000, 10).then(addCSS); utils.wait(() => Config.config !== null, 5000, 10).then(addCSS);
@@ -247,7 +264,7 @@ function messageListener(request: Message, sender: unknown, sendResponse: (respo
let addedSegments = false; let addedSegments = false;
for (const segment of importedSegments) { for (const segment of importedSegments) {
if (!sponsorTimesSubmitting.concat(sponsorTimes ?? []).some( if (!sponsorTimesSubmitting.concat(sponsorTimes ?? []).some(
(s) => Math.abs(s.segment[0] - segment.segment[0]) < 1 (s) => Math.abs(s.segment[0] - segment.segment[0]) < 1
&& Math.abs(s.segment[1] - segment.segment[1]) < 1) && Math.abs(s.segment[1] - segment.segment[1]) < 1)
&& (segment.category !== "chapter" || utils.getCategorySelection("chapter"))) { && (segment.category !== "chapter" || utils.getCategorySelection("chapter"))) {
sponsorTimesSubmitting.push(segment); sponsorTimesSubmitting.push(segment);
@@ -561,7 +578,7 @@ function startSponsorSchedule(includeIntersectingSegments = false, currentTime?:
const videoID = sponsorVideoID; const videoID = sponsorVideoID;
const skipBuffer = 0.003; const skipBuffer = 0.003;
if (videoMuted && !inMuteSegment(currentTime, skipInfo.index !== -1 if (videoMuted && !inMuteSegment(currentTime, skipInfo.index !== -1
&& timeUntilSponsor < skipBuffer && shouldAutoSkip(currentSkip))) { && timeUntilSponsor < skipBuffer && shouldAutoSkip(currentSkip))) {
video.muted = false; video.muted = false;
videoMuted = false; videoMuted = false;
@@ -628,8 +645,8 @@ function startSponsorSchedule(includeIntersectingSegments = false, currentTime?:
}); });
} }
} }
if (utils.getCategorySelection(currentSkip.category)?.option === CategorySkipOption.ManualSkip if (utils.getCategorySelection(currentSkip.category)?.option === CategorySkipOption.ManualSkip
|| currentSkip.actionType === ActionType.Mute) { || currentSkip.actionType === ActionType.Mute) {
forcedSkipTime = skipTime[0] + 0.001; forcedSkipTime = skipTime[0] + 0.001;
} else { } else {
@@ -672,7 +689,7 @@ function startSponsorSchedule(includeIntersectingSegments = false, currentTime?:
}, 1); }, 1);
} else { } else {
logDebug(`Starting timeout to skip ${video.currentTime} to skip at ${skipTime[0]}`); logDebug(`Starting timeout to skip ${video.currentTime} to skip at ${skipTime[0]}`);
// Schedule for right before to be more precise than normal timeout // Schedule for right before to be more precise than normal timeout
currentSkipSchedule = setTimeout(skippingFunction, Math.max(0, delayTime - 150)); currentSkipSchedule = setTimeout(skippingFunction, Math.max(0, delayTime - 150));
} }
@@ -692,8 +709,8 @@ function getVirtualTime(): number {
} }
function inMuteSegment(currentTime: number, includeOverlap: boolean): boolean { function inMuteSegment(currentTime: number, includeOverlap: boolean): boolean {
const checkFunction = (segment) => segment.actionType === ActionType.Mute const checkFunction = (segment) => segment.actionType === ActionType.Mute
&& segment.segment[0] <= currentTime && segment.segment[0] <= currentTime
&& (segment.segment[1] > currentTime || (includeOverlap && segment.segment[1] + 0.02 > currentTime)); && (segment.segment[1] > currentTime || (includeOverlap && segment.segment[1] + 0.02 > currentTime));
return sponsorTimes?.some(checkFunction) || sponsorTimesSubmitting.some(checkFunction); return sponsorTimes?.some(checkFunction) || sponsorTimesSubmitting.some(checkFunction);
} }
@@ -773,7 +790,7 @@ function setupVideoListeners() {
// If it is not the first event, then the only way to get to 0 is if there is a seek event // If it is not the first event, then the only way to get to 0 is if there is a seek event
// This check makes sure that changing the video resolution doesn't cause the extension to think it // This check makes sure that changing the video resolution doesn't cause the extension to think it
// gone back to the begining // gone back to the begining
if (video.readyState <= HTMLMediaElement.HAVE_CURRENT_DATA if (video.readyState <= HTMLMediaElement.HAVE_CURRENT_DATA
&& video.currentTime === 0) return; && video.currentTime === 0) return;
updateVirtualTime(); updateVirtualTime();
@@ -804,7 +821,7 @@ function setupVideoListeners() {
video.addEventListener('playing', () => { video.addEventListener('playing', () => {
updateVirtualTime(); updateVirtualTime();
lastPausedAtZero = false; lastPausedAtZero = false;
if (startedWaiting) { if (startedWaiting) {
startedWaiting = false; startedWaiting = false;
logDebug(`[SB] Playing event after buffering: ${Math.abs(lastCheckVideoTime - video.currentTime) > 0.3 logDebug(`[SB] Playing event after buffering: ${Math.abs(lastCheckVideoTime - video.currentTime) > 0.3
@@ -1062,7 +1079,7 @@ function retryFetch(errorCode: number): void {
sponsorDataFound = false; sponsorDataFound = false;
if (errorCode !== 404 && retryCount > 1) { if (errorCode !== 404 && retryCount > 1) {
// Too many errors (50x), give up // Too many errors (50x), give up
return; return;
} }
@@ -1070,7 +1087,7 @@ function retryFetch(errorCode: number): void {
const delay = errorCode === 404 ? (10000 + Math.random() * 30000) : (2000 + Math.random() * 10000); const delay = errorCode === 404 ? (10000 + Math.random() * 30000) : (2000 + Math.random() * 10000);
setTimeout(() => { setTimeout(() => {
if (sponsorVideoID && sponsorTimes?.length === 0 if (sponsorVideoID && sponsorTimes?.length === 0
|| sponsorTimes.every((segment) => segment.source !== SponsorSourceType.Server)) { || sponsorTimes.every((segment) => segment.source !== SponsorSourceType.Server)) {
sponsorsLookup(); sponsorsLookup();
} }
@@ -1334,7 +1351,7 @@ function getNextSkipIndex(currentTime: number, includeIntersectingSegments: bool
const minSponsorTimeIndexes = GenericUtils.indexesOf(sponsorStartTimes, Math.min(...sponsorStartTimesAfterCurrentTime)); const minSponsorTimeIndexes = GenericUtils.indexesOf(sponsorStartTimes, Math.min(...sponsorStartTimesAfterCurrentTime));
// Find auto skipping segments if possible, sort by duration otherwise // Find auto skipping segments if possible, sort by duration otherwise
const minSponsorTimeIndex = minSponsorTimeIndexes.sort( const minSponsorTimeIndex = minSponsorTimeIndexes.sort(
(a, b) => ((autoSkipSorter(submittedArray[a]) - autoSkipSorter(submittedArray[b])) (a, b) => ((autoSkipSorter(submittedArray[a]) - autoSkipSorter(submittedArray[b]))
|| (submittedArray[a].segment[1] - submittedArray[a].segment[0]) - (submittedArray[b].segment[1] - submittedArray[b].segment[0])))[0] ?? -1; || (submittedArray[a].segment[1] - submittedArray[a].segment[0]) - (submittedArray[b].segment[1] - submittedArray[b].segment[0])))[0] ?? -1;
// Store extra indexes for the non-auto skipping segments if others occur at the exact same start time // Store extra indexes for the non-auto skipping segments if others occur at the exact same start time
const extraIndexes = minSponsorTimeIndexes.filter((i) => i !== minSponsorTimeIndex && autoSkipSorter(submittedArray[i]) !== 0); const extraIndexes = minSponsorTimeIndexes.filter((i) => i !== minSponsorTimeIndex && autoSkipSorter(submittedArray[i]) !== 0);
@@ -1448,7 +1465,7 @@ function getStartTimes(sponsorTimes: SponsorTime[], includeIntersectingSegments:
for (let i = 0; i < possibleTimes.length; i++) { for (let i = 0; i < possibleTimes.length; i++) {
if ((minimum === undefined if ((minimum === undefined
|| ((includeNonIntersectingSegments && possibleTimes[i].scheduledTime >= minimum) || ((includeNonIntersectingSegments && possibleTimes[i].scheduledTime >= minimum)
|| (includeIntersectingSegments && possibleTimes[i].scheduledTime < minimum && possibleTimes[i].segment[1] > minimum))) || (includeIntersectingSegments && possibleTimes[i].scheduledTime < minimum && possibleTimes[i].segment[1] > minimum)))
&& (!hideHiddenSponsors || possibleTimes[i].hidden === SponsorHideType.Visible) && (!hideHiddenSponsors || possibleTimes[i].hidden === SponsorHideType.Visible)
&& possibleTimes[i].segment.length === 2 && possibleTimes[i].segment.length === 2
&& possibleTimes[i].actionType !== ActionType.Poi) { && possibleTimes[i].actionType !== ActionType.Poi) {
@@ -1576,13 +1593,13 @@ function skipToTime({v, skipTime, skippingSegments, openNotice, forceAutoSkip, u
function createSkipNotice(skippingSegments: SponsorTime[], autoSkip: boolean, unskipTime: number, startReskip: boolean) { function createSkipNotice(skippingSegments: SponsorTime[], autoSkip: boolean, unskipTime: number, startReskip: boolean) {
for (const skipNotice of skipNotices) { for (const skipNotice of skipNotices) {
if (skippingSegments.length === skipNotice.segments.length if (skippingSegments.length === skipNotice.segments.length
&& skippingSegments.every((segment) => skipNotice.segments.some((s) => s.UUID === segment.UUID))) { && skippingSegments.every((segment) => skipNotice.segments.some((s) => s.UUID === segment.UUID))) {
// Skip notice already exists // Skip notice already exists
return; return;
} }
} }
const newSkipNotice = new SkipNotice(skippingSegments, autoSkip, skipNoticeContentContainer, unskipTime, startReskip); const newSkipNotice = new SkipNotice(skippingSegments, autoSkip, skipNoticeContentContainer, unskipTime, startReskip);
if (onMobileYouTube || Config.config.skipKeybind == null) newSkipNotice.setShowKeybindHint(false); if (onMobileYouTube || Config.config.skipKeybind == null) newSkipNotice.setShowKeybindHint(false);
skipNotices.push(newSkipNotice); skipNotices.push(newSkipNotice);
@@ -1596,7 +1613,7 @@ function unskipSponsorTime(segment: SponsorTime, unskipTime: number = null, forc
video.muted = false; video.muted = false;
videoMuted = false; videoMuted = false;
} }
if (forceSeek || segment.actionType === ActionType.Skip) { if (forceSeek || segment.actionType === ActionType.Skip) {
//add a tiny bit of time to make sure it is not skipped again //add a tiny bit of time to make sure it is not skipped again
video.currentTime = unskipTime ?? segment.segment[0] + 0.001; video.currentTime = unskipTime ?? segment.segment[0] + 0.001;
@@ -1869,10 +1886,10 @@ function openInfoMenu() {
//hide info button //hide info button
if (playerButtons.info) playerButtons.info.button.style.display = "none"; if (playerButtons.info) playerButtons.info.button.style.display = "none";
const popup = document.createElement("div"); const popup = document.createElement("div");
popup.id = "sponsorBlockPopupContainer"; popup.id = "sponsorBlockPopupContainer";
const frame = document.createElement("iframe"); const frame = document.createElement("iframe");
frame.width = "374"; frame.width = "374";
frame.height = "500"; frame.height = "500";
@@ -1891,7 +1908,7 @@ function openInfoMenu() {
//old youtube theme //old youtube theme
parentNode = document.getElementById("watch7-sidebar-contents"); parentNode = document.getElementById("watch7-sidebar-contents");
} }
parentNode.insertBefore(popup, parentNode.firstChild); parentNode.insertBefore(popup, parentNode.firstChild);
} }
@@ -2178,7 +2195,7 @@ function nextChapter(): void {
.sort((a, b) => a.segment[1] - b.segment[1]); .sort((a, b) => a.segment[1] - b.segment[1]);
if (chapters.length <= 0) return; if (chapters.length <= 0) return;
const nextChapter = chapters.findIndex((time) => time.actionType === ActionType.Chapter const nextChapter = chapters.findIndex((time) => time.actionType === ActionType.Chapter
&& time.segment[1] > video.currentTime); && time.segment[1] > video.currentTime);
if (nextChapter !== -1) { if (nextChapter !== -1) {
reskipSponsorTime(chapters[nextChapter], true); reskipSponsorTime(chapters[nextChapter], true);
@@ -2193,7 +2210,7 @@ function previousChapter(): void {
// subtract 5 seconds to allow skipping back to the previous chapter if close to start of // subtract 5 seconds to allow skipping back to the previous chapter if close to start of
// the current one // the current one
const nextChapter = chapters.findIndex((time) => time.actionType === ActionType.Chapter const nextChapter = chapters.findIndex((time) => time.actionType === ActionType.Chapter
&& time.segment[0] > video.currentTime - Math.min(5, time.segment[1] - time.segment[0])); && time.segment[0] > video.currentTime - Math.min(5, time.segment[1] - time.segment[0]));
const previousChapter = nextChapter !== -1 ? (nextChapter - 1) : (chapters.length - 1); const previousChapter = nextChapter !== -1 ? (nextChapter - 1) : (chapters.length - 1);
if (previousChapter !== -1) { if (previousChapter !== -1) {
@@ -2320,7 +2337,7 @@ function showTimeWithoutSkips(skippedDuration: number): void {
display.appendChild(duration); display.appendChild(duration);
} }
const durationAfterSkips = GenericUtils.getFormattedTime(video?.duration - skippedDuration); const durationAfterSkips = GenericUtils.getFormattedTime(video?.duration - skippedDuration);
duration.innerText = (durationAfterSkips == null || skippedDuration <= 0) ? "" : " (" + durationAfterSkips + ")"; duration.innerText = (durationAfterSkips == null || skippedDuration <= 0) ? "" : " (" + durationAfterSkips + ")";
@@ -2343,6 +2360,7 @@ function checkForPreloadedSegment() {
UUID: GenericUtils.generateUserID() as SegmentUUID, UUID: GenericUtils.generateUserID() as SegmentUUID,
category: segment.category ? segment.category : Config.config.defaultCategory, category: segment.category ? segment.category : Config.config.defaultCategory,
actionType: segment.actionType ? segment.actionType : ActionType.Skip, actionType: segment.actionType ? segment.actionType : ActionType.Skip,
description: segment.description ?? "",
source: SponsorSourceType.Local source: SponsorSourceType.Local
}); });
@@ -2362,7 +2380,7 @@ function checkForPreloadedSegment() {
const navigationApiAvailable = "navigation" in window; const navigationApiAvailable = "navigation" in window;
if (navigationApiAvailable) { if (navigationApiAvailable) {
// TODO: Remove type cast once type declarations are updated // TODO: Remove type cast once type declarations are updated
(window as unknown as { navigation: EventTarget }).navigation.addEventListener("navigate", (e) => (window as unknown as { navigation: EventTarget }).navigation.addEventListener("navigate", (e) =>
videoIDChange(getYouTubeVideoID(document, (e as unknown as Record<string, Record<string, string>>).destination.url))); videoIDChange(getYouTubeVideoID(document, (e as unknown as Record<string, Record<string, string>>).destination.url)));
} }