Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save Explosion-Scratch/95f549e2eb92342b39cce9fb76437201 to your computer and use it in GitHub Desktop.
Save Explosion-Scratch/95f549e2eb92342b39cce9fb76437201 to your computer and use it in GitHub Desktop.
// ==UserScript==
// @name YouTube Inline Full Screen
// @namespace mailto:explosionscratch@gmail.com
// @version 1.0
// @description Toggle inline full screen on YouTube with Shift + F
// @match https://www.youtube.com/*
// @grant none
// ==/UserScript==
(function() {
'use strict';
let isFullMode = false;
let controlsCreated = false;
let watchContainer = null;
let mediaQueryContainer = null;
let resizeEvent = null;
let initialTheatreMode = false;
let isTheatreMode = false;
// Inject CSS
const style = document.createElement('style');
style.textContent = `
body.updated-full-mode {
overflow-y: hidden !important;
}
body.updated-full-mode .html5-video-container {
background-color: black;
}
body.updated-full-mode #masthead-container {
opacity: 0 !important;
}
.ytp-chrome-bottom {
padding-top: 0px !important;
}
.ytp-upnext {
top: 0px !important;
}
.svg-container {
margin: 9px;
}
.ad-container:not(.ad-overlay) {
top: 0px;
}
.ytp-browser-button {
display: inline-block !important;
}
body.updated-full-mode ytd-app ytd-watch #player.ytd-watch,
body.updated-full-mode ytd-app ytd-watch-grid #player-full-bleed-container.ytd-watch-grid,
body.updated-full-mode #full-bleed-container {
height: 100vh !important;
max-height: 100vh !important;
}
body.updated-full-mode ytd-page-manager,
body.updated-full-mode ytd-watch-flexy {
margin-top: 0 !important;
}
`;
document.head.appendChild(style);
function onPageReady() {
if (watchContainer) {
mediaQueryContainer = watchContainer.querySelector("iron-media-query[query='min-width: 882px']");
}
pageReadyInterval();
document.body.addEventListener("yt-navigate-finish", function () {
pageReadyInterval();
var loop = setInterval(function() {
if (isPageVideo() && !controlsCreated) {
pageReadyInterval();
} else if (controlsCreated) {
clearInterval(loop);
}
}, 500);
});
}
function pageReadyInterval() {
var video = document.querySelector("video[src^='blob:https://www.youtube.com'");
if (isPageVideo() && video && !controlsCreated) {
createControl();
watchContainer = document.querySelector("ytd-watch") || document.querySelector("ytd-watch-flexy");
mediaQueryContainer = null;
if (watchContainer) {
mediaQueryContainer = watchContainer.querySelector("iron-media-query[query='min-width: 882px']");
}
} else if (!isPageVideo() && isFullMode) {
leaveFullBrowser();
}
}
function toggleFullBrowser() {
if (isFullMode) {
leaveFullBrowser();
} else {
enterFullBrowser();
}
}
function enterFullBrowser() {
var original = document.getElementById("original-size");
var newControl = document.getElementById("full-size");
var watchContainer = document.querySelector("ytd-watch-grid") || document.querySelector("ytd-watch") || document.querySelector("ytd-watch-flexy") || document.querySelector("#player");
resizeEvent = window.matchMedia("(max-width: 882px)");
resizeEvent.addListener(handleMediaQuery);
isFullMode = true;
isTheatreMode = watchContainer.hasAttribute("theater");
initialTheatreMode = isTheatreMode;
if (!isTheatreMode) {
original.click();
isTheatreMode = true;
}
document.body.classList.add("updated-full-mode");
original.style.display = "none";
newControl.style.display = "inline-block";
newControl.innerHTML = "<svg width=\"20\" height=\"28\" viewBox=\"0 0 1792 1792\" xmlns=\"http://www.w3.org/2000/svg\" class=\"svg-container\"><path d=\"M896 960v448q0 26-19 45t-45 19-45-19l-144-144-332 332q-10 10-23 10t-23-10l-114-114q-10-10-10-23t10-23l332-332-144-144q-19-19-19-45t19-45 45-19h448q26 0 45 19t19 45zm755-672q0 13-10 23l-332 332 144 144q19 19 19 45t-19 45-45 19h-448q-26 0-45-19t-19-45v-448q0-26 19-45t45-19 45 19l144 144 332-332q10-10 23-10t23 10l114 114q10 10 10 23z\" style=\"fill: white;\"></path></svg>";
handleMediaQuery(resizeEvent);
window.dispatchEvent(new Event("resize"));
}
function leaveFullBrowser() {
var original = document.getElementById("original-size");
var newControl = document.getElementById("full-size");
isFullMode = false;
document.body.classList.remove("updated-full-mode");
original.style.display = "inline-block";
newControl.style.display = "inline-block";
newControl.innerHTML = "<svg width=\"20\" height=\"28\" viewBox=\"0 0 1792 1792\" xmlns=\"http://www.w3.org/2000/svg\" class=\"svg-container\"><path d=\"M883 1056q0 13-10 23l-332 332 144 144q19 19 19 45t-19 45-45 19h-448q-26 0-45-19t-19-45v-448q0-26 19-45t45-19 45 19l144 144 332-332q10-10 23-10t23 10l114 114q10 10 10 23zm781-864v448q0 26-19 45t-45 19-45-19l-144-144-332 332q-10 10-23 10t-23-10l-114-114q-10-10-10-23t10-23l332-332-144-144q-19-19-19-45t19-45 45-19h448q26 0 45 19t19 45z\" style=\"fill: white;\"></path></svg>";
if (!initialTheatreMode) {
original.click();
}
if (mediaQueryContainer) {
mediaQueryContainer.setAttribute("query", "min-width: 882px");
}
resizeEvent.removeListener(handleMediaQuery);
window.dispatchEvent(new Event("resize"));
}
function createControl() {
var original = document.querySelector("#movie_player button.ytp-settings-button");
var theatre = document.getElementsByClassName("ytp-size-button")[0];
var fullScreenButton = document.getElementsByClassName("ytp-fullscreen-button")[0];
var miniplayerButton = document.getElementsByClassName("ytp-miniplayer-button")[0];
var copy = original.cloneNode(true);
original.id = "settings-cog";
theatre.id = "original-size";
copy.id = "full-size";
var controls = document.getElementsByClassName("ytp-right-controls")[0];
var newControl = controls.insertBefore(copy, original);
newControl.title = `Full Browser Mode (Shift + F)`;
newControl.className = theatre.className + " ytp-button";
newControl.innerHTML = "<svg width=\"20\" height=\"28\" viewBox=\"0 0 1792 1792\" xmlns=\"http://www.w3.org/2000/svg\" class=\"svg-container\"><path d=\"M883 1056q0 13-10 23l-332 332 144 144q19 19 19 45t-19 45-45 19h-448q-26 0-45-19t-19-45v-448q0-26 19-45t45-19 45 19l144 144 332-332q10-10 23-10t23 10l114 114q10 10 10 23zm781-864v448q0 26-19 45t-45 19-45-19l-144-144-332 332q-10 10-23 10t-23-10l-114-114q-10-10-10-23t10-23l332-332-144-144q-19-19-19-45t19-45 45-19h448q26 0 45 19t19 45z\" style=\"fill: white;\"></path></svg>";
newControl.addEventListener("click", toggleFullBrowser);
document.addEventListener("fullscreenchange", function(e) {
toggleIcon();
});
document.body.addEventListener("keydown", function(e) {
if (e.key === 'Escape' && isFullMode && isPageVideo()) {
leaveFullBrowser();
}
if (e.target.nodeName == "TEXTAREA" || e.target.nodeName == "INPUT" || e.target.nodeName == "YT-FORMATTED-STRING" || (e.target.nodeName == "DIV" && e.target.className == "style-scope yt-formatted-string")) {
return;
}
if (isPageVideo() && e.shiftKey && e.key === 'F') {
toggleFullBrowser();
}
});
fullScreenButton.addEventListener("click", toggleIcon);
miniplayerButton.addEventListener("click", leaveFullBrowser);
controlsCreated = true;
}
function handleMediaQuery(mq) {
var original = document.getElementById("original-size");
if (mq.matches && mediaQueryContainer) {
mediaQueryContainer.setAttribute("query", "max-width: 882px");
original.style.display = "none";
} else if (mediaQueryContainer) {
mediaQueryContainer.setAttribute("query", "min-width: 882px");
}
}
function toggleIcon() {
var original = document.getElementById("original-size");
var newControl = document.getElementById("full-size");
if (!isFullScreenActive()) {
newControl.style.display = "inline-block";
if (isFullMode) {
original.style.display = "none";
}
} else {
newControl.style.display = "none";
}
}
function isPageVideo() {
return location.pathname.includes("/watch") || location.pathname.includes("/live/");
}
function isFullScreenActive() {
var el = document.getElementsByClassName("ytp-fullscreen-button")[0];
if (el) {
return el.title == "Exit full screen (f)";
} else {
return false;
}
}
onPageReady();
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment