Microsoft Loop Full Width (Single Element)

Makes Microsoft Loop use full screen width by updating a single element's CSS variable, and restores the original value via a toggle button with a fixed, translucent design.

  1. // ==UserScript==
  2. // @name Microsoft Loop Full Width (Single Element)
  3. // @namespace http://tampermonkey.net/
  4. // @version 2025-02-17
  5. // @description Makes Microsoft Loop use full screen width by updating a single element's CSS variable, and restores the original value via a toggle button with a fixed, translucent design.
  6. // @author Salo
  7. // @match https://loop.cloud.microsoft/p/*
  8. // @icon https://www.google.com/s2/favicons?sz=64&domain=cloud.microsoft
  9. // @grant none
  10. // @license MIT
  11. // ==/UserScript==
  12.  
  13. (function() {
  14. 'use strict';
  15.  
  16. let isActive = true; // Global flag for feature status
  17.  
  18. // Store the original value from the target element.
  19. let originalValue = null;
  20.  
  21. // Function to find the target element: the first element whose inline style contains "--max-canvas-content-width"
  22. function findTargetElement() {
  23. return document.querySelector('div[style*="--max-canvas-content-width"]');
  24. }
  25.  
  26. // Update the target element's property to the current screen width
  27. function updateTargetElement() {
  28. if (!isActive) return;
  29.  
  30. const element = findTargetElement();
  31. if (element) {
  32. // Store the original value only once
  33. if (originalValue === null) {
  34. // If there is no value before, keep it as null so we know to remove it later.
  35. originalValue = element.style.getPropertyValue('--max-canvas-content-width') || null;
  36. }
  37. const screenWidth = window.innerWidth;
  38. element.style.setProperty('--max-canvas-content-width', screenWidth + 'px');
  39. console.log('Updated target element with --max-canvas-content-width:', screenWidth + 'px');
  40. } else {
  41. console.warn('Target element not found.');
  42. }
  43. }
  44.  
  45. // Restore the target element's original CSS property value
  46. function restoreTargetElement() {
  47. const element = findTargetElement();
  48. if (element) {
  49. if (originalValue === null) {
  50. element.style.removeProperty('--max-canvas-content-width');
  51. console.log('Removed --max-canvas-content-width property from target element.');
  52. } else {
  53. element.style.setProperty('--max-canvas-content-width', originalValue);
  54. console.log('Restored target element with original --max-canvas-content-width:', originalValue);
  55. }
  56. }
  57. }
  58.  
  59. // Set up MutationObserver to update the target element if it is added later
  60. const observer = new MutationObserver(mutations => {
  61. if (!isActive) return;
  62. // Simply try to update the target element, if it's in the DOM.
  63. updateTargetElement();
  64. });
  65.  
  66. observer.observe(document.body, { childList: true, subtree: true });
  67.  
  68. // Create a floating toggle button with a fixed size and translucent style.
  69. function createToggleButton() {
  70. const btn = document.createElement('button');
  71. btn.id = 'toggleCanvasWidthUpdater';
  72. // Start with the "minimize" icon (🗕) for active functionality.
  73. btn.innerHTML = '🗕';
  74. Object.assign(btn.style, {
  75. position: 'fixed',
  76. bottom: '15px',
  77. right: '20px',
  78. zIndex: '9999',
  79. width: '25px',
  80. height: '25px',
  81. // Translucent blue background using RGBA (opacity 0.7)
  82. backgroundColor: 'rgba(0, 120, 215, 0.5)',
  83. color: '#fff',
  84. border: 'none',
  85. borderRadius: '7px',
  86. cursor: 'pointer',
  87. fontSize: '12px', // Increase icon size for visibility
  88. display: 'flex',
  89. alignItems: 'center',
  90. justifyContent: 'center',
  91. padding: '0',
  92. userSelect: 'none'
  93. });
  94. btn.addEventListener('click', () => {
  95. isActive = !isActive;
  96. // Toggle between the icons – 🗕 (active) and ⤢ (disabled)
  97. btn.innerHTML = isActive ? '🗕' : '⤢';
  98. console.log('Canvas update functionality is now', isActive ? 'enabled' : 'disabled');
  99. if (isActive) {
  100. updateTargetElement();
  101. } else {
  102. restoreTargetElement();
  103. }
  104. });
  105. document.body.appendChild(btn);
  106. }
  107.  
  108. // Update the target element on load and window resize
  109. window.addEventListener('load', () => {
  110. updateTargetElement();
  111. createToggleButton();
  112. });
  113. window.addEventListener('resize', updateTargetElement);
  114.  
  115. })();