mirror of
https://github.com/the1812/Bilibili-Evolved.git
synced 2025-11-04 21:22:45 +08:00
1 line
13 KiB
JavaScript
1 line
13 KiB
JavaScript
!function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t():"function"==typeof define&&define.amd?define([],t):"object"==typeof exports?exports["video/player/remember-speed"]=t():e["video/player/remember-speed"]=t()}(self,(function(){return function(){"use strict";var e,t,n={742:function(e,t,n){n.r(t),n.d(t,{VideoSpeedController:function(){return h},calcOrder:function(){return m},errorMessageDuration:function(){return u},maxValue:function(){return p},minValue:function(){return l},stepValue:function(){return c}});var s=coreApis.observer,i=n(407),a=coreApis.spinQuery,r=coreApis.utils.sort,o=coreApis.componentApis.video.playerAgent;function d(e,t,n){return t in e?Object.defineProperty(e,t,{value:n,enumerable:!0,configurable:!0,writable:!0}):e[t]=n,e}const l=.0625,p=16,c=.5,u=2e3,m=e=>(1e4*(p-e)).toString(),v=(e=unsafeWindow.aid)=>{if(!e)throw new Error("aid is unknown");return e},f=(0,i.getComponentSettings)("rememberVideoSpeed"),b=f.options,y=o.playerAgent.provideCustomQuery({video:{speedMenuList:"bilibili-player-video-btn-speed-menu",speedMenuItem:"bilibili-player-video-btn-speed-menu-list",speedNameBtn:"bilibili-player-video-btn-speed-name",speedContainer:"bilibili-player-video-btn-speed",active:"bilibili-player-active",show:"bilibili-player-speed-show"},bangumi:{speedMenuList:"squirtle-speed-select-list",speedMenuItem:"squirtle-select-item",speedNameBtn:"squirtle-speed-select-result",speedContainer:"squirtle-speed-wrap",active:"active",show:"bilibili-player-speed-show"}}),S=e=>e.replace(/^\./,"");class h{static get extendedSupportedRates(){return Array.from(new Set(b.extendList)).sort((0,r.ascendingSort)())}static get supportedRates(){return b.extend?[...h.nativeSupportedRates,...h.extendedSupportedRates].sort((0,r.ascendingSort)()):h.nativeSupportedRates}static get fallbackVideoSpeed(){return f.enabled?parseFloat(b.speed):null}static formatSpeedText(e){return 1===e?"倍速":Math.trunc(e)===e?`${e}.0x`:`${e}x`}static getRememberSpeed(e){for(const[t,n]of Object.entries(b.individualRememberList))if(n.some((t=>t===v(e))))return parseFloat(t);return null}static forgetSpeed(e){e=v(e);let t=-1;for(const n of Object.values(b.individualRememberList))if(t=n.indexOf(e),-1!==t){n.splice(t,1);break}return-1!==t}static rememberSpeed(e,t=!1,n){n=v(n);(h.forgetSpeed(n)||t)&&(b.individualRememberList[e]||(b.individualRememberList[e]=[]),b.individualRememberList[e].push(n))}static async getInstance(e,t){const n=await(0,a.select)(`.${h.classNameMap.speedContainer}`),s=await o.playerAgent.query.video.element();if(!n)throw new Error("speed container element not found!");if(!s)throw new Error("video element not found!");return new h(n,s,e,t)}constructor(e,t,n,s){this.containerElement=e,this.videoElement=t,d(this,"menuListElement",void 0),d(this,"nameBtn",void 0),d(this,"nativeSpeedVal",void 0),d(this,"previousSpeedVal",void 0);const i=h.instanceMap.get(e);if(i&&(!n||i.previousSpeedVal===n)&&(!s||i.nativeSpeedVal===s))return i;this.previousSpeedVal=n,this.nativeSpeedVal=s??(n&&h.nativeSupportedRates.includes(n)?n:1),this.nameBtn=this.containerElement.querySelector(`.${h.classNameMap.speedNameBtn}`),this.menuListElement=this.containerElement.querySelector(`.${h.classNameMap.speedMenuList}`),this.menuListElement.querySelectorAll(`.${h.classNameMap.speedMenuItem}`).forEach((e=>{if(!e.hasAttribute("data-value")){const t=parseFloat(e.textContent).toString();e.setAttribute("data-value",t)}})),h.instanceMap.set(e,this)}get playbackRate(){return this.videoElement.playbackRate}getSpeedMenuItem(e){return e?this.menuListElement.querySelector(`.${h.classNameMap.speedMenuItem}[data-value="${e}"]`):this.menuListElement.querySelector(`.${h.classNameMap.speedMenuItem}.${h.classNameMap.active}`)}observe(){(0,s.allMutationsOn)(this.menuListElement,(e=>{let[t,n]=[void 0,void 0];e.forEach((e=>{const s=e.target;if(!s.classList.contains(h.classNameMap.active))return void(t=parseFloat(s.dataset.value??"1"));n=parseFloat(s.dataset.value??"1");let i=!1;h.nativeSupportedRates.includes(n)&&(this.nativeSpeedVal=n,i=!0),this.containerElement.dispatchEvent(new CustomEvent("changed",{detail:{speed:n,isNativeSpeed:i,previousSpeed:this.previousSpeedVal}})),b.extend&&h.nativeSupportedRates.includes(n)&&this.menuListElement.querySelector(`.${h.classNameMap.speedMenuItem}.extended.${h.classNameMap.active}`)?.classList.remove(h.classNameMap.active),f.enabled&&(b.individualRemember?h.rememberSpeed(n,n!==h.fallbackVideoSpeed):b.speed=n.toString())})),t&&t!==n&&(this.previousSpeedVal=t)}))}toggleVideoSpeed(e="smart",t=!1){switch(e){case"smart":1===this.playbackRate?this.setVideoSpeed(this.previousSpeedVal):this.reset(t);break;case"classic":this.setVideoSpeed(this.previousSpeedVal)}}reset(e=!1){if(e){const{fallbackVideoSpeed:e}=h;if(!e)return;h.forgetSpeed(),this.setVideoSpeed(e)}else this.setVideoSpeed(1)}setVideoSpeed(e){e&&this.getSpeedMenuItem(e).click()}setExtendedVideoSpeed(e){h.nativeSupportedRates.includes(e)?this.getSpeedMenuItem(e).click():this.forceUpdate(e)}forceUpdate(e){this.menuListElement.querySelector(`.${h.classNameMap.speedMenuItem}[data-value="${this.playbackRate}"]`)?.classList.remove(h.classNameMap.active),this.menuListElement.querySelector(`.${h.classNameMap.speedMenuItem}[data-value="${e}"]`)?.classList.add(h.classNameMap.active),this.videoElement.playbackRate=e,this.containerElement.classList.remove(h.classNameMap.show),this.nameBtn.innerText=h.formatSpeedText(e)}}d(h,"classNameMap",{speedMenuList:S(y.custom.speedMenuList.selector),speedMenuItem:S(y.custom.speedMenuItem.selector),speedNameBtn:S(y.custom.speedNameBtn.selector),speedContainer:S(y.custom.speedContainer.selector),active:S(y.custom.active.selector),show:S(y.custom.show.selector),video:S(y.query.video.container.selector)}),d(h,"nativeSupportedRates",[.5,.75,1,1.25,1.5,2]),d(h,"instanceMap",new WeakMap),d(h,"init",lodash.once((()=>{let e,t,i=1;(0,s.videoChange)((async()=>{const{getExtraSpeedMenuItemElements:s}=await Promise.resolve().then(n.bind(n,515)),a=await h.getInstance(e,i);t=a.containerElement,t.classList.contains("extended")||(b.extend&&(a.menuListElement.prepend(...await s()),a.menuListElement.querySelectorAll(`.${h.classNameMap.speedMenuItem}[data-value]:not(.extended)`).forEach((e=>{e.style.order=m(parseFloat(e.getAttribute("data-value")))})),a.menuListElement.addEventListener("click",(e=>{const t=e.target,n=parseFloat(t.dataset.value);e.target.classList.contains("extended")&&a.setExtendedVideoSpeed(n),h.extendedSupportedRates.includes(a.playbackRate)&&a.nativeSpeedVal===n&&a.forceUpdate(n)}))),a.observe(),t.addEventListener("changed",(({detail:{speed:t,isNativeSpeed:n}})=>{e=t,n&&(i=t)})),setTimeout((()=>{a.setVideoSpeed(f.enabled&&b.individualRemember&&h.getRememberSpeed()||h.fallbackVideoSpeed||e)}),100),t.classList.add("extended"))}))})))},515:function(e,t,n){n.r(t),n.d(t,{getExtraSpeedMenuItemElements:function(){return d}});var s=n(407),i=coreApis.style,a=coreApis.utils.log;const{options:r}=(0,s.getComponentSettings)("rememberVideoSpeed");let o=r.extendList;const d=async()=>{const{VideoSpeedController:e,calcOrder:t,minValue:s,maxValue:d,stepValue:l,errorMessageDuration:p}=await Promise.resolve().then(n.bind(n,742)),c=n=>{const s=document.createElement("li");s.innerText=e.formatSpeedText(n),s.classList.add(e.classNameMap.speedMenuItem,"extended"),s.dataset.value=n.toString(),s.style.order=t(n);const i=document.createElement("i");return i.classList.add("mdi","mdi-close-circle"),i.addEventListener("click",(()=>{lodash.pull(o,n),s.remove()})),s.append(i),s};(0,i.addStyle)(`\n .${e.classNameMap.speedContainer} .${e.classNameMap.speedMenuItem}:first-child .mdi-playlist-plus {\n font-size: 1.5em;\n }\n .${e.classNameMap.speedContainer} .${e.classNameMap.speedMenuItem}:first-child input {\n font-size: inherit;\n color: inherit;\n line-height: inherit;\n background: transparent;\n outline: none;\n width: 100%;\n border: none;\n text-align: center;\n }\n .${e.classNameMap.speedMenuItem} .mdi-close-circle {\n color: inherit;\n opacity: 0.5;\n display: none;\n position: absolute;\n right: 4px;\n }\n .${e.classNameMap.speedMenuItem}:not(.${e.classNameMap.active}):hover .mdi-close-circle {\n display: inline;\n }\n .${e.classNameMap.speedMenuItem} .mdi-close-circle:hover {\n opacity: 1;\n transition: all .3s;\n }\n /* https://stackoverflow.com/a/4298216 */\n /* Chrome */\n .add-speed-entry::-webkit-outer-spin-button,\n .add-speed-entry::-webkit-inner-spin-button {\n -webkit-appearance: none;\n margin: 0;\n }\n /* Firefox */\n .add-speed-entry[type=number] {\n -moz-appearance:textfield;\n }\n .${e.classNameMap.speedMenuList} {\n display: flex;\n flex-direction: column;\n overflow-y: auto;\n max-height: 360px;\n }\n `,"extend-video-speed-style");const u=e.extendedSupportedRates.map((e=>c(e))).reverse();return u.unshift((()=>{const t=t=>{const n=(()=>{const t=e.supportedRates.slice(-1)[0]+l;return t>d?null:t})();t.setAttribute("min",n?t.value=n.toString():(t.value="",s.toString()))},n=document.createElement("li");n.classList.add(e.classNameMap.speedMenuItem);const i=document.createElement("i");i.classList.add("mdi","mdi-playlist-plus");const u=document.createElement("input");return u.classList.add("add-speed-entry"),u.setAttribute("type","number"),u.setAttribute("max",d.toString()),u.setAttribute("step",l.toString()),u.setAttribute("title","增加新的倍速值"),t(u),u.addEventListener("keydown",(i=>{if("Enter"===i.key){const i=parseFloat(u.value);if(!isFinite(i))return(0,a.logError)("无效的倍速值",p),!1;if(i<s)return(0,a.logError)("倍速值太小了",p),!1;if(i>d)return(0,a.logError)("倍速值太大了",p),!1;if(e.supportedRates.includes(i))return(0,a.logError)("不能重复添加已有的倍速值",p),!1;o.push(i),r.extendList=e.extendedSupportedRates,o=r.extendList;let l=n.nextElementSibling;for(;!l.dataset.value||parseFloat(l.dataset.value)>e.nativeSupportedRates.slice(-1)[0]&&i<parseFloat(l.dataset.value);)l=l.nextElementSibling;l.before(c(i)),t(u)}return!0})),n.prepend(i,u),u.style.display="none",n.addEventListener("mouseenter",(()=>{t(u),u.style.display="inline",i.style.display="none",u.focus()})),n.addEventListener("mouseleave",(()=>{i.style.display="inline",u.style.display="none"})),n})()),u}},407:function(e){e.exports=coreApis.settings}},s={};function i(e){var t=s[e];if(void 0!==t)return t.exports;var a=s[e]={exports:{}};return n[e](a,a.exports,i),a.exports}t=Object.getPrototypeOf?function(e){return Object.getPrototypeOf(e)}:function(e){return e.__proto__},i.t=function(n,s){if(1&s&&(n=this(n)),8&s)return n;if("object"==typeof n&&n){if(4&s&&n.__esModule)return n;if(16&s&&"function"==typeof n.then)return n}var a=Object.create(null);i.r(a);var r={};e=e||[null,t({}),t([]),t(t)];for(var o=2&s&&n;"object"==typeof o&&!~e.indexOf(o);o=t(o))Object.getOwnPropertyNames(o).forEach((function(e){r[e]=function(){return n[e]}}));return r.default=function(){return n},i.d(a,r),a},i.d=function(e,t){for(var n in t)i.o(t,n)&&!i.o(e,n)&&Object.defineProperty(e,n,{enumerable:!0,get:t[n]})},i.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},i.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var a={};return function(){i.d(a,{component:function(){return t}});var e=coreApis.utils.urls;const t={name:"rememberVideoSpeed",displayName:"倍速记忆",author:{name:"JLoeve",link:"https://github.com/LonelySteve"},description:{"zh-CN":"记忆上次选择的视频播放速度, 还可以使用更多倍速来扩展原生倍速菜单."},tags:[componentsTags.video],urlInclude:e.playerUrls,entry:async()=>{const{VideoSpeedController:e}=await Promise.resolve().then(i.bind(i,742));return e.init(),e},plugin:{displayName:"倍速记忆 - 快捷键支持",setup:async({addData:e})=>{const{getComponentSettings:t}=await Promise.resolve().then(i.t.bind(i,407,23)),n=async(e,t)=>{const{VideoSpeedController:n}=await Promise.resolve().then(i.bind(i,742)),s=await n.getInstance();t(s,n.supportedRates),e.showTip(`${s.playbackRate}x`,"mdi-fast-forward")};e("keymap.actions",(e=>{e.videoSpeedIncrease={displayName:"提高倍速",run:e=>(n(e,((e,t)=>{e.setVideoSpeed(t.find((t=>t>e.playbackRate))||t[t.length-1])})),!0)},e.videoSpeedDecrease={displayName:"降低倍速",run:e=>(n(e,((e,t)=>{e.setVideoSpeed([...t].reverse().find((t=>t<e.playbackRate))||t[0])})),!0)},e.videoSpeedReset={displayName:"重置倍速",run:e=>(n(e,(e=>{e.toggleVideoSpeed()})),!0)},t("rememberVideoSpeed").options.individualRemember&&(e.videoSpeedForget={displayName:"清除当前倍速记忆",run:e=>(n(e,(e=>{e.reset(!0)})),!0)})})),e("keymap.presets",(e=>{e.videoSpeedIncrease="shift > 》 arrowUp",e.videoSpeedDecrease="shift < 《 arrowDown",e.videoSpeedReset="shift ? ?",e.videoSpeedForget="shift : :"}))}},options:{speed:{displayName:"记忆的速度",defaultValue:"1.0",hidden:!0},extend:{displayName:"扩展倍速菜单",defaultValue:!0},extendList:{displayName:"扩展倍速列表",defaultValue:[2.5,3],hidden:!0},individualRemember:{displayName:"各视频分别记忆",defaultValue:!1,hidden:!0},individualRememberList:{displayName:"分别记忆倍速列表",defaultValue:{},hidden:!0}}}}(),a=a.component}()})); |