Skip to content

Instantly share code, notes, and snippets.

@ryanml
Last active November 3, 2018 01:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save ryanml/aeda735a5ddce136509ef8eacfc349cf to your computer and use it in GitHub Desktop.
Save ryanml/aeda735a5ddce136509ef8eacfc349cf to your computer and use it in GitHub Desktop.
// ==UserScript==
// @name Video Tipper
// @namespace https://github.com/ryanml
// @version 0.1
// @description Prompts user to tip Youtuber in BAT.
// @author ryanml
// @match https://www.youtube.com/*
// @grant none
// ==/UserScript==
(function() {
'use strict';
var globals = {
retries: 0,
maxRetries: 25,
currentUrl: '',
videoTipper: null,
appUrl: 'https://localhost:3000',
recipient: '0xb54dfd4888988af0fbce195a28ca9d2c8419fda9'
};
const ensureVideoTipper = () => {
globals.videoTipper = setInterval(() => {
if (globals.retries === globals.maxRetries) {
clearInterval(globals.videoTipper);
globals.retries = 0;
return;
}
const likeButton = document.querySelector('#top-level-buttons yt-icon-button');
if (likeButton) {
likeButton.addEventListener('click', onLikeVideo);
clearInterval(globals.videoTipper);
globals.retries = 0;
} else {
globals.retries = globals.retries++;
}
}, 100);
}
const buildUrl = (params) => {
let index = 0;
let queryString = '';
for (let key in params) {
const char = index === 0 ? '?' : '&';
queryString += char + key + '=' + params[key];
index++;
}
return globals.appUrl + encodeURI(queryString);
}
const getRequestUrl = () => {
const faviconUrl = document.querySelector('#top-row #img').src;
const publisherName = document.querySelector('#owner-container a').textContent.trim();
const videoTitle = document.querySelector('.title yt-formatted-string').textContent.trim();
const queryParams = {
publisher: publisherName,
faviconurl: faviconUrl,
videotitle: videoTitle,
address: globals.recipient
}
return buildUrl(queryParams);
}
const onLikeVideo = (e) => {
e.preventDefault();
e.stopPropagation();
buildFrameView(e.target);
}
const buildFrameView = (button) => {
const buttonRect = button.getBoundingClientRect();
const pluginClose = document.createElement('span');
const pluginContainer = document.createElement('div');
const pluginIframe = document.createElement('iframe');
pluginClose.innerHTML = 'X';
pluginIframe.id = 'bg-iframe';
pluginIframe.src = getRequestUrl();
/* Close Icon Styling */
const closeTop = (buttonRect.top - 500) + 'px';
const closeLeft = (buttonRect.left + 250) + 'px';
pluginClose.style = 'font-size:15px;z-index:9999;color:gray;width:15px;height:15px;cursor:pointer;position:fixed;top:' + closeTop + ';left:' + closeLeft + ';';
/* Iframe Styling */
const iframeTop = (buttonRect.top - 520) + 'px';
const iframeLeft = (buttonRect.left - 100) + 'px';
pluginIframe.style = 'z-index:9999;width:375px;height:625px;position:fixed;border:1px solid #eee;top:' + iframeTop + ';left:' + iframeLeft + ';';
pluginClose.addEventListener('click', function(e) {
pluginContainer.parentElement.removeChild(pluginContainer);
});
pluginContainer.appendChild(pluginIframe);
pluginContainer.appendChild(pluginClose);
document.body.appendChild(pluginContainer);
}
globals.currentUrl = window.location.href;
setInterval(() => {
if (window.location.href !== globals.currentUrl) {
const existingIframe = document.querySelector('#bg-iframe');
if (existingIframe) existingIframe.parentElement.removeChild(existingIframe);
globals.currentUrl = window.location.href;
globals.retries = 0;
if (globals.videoTipper) clearInterval(globals.videoTipper);
ensureVideoTipper();
}
}, 500);
window.onload = ensureVideoTipper;
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment