User:Phlip/Greasemonkey
From Homestar Runner Wiki
(Difference between revisions)
(not a script update, just changing the comments) |
(w00t! Big major changes! Update today! Now with 155% more exclamation points!) |
||
| Line 1: | Line 1: | ||
| - | // If you want to install this script, right-click [http://www.hrwiki.org/index.php?title=User:Phlip/Greasemonkey&action=raw&ctype=text/javascript&fakeextension=.user.js this link] and chose "Install User Script". | + | // If you want to install this script, right-click [http://www.hrwiki.org/index.php?title=User:Phlip/Greasemonkey&action=raw&ctype=text/javascript&fakeextension=.user.js this link] and chose "Install User Script".<br> |
| - | // If that option is not there, then you need to install [http://greasemonkey.mozdev.org/ Greasemonkey], and then restart Firefox and return to this page. <pre> | + | // If that option is not there, then you need to install [http://greasemonkey.mozdev.org/ Greasemonkey], and then restart Firefox and return to this page.<br> |
| + | // To update the script, if you have an old version, Go to Tools→Manage User Scripts, click on "Homestar All‑In‑One" and click "Uninstall". Then re-install it from the link above. <pre> | ||
// Homestar All-In-One | // Homestar All-In-One | ||
| - | // version | + | // version 2.0 |
// 2006-03-08 | // 2006-03-08 | ||
// Copyright (c) Phillip Bradbury, T Rice and Jesse Ruderman | // Copyright (c) Phillip Bradbury, T Rice and Jesse Ruderman | ||
// | // | ||
| - | // A combination of | + | // A combination of several useful scripts for Homestar Runner cartoons: |
// Homestar-Fullon, a greasemonkey script for making H*R cartoons fullscreen | // Homestar-Fullon, a greasemonkey script for making H*R cartoons fullscreen | ||
// Seek Bar, a bookmarklet that adds a progress bar to flash cartoons | // Seek Bar, a bookmarklet that adds a progress bar to flash cartoons | ||
// (with modifications) | // (with modifications) | ||
// Previous/Next buttons for Strong Bad Emails, TGS, Marzipan's | // Previous/Next buttons for Strong Bad Emails, TGS, Marzipan's | ||
| - | // Answering Machine, Biz Cas Fri | + | // Answering Machine, Biz Cas Fri, Puppet Jams and main pages. |
// An HRWiki link on all pages. | // An HRWiki link on all pages. | ||
| + | // The ability, if you turn on the "fullscreen" option, to keep the actual | ||
| + | // stage the same size (so you can see "outside the frame") | ||
| + | // Turning everything upside-down, like on April Fools Day, 2006 | ||
| + | // A plain-HTML navbar, to replace the Flash one. This is mostly for me | ||
| + | // as the navbar doesn't work right on my computer (font problems). | ||
| + | // All of these can easily be turned on or off with the "Preferences" box | ||
| + | // in the top left. | ||
// | // | ||
| - | // Released under the GPL | + | // Released under the GPL. |
// | // | ||
// Homestar-Fullon written by T Rice <timgm@bcheck.net> and is | // Homestar-Fullon written by T Rice <timgm@bcheck.net> and is | ||
| Line 45: | Line 53: | ||
// | // | ||
// WARNING: This script explicitly avoids use one of Greasemonkey's security | // WARNING: This script explicitly avoids use one of Greasemonkey's security | ||
| - | // features. THIS SCRIPT SHOULD NOT BE USED on | + | // features. THIS SCRIPT SHOULD NOT BE USED on ANY page where you do not trust |
// the page writer. Not that it would make sense to anyway, given it's rather | // the page writer. Not that it would make sense to anyway, given it's rather | ||
| - | // Homestar-specific. | + | // Homestar-specific. Your use of this script is stating that you trust |
| + | // The Brothers Chaps to not insert malicious code into the Homstar Runner site, | ||
| + | // and the HRWiki admins to not put any on the mirror. | ||
// | // | ||
// One of the security features of Greasemonkey, used to plug its holes in | // One of the security features of Greasemonkey, used to plug its holes in | ||
| Line 53: | Line 63: | ||
// that you're calling the real functions of objects on the page, and not | // that you're calling the real functions of objects on the page, and not | ||
// weird and potentially hazardous ones written by the page designer. However | // weird and potentially hazardous ones written by the page designer. However | ||
| - | // this also blocks functions like flashmovie. | + | // this also blocks functions like flashmovie.CurrentFrame() which are needed |
// by the seek bar. Thus to make the seek bar work, I needed to turn this off. | // by the seek bar. Thus to make the seek bar work, I needed to turn this off. | ||
// | // | ||
| Line 66: | Line 76: | ||
// | // | ||
// To uninstall, go to Tools/Manage User Scripts, | // To uninstall, go to Tools/Manage User Scripts, | ||
| - | // select "Homestar- | + | // select "Homestar All-In-One", and click Uninstall. |
| + | // | ||
| + | // -------------------------------------------------------------------- | ||
| + | // | ||
| + | // This program is free software; you can redistribute it and/or modify | ||
| + | // it under the terms of the GNU General Public License as published by | ||
| + | // the Free Software Foundation; either version 2 of the License, or | ||
| + | // (at your option) any later version. | ||
| + | // | ||
| + | // This program is distributed in the hope that it will be useful, | ||
| + | // but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| + | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| + | // GNU General Public License for more details. | ||
| + | // | ||
| + | // You should have received a copy of the GNU General Public License | ||
| + | // along with this program; if not, write to the Free Software | ||
| + | // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | ||
| + | // | ||
| + | // -------------------------------------------------------------------- | ||
// | // | ||
// ==UserScript== | // ==UserScript== | ||
| - | // @name Homestar All-In-One | + | // @name Homestar All-In-One 2.0 |
// @namespace http://www.hrwiki.org/ | // @namespace http://www.hrwiki.org/ | ||
// @description Combination of many Homestar Runner scripts | // @description Combination of many Homestar Runner scripts | ||
| Line 75: | Line 103: | ||
// @include http://www.homestarrunner.com/* | // @include http://www.homestarrunner.com/* | ||
// @include http://podstar.homestarrunner.com/* | // @include http://podstar.homestarrunner.com/* | ||
| + | // @include http://videlectrix.com/* | ||
| + | // @include http://www.videlectrix.com/* | ||
| + | // @include http://hrwiki.org/mirror/* | ||
| + | // @include http://www.hrwiki.org/mirror/* | ||
// ==/UserScript== | // ==/UserScript== | ||
| - | ( | + | // Podstar/Videlectrix and HRWiki error pages, respectively. Don't do anything on those pages. |
| - | var | + | if (document.title != "The page cannot be found" && document.title != "Homestar Runner Wiki - 404 Not Found") |
| - | + | { | |
| - | // | + | var whichsite = 0; |
| - | + | if (location.hostname.indexOf("podstar") >= 0) whichsite = 1; | |
| - | if | + | if (location.hostname.indexOf("videlectrix") >= 0) whichsite = 2; |
| - | + | if (location.pathname.indexOf("/mirror/") >= 0) whichsite = 3; | |
| - | + | ||
| - | var | + | // icons, as Base64-encoded PNG files. |
| - | if( | + | // the hrwiki one used to hotlink http://www.hrwiki.org/favicon.ico but now |
| - | + | // use "data:" to avoid bandwidth-leeching (even this minor) | |
| + | var image_hrwiki = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQ" + | ||
| + | "CAMAAAAoLQ9TAAAAzFBMVEXsFQgrPqLjBgDQDw7yAwA8PrbBGhr/AABCRcLfHBvTIiHBKy5" + | ||
| + | "OVKvCNTj/HRS8S1T/MzPgR0b2Q0Rcf611d7jSWGG9Ynd6fc5fkdPpZW5mmcybhaekgqK2fJ" + | ||
| + | "SWlXF4lctlnt3/ZmbbdXqFlMWSkbi5kkqVnIN9ncvYfIeToaqhmrCApNaolruNoc/Ij53/f" + | ||
| + | "Xy1p2eFqty1qX+Tr8/0jpSgsteftdDCr8q4ud3Wtanqq6qtweLrtMDVwszsxb3M1eLu59j7" + | ||
| + | "9PT///8lJce4h/WNAAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAs" + | ||
| + | "TAQCanBgAAAAHdElNRQfWBRkTLxz1P7v8AAAAyklEQVQY02XP23aCMBAF0DQaIxUjBrCjEi" + | ||
| + | "9oRIWotRUrWC/w//9kIssn5+GsOXvNyyD0NnI/MqnnBTaRcrH+WS92FUmPzCMV5XEs/KfIV" + | ||
| + | "VkSL73nS2Z9GpGjsvk1uxdF1k96T5Ckmdp/xc0KYGUgGrhEefZH2g1c10YIklMylgd1Gl90" + | ||
| + | "bEADdxSKz3x4zc/MB33CqYDDlvoDNcW6Iwgo/84Yrqsj6xhA4LB/3l7S7BcPKxDMwUIxp96" + | ||
| + | "G6htguAWTkNbEC0KzgtUw/QHI7xdXgqr/KgAAAABJRU5ErkJggg=="; | ||
| + | var image_prefs = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQC" + | ||
| + | "AMAAAAoLQ9TAAAAllBMVEUAGQASEhIfHx8fJy8pKSk2NjZBQUFJR0ZQUE9RUVFSUlJNX3No" + | ||
| + | "aGhsaWdramlycG1meY98fHx+fn5wgpV0iqKKh4R4jaR9jJx8kad9kad/mbONmaWEnrmEnrq" + | ||
| + | "koZy3t7fIx8bKyMHT0c3S0dDU09DV1NPP1t3W1dXY2Njb2tfe29bf3tzj4uHr6+js6+r39/" + | ||
| + | "f5+PgAAABrL3yvAAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAsTA" + | ||
| + | "QCanBgAAAAHdElNRQfWBRoFKh31UQ8DAAAAgUlEQVQY022OxxLCMAwFRSc4BEIPJZQQ08v+" + | ||
| + | "/8+RsTExDDpIe3ijfSJ/hx9g62Dt4GaAI+8YT0t27+BxxvvE/no5pYT10lGFrE34Ja40W3g" + | ||
| + | "1oMGmW7YZ6hnCYexKTPVkXivuvWe1Cz1aKqPNI3N0slI2TNYZiARJX30qERc7wBPKC4WRDz" + | ||
| + | "WdWHfmAAAAAElFTkSuQmCC"; | ||
| + | var image_close = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQC" + | ||
| + | "AQAAAC1+jfqAAAAAmJLR0QA/4ePzL8AAAAJcEhZcwAACxMAAAsTAQCanBgAAAAHdElNRQfW" + | ||
| + | "BRkTNhxuPxLkAAAAHXRFWHRDb21tZW50AENyZWF0ZWQgd2l0aCBUaGUgR0lNUO9kJW4AAAE" + | ||
| + | "KSURBVCjPhdGxSgNBFAXQMzpgYWwsLEQUDBJBQgqFIChZEPR7/DA/QCGQTgQtJE1ENoWohY" + | ||
| + | "UgbGKQyFjErNv52nObe19wqGWg7z0l5YVgVdOu+wUt507tqIVQ4Zodp861ooELe15M5KFI6" + | ||
| + | "Zfr9u25MIj6Jl4cmSIPBWrq2o5cufO4aOJDYSozNTa2pK4t03PtwUdMKRRykAmW0dTRcyNX" + | ||
| + | "pBQpI8GJDTR050zkNzK0bMMZLvUNZ8yCfy6Wvbc1NVyi4dloXjqWvds6uvp41pFmpVOKJWd" + | ||
| + | "6bgwxkmTMIotWKpwrfBkZl7uMonUHf5wSlV2+fUZrjnXdzrmyy7djD8GWTW9e51z557o1Tz" + | ||
| + | "85FH/WkOkaHQAAAABJRU5ErkJggg=="; | ||
| + | // a page to wrap the rando.swf in, to link to if the navbar is replaced. | ||
| + | var page_rando = "data:text/html,%3Chtml%3E%3Chead%3E%3Ctitle%3ERando%3C%2" + | ||
| + | "Ftitle%3E%3Cbase%20href%3D%22http%3A%2F%2Fwww.homestarrunner.com%2F%22%" + | ||
| + | "3E%3C%2Fhead%3E%3Cbody%20style%3D%22margin%3A0%22%3E%3Cembed%20src%3D%2" + | ||
| + | "2rando.swf%22%20quality%3D%22high%22%20bgcolor%3D%22%23000000%22%20widt" + | ||
| + | "h%3D%22100%25%22%20height%3D%22100%25%22%20type%3D%22application%2Fx-sh" + | ||
| + | "ockwave-flash%22%20pluginspage%3D%22http%3A%2F%2Fwww.macromedia.com%2Fs" + | ||
| + | "hockwave%2Fdownload%2Findex.cgi%3FP1_Prod_Version%3DShockwaveFlash%22%3" + | ||
| + | "E%3C%2Fembed%3E%3C%2Fbody%3E%3C%2Fbody%3E"; | ||
| + | |||
| + | settingnames = new Array( | ||
| + | {name: 'resize', title: 'Resize flash to full-screen', def: 1}, | ||
| + | {name: 'noscale', title: ' Show outside-the-frame action', def: 0}, | ||
| + | {name: 'seekbar', title: 'Show seek bar', def: 1}, | ||
| + | {name: 'frames', title: ' Show frame counter on seek bar', def: 1}, | ||
| + | {name: 'hrwiki', title: 'Add HRWiki link', def: 1}, | ||
| + | {name: 'prevnext', title: 'Show previous/next buttons', def: 1}, | ||
| + | {name: 'flipper', title: 'Turn upside-down, as on April Fools Day, 2006', def: 0}, | ||
| + | {name: 'navbar', title: 'Plain HTML navbar', def: 0}, | ||
| + | {name: 'rando', title: ' More better "rando" link', def: 1} | ||
| + | ); | ||
| + | settings = {}; | ||
| + | for (i = 0; i < settingnames.length; i++) | ||
| + | settings[settingnames[i].name] = GM_getValue(settingnames[i].name, settingnames[i].def) != 0; | ||
| + | |||
| + | addsettingsbox(); | ||
| + | |||
| + | document.body.style.margin = "0px"; | ||
| + | |||
| + | // find flash objects | ||
| + | switch (whichsite) | ||
| + | { | ||
| + | case 0: // www.homestarrunner.com | ||
| + | var objs = document.getElementsByTagName("EMBED"); | ||
| + | if (objs && objs.length >= 2) | ||
| + | { | ||
| + | var flashmovie = objs[0]; | ||
| + | var navbar = objs[1]; | ||
| + | } | ||
| + | else if (objs && objs.length >= 1) | ||
| + | { | ||
| + | var flashmovie = objs[0]; | ||
| + | var navbar = false; | ||
| + | } | ||
else | else | ||
| - | + | { | |
| + | var flashmovie = false; | ||
| + | var navbar = false; | ||
| + | } | ||
| + | if (!flashmovie) | ||
| + | { | ||
| + | objs = document.getElementsByTagName("OBJECT"); | ||
| + | if (objs && objs.length >= 1) | ||
| + | var flashmovie = objs[0]; | ||
| + | } | ||
| + | break; | ||
| + | case 1: // podstar.homestarrunner.com | ||
| + | var objs = document.getElementsByTagName("EMBED"); | ||
| + | var flashmovie = false; | ||
| + | if (objs && objs.length >= 1) | ||
| + | var navbar = objs[0]; | ||
| + | else | ||
| + | var navbar = false; | ||
| + | break; | ||
| + | case 2: // videlectrix | ||
| + | var objs = document.getElementsByTagName("EMBED"); | ||
| + | var navbar = false; | ||
| + | if (objs && objs.length >= 1) | ||
| + | var flashmovie = objs[0]; | ||
| + | else | ||
| + | var flashmovie = false; | ||
| + | settings.navbar = false; | ||
| + | break; | ||
| + | case 3: // mirror | ||
| + | var objs = document.getElementsByTagName("EMBED"); | ||
| + | var flashmovie = false; | ||
| + | if (objs && objs.length >= 1) | ||
| + | var flashmovie = objs[0]; | ||
| + | if (!flashmovie) | ||
| + | { | ||
| + | objs = document.getElementsByTagName("OBJECT"); | ||
| + | if (objs && objs.length >= 1) | ||
| + | var flashmovie = objs[0]; | ||
| + | } | ||
| + | navbar = document.getElementById('navbar'); | ||
| + | if (!navbar) | ||
| + | settings.navbar = false; | ||
| + | var flashcontainer = document.getElementById('flash'); | ||
| + | if (flashcontainer) | ||
| + | flashcontainer.style.width = "auto"; | ||
| + | break; | ||
| + | } | ||
| + | |||
| + | if (!flashmovie) | ||
| + | settings.resize = settings.seekbar = settings.frames = settings.flipper = settings.noscale = false; | ||
| + | if (settings.flipper) | ||
| + | settings.seekbar = false; | ||
| + | |||
| + | // globals | ||
| + | var seekbar; | ||
| + | var isPercentage = false; | ||
| + | var aspect = 1.0; | ||
| + | var randolink; | ||
| + | var randourls = new Array(); | ||
| + | |||
| + | // used by wikilink, prevnext, flipper... put it out here. | ||
| + | var filename = location.pathname.toLowerCase(); | ||
| + | i = filename.lastIndexOf('/'); | ||
| + | if (i >= 0) | ||
| + | filename = filename.substr(i + 1); | ||
| + | i = filename.lastIndexOf('.'); | ||
| + | if (i >= 0) | ||
| + | filename = filename.substr(0,i); | ||
| + | |||
| + | if (settings.navbar) | ||
| + | replacenavbar(); | ||
| + | if (settings.seekbar) | ||
| + | // note use of wrappedJSObject so that the seek bar can access the Flash methods - see warning above | ||
| + | addFlashControls(flashmovie.wrappedJSObject); | ||
| + | if (settings.resize) | ||
| + | resize(); | ||
| + | if (settings.resize && settings.noscale) | ||
| + | noscale(); | ||
| + | if (settings.hrwiki) | ||
| + | wikilink(); | ||
| + | if (settings.prevnext) | ||
| + | prevnext(); | ||
| + | if (settings.flipper && whichsite == 0) | ||
| + | flipper(); | ||
| + | } | ||
| - | + | function addsettingsbox() | |
| - | + | { | |
| - | + | var settingsbox = document.createElement('div'); | |
| + | settingsbox.style.borderRight = settingsbox.style.borderBottom = '1px solid #666'; | ||
| + | settingsbox.style.background = '#EEE'; | ||
| + | settingsbox.style.color = '#000'; | ||
| + | settingsbox.style.position = 'fixed'; | ||
| + | settingsbox.style.left = 0; | ||
| + | settingsbox.style.top = 0; | ||
| + | settingsbox.style.width = '350px'; | ||
| + | settingsbox.style.font = '12px sans-serif'; | ||
| + | settingsbox.style.textAlign = 'left'; | ||
| + | settingsbox.style.display = 'none'; | ||
| + | document.body.appendChild(settingsbox); | ||
| + | var titlebar = document.createElement('div'); | ||
| + | titlebar.style.fontWeight = "bolder"; | ||
| + | titlebar.style.background = "#CCC"; | ||
| + | titlebar.style.borderBottom = "1px solid #666"; | ||
| + | titlebar.style.padding = '3px'; | ||
| + | settingsbox.appendChild(titlebar); | ||
| + | var closebutton = document.createElement('img'); | ||
| + | closebutton.src = image_close; | ||
| + | closebutton.title = "Click to hide preferences"; | ||
| + | closebutton.style.cssFloat = "right"; | ||
| + | closebutton.style.verticalAlign = "text-bottom"; | ||
| + | closebutton.style.cursor = "pointer"; | ||
| + | closebutton.addEventListener('click', function(){settingsbox.style.display = "none"; settingslink.style.display = "block";}, false); | ||
| + | titlebar.appendChild(closebutton); | ||
| + | var prefslogo = document.createElement('img'); | ||
| + | prefslogo.src = image_prefs; | ||
| + | prefslogo.style.verticalAlign = "text-bottom"; | ||
| + | titlebar.appendChild(prefslogo); | ||
| + | titlebar.appendChild(document.createTextNode(" Preferences")); | ||
| + | var settingsform = document.createElement('form'); | ||
| + | settingsform.style.margin = 0; | ||
| + | settingsform.style.padding = '3px'; | ||
| + | settingsbox.appendChild(settingsform); | ||
| + | var settingslist = document.createElement('ul'); | ||
| + | settingslist.style.listStyle = "none"; | ||
| + | settingslist.style.padding = settingslist.style.margin = 0; | ||
| + | settingsform.appendChild(settingslist); | ||
| + | for (i = 0; i < settingnames.length; i++) | ||
| + | { | ||
| + | var settingrow = document.createElement('li'); | ||
| + | settingrow.style.list | ||
| + | var settingcheckbox = document.createElement('input'); | ||
| + | settingcheckbox.id = settingcheckbox.name = "setting_" + settingnames[i].name; | ||
| + | settingcheckbox.type = "checkbox"; | ||
| + | settingcheckbox.checked = settings[settingnames[i].name]; | ||
| + | settingrow.appendChild(settingcheckbox); | ||
| + | var settinglabel = document.createElement('label'); | ||
| + | settinglabel.htmlFor = "setting_" + settingnames[i].name; | ||
| + | settinglabel.appendChild(document.createTextNode(' ' + settingnames[i].title)); | ||
| + | settingrow.appendChild(settinglabel); | ||
| + | settingslist.appendChild(settingrow); | ||
| + | |||
| + | if (settingnames[i].title.indexOf(' ') == 0) | ||
| + | { | ||
| + | settingcheckbox.style.marginLeft = "2em"; | ||
| + | var previousindex = i - 1; | ||
| + | while (previousindex > 0 && settingnames[previousindex].title.indexOf('\xA0') == 0) | ||
| + | previousindex--; | ||
| + | if (previousindex >= 0) | ||
| + | { | ||
| + | if (!settings[settingnames[i - 1].name]) | ||
| + | { | ||
| + | //settingcheckbox.checked = false; | ||
| + | settingcheckbox.disabled = true; | ||
| + | settinglabel.style.color = "#666"; | ||
| + | } | ||
| + | var previous = document.getElementById("setting_" + settingnames[previousindex].name); | ||
| + | if (previous) | ||
| + | addhookfordisable(previous, settingcheckbox, settinglabel); | ||
| + | } | ||
} | } | ||
} | } | ||
| + | var savebutton = document.createElement('input'); | ||
| + | savebutton.type = "submit"; | ||
| + | savebutton.value = "Save and Apply"; | ||
| + | savebutton.style.display = "block"; | ||
| + | savebutton.style.margin = "0 auto"; | ||
| + | settingsform.appendChild(savebutton); | ||
| + | settingsform.addEventListener("submit", savesettings, false); | ||
| + | |||
| + | var settingslink = document.createElement('div'); | ||
| + | settingslink.style.borderRight = settingslink.style.borderBottom = '1px solid #666'; | ||
| + | settingslink.style.background = '#EEE'; | ||
| + | settingslink.style.display = "block"; | ||
| + | settingslink.style.position = 'fixed'; | ||
| + | settingslink.style.left = '0px'; | ||
| + | settingslink.style.top = '0px'; | ||
| + | settingslink.style.padding = '3px'; | ||
| + | var settingslinkimage = document.createElement('img'); | ||
| + | settingslinkimage.src = image_prefs; | ||
| + | settingslinkimage.title = "Click to show preferences"; | ||
| + | settingslinkimage.style.cursor = "pointer"; | ||
| + | settingslinkimage.addEventListener('click', function(){settingsbox.style.display = "block"; settingslink.style.display = "none";}, false); | ||
| + | settingslink.appendChild(settingslinkimage); | ||
| + | document.body.appendChild(settingslink); | ||
| + | } | ||
| + | function addhookfordisable(clicked, checkbox, label) | ||
| + | { | ||
| + | // seperate function to make closure | ||
| + | function handler() | ||
| + | { | ||
| + | //checkbox.checked = false; | ||
| + | checkbox.disabled = !clicked.checked; | ||
| + | label.style.color = clicked.checked ? "inherit" : "#666"; | ||
| + | } | ||
| + | clicked.addEventListener('click', handler, false); | ||
| + | } | ||
| + | function savesettings(e) | ||
| + | { | ||
| + | for (i = 0; i < settingnames.length; i++) | ||
| + | { | ||
| + | settingbox = document.getElementById("setting_" + settingnames[i].name); | ||
| + | if (settingbox) | ||
| + | GM_setValue(settingnames[i].name, settingbox.checked ? 1 : 0); | ||
| + | } | ||
| + | location.reload(); | ||
| + | // stop the form from actually being submitted | ||
| + | if (e && e.preventDefault) | ||
| + | e.preventDefault(); | ||
| + | } | ||
| - | var | + | // modified from Homestar-Fullon |
| - | if ( | + | function doResize() |
| + | { | ||
| + | var dw = window.innerWidth; | ||
| + | var dh = window.innerHeight - 10; // things get weird sometimes... -10 to make sure we don't get scrollbars. | ||
| + | if (navbar) | ||
{ | { | ||
| - | + | // parseInt will take the number part at the start, turning eg "10px" into 10 | |
| - | + | dh -= parseInt(document.defaultView.getComputedStyle(navbar, null).height,10); | |
| - | document. | + | dh -= parseInt(document.defaultView.getComputedStyle(navbar, null).marginTop,10); |
| - | + | dh -= parseInt(document.defaultView.getComputedStyle(navbar, null).marginBottom,10); | |
| - | + | } | |
| + | if (seekbar) | ||
| + | { | ||
| + | dh -= parseInt(document.defaultView.getComputedStyle(seekbar, null).height,10); | ||
| + | dh -= parseInt(document.defaultView.getComputedStyle(seekbar, null).marginTop,10); | ||
| + | dh -= parseInt(document.defaultView.getComputedStyle(seekbar, null).marginBottom,10); | ||
| + | } | ||
| + | // if it was a percentage size, or we're looking outside the frame, just fill the whole window. | ||
| + | // otherwise, keep the aspect ratio correct... "touch inside" mode. | ||
| + | if (!isPercentage && !settings.noscale) | ||
| + | { | ||
| + | if(dw/aspect <= dh) | ||
| + | dh = Math.floor(dw / aspect); | ||
| + | else | ||
| + | dw = Math.floor(dh * aspect); | ||
} | } | ||
| - | // modified from the seek bar bookmarklet | + | /* set embed's size */ |
| - | + | flashmovie.width = dw; | |
| + | flashmovie.height = dh; | ||
| + | if (seekbar) | ||
| + | seekbar.style.width = Math.max(dw, 450) + "px"; | ||
| + | } | ||
| + | function resize() | ||
| + | { | ||
| + | if (flashmovie.width.toString().indexOf('%') >= 0 || flashmovie.width.toString().indexOf('%') >= 0) | ||
| + | isPercentage = true; | ||
| + | else | ||
| + | aspect = flashmovie.width/flashmovie.height; | ||
| + | window.addEventListener('resize', doResize, false); | ||
| + | doResize(); | ||
| + | } | ||
| + | |||
| + | // modified from the seek bar bookmarklet | ||
| + | function addFlashControls(flash) | ||
| + | { | ||
| + | seekbar=document.createElement("div"); | ||
| + | seekbar.style.width=Math.max(parseInt(flash.width)||0,450) + "px"; | ||
| + | seekbar.style.margin = "0 auto"; | ||
| + | var where=flash; | ||
| + | while(where.parentNode.tagName.toLowerCase()=="object") | ||
| + | where=where.parentNode; | ||
| + | where.parentNode.insertBefore(seekbar,where.nextSibling); | ||
| + | var table=document.createElement("table"); | ||
| + | table.style.width="100%"; | ||
| + | seekbar.appendChild(table); | ||
| + | var row=table.insertRow(-1); | ||
| + | var pauseButton=document.createElement("button"); | ||
| + | pauseButton.appendChild(document.createTextNode("Pause")); | ||
| + | var buttonCell=row.insertCell(-1); | ||
| + | buttonCell.appendChild(pauseButton); | ||
| + | var prevCell=row.insertCell(-1); | ||
| + | var prevButton=document.createElement("button"); | ||
| + | prevButton.appendChild(document.createTextNode("|<")); | ||
| + | prevCell.appendChild(prevButton); | ||
| + | var slider=row.insertCell(-1); | ||
| + | slider.width="100%"; | ||
| + | var visibleSlider=document.createElement("div"); | ||
| + | visibleSlider.style.position="relative"; | ||
| + | visibleSlider.style.height="10px"; | ||
| + | visibleSlider.style.width="100%"; | ||
| + | visibleSlider.style.MozBorderRadius="4px"; | ||
| + | visibleSlider.style.background="#aaa"; | ||
| + | slider.appendChild(visibleSlider); | ||
| + | var thumb=document.createElement("div"); | ||
| + | thumb.style.position="absolute"; | ||
| + | thumb.style.height="20px"; | ||
| + | thumb.style.width="10px"; | ||
| + | thumb.style.top="-5px"; | ||
| + | thumb.style.MozBorderRadius="4px"; | ||
| + | thumb.style.background="#666"; | ||
| + | visibleSlider.appendChild(thumb); | ||
| + | var nextCell=row.insertCell(-1); | ||
| + | var nextButton=document.createElement("button"); | ||
| + | nextButton.appendChild(document.createTextNode(">|")); | ||
| + | nextCell.appendChild(nextButton); | ||
| + | if (settings.frames) | ||
{ | { | ||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
var frameCell=row.insertCell(-1); | var frameCell=row.insertCell(-1); | ||
var framecounter=document.createElement("div"); | var framecounter=document.createElement("div"); | ||
| Line 155: | Line 502: | ||
framecountertext=document.createTextNode(""); | framecountertext=document.createTextNode(""); | ||
framecounter.appendChild(framecountertext); | framecounter.appendChild(framecountertext); | ||
| + | } | ||
| + | else | ||
| + | framecountertext = false; | ||
| + | if (!settings.noscale) | ||
| + | { | ||
var zoomOutCell=row.insertCell(-1); | var zoomOutCell=row.insertCell(-1); | ||
var zoomOutButton=document.createElement("button"); | var zoomOutButton=document.createElement("button"); | ||
| - | // | + | // \u2212 is − |
| - | + | zoomOutButton.appendChild(document.createTextNode("\u2212")); | |
| - | + | ||
| - | + | ||
| - | zoomOutButton.appendChild(document.createTextNode( | + | |
zoomOutCell.appendChild(zoomOutButton); | zoomOutCell.appendChild(zoomOutButton); | ||
var zoomNormalCell=row.insertCell(-1); | var zoomNormalCell=row.insertCell(-1); | ||
| Line 171: | Line 520: | ||
zoomInButton.appendChild(document.createTextNode("+")); | zoomInButton.appendChild(document.createTextNode("+")); | ||
zoomInCell.appendChild(zoomInButton); | zoomInCell.appendChild(zoomInButton); | ||
| - | + | } | |
| - | + | var sliderWidth; | |
| - | + | var paused=false; | |
| - | + | var dragging=false; | |
| - | + | var lastframe=-1; | |
| - | + | addEvent(pauseButton,"click",pauseUnpause); | |
| - | + | addEvent(prevButton,"click",prevFrame); | |
| - | + | addEvent(nextButton,"click",nextFrame); | |
| + | if (!settings.noscale) | ||
| + | { | ||
addEvent(zoomOutButton,"click",zoomOut); | addEvent(zoomOutButton,"click",zoomOut); | ||
addEvent(zoomNormalButton,"click",zoomNormal); | addEvent(zoomNormalButton,"click",zoomNormal); | ||
addEvent(zoomInButton,"click",zoomIn); | addEvent(zoomInButton,"click",zoomIn); | ||
| - | + | } | |
| - | + | addEvent(slider,"mousedown",drag); | |
| - | + | addEvent(slider,"drag",function(){return false;}); | |
| - | + | window.setInterval(update,30); | |
| - | + | function pauseUnpause(){paused=flash.IsPlaying();pauseButton.style.borderStyle=paused?"inset":"";if(paused)flash.StopPlay();else flash.Play();} | |
| - | + | function prevFrame(){flash.GotoFrame(flash.CurrentFrame()-1);} | |
| - | + | function nextFrame(){flash.GotoFrame(flash.CurrentFrame()+1);} | |
| - | + | function zoomIn(){flash.Zoom(67);} | |
| - | + | function zoomOut(){flash.Zoom(150);} | |
| - | + | function zoomNormal(){flash.Zoom(0);} | |
| + | function update() | ||
| + | { | ||
| + | sliderWidth=parseInt(getWidth(slider)-getWidth(thumb)); | ||
| + | frame=flash.CurrentFrame(); | ||
| + | tot=totalFrames(); | ||
| + | if (tot > 0) | ||
{ | { | ||
| - | + | if (framecountertext) | |
| - | + | ||
| - | + | ||
| - | if ( | + | |
| - | + | ||
framecountertext.nodeValue="\xA0"+(frame+1)+"/"+tot+"\xA0"; | framecountertext.nodeValue="\xA0"+(frame+1)+"/"+tot+"\xA0"; | ||
| - | + | if(!dragging) | |
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
{ | { | ||
| - | + | thumb.style.left=parseInt(frame/tot*sliderWidth)+"px"; | |
| + | paused=!flash.IsPlaying(); | ||
| + | pauseButton.style.borderStyle=paused?"inset":""; | ||
} | } | ||
} | } | ||
| - | + | else if (framecountertext) | |
{ | { | ||
| - | + | framecountertext.nodeValue="\xA0Loading...\xA0"; | |
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
} | } | ||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
} | } | ||
| - | / | + | function dragMousemove(e) |
| - | if ( | + | { |
| - | + | var pageX=e.clientX+document.body.scrollLeft; | |
| + | var pos=bounds(0,pageX-getX(slider)-5,sliderWidth); | ||
| + | var frame=bounds(1,Math.ceil(totalFrames()*pos/sliderWidth),totalFrames()-2); | ||
| + | thumb.style.left=pos+"px"; | ||
| + | flash.GotoFrame(frame); | ||
| + | } | ||
| + | function release(e){removeEvent(document,"mousemove",dragMousemove);removeEvent(document,"mouseup",release);if(!paused)flash.Play();dragging=false;} | ||
| + | function drag(e){addEvent(document,"mousemove",dragMousemove);addEvent(document,"mouseup",release);dragging=true;dragMousemove(e);} | ||
| + | function bounds(min,val,max){return Math.min(Math.max(min,val),max);} | ||
| + | function totalFrames(){if(typeof flash.TotalFrames=="number")return flash.TotalFrames;else if(typeof flash.TotalFrames=="function")return flash.TotalFrames();else return 1;} | ||
| + | function getWidth(elem){if(document.defaultView&&document.defaultView.getComputedStyle)return parseFloat(document.defaultView.getComputedStyle(elem,null).getPropertyValue("width"));else return parseFloat(elem.offsetWidth);} | ||
| + | function getX(elem){if(!elem) return 0;return(elem.offsetLeft)+getX(elem.offsetParent);} | ||
| + | function addEvent(elem,eventName,fun){if(elem.addEventListener)elem.addEventListener(eventName,fun,false);else elem.attachEvent("on"+eventName,fun);} | ||
| + | function removeEvent(elem,eventName,fun){if(elem.addEventListener)elem.removeEventListener(eventName,fun,false);else elem.detachEvent("on"+eventName,fun);} | ||
| + | } | ||
| + | function noscale() | ||
| + | { | ||
| + | // have to wait until the Flash has loaded, otherwise SetVariable will fail. | ||
| + | // best way I have found to test this, is if the current frame is >= 0... | ||
| + | // before it's loaded, it's -1. | ||
| + | // Before Flash itself initialises, CurrentFrame doesn't exist, so check for that too. | ||
| + | var a = flashmovie.wrappedJSObject.CurrentFrame; | ||
| + | if (typeof(a) == "function") | ||
| + | a = a(); | ||
| + | if (typeof(a) == "number" && a >= 0 && flashmovie.wrappedJSObject.SetVariable) | ||
| + | flashmovie.wrappedJSObject.SetVariable("Stage.scaleMode", "noScale"); | ||
| + | else | ||
| + | setTimeout(noscale, 10); | ||
| + | } | ||
| - | + | function addHRWikiLink(pagename, isurl) | |
| + | { | ||
| + | link = document.createElement("a"); | ||
| + | if (isurl) | ||
| + | link.href = pagename; | ||
| + | else | ||
| + | link.href = "http://www.hrwiki.org/index.php/" + pagename; | ||
| + | link.style.borderLeft = link.style.borderBottom = '1px solid #666'; | ||
| + | link.style.background = '#EEE'; | ||
| + | link.style.display="block"; | ||
| + | link.style.position="fixed"; | ||
| + | link.style.right="0px"; | ||
| + | link.style.top="0px"; | ||
| + | link.style.padding="3px"; | ||
| + | document.body.appendChild(link); | ||
| + | img=document.createElement("img"); | ||
| + | img.style.border="0px"; | ||
| + | img.src=image_hrwiki; | ||
| + | link.appendChild(img); | ||
| + | } | ||
| + | function wikilink() | ||
| + | { | ||
| + | // many pages on the mirror have an "info" link in the navbar (thanks Tom!)... use that | ||
| + | if (whichsite == 3) | ||
{ | { | ||
| - | + | var a = document.getElementById("navbar"); | |
| - | + | if (a) a = a.getElementsByTagName("a"); | |
| - | + | if (a) | |
| - | + | { | |
| - | + | for (i = 0; i < a.length; i++) | |
| - | + | { | |
| - | + | if (a[i].firstChild.nodeType == 3 && a[i].firstChild.nodeValue == "info") | |
| - | + | { | |
| - | + | addHRWikiLink(a[i].href, true); | |
| - | + | return; | |
| - | + | } | |
| + | } | ||
| + | } | ||
} | } | ||
| + | |||
// pull the filename from the url, use it as a link to HRWiki | // pull the filename from the url, use it as a link to HRWiki | ||
| - | // all the filenames except | + | // all the filenames except a couple of special-cases are |
// redirects to their articles | // redirects to their articles | ||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
| - | |||
// don't link to certain pages, they aren't redirects, but already existing pages | // don't link to certain pages, they aren't redirects, but already existing pages | ||
// also detect a 404 error and special-case Strong Sad's Lament | // also detect a 404 error and special-case Strong Sad's Lament | ||
if (document.title == "Oops! You bwoke it.") | if (document.title == "Oops! You bwoke it.") | ||
addHRWikiLink("404'd"); | addHRWikiLink("404'd"); | ||
| - | else if ( | + | else if (document.title == "The page cannot be found") |
| - | + | ; | |
| + | else if (document.title == "Homestar Runner Wiki - 404 Not Found") | ||
| + | ; // the Wiki's 404 page - do nothing. | ||
else if (filename == "interview") | else if (filename == "interview") | ||
addHRWikiLink("The_Interview"); | addHRWikiLink("The_Interview"); | ||
| Line 275: | Line 659: | ||
addHRWikiLink("Strong_Sad%27s_Lament"); | addHRWikiLink("Strong_Sad%27s_Lament"); | ||
else if (filename == "") | else if (filename == "") | ||
| - | + | { | |
| + | if (whichsite == 0) | ||
| + | addHRWikiLink("Index_Page"); | ||
| + | else if (whichsite == 1) | ||
| + | addHRWikiLink("Podstar_Runner"); | ||
| + | else if (whichsite == 2) | ||
| + | addHRWikiLink("Videlectrix"); | ||
| + | else if (whichsite == 3) | ||
| + | ; // this will be a 403 page - do nothing. | ||
| + | } | ||
else | else | ||
addHRWikiLink(filename); | addHRWikiLink(filename); | ||
| - | + | } | |
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | + | ||
| - | var | + | // Prev/Next links |
| + | function addprevnextlinks(prefix,number) | ||
| + | { | ||
| + | if (number > 1) | ||
| + | { | ||
| + | var prevnum = (number - 1).toString(); | ||
var link = document.createElement("a"); | var link = document.createElement("a"); | ||
| - | if (prefix == "sbemail" && number == | + | if (prefix == "sbemail" && number == 101) |
link.href="sbemailahundred.html"; | link.href="sbemailahundred.html"; | ||
| - | else if (prefix == "sbemail" && number == | + | else if (prefix == "sbemail" && number == 152) |
link.href="kotpoptoon.html"; | link.href="kotpoptoon.html"; | ||
else | else | ||
| - | link.href=prefix+ | + | link.href=prefix+prevnum+".html"; |
link.style.position="fixed"; | link.style.position="fixed"; | ||
| - | link.style. | + | link.style.left="0px"; |
link.style.bottom="0px"; | link.style.bottom="0px"; | ||
| - | link.style.padding=" | + | link.style.padding="3px"; |
link.style.background="white"; | link.style.background="white"; | ||
link.style.border="1px solid black"; | link.style.border="1px solid black"; | ||
link.style.textDecoration="none"; | link.style.textDecoration="none"; | ||
| - | link.appendChild(document.createTextNode(' | + | link.appendChild(document.createTextNode('<')); |
document.body.appendChild(link); | document.body.appendChild(link); | ||
} | } | ||
| - | + | ||
| + | var nextnum = (number + 1).toString(); | ||
| + | var link = document.createElement("a"); | ||
| + | if (prefix == "sbemail" && number == 99) | ||
| + | link.href="sbemailahundred.html"; | ||
| + | else if (prefix == "sbemail" && number == 150) | ||
| + | link.href="kotpoptoon.html"; | ||
| + | else | ||
| + | link.href=prefix+nextnum+".html"; | ||
| + | link.style.position="fixed"; | ||
| + | link.style.right="0px"; | ||
| + | link.style.bottom="0px"; | ||
| + | link.style.padding="3px"; | ||
| + | link.style.background="white"; | ||
| + | link.style.border="1px solid black"; | ||
| + | link.style.textDecoration="none"; | ||
| + | link.appendChild(document.createTextNode('>')); | ||
| + | document.body.appendChild(link); | ||
| + | } | ||
| + | function prevnext() | ||
| + | { | ||
// this is coded like this instead of just looking for /(\d+)/ so that it | // this is coded like this instead of just looking for /(\d+)/ so that it | ||
// doesn't find pages like commandos3 or xmas04 | // doesn't find pages like commandos3 or xmas04 | ||
| Line 336: | Line 731: | ||
else if (filename == "dween_tgs") | else if (filename == "dween_tgs") | ||
addprevnextlinks("tgs", 6); | addprevnextlinks("tgs", 6); | ||
| - | })(); | + | } |
| + | |||
| + | function flipper() | ||
| + | { | ||
| + | if (filename == "toons") | ||
| + | flashmovie.src = "theyCallHimFlipperToons.swf?contentURL=" + escape(flashmovie.src); | ||
| + | else if (filename == "games") | ||
| + | flashmovie.src = "theyCallHimFlipperGames.swf?contentURL=" + escape(flashmovie.src); | ||
| + | else if (filename == "payplus") | ||
| + | flashmovie.src = "theyCallHimFlipperPayPlus.swf?contentURL=" + escape(flashmovie.src); | ||
| + | else if (filename == "main22") | ||
| + | flashmovie.src = "theyCallHimFlipperVirusMain.swf?contentURL=" + escape(flashmovie.src); | ||
| + | else if (filename == "sbemail118") | ||
| + | // virus *wasn't* flipped correctly originally, but I think having it work is better than | ||
| + | // preserving the glitch. | ||
| + | flashmovie.src = "theyCallHimFlipperVirusMain.swf?contentURL=" + escape(flashmovie.src); | ||
| + | else if (filename == "sbemailahundred") | ||
| + | flashmovie.src = "theyCallHimFlipperHundred.swf?contentURL=" + escape(flashmovie.src); | ||
| + | else | ||
| + | flashmovie.src = "theyCallHimFlipper.swf?contentURL=" + escape(flashmovie.src); | ||
| + | } | ||
| + | |||
| + | function addnavbarlink(ul,href,title) | ||
| + | { | ||
| + | var li = document.createElement("li"); | ||
| + | var link = document.createElement("a"); | ||
| + | link.href = href; | ||
| + | link.appendChild(document.createTextNode(title)); | ||
| + | li.appendChild(link); | ||
| + | ul.appendChild(li); | ||
| + | return link; | ||
| + | } | ||
| + | function replacenavbar() | ||
| + | { | ||
| + | // need to add the styles as a stylesheet, rather than inline styles | ||
| + | // so that we can use :hover | ||
| + | var stylesheet = document.createElement("style"); | ||
| + | stylesheet.type = "text/css"; | ||
| + | stylesheet.appendChild(document.createTextNode( | ||
| + | "#newnavbar { margin: 0; padding: 0; text-align: center; text-transform: lowercase; } " + | ||
| + | "#newnavbar li { margin: 0; padding: 0; display: inline; } " + | ||
| + | "#newnavbar :link, #newnavbar :visited { color: #666; font-family: sans-serif; text-decoration: none; padding: 0 1em; } " + | ||
| + | "#newnavbar :link:hover, #newnavbar :visited:hover { color: #CCC; } " + | ||
| + | // for overriding podstar's settings: | ||
| + | "#newnavbar :link, #newnavbar :visited { font-weight: normal; } " + | ||
| + | "#newnavbar :link:hover, #newnavbar :visited:hover { background: transparent; font-weight: normal; } " | ||
| + | )); | ||
| + | var head = document.getElementsByTagName('head'); | ||
| + | if (head && head[0]) | ||
| + | head[0].appendChild(stylesheet); | ||
| + | else | ||
| + | document.body.appendChild(stylesheet); | ||
| + | var newnavbar = document.createElement("ul"); | ||
| + | newnavbar.id = "newnavbar"; | ||
| + | newnavbar.style.height = newnavbar.style.fontSize = newnavbar.style.lineHeight = "10px"; | ||
| + | if (!settings.seekbar) | ||
| + | newnavbar.style.marginTop = "10px"; | ||
| + | if (navbar) | ||
| + | { | ||
| + | var where = navbar; | ||
| + | while(where.parentNode.tagName.toLowerCase() == "object") | ||
| + | where = where.parentNode; | ||
| + | where.parentNode.insertBefore(newnavbar, where); | ||
| + | if (whichsite == 3) | ||
| + | where.style.display = "none"; | ||
| + | else | ||
| + | where.parentNode.removeChild(where); | ||
| + | } | ||
| + | else | ||
| + | document.body.appendChild(newnavbar); | ||
| + | mainlink = addnavbarlink(newnavbar, "http://www.homestarrunner.com/main" + Math.floor(Math.random() * 23 + 1) + ".html", "Main"); | ||
| + | // just for fun, re-randomise on each mouse-over (for the status bar) | ||
| + | mainlink.addEventListener("mouseover",function(){mainlink.href="http://www.homestarrunner.com/main" + Math.floor(Math.random() * 23 + 1) + ".html"}, false); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/toons.html", "Toons"); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/games.html", "Games"); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/characters2.html", "Characters"); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/downloads.html", "Downloads"); | ||
| + | addnavbarlink(newnavbar, "http://homestarrunner.stores.yahoo.net/", "Store"); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/sbemail.html", "SB Emails"); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/email.html", "Contact"); | ||
| + | addnavbarlink(newnavbar, "http://www.homestarrunner.com/legal.html", "Legal"); | ||
| + | // there's no HTML page on H*R that you can simply link to for rando... it's done internally by the real navbar. | ||
| + | // linking to rando.swf will sometimes cause the "Download" box to pop up, I'm not sure why. | ||
| + | // so have to make a HTML file to show it in. | ||
| + | randolink = addnavbarlink(newnavbar, page_rando, "Rando"); | ||
| + | // optionally load the real rando.xml and do it all internally | ||
| + | if (settings.rando) | ||
| + | { | ||
| + | GM_xmlhttpRequest({ | ||
| + | method: "GET", | ||
| + | url: "http://www.homestarrunner.com/rando.xml", | ||
| + | onload: randoxml_loaded | ||
| + | }); | ||
| + | } | ||
| + | |||
| + | navbar = newnavbar; | ||
| + | } | ||
| + | function randoxml_loaded(results) | ||
| + | { | ||
| + | // info on DOMParser stole from http://www.webreference.com/programming/javascript/domwrapper/3.html | ||
| + | // Greasemonkey workaround from http://greaseblog.blogspot.com/2005/12/workarounds-for-missing-xmlhttprequest.html | ||
| + | // (oh noes! unsafeWindow!) | ||
| + | var parser = new unsafeWindow.DOMParser(); | ||
| + | // fix invalid XML... | ||
| + | // add missing root element | ||
| + | doc = results.responseText.replace(/<\?xml.*?\?>/g, ""); // strip <?xml ?> tag | ||
| + | doc = "<?xml version=\"1.0\" encoding=\"iso-8859-1\"?>\n<rando>" + doc + "</rando>"; | ||
| + | // fix bad ampersands | ||
| + | doc = doc.replace(/&(?!\w*;)/g, "&"); | ||
| + | doc = parser.parseFromString(doc, "text/xml"); | ||
| + | var sbemailcounter = 0; | ||
| + | for (i = 0; i < doc.documentElement.childNodes.length; i++) | ||
| + | { | ||
| + | if (doc.documentElement.childNodes[i].nodeType == 1) | ||
| + | { | ||
| + | if (doc.documentElement.childNodes[i].nodeName.toLowerCase() == "sb") | ||
| + | sbemailcounter++; | ||
| + | u = doc.documentElement.childNodes[i].getAttribute('u'); | ||
| + | n = doc.documentElement.childNodes[i].getAttribute('n'); | ||
| + | if (!n) n = "Untitled"; | ||
| + | if (u) | ||
| + | randourls[randourls.length] = {u: "http://www.homestarrunner.com/" + u, n: n}; | ||
| + | else | ||
| + | randourls[randourls.length] = {u: "http://www.homestarrunner.com/sbemail" + sbemailcounter + ".html", n: "SBEmail: " + n}; | ||
| + | } | ||
| + | } | ||
| + | newrandolink() | ||
| + | // just for fun, re-randomise on each mouse-over (for the status bar) | ||
| + | randolink.addEventListener('mouseover', newrandolink, false); | ||
| + | } | ||
| + | function newrandolink() | ||
| + | { | ||
| + | r = randourls[Math.floor(Math.random() * randourls.length)]; | ||
| + | randolink.href = r.u; | ||
| + | randolink.title = r.n; | ||
| + | } | ||
//</pre> | //</pre> | ||
Revision as of 06:38, 26 May 2006
// If you want to install this script, right-click this link and chose "Install User Script".
// If that option is not there, then you need to install Greasemonkey, and then restart Firefox and return to this page.
// Homestar All-In-One
// version 2.0
// 2006-03-08
// Copyright (c) Phillip Bradbury, T Rice and Jesse Ruderman
//
// A combination of several useful scripts for Homestar Runner cartoons:
// Homestar-Fullon, a greasemonkey script for making H*R cartoons fullscreen
// Seek Bar, a bookmarklet that adds a progress bar to flash cartoons
// (with modifications)
// Previous/Next buttons for Strong Bad Emails, TGS, Marzipan's
// Answering Machine, Biz Cas Fri, Puppet Jams and main pages.
// An HRWiki link on all pages.
// The ability, if you turn on the "fullscreen" option, to keep the actual
// stage the same size (so you can see "outside the frame")
// Turning everything upside-down, like on April Fools Day, 2006
// A plain-HTML navbar, to replace the Flash one. This is mostly for me
// as the navbar doesn't work right on my computer (font problems).
// All of these can easily be turned on or off with the "Preferences" box
// in the top left.
//
// Released under the GPL.
//
// Homestar-Fullon written by T Rice <timgm@bcheck.net> and is
// released under the GPL.
// http://dana.ucc.nau.edu/~tsr22/apps/greasemonkey/
//
// Seek bar written by Jesse Ruderman <jruderman@hmc.edu> and is
// distributed with permission ("You may modify and/or distribute
// up to three bookmarklets from this site in any way you want.")
// http://www.squarefree.com/bookmarklets/
// Originally it was just the Pause button and the seek bar,
// I modified it to add a frame counter, frame step buttons and zoom buttons.
// I also modified it so the Pause button automatically updates when the flash
// movie pauses itself (eg at the end of the toon).
//
// Previous/Next buttons written by Phillip Bradbury, but inspired by
// StrongBad Emails: Prev & Next from http://userscripts.org/scripts/show/1015
//
// HRWiki link also written by Phillip Bradbury, but inspired by an attempt
// by Tom Preuss to do the same thing - except it did the translation from
// URL to Wiki page name in the script, this does it at the HRWiki server
// so that when a new toon comes out, the script doesn't need to be changed.
// http://www.hrwiki.org/index.php/User:Tom/Greasemonkey_Script
//
// Direct any comments to
// http://www.hrwiki.org/index.php/User_talk:Phlip/Greasemonkey
//
// --------------------------------------------------------------------
//
// WARNING: This script explicitly avoids use one of Greasemonkey's security
// features. THIS SCRIPT SHOULD NOT BE USED on ANY page where you do not trust
// the page writer. Not that it would make sense to anyway, given it's rather
// Homestar-specific. Your use of this script is stating that you trust
// The Brothers Chaps to not insert malicious code into the Homstar Runner site,
// and the HRWiki admins to not put any on the mirror.
//
// One of the security features of Greasemonkey, used to plug its holes in
// previous versions, is Mozilla's XPCNativeWrapper, which is used to ensure
// that you're calling the real functions of objects on the page, and not
// weird and potentially hazardous ones written by the page designer. However
// this also blocks functions like flashmovie.CurrentFrame() which are needed
// by the seek bar. Thus to make the seek bar work, I needed to turn this off.
//
// --------------------------------------------------------------------
//
// This is a Greasemonkey user script.
//
// To install, you need Greasemonkey: http://greasemonkey.mozdev.org/
// Then restart Firefox and revisit this script.
// Under Tools, there will be a new menu item to "Install User Script".
// Accept the default configuration and install.
//
// To uninstall, go to Tools/Manage User Scripts,
// select "Homestar All-In-One", and click Uninstall.
//
// --------------------------------------------------------------------
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
//
// --------------------------------------------------------------------
//
// ==UserScript==
// @name Homestar All-In-One 2.0
// @namespace http://www.hrwiki.org/
// @description Combination of many Homestar Runner scripts
// @include http://homestarrunner.com/*
// @include http://www.homestarrunner.com/*
// @include http://podstar.homestarrunner.com/*
// @include http://videlectrix.com/*
// @include http://www.videlectrix.com/*
// @include http://hrwiki.org/mirror/*
// @include http://www.hrwiki.org/mirror/*
// ==/UserScript==
// Podstar/Videlectrix and HRWiki error pages, respectively. Don't do anything on those pages.
if (document.title != "The page cannot be found" && document.title != "Homestar Runner Wiki - 404 Not Found")
{
var whichsite = 0;
if (location.hostname.indexOf("podstar") >= 0) whichsite = 1;
if (location.hostname.indexOf("videlectrix") >= 0) whichsite = 2;
if (location.pathname.indexOf("/mirror/") >= 0) whichsite = 3;
// icons, as Base64-encoded PNG files.
// the hrwiki one used to hotlink http://www.hrwiki.org/favicon.ico but now
// use "data:" to avoid bandwidth-leeching (even this minor)
var image_hrwiki = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQ" +
"CAMAAAAoLQ9TAAAAzFBMVEXsFQgrPqLjBgDQDw7yAwA8PrbBGhr/AABCRcLfHBvTIiHBKy5" +
"OVKvCNTj/HRS8S1T/MzPgR0b2Q0Rcf611d7jSWGG9Ynd6fc5fkdPpZW5mmcybhaekgqK2fJ" +
"SWlXF4lctlnt3/ZmbbdXqFlMWSkbi5kkqVnIN9ncvYfIeToaqhmrCApNaolruNoc/Ij53/f" +
"Xy1p2eFqty1qX+Tr8/0jpSgsteftdDCr8q4ud3Wtanqq6qtweLrtMDVwszsxb3M1eLu59j7" +
"9PT///8lJce4h/WNAAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAs" +
"TAQCanBgAAAAHdElNRQfWBRkTLxz1P7v8AAAAyklEQVQY02XP23aCMBAF0DQaIxUjBrCjEi" +
"9oRIWotRUrWC/w//9kIssn5+GsOXvNyyD0NnI/MqnnBTaRcrH+WS92FUmPzCMV5XEs/KfIV" +
"VkSL73nS2Z9GpGjsvk1uxdF1k96T5Ckmdp/xc0KYGUgGrhEefZH2g1c10YIklMylgd1Gl90" +
"bEADdxSKz3x4zc/MB33CqYDDlvoDNcW6Iwgo/84Yrqsj6xhA4LB/3l7S7BcPKxDMwUIxp96" +
"G6htguAWTkNbEC0KzgtUw/QHI7xdXgqr/KgAAAABJRU5ErkJggg==";
var image_prefs = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQC" +
"AMAAAAoLQ9TAAAAllBMVEUAGQASEhIfHx8fJy8pKSk2NjZBQUFJR0ZQUE9RUVFSUlJNX3No" +
"aGhsaWdramlycG1meY98fHx+fn5wgpV0iqKKh4R4jaR9jJx8kad9kad/mbONmaWEnrmEnrq" +
"koZy3t7fIx8bKyMHT0c3S0dDU09DV1NPP1t3W1dXY2Njb2tfe29bf3tzj4uHr6+js6+r39/" +
"f5+PgAAABrL3yvAAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAsTA" +
"QCanBgAAAAHdElNRQfWBRoFKh31UQ8DAAAAgUlEQVQY022OxxLCMAwFRSc4BEIPJZQQ08v+" +
"/8+RsTExDDpIe3ijfSJ/hx9g62Dt4GaAI+8YT0t27+BxxvvE/no5pYT10lGFrE34Ja40W3g" +
"1oMGmW7YZ6hnCYexKTPVkXivuvWe1Cz1aKqPNI3N0slI2TNYZiARJX30qERc7wBPKC4WRDz" +
"WdWHfmAAAAAElFTkSuQmCC";
var image_close = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQC" +
"AQAAAC1+jfqAAAAAmJLR0QA/4ePzL8AAAAJcEhZcwAACxMAAAsTAQCanBgAAAAHdElNRQfW" +
"BRkTNhxuPxLkAAAAHXRFWHRDb21tZW50AENyZWF0ZWQgd2l0aCBUaGUgR0lNUO9kJW4AAAE" +
"KSURBVCjPhdGxSgNBFAXQMzpgYWwsLEQUDBJBQgqFIChZEPR7/DA/QCGQTgQtJE1ENoWohY" +
"UgbGKQyFjErNv52nObe19wqGWg7z0l5YVgVdOu+wUt507tqIVQ4Zodp861ooELe15M5KFI6" +
"Zfr9u25MIj6Jl4cmSIPBWrq2o5cufO4aOJDYSozNTa2pK4t03PtwUdMKRRykAmW0dTRcyNX" +
"pBQpI8GJDTR050zkNzK0bMMZLvUNZ8yCfy6Wvbc1NVyi4dloXjqWvds6uvp41pFmpVOKJWd" +
"6bgwxkmTMIotWKpwrfBkZl7uMonUHf5wSlV2+fUZrjnXdzrmyy7djD8GWTW9e51z557o1Tz" +
"85FH/WkOkaHQAAAABJRU5ErkJggg==";
// a page to wrap the rando.swf in, to link to if the navbar is replaced.
var page_rando = "data:text/html,%3Chtml%3E%3Chead%3E%3Ctitle%3ERando%3C%2" +
"Ftitle%3E%3Cbase%20href%3D%22http%3A%2F%2Fwww.homestarrunner.com%2F%22%" +
"3E%3C%2Fhead%3E%3Cbody%20style%3D%22margin%3A0%22%3E%3Cembed%20src%3D%2" +
"2rando.swf%22%20quality%3D%22high%22%20bgcolor%3D%22%23000000%22%20widt" +
"h%3D%22100%25%22%20height%3D%22100%25%22%20type%3D%22application%2Fx-sh" +
"ockwave-flash%22%20pluginspage%3D%22http%3A%2F%2Fwww.macromedia.com%2Fs" +
"hockwave%2Fdownload%2Findex.cgi%3FP1_Prod_Version%3DShockwaveFlash%22%3" +
"E%3C%2Fembed%3E%3C%2Fbody%3E%3C%2Fbody%3E";
settingnames = new Array(
{name: 'resize', title: 'Resize flash to full-screen', def: 1},
{name: 'noscale', title: ' Show outside-the-frame action', def: 0},
{name: 'seekbar', title: 'Show seek bar', def: 1},
{name: 'frames', title: ' Show frame counter on seek bar', def: 1},
{name: 'hrwiki', title: 'Add HRWiki link', def: 1},
{name: 'prevnext', title: 'Show previous/next buttons', def: 1},
{name: 'flipper', title: 'Turn upside-down, as on April Fools Day, 2006', def: 0},
{name: 'navbar', title: 'Plain HTML navbar', def: 0},
{name: 'rando', title: ' More better "rando" link', def: 1}
);
settings = {};
for (i = 0; i < settingnames.length; i++)
settings[settingnames[i].name] = GM_getValue(settingnames[i].name, settingnames[i].def) != 0;
addsettingsbox();
document.body.style.margin = "0px";
// find flash objects
switch (whichsite)
{
case 0: // www.homestarrunner.com
var objs = document.getElementsByTagName("EMBED");
if (objs && objs.length >= 2)
{
var flashmovie = objs[0];
var navbar = objs[1];
}
else if (objs && objs.length >= 1)
{
var flashmovie = objs[0];
var navbar = false;
}
else
{
var flashmovie = false;
var navbar = false;
}
if (!flashmovie)
{
objs = document.getElementsByTagName("OBJECT");
if (objs && objs.length >= 1)
var flashmovie = objs[0];
}
break;
case 1: // podstar.homestarrunner.com
var objs = document.getElementsByTagName("EMBED");
var flashmovie = false;
if (objs && objs.length >= 1)
var navbar = objs[0];
else
var navbar = false;
break;
case 2: // videlectrix
var objs = document.getElementsByTagName("EMBED");
var navbar = false;
if (objs && objs.length >= 1)
var flashmovie = objs[0];
else
var flashmovie = false;
settings.navbar = false;
break;
case 3: // mirror
var objs = document.getElementsByTagName("EMBED");
var flashmovie = false;
if (objs && objs.length >= 1)
var flashmovie = objs[0];
if (!flashmovie)
{
objs = document.getElementsByTagName("OBJECT");
if (objs && objs.length >= 1)
var flashmovie = objs[0];
}
navbar = document.getElementById('navbar');
if (!navbar)
settings.navbar = false;
var flashcontainer = document.getElementById('flash');
if (flashcontainer)
flashcontainer.style.width = "auto";
break;
}
if (!flashmovie)
settings.resize = settings.seekbar = settings.frames = settings.flipper = settings.noscale = false;
if (settings.flipper)
settings.seekbar = false;
// globals
var seekbar;
var isPercentage = false;
var aspect = 1.0;
var randolink;
var randourls = new Array();
// used by wikilink, prevnext, flipper... put it out here.
var filename = location.pathname.toLowerCase();
i = filename.lastIndexOf('/');
if (i >= 0)
filename = filename.substr(i + 1);
i = filename.lastIndexOf('.');
if (i >= 0)
filename = filename.substr(0,i);
if (settings.navbar)
replacenavbar();
if (settings.seekbar)
// note use of wrappedJSObject so that the seek bar can access the Flash methods - see warning above
addFlashControls(flashmovie.wrappedJSObject);
if (settings.resize)
resize();
if (settings.resize && settings.noscale)
noscale();
if (settings.hrwiki)
wikilink();
if (settings.prevnext)
prevnext();
if (settings.flipper && whichsite == 0)
flipper();
}
function addsettingsbox()
{
var settingsbox = document.createElement('div');
settingsbox.style.borderRight = settingsbox.style.borderBottom = '1px solid #666';
settingsbox.style.background = '#EEE';
settingsbox.style.color = '#000';
settingsbox.style.position = 'fixed';
settingsbox.style.left = 0;
settingsbox.style.top = 0;
settingsbox.style.width = '350px';
settingsbox.style.font = '12px sans-serif';
settingsbox.style.textAlign = 'left';
settingsbox.style.display = 'none';
document.body.appendChild(settingsbox);
var titlebar = document.createElement('div');
titlebar.style.fontWeight = "bolder";
titlebar.style.background = "#CCC";
titlebar.style.borderBottom = "1px solid #666";
titlebar.style.padding = '3px';
settingsbox.appendChild(titlebar);
var closebutton = document.createElement('img');
closebutton.src = image_close;
closebutton.title = "Click to hide preferences";
closebutton.style.cssFloat = "right";
closebutton.style.verticalAlign = "text-bottom";
closebutton.style.cursor = "pointer";
closebutton.addEventListener('click', function(){settingsbox.style.display = "none"; settingslink.style.display = "block";}, false);
titlebar.appendChild(closebutton);
var prefslogo = document.createElement('img');
prefslogo.src = image_prefs;
prefslogo.style.verticalAlign = "text-bottom";
titlebar.appendChild(prefslogo);
titlebar.appendChild(document.createTextNode(" Preferences"));
var settingsform = document.createElement('form');
settingsform.style.margin = 0;
settingsform.style.padding = '3px';
settingsbox.appendChild(settingsform);
var settingslist = document.createElement('ul');
settingslist.style.listStyle = "none";
settingslist.style.padding = settingslist.style.margin = 0;
settingsform.appendChild(settingslist);
for (i = 0; i < settingnames.length; i++)
{
var settingrow = document.createElement('li');
settingrow.style.list
var settingcheckbox = document.createElement('input');
settingcheckbox.id = settingcheckbox.name = "setting_" + settingnames[i].name;
settingcheckbox.type = "checkbox";
settingcheckbox.checked = settings[settingnames[i].name];
settingrow.appendChild(settingcheckbox);
var settinglabel = document.createElement('label');
settinglabel.htmlFor = "setting_" + settingnames[i].name;
settinglabel.appendChild(document.createTextNode(' ' + settingnames[i].title));
settingrow.appendChild(settinglabel);
settingslist.appendChild(settingrow);
if (settingnames[i].title.indexOf(' ') == 0)
{
settingcheckbox.style.marginLeft = "2em";
var previousindex = i - 1;
while (previousindex > 0 && settingnames[previousindex].title.indexOf('\xA0') == 0)
previousindex--;
if (previousindex >= 0)
{
if (!settings[settingnames[i - 1].name])
{
//settingcheckbox.checked = false;
settingcheckbox.disabled = true;
settinglabel.style.color = "#666";
}
var previous = document.getElementById("setting_" + settingnames[previousindex].name);
if (previous)
addhookfordisable(previous, settingcheckbox, settinglabel);
}
}
}
var savebutton = document.createElement('input');
savebutton.type = "submit";
savebutton.value = "Save and Apply";
savebutton.style.display = "block";
savebutton.style.margin = "0 auto";
settingsform.appendChild(savebutton);
settingsform.addEventListener("submit", savesettings, false);
var settingslink = document.createElement('div');
settingslink.style.borderRight = settingslink.style.borderBottom = '1px solid #666';
settingslink.style.background = '#EEE';
settingslink.style.display = "block";
settingslink.style.position = 'fixed';
settingslink.style.left = '0px';
settingslink.style.top = '0px';
settingslink.style.padding = '3px';
var settingslinkimage = document.createElement('img');
settingslinkimage.src = image_prefs;
settingslinkimage.title = "Click to show preferences";
settingslinkimage.style.cursor = "pointer";
settingslinkimage.addEventListener('click', function(){settingsbox.style.display = "block"; settingslink.style.display = "none";}, false);
settingslink.appendChild(settingslinkimage);
document.body.appendChild(settingslink);
}
function addhookfordisable(clicked, checkbox, label)
{
// seperate function to make closure
function handler()
{
//checkbox.checked = false;
checkbox.disabled = !clicked.checked;
label.style.color = clicked.checked ? "inherit" : "#666";
}
clicked.addEventListener('click', handler, false);
}
function savesettings(e)
{
for (i = 0; i < settingnames.length; i++)
{
settingbox = document.getElementById("setting_" + settingnames[i].name);
if (settingbox)
GM_setValue(settingnames[i].name, settingbox.checked ? 1 : 0);
}
location.reload();
// stop the form from actually being submitted
if (e && e.preventDefault)
e.preventDefault();
}
// modified from Homestar-Fullon
function doResize()
{
var dw = window.innerWidth;
var dh = window.innerHeight - 10; // things get weird sometimes... -10 to make sure we don't get scrollbars.
if (navbar)
{
// parseInt will take the number part at the start, turning eg "10px" into 10
dh -= parseInt(document.defaultView.getComputedStyle(navbar, null).height,10);
dh -= parseInt(document.defaultView.getComputedStyle(navbar, null).marginTop,10);
dh -= parseInt(document.defaultView.getComputedStyle(navbar, null).marginBottom,10);
}
if (seekbar)
{
dh -= parseInt(document.defaultView.getComputedStyle(seekbar, null).height,10);
dh -= parseInt(document.defaultView.getComputedStyle(seekbar, null).marginTop,10);
dh -= parseInt(document.defaultView.getComputedStyle(seekbar, null).marginBottom,10);
}
// if it was a percentage size, or we're looking outside the frame, just fill the whole window.
// otherwise, keep the aspect ratio correct... "touch inside" mode.
if (!isPercentage && !settings.noscale)
{
if(dw/aspect <= dh)
dh = Math.floor(dw / aspect);
else
dw = Math.floor(dh * aspect);
}
/* set embed's size */
flashmovie.width = dw;
flashmovie.height = dh;
if (seekbar)
seekbar.style.width = Math.max(dw, 450) + "px";
}
function resize()
{
if (flashmovie.width.toString().indexOf('%') >= 0 || flashmovie.width.toString().indexOf('%') >= 0)
isPercentage = true;
else
aspect = flashmovie.width/flashmovie.height;
window.addEventListener('resize', doResize, false);
doResize();
}
// modified from the seek bar bookmarklet
function addFlashControls(flash)
{
seekbar=document.createElement("div");
seekbar.style.width=Math.max(parseInt(flash.width)||0,450) + "px";
seekbar.style.margin = "0 auto";
var where=flash;
while(where.parentNode.tagName.toLowerCase()=="object")
where=where.parentNode;
where.parentNode.insertBefore(seekbar,where.nextSibling);
var table=document.createElement("table");
table.style.width="100%";
seekbar.appendChild(table);
var row=table.insertRow(-1);
var pauseButton=document.createElement("button");
pauseButton.appendChild(document.createTextNode("Pause"));
var buttonCell=row.insertCell(-1);
buttonCell.appendChild(pauseButton);
var prevCell=row.insertCell(-1);
var prevButton=document.createElement("button");
prevButton.appendChild(document.createTextNode("|<"));
prevCell.appendChild(prevButton);
var slider=row.insertCell(-1);
slider.width="100%";
var visibleSlider=document.createElement("div");
visibleSlider.style.position="relative";
visibleSlider.style.height="10px";
visibleSlider.style.width="100%";
visibleSlider.style.MozBorderRadius="4px";
visibleSlider.style.background="#aaa";
slider.appendChild(visibleSlider);
var thumb=document.createElement("div");
thumb.style.position="absolute";
thumb.style.height="20px";
thumb.style.width="10px";
thumb.style.top="-5px";
thumb.style.MozBorderRadius="4px";
thumb.style.background="#666";
visibleSlider.appendChild(thumb);
var nextCell=row.insertCell(-1);
var nextButton=document.createElement("button");
nextButton.appendChild(document.createTextNode(">|"));
nextCell.appendChild(nextButton);
if (settings.frames)
{
var frameCell=row.insertCell(-1);
var framecounter=document.createElement("div");
framecounter.style.background="#ccc";
framecounter.style.color="#000";
framecounter.style.fontWeight="bold";
frameCell.appendChild(framecounter);
framecountertext=document.createTextNode("");
framecounter.appendChild(framecountertext);
}
else
framecountertext = false;
if (!settings.noscale)
{
var zoomOutCell=row.insertCell(-1);
var zoomOutButton=document.createElement("button");
// \u2212 is −
zoomOutButton.appendChild(document.createTextNode("\u2212"));
zoomOutCell.appendChild(zoomOutButton);
var zoomNormalCell=row.insertCell(-1);
var zoomNormalButton=document.createElement("button");
zoomNormalButton.appendChild(document.createTextNode("0"));
zoomNormalCell.appendChild(zoomNormalButton);
var zoomInCell=row.insertCell(-1);
var zoomInButton=document.createElement("button");
zoomInButton.appendChild(document.createTextNode("+"));
zoomInCell.appendChild(zoomInButton);
}
var sliderWidth;
var paused=false;
var dragging=false;
var lastframe=-1;
addEvent(pauseButton,"click",pauseUnpause);
addEvent(prevButton,"click",prevFrame);
addEvent(nextButton,"click",nextFrame);
if (!settings.noscale)
{
addEvent(zoomOutButton,"click",zoomOut);
addEvent(zoomNormalButton,"click",zoomNormal);
addEvent(zoomInButton,"click",zoomIn);
}
addEvent(slider,"mousedown",drag);
addEvent(slider,"drag",function(){return false;});
window.setInterval(update,30);
function pauseUnpause(){paused=flash.IsPlaying();pauseButton.style.borderStyle=paused?"inset":"";if(paused)flash.StopPlay();else flash.Play();}
function prevFrame(){flash.GotoFrame(flash.CurrentFrame()-1);}
function nextFrame(){flash.GotoFrame(flash.CurrentFrame()+1);}
function zoomIn(){flash.Zoom(67);}
function zoomOut(){flash.Zoom(150);}
function zoomNormal(){flash.Zoom(0);}
function update()
{
sliderWidth=parseInt(getWidth(slider)-getWidth(thumb));
frame=flash.CurrentFrame();
tot=totalFrames();
if (tot > 0)
{
if (framecountertext)
framecountertext.nodeValue="\xA0"+(frame+1)+"/"+tot+"\xA0";
if(!dragging)
{
thumb.style.left=parseInt(frame/tot*sliderWidth)+"px";
paused=!flash.IsPlaying();
pauseButton.style.borderStyle=paused?"inset":"";
}
}
else if (framecountertext)
{
framecountertext.nodeValue="\xA0Loading...\xA0";
}
}
function dragMousemove(e)
{
var pageX=e.clientX+document.body.scrollLeft;
var pos=bounds(0,pageX-getX(slider)-5,sliderWidth);
var frame=bounds(1,Math.ceil(totalFrames()*pos/sliderWidth),totalFrames()-2);
thumb.style.left=pos+"px";
flash.GotoFrame(frame);
}
function release(e){removeEvent(document,"mousemove",dragMousemove);removeEvent(document,"mouseup",release);if(!paused)flash.Play();dragging=false;}
function drag(e){addEvent(document,"mousemove",dragMousemove);addEvent(document,"mouseup",release);dragging=true;dragMousemove(e);}
function bounds(min,val,max){return Math.min(Math.max(min,val),max);}
function totalFrames(){if(typeof flash.TotalFrames=="number")return flash.TotalFrames;else if(typeof flash.TotalFrames=="function")return flash.TotalFrames();else return 1;}
function getWidth(elem){if(document.defaultView&&document.defaultView.getComputedStyle)return parseFloat(document.defaultView.getComputedStyle(elem,null).getPropertyValue("width"));else return parseFloat(elem.offsetWidth);}
function getX(elem){if(!elem) return 0;return(elem.offsetLeft)+getX(elem.offsetParent);}
function addEvent(elem,eventName,fun){if(elem.addEventListener)elem.addEventListener(eventName,fun,false);else elem.attachEvent("on"+eventName,fun);}
function removeEvent(elem,eventName,fun){if(elem.addEventListener)elem.removeEventListener(eventName,fun,false);else elem.detachEvent("on"+eventName,fun);}
}
function noscale()
{
// have to wait until the Flash has loaded, otherwise SetVariable will fail.
// best way I have found to test this, is if the current frame is >= 0...
// before it's loaded, it's -1.
// Before Flash itself initialises, CurrentFrame doesn't exist, so check for that too.
var a = flashmovie.wrappedJSObject.CurrentFrame;
if (typeof(a) == "function")
a = a();
if (typeof(a) == "number" && a >= 0 && flashmovie.wrappedJSObject.SetVariable)
flashmovie.wrappedJSObject.SetVariable("Stage.scaleMode", "noScale");
else
setTimeout(noscale, 10);
}
function addHRWikiLink(pagename, isurl)
{
link = document.createElement("a");
if (isurl)
link.href = pagename;
else
link.href = "http://www.hrwiki.org/index.php/" + pagename;
link.style.borderLeft = link.style.borderBottom = '1px solid #666';
link.style.background = '#EEE';
link.style.display="block";
link.style.position="fixed";
link.style.right="0px";
link.style.top="0px";
link.style.padding="3px";
document.body.appendChild(link);
img=document.createElement("img");
img.style.border="0px";
img.src=image_hrwiki;
link.appendChild(img);
}
function wikilink()
{
// many pages on the mirror have an "info" link in the navbar (thanks Tom!)... use that
if (whichsite == 3)
{
var a = document.getElementById("navbar");
if (a) a = a.getElementsByTagName("a");
if (a)
{
for (i = 0; i < a.length; i++)
{
if (a[i].firstChild.nodeType == 3 && a[i].firstChild.nodeValue == "info")
{
addHRWikiLink(a[i].href, true);
return;
}
}
}
}
// pull the filename from the url, use it as a link to HRWiki
// all the filenames except a couple of special-cases are
// redirects to their articles
// don't link to certain pages, they aren't redirects, but already existing pages
// also detect a 404 error and special-case Strong Sad's Lament
if (document.title == "Oops! You bwoke it.")
addHRWikiLink("404'd");
else if (document.title == "The page cannot be found")
;
else if (document.title == "Homestar Runner Wiki - 404 Not Found")
; // the Wiki's 404 page - do nothing.
else if (filename == "interview")
addHRWikiLink("The_Interview");
else if (filename == "fhqwhgads")
addHRWikiLink("Everybody_to_the_Limit");
else if (filename == "trogdor")
addHRWikiLink("TROGDOR%21");
else if (filename == "marshie")
addHRWikiLink("Meet_Marshie");
else if (location.pathname.substr(0, 12) == "/sadjournal/" && filename != "wonderyears" && filename != "super8")
addHRWikiLink("Strong_Sad%27s_Lament");
else if (filename == "")
{
if (whichsite == 0)
addHRWikiLink("Index_Page");
else if (whichsite == 1)
addHRWikiLink("Podstar_Runner");
else if (whichsite == 2)
addHRWikiLink("Videlectrix");
else if (whichsite == 3)
; // this will be a 403 page - do nothing.
}
else
addHRWikiLink(filename);
}
// Prev/Next links
function addprevnextlinks(prefix,number)
{
if (number > 1)
{
var prevnum = (number - 1).toString();
var link = document.createElement("a");
if (prefix == "sbemail" && number == 101)
link.href="sbemailahundred.html";
else if (prefix == "sbemail" && number == 152)
link.href="kotpoptoon.html";
else
link.href=prefix+prevnum+".html";
link.style.position="fixed";
link.style.left="0px";
link.style.bottom="0px";
link.style.padding="3px";
link.style.background="white";
link.style.border="1px solid black";
link.style.textDecoration="none";
link.appendChild(document.createTextNode('<'));
document.body.appendChild(link);
}
var nextnum = (number + 1).toString();
var link = document.createElement("a");
if (prefix == "sbemail" && number == 99)
link.href="sbemailahundred.html";
else if (prefix == "sbemail" && number == 150)
link.href="kotpoptoon.html";
else
link.href=prefix+nextnum+".html";
link.style.position="fixed";
link.style.right="0px";
link.style.bottom="0px";
link.style.padding="3px";
link.style.background="white";
link.style.border="1px solid black";
link.style.textDecoration="none";
link.appendChild(document.createTextNode('>'));
document.body.appendChild(link);
}
function prevnext()
{
// this is coded like this instead of just looking for /(\d+)/ so that it
// doesn't find pages like commandos3 or xmas04
var result;
if ((result = filename.match(/^(sbemail|tgs|answer|bizcasfri|puppetjam|main)(\d+)$/)))
{
if (result[1] != "sbemail" || result[2] != "100")
addprevnextlinks(result[1],parseInt(result[2],10));
}
else if (filename == "sbemailahundred")
addprevnextlinks("sbemail", 100);
else if (filename == "kotpoptoon")
addprevnextlinks("sbemail", 151);
else if (filename == "dween_tgs")
addprevnextlinks("tgs", 6);
}
function flipper()
{
if (filename == "toons")
flashmovie.src = "theyCallHimFlipperToons.swf?contentURL=" + escape(flashmovie.src);
else if (filename == "games")
flashmovie.src = "theyCallHimFlipperGames.swf?contentURL=" + escape(flashmovie.src);
else if (filename == "payplus")
flashmovie.src = "theyCallHimFlipperPayPlus.swf?contentURL=" + escape(flashmovie.src);
else if (filename == "main22")
flashmovie.src = "theyCallHimFlipperVirusMain.swf?contentURL=" + escape(flashmovie.src);
else if (filename == "sbemail118")
// virus *wasn't* flipped correctly originally, but I think having it work is better than
// preserving the glitch.
flashmovie.src = "theyCallHimFlipperVirusMain.swf?contentURL=" + escape(flashmovie.src);
else if (filename == "sbemailahundred")
flashmovie.src = "theyCallHimFlipperHundred.swf?contentURL=" + escape(flashmovie.src);
else
flashmovie.src = "theyCallHimFlipper.swf?contentURL=" + escape(flashmovie.src);
}
function addnavbarlink(ul,href,title)
{
var li = document.createElement("li");
var link = document.createElement("a");
link.href = href;
link.appendChild(document.createTextNode(title));
li.appendChild(link);
ul.appendChild(li);
return link;
}
function replacenavbar()
{
// need to add the styles as a stylesheet, rather than inline styles
// so that we can use :hover
var stylesheet = document.createElement("style");
stylesheet.type = "text/css";
stylesheet.appendChild(document.createTextNode(
"#newnavbar { margin: 0; padding: 0; text-align: center; text-transform: lowercase; } " +
"#newnavbar li { margin: 0; padding: 0; display: inline; } " +
"#newnavbar :link, #newnavbar :visited { color: #666; font-family: sans-serif; text-decoration: none; padding: 0 1em; } " +
"#newnavbar :link:hover, #newnavbar :visited:hover { color: #CCC; } " +
// for overriding podstar's settings:
"#newnavbar :link, #newnavbar :visited { font-weight: normal; } " +
"#newnavbar :link:hover, #newnavbar :visited:hover { background: transparent; font-weight: normal; } "
));
var head = document.getElementsByTagName('head');
if (head && head[0])
head[0].appendChild(stylesheet);
else
document.body.appendChild(stylesheet);
var newnavbar = document.createElement("ul");
newnavbar.id = "newnavbar";
newnavbar.style.height = newnavbar.style.fontSize = newnavbar.style.lineHeight = "10px";
if (!settings.seekbar)
newnavbar.style.marginTop = "10px";
if (navbar)
{
var where = navbar;
while(where.parentNode.tagName.toLowerCase() == "object")
where = where.parentNode;
where.parentNode.insertBefore(newnavbar, where);
if (whichsite == 3)
where.style.display = "none";
else
where.parentNode.removeChild(where);
}
else
document.body.appendChild(newnavbar);
mainlink = addnavbarlink(newnavbar, "http://www.homestarrunner.com/main" + Math.floor(Math.random() * 23 + 1) + ".html", "Main");
// just for fun, re-randomise on each mouse-over (for the status bar)
mainlink.addEventListener("mouseover",function(){mainlink.href="http://www.homestarrunner.com/main" + Math.floor(Math.random() * 23 + 1) + ".html"}, false);
addnavbarlink(newnavbar, "http://www.homestarrunner.com/toons.html", "Toons");
addnavbarlink(newnavbar, "http://www.homestarrunner.com/games.html", "Games");
addnavbarlink(newnavbar, "http://www.homestarrunner.com/characters2.html", "Characters");
addnavbarlink(newnavbar, "http://www.homestarrunner.com/downloads.html", "Downloads");
addnavbarlink(newnavbar, "http://homestarrunner.stores.yahoo.net/", "Store");
addnavbarlink(newnavbar, "http://www.homestarrunner.com/sbemail.html", "SB Emails");
addnavbarlink(newnavbar, "http://www.homestarrunner.com/email.html", "Contact");
addnavbarlink(newnavbar, "http://www.homestarrunner.com/legal.html", "Legal");
// there's no HTML page on H*R that you can simply link to for rando... it's done internally by the real navbar.
// linking to rando.swf will sometimes cause the "Download" box to pop up, I'm not sure why.
// so have to make a HTML file to show it in.
randolink = addnavbarlink(newnavbar, page_rando, "Rando");
// optionally load the real rando.xml and do it all internally
if (settings.rando)
{
GM_xmlhttpRequest({
method: "GET",
url: "http://www.homestarrunner.com/rando.xml",
onload: randoxml_loaded
});
}
navbar = newnavbar;
}
function randoxml_loaded(results)
{
// info on DOMParser stole from http://www.webreference.com/programming/javascript/domwrapper/3.html
// Greasemonkey workaround from http://greaseblog.blogspot.com/2005/12/workarounds-for-missing-xmlhttprequest.html
// (oh noes! unsafeWindow!)
var parser = new unsafeWindow.DOMParser();
// fix invalid XML...
// add missing root element
doc = results.responseText.replace(/<\?xml.*?\?>/g, ""); // strip <?xml ?> tag
doc = "<?xml version=\"1.0\" encoding=\"iso-8859-1\"?>\n<rando>" + doc + "</rando>";
// fix bad ampersands
doc = doc.replace(/&(?!\w*;)/g, "&");
doc = parser.parseFromString(doc, "text/xml");
var sbemailcounter = 0;
for (i = 0; i < doc.documentElement.childNodes.length; i++)
{
if (doc.documentElement.childNodes[i].nodeType == 1)
{
if (doc.documentElement.childNodes[i].nodeName.toLowerCase() == "sb")
sbemailcounter++;
u = doc.documentElement.childNodes[i].getAttribute('u');
n = doc.documentElement.childNodes[i].getAttribute('n');
if (!n) n = "Untitled";
if (u)
randourls[randourls.length] = {u: "http://www.homestarrunner.com/" + u, n: n};
else
randourls[randourls.length] = {u: "http://www.homestarrunner.com/sbemail" + sbemailcounter + ".html", n: "SBEmail: " + n};
}
}
newrandolink()
// just for fun, re-randomise on each mouse-over (for the status bar)
randolink.addEventListener('mouseover', newrandolink, false);
}
function newrandolink()
{
r = randourls[Math.floor(Math.random() * randourls.length)];
randolink.href = r.u;
randolink.title = r.n;
}
//
