From 15d9da12b3552d42033fef6f5b737611529bd589 Mon Sep 17 00:00:00 2001 From: W0LH Date: Mon, 2 Mar 2026 14:01:46 +0100 Subject: [PATCH 1/8] Add toggle to change volume with scroll button + left ctrl and 2 shortcuts Add toggle to change volume with scroll button + left ctrl and 2 shortcuts --- _locales/en/messages.json | 3 + js&css/web-accessible/core.js | 10 ++- js&css/web-accessible/functions.js | 60 ++++++++++++++- .../www.youtube.com/shortcuts.js | 73 ++++++++++++++++++- menu/skeleton-parts/shortcuts.js | 29 +++++++- 5 files changed, 167 insertions(+), 8 deletions(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index 3ea352b29..bb4248856 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -1552,6 +1552,9 @@ "volume": { "message": "Volume" }, + "ctrlWheelVolume": { + "message": "Ctrl + mouse wheel for changing volume" + }, "watchedVideos": { "message": "Watched videos" }, diff --git a/js&css/web-accessible/core.js b/js&css/web-accessible/core.js index dbaf8a4ed..78c2f6411 100644 --- a/js&css/web-accessible/core.js +++ b/js&css/web-accessible/core.js @@ -66,7 +66,8 @@ var ImprovedTube = { wheel: 0, alt: false, ctrl: false, - shift: false + shift: false, + ctrlSide: null }, cancelled: new Set(), ignoreElements: ['EMBED', 'INPUT', 'OBJECT', 'TEXTAREA', 'IFRAME'], @@ -528,7 +529,12 @@ document.addEventListener('it-message-from-extension', function () { } // dont trigger shortcuts on config change, reinitialize handler instead - if (message.key.startsWith('shortcut_')) camelized_key = 'shortcuts'; + if (message.key.startsWith('shortcut_') || message.key === 'shortcuts_volume_wheel_ctrl') { + camelized_key = 'shortcuts'; + if (typeof ImprovedTube.shortcutsInit === 'function') { + ImprovedTube.shortcutsInit(); + } + } if (ImprovedTube[camelized_key]) { try { ImprovedTube[camelized_key]() } catch { }; } diff --git a/js&css/web-accessible/functions.js b/js&css/web-accessible/functions.js index 08534e696..0a77f8e39 100644 --- a/js&css/web-accessible/functions.js +++ b/js&css/web-accessible/functions.js @@ -752,11 +752,63 @@ ImprovedTube.showStatus = function (value) { this.elements.status.id = 'it-status'; } - if (typeof value === 'number') { - value = value.toFixed(2); - } + if (typeof value === 'object' && value?.type === 'volume') { + const player = this.elements.player; + const bezel = player?.querySelector('.ytp-bezel'); + if (bezel) { + let bezelIcon = bezel.querySelector('.ytp-bezel-icon'); + if (!bezelIcon) { + bezelIcon = document.createElement('div'); + bezelIcon.className = 'ytp-bezel-icon'; + bezel.appendChild(bezelIcon); + } + + const iconSource = player?.querySelector('.ytp-volume-panel .ytp-volume-icon') + || player?.querySelector('.ytp-mute-button'); + if (iconSource) { + const svg = iconSource.querySelector('svg')?.cloneNode(true) || iconSource.cloneNode(true); + while (bezelIcon.firstChild) bezelIcon.firstChild.remove(); + bezelIcon.appendChild(svg); + } + + const bezelText = bezel.querySelector('.ytp-bezel-text'); + if (bezelText) { + const volumeValue = typeof value.value === 'number' ? value.value : (player?.getVolume ? player.getVolume() : 0); + bezelText.textContent = `${Math.round(volumeValue)}%`; + } + + bezel.classList.add('ytp-bezel-showing'); + clearTimeout(ImprovedTube.status_timer); + ImprovedTube.status_timer = setTimeout(function () { + bezel.classList.remove('ytp-bezel-showing'); + }, 500); + return; + } + + this.elements.status.textContent = ''; - this.elements.status.textContent = value; + const iconSource = player?.querySelector('.ytp-volume-panel .ytp-volume-icon') + || player?.querySelector('.ytp-mute-button'); + let iconElement; + + if (iconSource) { + iconElement = iconSource.cloneNode(true); + iconElement.removeAttribute('id'); + iconElement.removeAttribute('aria-label'); + iconElement.removeAttribute('title'); + } else { + iconElement = document.createElement('div'); + iconElement.textContent = (value.muted || value.value === 0) ? '🔇' : (value.value <= 50 ? '🔈' : '🔊'); + } + + this.elements.status.appendChild(iconElement); + } else { + if (typeof value === 'number') { + value = value.toFixed(2); + } + + this.elements.status.textContent = value; + } if (ImprovedTube.status_timer) { clearTimeout(ImprovedTube.status_timer); diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index a7a27104d..de24762b5 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -10,11 +10,29 @@ ImprovedTube.shortcutsInit = function () { // those four are _references_ to source Objects, not copies const listening = ImprovedTube.input.listening, listeners = ImprovedTube.input.listeners; + const volumeWheelEnabled = this.storage.shortcuts_volume_wheel_ctrl === true; + const volumeWheelDefaults = { + shortcut_increase_volume_wheel_ctrl: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: -1 + }, + shortcut_decrease_volume_wheel_ctrl: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: 1 + } + }; // reset 'listening' shortcuts for (var key in listening) delete listening[key]; // extract shortcuts from User Settings and initialize 'listening' for (const [name, keys] of Object.entries(this.storage).filter(v => v[0].startsWith('shortcut_'))) { + if (!volumeWheelEnabled && (name in volumeWheelDefaults)) continue; if (!keys) continue; // camelCase(name) const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); @@ -40,6 +58,33 @@ ImprovedTube.shortcutsInit = function () { } if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; } + // inject defaults for Ctrl+wheel volume if enabled and unset + if (volumeWheelEnabled) { + for (const [name, keys] of Object.entries(volumeWheelDefaults)) { + if (this.storage[name]) continue; + const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); + let potentialShortcut = {}; + for (const button of ['alt', 'ctrl', 'shift', 'wheel', 'keys', 'toggle']) { + switch (button) { + case 'alt': + case 'ctrl': + case 'shift': + case 'toggle': + potentialShortcut[button] = keys[button] || false; + break + + case 'wheel': + potentialShortcut[button] = keys[button] || 0; + break + + case 'keys': + potentialShortcut[button] = keys[button] ? new Set(Object.keys(keys[button]).map(s=>Number(s))) : new Set(); + break + } + } + if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; + } + } // initialize 'listeners' only if there are actual shortcuts active if (Object.keys(listening).length) { for (const [name, handler] of Object.entries(this.shortcutsListeners)) { @@ -72,6 +117,9 @@ ImprovedTube.shortcutsHandler = function () { if (!shortcut.keys.has(pressedKey)) continue check; } + const requiresLeftCtrl = key === 'shortcutIncreaseVolumeWheelCtrl' || key === 'shortcutDecreaseVolumeWheelCtrl'; + if (requiresLeftCtrl && ImprovedTube.input.pressed.ctrlSide !== 'left') continue; + // cancel keydown/wheel event before we call target handler // this way crashing handler wont keep 'cancelled' keys stuck event.preventDefault(); @@ -104,6 +152,11 @@ ImprovedTube.shortcutsListeners = { ImprovedTube.input.pressed.alt = event.altKey; ImprovedTube.input.pressed.ctrl = event.ctrlKey; ImprovedTube.input.pressed.shift = event.shiftKey; + if (event.code === 'ControlLeft') { + ImprovedTube.input.pressed.ctrlSide = 'left'; + } else if (event.code === 'ControlRight') { + ImprovedTube.input.pressed.ctrlSide = 'right'; + } ImprovedTube.shortcutsHandler(); }, @@ -113,6 +166,9 @@ ImprovedTube.shortcutsListeners = { ImprovedTube.input.pressed.alt = event.altKey; ImprovedTube.input.pressed.ctrl = event.ctrlKey; ImprovedTube.input.pressed.shift = event.shiftKey; + if (event.code === 'ControlLeft' || event.code === 'ControlRight') { + ImprovedTube.input.pressed.ctrlSide = null; + } // cancel keyup events corresponding to keys that triggered one of our shortcuts if (ImprovedTube.input.cancelled.has(event.keyCode)) { @@ -146,6 +202,7 @@ ImprovedTube.shortcutsListeners = { ImprovedTube.input.pressed.alt = false; ImprovedTube.input.pressed.ctrl = false; ImprovedTube.input.pressed.shift = false; + ImprovedTube.input.pressed.ctrlSide = null; } }; /*--- jump To Key Scene ----*/ @@ -356,7 +413,11 @@ ImprovedTube.shortcutIncreaseVolume = function (decrease) { sessionStorage['yt-player-volume'] = localStorage['yt-player-volume']; - this.showStatus(player.getVolume()); + this.showStatus({ + type: 'volume', + value: player.getVolume(), + muted: player.isMuted ? player.isMuted() : player.getVolume() === 0 + }); }; /*------------------------------------------------------------------------------ 4.7.14 DECREASE VOLUME @@ -365,6 +426,16 @@ ImprovedTube.shortcutDecreaseVolume = function () { ImprovedTube.shortcutIncreaseVolume(true); }; /*------------------------------------------------------------------------------ +CTRL + WHEEL VOLUME +------------------------------------------------------------------------------*/ +ImprovedTube.shortcutIncreaseVolumeWheelCtrl = function () { + ImprovedTube.shortcutIncreaseVolume(false); +}; + +ImprovedTube.shortcutDecreaseVolumeWheelCtrl = function () { + ImprovedTube.shortcutIncreaseVolume(true); +}; +/*------------------------------------------------------------------------------ 4.7.15 SCREENSHOT ------------------------------------------------------------------------------*/ ImprovedTube.shortcutScreenshot = ImprovedTube.screenshot; diff --git a/menu/skeleton-parts/shortcuts.js b/menu/skeleton-parts/shortcuts.js index 4bf324ff2..f228758aa 100644 --- a/menu/skeleton-parts/shortcuts.js +++ b/menu/skeleton-parts/shortcuts.js @@ -83,6 +83,11 @@ extension.skeleton.main.layers.section.shortcuts = { max: 25, step: 1, value: 5 + }, + shortcuts_volume_wheel_ctrl: { + component: 'checkbox', + text: 'ctrlWheelVolume', + value: false } }, @@ -111,7 +116,29 @@ extension.skeleton.main.layers.section.shortcuts = { } } } - } + }, + shortcut_increase_volume_wheel_ctrl: { + component: 'shortcut', + text: 'increaseVolume', + value: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: -1 + } + }, + shortcut_decrease_volume_wheel_ctrl: { + component: 'shortcut', + text: 'decreaseVolume', + value: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: 1 + } + }, } } } From 9a74a30b9d7db69d6e342f2718396e5188e5f79e Mon Sep 17 00:00:00 2001 From: W0LH Date: Mon, 2 Mar 2026 15:18:40 +0100 Subject: [PATCH 2/8] delete restriction to only use left ctrl delete restriction to only use left ctrl --- js&css/web-accessible/core.js | 3 +-- js&css/web-accessible/www.youtube.com/shortcuts.js | 12 ------------ 2 files changed, 1 insertion(+), 14 deletions(-) diff --git a/js&css/web-accessible/core.js b/js&css/web-accessible/core.js index 78c2f6411..2e92f2b09 100644 --- a/js&css/web-accessible/core.js +++ b/js&css/web-accessible/core.js @@ -66,8 +66,7 @@ var ImprovedTube = { wheel: 0, alt: false, ctrl: false, - shift: false, - ctrlSide: null + shift: false }, cancelled: new Set(), ignoreElements: ['EMBED', 'INPUT', 'OBJECT', 'TEXTAREA', 'IFRAME'], diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index de24762b5..355cb1209 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -117,9 +117,6 @@ ImprovedTube.shortcutsHandler = function () { if (!shortcut.keys.has(pressedKey)) continue check; } - const requiresLeftCtrl = key === 'shortcutIncreaseVolumeWheelCtrl' || key === 'shortcutDecreaseVolumeWheelCtrl'; - if (requiresLeftCtrl && ImprovedTube.input.pressed.ctrlSide !== 'left') continue; - // cancel keydown/wheel event before we call target handler // this way crashing handler wont keep 'cancelled' keys stuck event.preventDefault(); @@ -152,11 +149,6 @@ ImprovedTube.shortcutsListeners = { ImprovedTube.input.pressed.alt = event.altKey; ImprovedTube.input.pressed.ctrl = event.ctrlKey; ImprovedTube.input.pressed.shift = event.shiftKey; - if (event.code === 'ControlLeft') { - ImprovedTube.input.pressed.ctrlSide = 'left'; - } else if (event.code === 'ControlRight') { - ImprovedTube.input.pressed.ctrlSide = 'right'; - } ImprovedTube.shortcutsHandler(); }, @@ -166,9 +158,6 @@ ImprovedTube.shortcutsListeners = { ImprovedTube.input.pressed.alt = event.altKey; ImprovedTube.input.pressed.ctrl = event.ctrlKey; ImprovedTube.input.pressed.shift = event.shiftKey; - if (event.code === 'ControlLeft' || event.code === 'ControlRight') { - ImprovedTube.input.pressed.ctrlSide = null; - } // cancel keyup events corresponding to keys that triggered one of our shortcuts if (ImprovedTube.input.cancelled.has(event.keyCode)) { @@ -202,7 +191,6 @@ ImprovedTube.shortcutsListeners = { ImprovedTube.input.pressed.alt = false; ImprovedTube.input.pressed.ctrl = false; ImprovedTube.input.pressed.shift = false; - ImprovedTube.input.pressed.ctrlSide = null; } }; /*--- jump To Key Scene ----*/ From dd925348878e3ab3e9bbf775d7726cc9ef6155a9 Mon Sep 17 00:00:00 2001 From: W0LH Date: Tue, 3 Mar 2026 14:45:38 +0100 Subject: [PATCH 3/8] Add possibility to used also Shift or Alt --- _locales/en/messages.json | 2 +- .../www.youtube.com/shortcuts.js | 44 +++++++++++++++++++ 2 files changed, 45 insertions(+), 1 deletion(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index bb4248856..e8f353c6f 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -1553,7 +1553,7 @@ "message": "Volume" }, "ctrlWheelVolume": { - "message": "Ctrl + mouse wheel for changing volume" + "message": "Ctrl/Alt/Shift + mouse wheel for changing volume" }, "watchedVideos": { "message": "Watched videos" diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index 355cb1209..8bc1b6a44 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -25,6 +25,34 @@ ImprovedTube.shortcutsInit = function () { shift: false, keys: {}, wheel: 1 + }, + shortcut_increase_volume_wheel_alt: { + alt: true, + ctrl: false, + shift: false, + keys: {}, + wheel: -1 + }, + shortcut_decrease_volume_wheel_alt: { + alt: true, + ctrl: false, + shift: false, + keys: {}, + wheel: 1 + }, + shortcut_increase_volume_wheel_shift: { + alt: false, + ctrl: false, + shift: true, + keys: {}, + wheel: -1 + }, + shortcut_decrease_volume_wheel_shift: { + alt: false, + ctrl: false, + shift: true, + keys: {}, + wheel: 1 } }; @@ -423,6 +451,22 @@ ImprovedTube.shortcutIncreaseVolumeWheelCtrl = function () { ImprovedTube.shortcutDecreaseVolumeWheelCtrl = function () { ImprovedTube.shortcutIncreaseVolume(true); }; + +ImprovedTube.shortcutIncreaseVolumeWheelAlt = function () { + ImprovedTube.shortcutIncreaseVolume(false); +}; + +ImprovedTube.shortcutDecreaseVolumeWheelAlt = function () { + ImprovedTube.shortcutIncreaseVolume(true); +}; + +ImprovedTube.shortcutIncreaseVolumeWheelShift = function () { + ImprovedTube.shortcutIncreaseVolume(false); +}; + +ImprovedTube.shortcutDecreaseVolumeWheelShift = function () { + ImprovedTube.shortcutIncreaseVolume(true); +}; /*------------------------------------------------------------------------------ 4.7.15 SCREENSHOT ------------------------------------------------------------------------------*/ From 3087e28546a0e45e784771bd7e594f6ecc5c1191 Mon Sep 17 00:00:00 2001 From: W0LH Date: Tue, 3 Mar 2026 17:22:54 +0100 Subject: [PATCH 4/8] Change description --- _locales/en/messages.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index e8f353c6f..9327c1336 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -1553,7 +1553,7 @@ "message": "Volume" }, "ctrlWheelVolume": { - "message": "Ctrl/Alt/Shift + mouse wheel for changing volume" + "message": "Mouse wheel for changing volume" }, "watchedVideos": { "message": "Watched videos" From 16888fbd7d55cfafa064bf1c5cb6f45bf2e1e901 Mon Sep 17 00:00:00 2001 From: W0LH Date: Tue, 3 Mar 2026 19:01:04 +0100 Subject: [PATCH 5/8] Add possibility to change playback speed with mouse wheel/scroll Add possibility to change playback speed with mouse wheel/scroll --- _locales/en/messages.json | 3 + js&css/web-accessible/core.js | 2 +- .../www.youtube.com/shortcuts.js | 99 +++++++++++++++++++ menu/skeleton-parts/shortcuts.js | 5 + 4 files changed, 108 insertions(+), 1 deletion(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index 9327c1336..152fc1b82 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -1555,6 +1555,9 @@ "ctrlWheelVolume": { "message": "Mouse wheel for changing volume" }, + "wheelPlaybackSpeed": { + "message": "Mouse wheel for changing playback speed" + }, "watchedVideos": { "message": "Watched videos" }, diff --git a/js&css/web-accessible/core.js b/js&css/web-accessible/core.js index 2e92f2b09..08241cf46 100644 --- a/js&css/web-accessible/core.js +++ b/js&css/web-accessible/core.js @@ -528,7 +528,7 @@ document.addEventListener('it-message-from-extension', function () { } // dont trigger shortcuts on config change, reinitialize handler instead - if (message.key.startsWith('shortcut_') || message.key === 'shortcuts_volume_wheel_ctrl') { + if (message.key.startsWith('shortcut_') || message.key === 'shortcuts_volume_wheel_ctrl' || message.key === 'shortcuts_playback_speed_wheel') { camelized_key = 'shortcuts'; if (typeof ImprovedTube.shortcutsInit === 'function') { ImprovedTube.shortcutsInit(); diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index 8bc1b6a44..fa6b68f90 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -11,6 +11,7 @@ ImprovedTube.shortcutsInit = function () { const listening = ImprovedTube.input.listening, listeners = ImprovedTube.input.listeners; const volumeWheelEnabled = this.storage.shortcuts_volume_wheel_ctrl === true; + const playbackSpeedWheelEnabled = this.storage.shortcuts_playback_speed_wheel === true; const volumeWheelDefaults = { shortcut_increase_volume_wheel_ctrl: { alt: false, @@ -55,12 +56,57 @@ ImprovedTube.shortcutsInit = function () { wheel: 1 } }; + const playbackSpeedWheelDefaults = { + shortcut_increase_playback_speed_wheel_ctrl: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: -1 + }, + shortcut_decrease_playback_speed_wheel_ctrl: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: 1 + }, + shortcut_increase_playback_speed_wheel_alt: { + alt: true, + ctrl: false, + shift: false, + keys: {}, + wheel: -1 + }, + shortcut_decrease_playback_speed_wheel_alt: { + alt: true, + ctrl: false, + shift: false, + keys: {}, + wheel: 1 + }, + shortcut_increase_playback_speed_wheel_shift: { + alt: false, + ctrl: false, + shift: true, + keys: {}, + wheel: -1 + }, + shortcut_decrease_playback_speed_wheel_shift: { + alt: false, + ctrl: false, + shift: true, + keys: {}, + wheel: 1 + } + }; // reset 'listening' shortcuts for (var key in listening) delete listening[key]; // extract shortcuts from User Settings and initialize 'listening' for (const [name, keys] of Object.entries(this.storage).filter(v => v[0].startsWith('shortcut_'))) { if (!volumeWheelEnabled && (name in volumeWheelDefaults)) continue; + if (!playbackSpeedWheelEnabled && (name in playbackSpeedWheelDefaults)) continue; if (!keys) continue; // camelCase(name) const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); @@ -113,6 +159,33 @@ ImprovedTube.shortcutsInit = function () { if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; } } + // inject defaults for wheel playback speed if enabled and unset + if (playbackSpeedWheelEnabled) { + for (const [name, keys] of Object.entries(playbackSpeedWheelDefaults)) { + if (this.storage[name]) continue; + const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); + let potentialShortcut = {}; + for (const button of ['alt', 'ctrl', 'shift', 'wheel', 'keys', 'toggle']) { + switch (button) { + case 'alt': + case 'ctrl': + case 'shift': + case 'toggle': + potentialShortcut[button] = keys[button] || false; + break + + case 'wheel': + potentialShortcut[button] = keys[button] || 0; + break + + case 'keys': + potentialShortcut[button] = keys[button] ? new Set(Object.keys(keys[button]).map(s=>Number(s))) : new Set(); + break + } + } + if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; + } + } // initialize 'listeners' only if there are actual shortcuts active if (Object.keys(listening).length) { for (const [name, handler] of Object.entries(this.shortcutsListeners)) { @@ -468,6 +541,32 @@ ImprovedTube.shortcutDecreaseVolumeWheelShift = function () { ImprovedTube.shortcutIncreaseVolume(true); }; /*------------------------------------------------------------------------------ +PLAYBACK SPEED + WHEEL +------------------------------------------------------------------------------*/ +ImprovedTube.shortcutIncreasePlaybackSpeedWheelCtrl = function () { + ImprovedTube.shortcutIncreasePlaybackSpeed(false); +}; + +ImprovedTube.shortcutDecreasePlaybackSpeedWheelCtrl = function () { + ImprovedTube.shortcutIncreasePlaybackSpeed(true); +}; + +ImprovedTube.shortcutIncreasePlaybackSpeedWheelAlt = function () { + ImprovedTube.shortcutIncreasePlaybackSpeed(false); +}; + +ImprovedTube.shortcutDecreasePlaybackSpeedWheelAlt = function () { + ImprovedTube.shortcutIncreasePlaybackSpeed(true); +}; + +ImprovedTube.shortcutIncreasePlaybackSpeedWheelShift = function () { + ImprovedTube.shortcutIncreasePlaybackSpeed(false); +}; + +ImprovedTube.shortcutDecreasePlaybackSpeedWheelShift = function () { + ImprovedTube.shortcutIncreasePlaybackSpeed(true); +}; +/*------------------------------------------------------------------------------ 4.7.15 SCREENSHOT ------------------------------------------------------------------------------*/ ImprovedTube.shortcutScreenshot = ImprovedTube.screenshot; diff --git a/menu/skeleton-parts/shortcuts.js b/menu/skeleton-parts/shortcuts.js index f228758aa..a4b09807f 100644 --- a/menu/skeleton-parts/shortcuts.js +++ b/menu/skeleton-parts/shortcuts.js @@ -159,6 +159,11 @@ extension.skeleton.main.layers.section.shortcuts = { max: 2, step: .05, value: .05 + }, + shortcuts_playback_speed_wheel: { + component: 'checkbox', + text: 'wheelPlaybackSpeed', + value: false } }, From 6e47f6e7ea730540be2efc25848199e54f910ff9 Mon Sep 17 00:00:00 2001 From: W0LH Date: Tue, 3 Mar 2026 20:36:54 +0100 Subject: [PATCH 6/8] Fix problem where playback speed can be change without preset shortcuts Fix problem where playback speed can be change without preset shortcuts --- .../www.youtube.com/shortcuts.js | 73 +------------------ menu/skeleton-parts/shortcuts.js | 22 ++++++ 2 files changed, 23 insertions(+), 72 deletions(-) diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index fa6b68f90..9fe1bec43 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -56,57 +56,13 @@ ImprovedTube.shortcutsInit = function () { wheel: 1 } }; - const playbackSpeedWheelDefaults = { - shortcut_increase_playback_speed_wheel_ctrl: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: -1 - }, - shortcut_decrease_playback_speed_wheel_ctrl: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: 1 - }, - shortcut_increase_playback_speed_wheel_alt: { - alt: true, - ctrl: false, - shift: false, - keys: {}, - wheel: -1 - }, - shortcut_decrease_playback_speed_wheel_alt: { - alt: true, - ctrl: false, - shift: false, - keys: {}, - wheel: 1 - }, - shortcut_increase_playback_speed_wheel_shift: { - alt: false, - ctrl: false, - shift: true, - keys: {}, - wheel: -1 - }, - shortcut_decrease_playback_speed_wheel_shift: { - alt: false, - ctrl: false, - shift: true, - keys: {}, - wheel: 1 - } - }; // reset 'listening' shortcuts for (var key in listening) delete listening[key]; // extract shortcuts from User Settings and initialize 'listening' for (const [name, keys] of Object.entries(this.storage).filter(v => v[0].startsWith('shortcut_'))) { if (!volumeWheelEnabled && (name in volumeWheelDefaults)) continue; - if (!playbackSpeedWheelEnabled && (name in playbackSpeedWheelDefaults)) continue; + if (!playbackSpeedWheelEnabled && name.startsWith('shortcut_') && name.includes('_playback_speed_wheel_')) continue; if (!keys) continue; // camelCase(name) const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); @@ -159,33 +115,6 @@ ImprovedTube.shortcutsInit = function () { if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; } } - // inject defaults for wheel playback speed if enabled and unset - if (playbackSpeedWheelEnabled) { - for (const [name, keys] of Object.entries(playbackSpeedWheelDefaults)) { - if (this.storage[name]) continue; - const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); - let potentialShortcut = {}; - for (const button of ['alt', 'ctrl', 'shift', 'wheel', 'keys', 'toggle']) { - switch (button) { - case 'alt': - case 'ctrl': - case 'shift': - case 'toggle': - potentialShortcut[button] = keys[button] || false; - break - - case 'wheel': - potentialShortcut[button] = keys[button] || 0; - break - - case 'keys': - potentialShortcut[button] = keys[button] ? new Set(Object.keys(keys[button]).map(s=>Number(s))) : new Set(); - break - } - } - if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; - } - } // initialize 'listeners' only if there are actual shortcuts active if (Object.keys(listening).length) { for (const [name, handler] of Object.entries(this.shortcutsListeners)) { diff --git a/menu/skeleton-parts/shortcuts.js b/menu/skeleton-parts/shortcuts.js index a4b09807f..8e76ecc18 100644 --- a/menu/skeleton-parts/shortcuts.js +++ b/menu/skeleton-parts/shortcuts.js @@ -193,6 +193,28 @@ extension.skeleton.main.layers.section.shortcuts = { } } }, + shortcut_increase_playback_speed_wheel_ctrl: { + component: 'shortcut', + text: 'increasePlaybackSpeed', + value: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: -1 + } + }, + shortcut_decrease_playback_speed_wheel_ctrl: { + component: 'shortcut', + text: 'decreasePlaybackSpeed', + value: { + alt: false, + ctrl: true, + shift: false, + keys: {}, + wheel: 1 + } + }, shortcut_reset_playback_speed: { component: 'shortcut', text: 'reset' From b6d4d057a0f5d44a6739c1086c34c8aa2531a32e Mon Sep 17 00:00:00 2001 From: W0LH Date: Tue, 3 Mar 2026 21:06:10 +0100 Subject: [PATCH 7/8] Fix problem where volume can be change without preset shortcuts Fix problem where volume can be change without preset shortcuts --- .../www.youtube.com/shortcuts.js | 75 +------------------ menu/skeleton-parts/shortcuts.js | 32 +------- 2 files changed, 6 insertions(+), 101 deletions(-) diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index 9fe1bec43..0de094494 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -12,57 +12,13 @@ ImprovedTube.shortcutsInit = function () { listeners = ImprovedTube.input.listeners; const volumeWheelEnabled = this.storage.shortcuts_volume_wheel_ctrl === true; const playbackSpeedWheelEnabled = this.storage.shortcuts_playback_speed_wheel === true; - const volumeWheelDefaults = { - shortcut_increase_volume_wheel_ctrl: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: -1 - }, - shortcut_decrease_volume_wheel_ctrl: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: 1 - }, - shortcut_increase_volume_wheel_alt: { - alt: true, - ctrl: false, - shift: false, - keys: {}, - wheel: -1 - }, - shortcut_decrease_volume_wheel_alt: { - alt: true, - ctrl: false, - shift: false, - keys: {}, - wheel: 1 - }, - shortcut_increase_volume_wheel_shift: { - alt: false, - ctrl: false, - shift: true, - keys: {}, - wheel: -1 - }, - shortcut_decrease_volume_wheel_shift: { - alt: false, - ctrl: false, - shift: true, - keys: {}, - wheel: 1 - } - }; // reset 'listening' shortcuts for (var key in listening) delete listening[key]; // extract shortcuts from User Settings and initialize 'listening' for (const [name, keys] of Object.entries(this.storage).filter(v => v[0].startsWith('shortcut_'))) { - if (!volumeWheelEnabled && (name in volumeWheelDefaults)) continue; - if (!playbackSpeedWheelEnabled && name.startsWith('shortcut_') && name.includes('_playback_speed_wheel_')) continue; + if (!volumeWheelEnabled && name.includes('_volume_wheel_')) continue; + if (!playbackSpeedWheelEnabled && name.includes('_playback_speed_wheel_')) continue; if (!keys) continue; // camelCase(name) const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); @@ -88,33 +44,6 @@ ImprovedTube.shortcutsInit = function () { } if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; } - // inject defaults for Ctrl+wheel volume if enabled and unset - if (volumeWheelEnabled) { - for (const [name, keys] of Object.entries(volumeWheelDefaults)) { - if (this.storage[name]) continue; - const camelName = name.replace(/_(.)/g, (m, l) => l.toUpperCase()); - let potentialShortcut = {}; - for (const button of ['alt', 'ctrl', 'shift', 'wheel', 'keys', 'toggle']) { - switch (button) { - case 'alt': - case 'ctrl': - case 'shift': - case 'toggle': - potentialShortcut[button] = keys[button] || false; - break - - case 'wheel': - potentialShortcut[button] = keys[button] || 0; - break - - case 'keys': - potentialShortcut[button] = keys[button] ? new Set(Object.keys(keys[button]).map(s=>Number(s))) : new Set(); - break - } - } - if (potentialShortcut['keys'].size || potentialShortcut['wheel']) listening[camelName] = potentialShortcut; - } - } // initialize 'listeners' only if there are actual shortcuts active if (Object.keys(listening).length) { for (const [name, handler] of Object.entries(this.shortcutsListeners)) { diff --git a/menu/skeleton-parts/shortcuts.js b/menu/skeleton-parts/shortcuts.js index 8e76ecc18..34ff0997f 100644 --- a/menu/skeleton-parts/shortcuts.js +++ b/menu/skeleton-parts/shortcuts.js @@ -120,24 +120,12 @@ extension.skeleton.main.layers.section.shortcuts = { shortcut_increase_volume_wheel_ctrl: { component: 'shortcut', text: 'increaseVolume', - value: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: -1 - } + value: {} }, shortcut_decrease_volume_wheel_ctrl: { component: 'shortcut', text: 'decreaseVolume', - value: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: 1 - } + value: {} }, } } @@ -196,24 +184,12 @@ extension.skeleton.main.layers.section.shortcuts = { shortcut_increase_playback_speed_wheel_ctrl: { component: 'shortcut', text: 'increasePlaybackSpeed', - value: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: -1 - } + value: {} }, shortcut_decrease_playback_speed_wheel_ctrl: { component: 'shortcut', text: 'decreasePlaybackSpeed', - value: { - alt: false, - ctrl: true, - shift: false, - keys: {}, - wheel: 1 - } + value: {} }, shortcut_reset_playback_speed: { component: 'shortcut', From 7f1298c669949ca669119ee450e0dbb806177204 Mon Sep 17 00:00:00 2001 From: W0LH Date: Tue, 3 Mar 2026 21:26:56 +0100 Subject: [PATCH 8/8] I delete the idea of displaying the same YouTube sound icons when I change the volume I delete the idea of displaying the same YouTube sound icons when I change the volume --- js&css/web-accessible/functions.js | 60 ++----------------- .../www.youtube.com/shortcuts.js | 6 +- 2 files changed, 5 insertions(+), 61 deletions(-) diff --git a/js&css/web-accessible/functions.js b/js&css/web-accessible/functions.js index 0a77f8e39..08534e696 100644 --- a/js&css/web-accessible/functions.js +++ b/js&css/web-accessible/functions.js @@ -752,64 +752,12 @@ ImprovedTube.showStatus = function (value) { this.elements.status.id = 'it-status'; } - if (typeof value === 'object' && value?.type === 'volume') { - const player = this.elements.player; - const bezel = player?.querySelector('.ytp-bezel'); - if (bezel) { - let bezelIcon = bezel.querySelector('.ytp-bezel-icon'); - if (!bezelIcon) { - bezelIcon = document.createElement('div'); - bezelIcon.className = 'ytp-bezel-icon'; - bezel.appendChild(bezelIcon); - } - - const iconSource = player?.querySelector('.ytp-volume-panel .ytp-volume-icon') - || player?.querySelector('.ytp-mute-button'); - if (iconSource) { - const svg = iconSource.querySelector('svg')?.cloneNode(true) || iconSource.cloneNode(true); - while (bezelIcon.firstChild) bezelIcon.firstChild.remove(); - bezelIcon.appendChild(svg); - } - - const bezelText = bezel.querySelector('.ytp-bezel-text'); - if (bezelText) { - const volumeValue = typeof value.value === 'number' ? value.value : (player?.getVolume ? player.getVolume() : 0); - bezelText.textContent = `${Math.round(volumeValue)}%`; - } - - bezel.classList.add('ytp-bezel-showing'); - clearTimeout(ImprovedTube.status_timer); - ImprovedTube.status_timer = setTimeout(function () { - bezel.classList.remove('ytp-bezel-showing'); - }, 500); - return; - } - - this.elements.status.textContent = ''; - - const iconSource = player?.querySelector('.ytp-volume-panel .ytp-volume-icon') - || player?.querySelector('.ytp-mute-button'); - let iconElement; - - if (iconSource) { - iconElement = iconSource.cloneNode(true); - iconElement.removeAttribute('id'); - iconElement.removeAttribute('aria-label'); - iconElement.removeAttribute('title'); - } else { - iconElement = document.createElement('div'); - iconElement.textContent = (value.muted || value.value === 0) ? '🔇' : (value.value <= 50 ? '🔈' : '🔊'); - } - - this.elements.status.appendChild(iconElement); - } else { - if (typeof value === 'number') { - value = value.toFixed(2); - } - - this.elements.status.textContent = value; + if (typeof value === 'number') { + value = value.toFixed(2); } + this.elements.status.textContent = value; + if (ImprovedTube.status_timer) { clearTimeout(ImprovedTube.status_timer); } diff --git a/js&css/web-accessible/www.youtube.com/shortcuts.js b/js&css/web-accessible/www.youtube.com/shortcuts.js index 0de094494..073ff5975 100644 --- a/js&css/web-accessible/www.youtube.com/shortcuts.js +++ b/js&css/web-accessible/www.youtube.com/shortcuts.js @@ -360,11 +360,7 @@ ImprovedTube.shortcutIncreaseVolume = function (decrease) { sessionStorage['yt-player-volume'] = localStorage['yt-player-volume']; - this.showStatus({ - type: 'volume', - value: player.getVolume(), - muted: player.isMuted ? player.isMuted() : player.getVolume() === 0 - }); + this.showStatus(player.getVolume()); }; /*------------------------------------------------------------------------------ 4.7.14 DECREASE VOLUME