Last active
May 13, 2025 22:58
-
-
Save kylebarlow/2b09877d0372c8499def7d34c2f21daf to your computer and use it in GitHub Desktop.
Greasemonkey/tampermonkety user script to highlight your league and team's taken players when viewing fangraph pages
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// ==UserScript== | |
// @name FanGraphs Script for Yahoo Leagues | |
// @include https://fantasy.fangraphs.com/* | |
// @include https://www.fangraphs.com/* | |
// @version 1.2 | |
// @grant GM.xmlHttpRequest | |
// ==/UserScript== | |
// Created 4/1/2021 u/jackries | |
// Updated May 2025 by KB | |
// Wait to run code until page finished loading as in https://stackoverflow.com/questions/12897446/userscript-to-wait-for-page-to-load-before-executing-code-techniques | |
var observer = new MutationObserver(resetTimer); | |
var timer = setTimeout(action, 2000, observer); // wait for the page to stay still for 2 seconds | |
observer.observe(document, {childList: true, subtree: true}); | |
// reset timer every time something changes | |
function resetTimer(changes, observer) { | |
clearTimeout(timer); | |
timer = setTimeout(action, 3000, observer); | |
} | |
function action(observer) { | |
// observer.disconnect(); | |
// Note: Your league data must be publicly viewable | |
// Update this URL to your league's starting rosters page in Yahoo! | |
var ownedPlayersURL = "https://baseball.fantasysports.yahoo.com/b1/XXXXX/startingrosters"; | |
// Update this URL to your team's page in Yahoo! | |
var myPlayers = "https://baseball.fantasysports.yahoo.com/b1/XXXXX/X"; | |
var players = []; | |
var players2 = []; | |
// Comprehensive accent map for baseball player names | |
var accent_map = { | |
// Spanish accents | |
'á':'a', 'é':'e', 'í':'i', 'ó':'o', 'ú':'u', 'ü':'u', 'ñ':'n', | |
'Á':'A', 'É':'E', 'Í':'I', 'Ó':'O', 'Ú':'U', 'Ü':'U', 'Ñ':'N', | |
// French accents | |
'à':'a', 'è':'e', 'ì':'i', 'ò':'o', 'ù':'u', | |
'â':'a', 'ê':'e', 'î':'i', 'ô':'o', 'û':'u', | |
'ë':'e', 'ï':'i', 'ç':'c', | |
'À':'A', 'È':'E', 'Ì':'I', 'Ò':'O', 'Ù':'U', | |
'Â':'A', 'Ê':'E', 'Î':'I', 'Ô':'O', 'Û':'U', | |
'Ë':'E', 'Ï':'I', 'Ç':'C', | |
// Other European accents | |
'ä':'a', 'ö':'o', 'ß':'s', | |
'Ä':'A', 'Ö':'O', | |
// Latin American player names | |
'ã':'a', 'õ':'o', | |
'Ã':'A', 'Õ':'O', | |
// Japanese characters that might appear in romanized names | |
'ō':'o', 'ū':'u', 'ī':'i', | |
'Ō':'O', 'Ū':'U', 'Ī':'I', | |
// Korean characters that might appear in romanized names | |
'ŭ':'u', | |
'Ŭ':'U' | |
}; | |
GetPlayers(); | |
// Function to get players from Yahoo! Rosters page for the league | |
function GetPlayers() | |
{ | |
GM.xmlHttpRequest( | |
{ | |
method: 'GET', | |
url: ownedPlayersURL, | |
onload: function( responseDetails ) | |
{ | |
var responseXML = new DOMParser().parseFromString(responseDetails.responseText,"text/html"); | |
buildPlayersArray(responseXML); | |
showValues(); | |
}, | |
}); | |
} | |
// Function to build an array of taken player data from the owned page | |
function buildPlayersArray(playersXML) | |
{ | |
var ahrefsYahoo = playersXML.getElementsByTagName("a"); | |
var yahooMatch = /.*sports\.yahoo\.com\/mlb\/players\/(\d*)$/; | |
var j = 0; | |
for (var i = 0; i < ahrefsYahoo.length; i++) | |
{ | |
var resultID = ahrefsYahoo[i].href.match(yahooMatch); | |
if (resultID !== null) | |
{ | |
players[j] = {}; | |
players[j].playerName = ahrefsYahoo[i].innerHTML; | |
players[j].normalizedName = accent_fold(ahrefsYahoo[i].innerHTML); | |
console.log("Yahoo", ahrefsYahoo[i].innerHTML, players[j].normalizedName); | |
j++; | |
} | |
} | |
} | |
// Function to match taken Yahoo! players and mark as owned in FanGraphs | |
function showValues() | |
{ | |
var fanMatch = /.*fangraphs\.com\/*/; | |
var stat = []; | |
var resultName = ""; | |
var resultIDFan = ""; | |
for (var i = 0; i < ahrefs.length; i++) | |
{ | |
resultName = ahrefs[i].innerHTML; | |
resultIDFan = ahrefs[i].href.match(fanMatch); | |
if (resultIDFan !== null) | |
{ | |
var normalizedFanName = accent_fold(resultName); | |
for (var j = 0; j < (players.length); j++) | |
{ | |
// Compare normalized names to handle accents | |
if (normalizedFanName === players[j].normalizedName || | |
normalizedFanName === players[j].normalizedName.replace(/\s+/g, ' ').trim()) | |
{ | |
// Change the color of the matching name | |
setAOwned(i,j); | |
break; | |
} | |
} | |
} | |
} | |
} | |
// Function to handle marking a player as owned | |
function setAOwned(i,j) | |
{ | |
ahrefs[i].style.color = "#0000FF"; | |
} | |
// Delay for 3 seconds since sometimes your team's players load before the taken players | |
function sleep(milliseconds) { | |
const date = Date.now(); | |
let currentDate = null; | |
do { | |
currentDate = Date.now(); | |
} while (currentDate - date < milliseconds); | |
} | |
sleep(3000); | |
var ahrefs = document.getElementsByTagName("a"); | |
// REPEAT THE SAME PROCESS AS ABOVE BUT FOR PLAYERS ON YOUR TEAM | |
GetPlayers2(); | |
// Function to get your players from Yahoo! | |
function GetPlayers2() | |
{ | |
GM.xmlHttpRequest( | |
{ | |
method: 'GET', | |
url: myPlayers, | |
onload: function( responseDetails2 ) | |
{ | |
var responseXML2 = new DOMParser().parseFromString(responseDetails2.responseText,"text/html"); | |
buildPlayersArray2(responseXML2); | |
showValues2(); | |
}, | |
}); | |
} | |
// Function to build an array of player data from the owned page | |
function buildPlayersArray2(playersXML2) | |
{ | |
var ahrefsYahoo = playersXML2.getElementsByTagName("a"); | |
var yahooMatch = /.*sports\.yahoo\.com\/mlb\/players\/(\d*)$/; | |
var j = 0; | |
for (var i = 0; i < ahrefsYahoo.length; i++) | |
{ | |
var resultID2 = ahrefsYahoo[i].href.match(yahooMatch); | |
if (resultID2 !== null) | |
{ | |
players2[j] = {}; | |
players2[j].playerName = ahrefsYahoo[i].innerHTML; | |
players2[j].normalizedName = accent_fold(ahrefsYahoo[i].innerHTML); | |
j++; | |
} | |
} | |
} | |
// Function to match your Yahoo! players and mark as owned in FanGraphs | |
function showValues2() | |
{ | |
var fanMatch2 = /.*fangraphs\.com\/*/; | |
var stat = []; | |
var resultName2 = ""; | |
var resultIDFan2 = ""; | |
for (var i = 0; i < ahrefs.length; i++) | |
{ | |
resultName2 = ahrefs[i].innerHTML; | |
resultIDFan2 = ahrefs[i].href.match(fanMatch2); | |
if (resultIDFan2 !== null) | |
{ | |
var normalizedFanName = accent_fold(resultName2); | |
for (var j = 0; j < (players2.length); j++) | |
{ | |
// Compare normalized names to handle accents | |
if (normalizedFanName === players2[j].normalizedName || | |
normalizedFanName === players2[j].normalizedName.replace(/\s+/g, ' ').trim()) | |
{ | |
// Change the color of the matching name | |
setAOwned2(i,j); | |
break; | |
} | |
} | |
} | |
} | |
} | |
// Function to change the font color for a player on your team | |
function setAOwned2(i,j) | |
{ | |
ahrefs[i].style.color = "#ff6200"; | |
} | |
// Consolidated accent folding function - converts accented characters to non-accented equivalents | |
function accent_fold(s) { | |
if (!s) { return ''; } | |
var ret = ''; | |
for (var i = 0; i < s.length; i++) { | |
ret += accent_map[s.charAt(i)] || s.charAt(i); | |
} | |
return ret; | |
} | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment