content.ts 9.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150
  1. export default defineContentScript({
  2. matches: ['<all_urls>'],
  3. main() {
  4. console.log('Slacking mode initialized. Press Alt+M to toggle.');
  5. // Create the overlay element
  6. const overlay = document.createElement('div');
  7. overlay.id = 'slacking-blur-overlay';
  8. // Create a fake GitHub UI inside the overlay
  9. overlay.innerHTML = `
  10. <div style="display: flex; flex-direction: column; width: 100vw; height: 100vh; background-color: #0d1117; color: #c9d1d9; font-family: -apple-system,BlinkMacSystemFont,Segoe UI,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji;">
  11. <!-- Fake Header -->
  12. <div style="height: 64px; background-color: #161b22; border-bottom: 1px solid #21262d; display: flex; align-items: center; padding: 0 32px; gap: 16px;">
  13. <div style="color: #fff;">
  14. <svg height="32" viewBox="0 0 16 16" version="1.1" width="32" fill="currentColor"><path d="M8 0C3.58 0 0 3.58 0 8c0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38 0-.19-.01-.82-.01-1.49-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38A8.013 8.013 0 0016 8c0-4.42-3.58-8-8-8z"></path></svg>
  15. </div>
  16. <div style="display: flex; gap: 16px; font-size: 14px; font-weight: 600; margin-left: 8px;">
  17. <span style="color: #fff;">Pull requests</span>
  18. <span style="color: #fff;">Issues</span>
  19. <span style="color: #fff;">Marketplace</span>
  20. <span style="color: #fff;">Explore</span>
  21. </div>
  22. </div>
  23. <!-- Fake Main Layout -->
  24. <div style="display: flex; flex: 1; overflow: hidden;">
  25. <!-- Fake Sidebar -->
  26. <div style="width: 296px; border-right: 1px solid #21262d; padding: 24px 16px; display: flex; flex-direction: column; gap: 16px;">
  27. <div style="font-size: 14px; font-weight: 600;">Top Repositories</div>
  28. <div style="height: 32px; background-color: #21262d; border-radius: 6px; border: 1px solid #30363d; display: flex; align-items: center; padding: 0 12px; font-size: 14px; color: #8b949e;">Find a repository...</div>
  29. <div style="display: flex; flex-direction: column; gap: 12px; margin-top: 8px;">
  30. <div style="font-size: 14px; color: #58a6ff; font-weight: 600; display: flex; align-items: center; gap: 8px;"><span style="color: #8b949e;">🗄️</span> facebook / react</div>
  31. <div style="font-size: 14px; color: #58a6ff; font-weight: 600; display: flex; align-items: center; gap: 8px;"><span style="color: #8b949e;">🗄️</span> vuejs / core</div>
  32. <div style="font-size: 14px; color: #58a6ff; font-weight: 600; display: flex; align-items: center; gap: 8px;"><span style="color: #8b949e;">🗄️</span> torvalds / linux</div>
  33. <div style="font-size: 14px; color: #58a6ff; font-weight: 600; display: flex; align-items: center; gap: 8px;"><span style="color: #8b949e;">🗄️</span> golang / go</div>
  34. </div>
  35. </div>
  36. <!-- Fake Content Area -->
  37. <div style="flex: 1; padding: 24px 32px; display: flex; flex-direction: column; gap: 16px;">
  38. <div style="display: flex; justify-content: space-between; align-items: center;">
  39. <div style="font-size: 20px; font-weight: 600; color: #58a6ff;">hardworking / productivity-tool</div>
  40. <div style="display: flex; gap: 8px;">
  41. <div style="padding: 4px 12px; background-color: #21262d; border: 1px solid #30363d; border-radius: 6px; font-size: 12px; font-weight: 600; color: #c9d1d9;">Watch</div>
  42. <div style="padding: 4px 12px; background-color: #21262d; border: 1px solid #30363d; border-radius: 6px; font-size: 12px; font-weight: 600; color: #c9d1d9;">Fork</div>
  43. <div style="padding: 4px 12px; background-color: #21262d; border: 1px solid #30363d; border-radius: 6px; font-size: 12px; font-weight: 600; color: #c9d1d9;">Star</div>
  44. </div>
  45. </div>
  46. <!-- Fake File List -->
  47. <div style="border: 1px solid #30363d; border-radius: 6px; background-color: #0d1117; margin-top: 16px;">
  48. <div style="padding: 16px; background-color: #161b22; border-bottom: 1px solid #30363d; font-size: 14px; font-weight: 600; border-radius: 6px 6px 0 0; display: flex; gap: 12px; align-items: center;">
  49. <img src="https://github.com/fluidicon.png" style="width: 24px; height: 24px; border-radius: 50%;" />
  50. <span>developer</span>
  51. <span style="color: #8b949e; font-weight: normal;">Update core logic</span>
  52. </div>
  53. <div style="padding: 16px; display: flex; flex-direction: column; gap: 16px; font-size: 14px;">
  54. <div style="display: flex; gap: 16px;"><span style="color: #54aeff;">📁</span> <span style="color: #c9d1d9;">src</span> <span style="color: #8b949e; margin-left: auto;">feat: optimize rendering</span></div>
  55. <div style="border-bottom: 1px solid #21262d;"></div>
  56. <div style="display: flex; gap: 16px;"><span style="color: #54aeff;">📁</span> <span style="color: #c9d1d9;">components</span> <span style="color: #8b949e; margin-left: auto;">refactor: extract mask logic</span></div>
  57. <div style="border-bottom: 1px solid #21262d;"></div>
  58. <div style="display: flex; gap: 16px;"><span style="color: #8b949e;">📄</span> <span style="color: #c9d1d9;">index.html</span> <span style="color: #8b949e; margin-left: auto;">fix typo in header</span></div>
  59. <div style="border-bottom: 1px solid #21262d;"></div>
  60. <div style="display: flex; gap: 16px;"><span style="color: #8b949e;">📄</span> <span style="color: #c9d1d9;">package.json</span> <span style="color: #8b949e; margin-left: auto;">chore: bump dependencies</span></div>
  61. <div style="border-bottom: 1px solid #21262d;"></div>
  62. <div style="display: flex; gap: 16px;"><span style="color: #8b949e;">📄</span> <span style="color: #c9d1d9;">README.md</span> <span style="color: #8b949e; margin-left: auto;">docs: add slacking mode manual</span></div>
  63. </div>
  64. </div>
  65. <!-- Fake Readme -->
  66. <div style="border: 1px solid #30363d; border-radius: 6px; padding: 24px; margin-top: 16px;">
  67. <h2 style="margin-top: 0; border-bottom: 1px solid #21262d; padding-bottom: 8px;">README.md</h2>
  68. <p style="color: #8b949e; line-height: 1.5; font-size: 14px;">This project focuses on extreme productivity and code optimization. Make sure you read the contribution guidelines before submitting a PR.</p>
  69. <pre style="background-color: #161b22; padding: 16px; border-radius: 6px; color: #e6edf3; font-family: monospace; font-size: 14px; line-height: 1.5;"><code>npm install<br>npm run start:prod</code></pre>
  70. </div>
  71. </div>
  72. </div>
  73. </div>
  74. `;
  75. // Apply styling
  76. Object.assign(overlay.style, {
  77. position: 'fixed',
  78. top: '0',
  79. left: '0',
  80. width: '100vw',
  81. height: '100vh',
  82. zIndex: '2147483647', // Max z-index
  83. pointerEvents: 'none', // Allow clicks to pass through
  84. // Re-enable mask-image to punch a hole through the GitHub UI, with a larger radius
  85. maskImage: 'radial-gradient(circle at var(--mouse-x, -100px) var(--mouse-y, -100px), transparent 120px, black 240px)',
  86. WebkitMaskImage: 'radial-gradient(circle at var(--mouse-x, -100px) var(--mouse-y, -100px), transparent 120px, black 240px)',
  87. willChange: 'mask-image, -webkit-mask-image', // Hardware acceleration hint
  88. display: 'block' // Visible by default
  89. });
  90. // Append to body
  91. document.body.appendChild(overlay);
  92. let isEnabled = true;
  93. // Toggle on Alt+M (Option+M on Mac)
  94. document.addEventListener('keydown', (e) => {
  95. // Use e.code instead of e.key because Option+M on Mac produces "µ" instead of "m"
  96. if (e.altKey && e.code === 'KeyM') {
  97. isEnabled = !isEnabled;
  98. overlay.style.display = isEnabled ? 'block' : 'none';
  99. console.log(`Slacking mode ${isEnabled ? 'ON' : 'OFF'}`);
  100. }
  101. });
  102. // Optimization: Use requestAnimationFrame to avoid layout thrashing on mousemove
  103. let ticking = false;
  104. let mouseX = -100;
  105. let mouseY = -100;
  106. const updateMask = () => {
  107. overlay.style.setProperty('--mouse-x', `${mouseX}px`);
  108. overlay.style.setProperty('--mouse-y', `${mouseY}px`);
  109. ticking = false;
  110. };
  111. // Track mouse movement
  112. document.addEventListener('mousemove', (e) => {
  113. if (!isEnabled) return;
  114. mouseX = e.clientX;
  115. mouseY = e.clientY;
  116. if (!ticking) {
  117. requestAnimationFrame(updateMask);
  118. ticking = true;
  119. }
  120. });
  121. // Hide the hole when the mouse leaves the window
  122. document.addEventListener('mouseleave', () => {
  123. if (!isEnabled) return;
  124. // Move the clear hole far outside the viewport to make the whole page opaque
  125. mouseX = -1000;
  126. mouseY = -1000;
  127. if (!ticking) {
  128. requestAnimationFrame(updateMask);
  129. ticking = true;
  130. }
  131. });
  132. },
  133. });