misc/graves_js_anim.xhtml
changeset 15605 969bc30928da
child 15606 c61dddd7c1a8
equal deleted inserted replaced
15604:22d0a3d6e2be 15605:969bc30928da
       
     1 <!DOCTYPE HTML>
       
     2 <html xmlns="http://www.w3.org/1999/xhtml">
       
     3 <head>
       
     4 <!-- There is, at present, no official xsd for (X)HTML5. A pity. Usefulness would depend on the parser and extensions made by the site.  -->
       
     5     <title>Hedgewars Graves</title>
       
     6 
       
     7     <style type="text/css">
       
     8 * {padding: 0; margin: 0; }
       
     9 body
       
    10 {
       
    11     background: url('//hg.hedgewars.org/hedgewars/raw-file/tip/share/hedgewars/Data/Themes/Nature/Sky.png') fixed no-repeat bottom left;
       
    12     background-color: #0B203D;
       
    13     color: #FFD902;
       
    14     -moz-background-size: 200%;
       
    15     background-size: 100% 100%;
       
    16     font-family: sans-serif;
       
    17 }
       
    18 form, p
       
    19 {
       
    20     background-color: #0B203D;
       
    21     padding: 1em;
       
    22     margin: 1em;
       
    23     border-style: solid;
       
    24     border-radius: 5px;
       
    25     border-width: 2px;
       
    26     border-color: #FFD902;
       
    27 }
       
    28 h1 {
       
    29     text-shadow: 0 0 2px white;
       
    30     color: black;
       
    31     margin:10px;
       
    32 }
       
    33 a {
       
    34     color: #BFBED0;
       
    35     text-decoration: none;
       
    36 }
       
    37 .grave
       
    38 {
       
    39     margin-top: 12px;
       
    40     margin-left: 20px;
       
    41     float: left;
       
    42     height: 32px;
       
    43     width: 32px;
       
    44     color: transparent;
       
    45 }
       
    46 .girder
       
    47 {
       
    48     width: 100%;
       
    49     height: 30px;
       
    50     clear: left;
       
    51     background-image: url('//hg.hedgewars.org/hedgewars/raw-file/tip/share/hedgewars/Data/Themes/Nature/Girder.png');
       
    52     background-repeat: repeat-x;
       
    53 }
       
    54 .hide { visibility: hidden; }
       
    55 a div
       
    56 {
       
    57     margin-top: -5px;
       
    58     height: 32px;
       
    59     width: 32px;
       
    60 }
       
    61     </style>
       
    62     <script type="application/ecmascript">
       
    63 //<![CDATA[
       
    64 var IS_LOCAL=false; // set to true to fetch graves locally. Useful for testing.
       
    65 var graves;
       
    66 if (IS_LOCAL) {
       
    67 /* JavaScript version of a sprite sheet - this could be pretty trivially done in pure HTML, but maintenance
       
    68 would be easier with a server-side portion. list of sprites could be gotten from server, but would require XSS whitelisting */
       
    69 // Last updated: 1.0.0
       
    70 graves=["Badger","Bone","bp2","bubble","Cherry","chest","Clover","coffin",
       
    71 "deadhog","dragonball","Duck2","Earth","Egg","eyecross","Flower","Ghost",
       
    72 "Grave","heart","money","mouton1","octopus","Old_Apple","pi","plant2",
       
    73 "plant3","Plinko","pokeball","pyramid","ring","Rip","Rubberduck","Simple",
       
    74 "Simple_reversed","skull","star","Statue","TV","Whisky","Yin_and_Yang"];
       
    75 }
       
    76 else
       
    77 {
       
    78 graves = [];
       
    79 }
       
    80 
       
    81 var themes = {
       
    82 // Last updated: 1.0.0
       
    83 "Art":1,
       
    84 "Beach":1,
       
    85 "Bamboo":1,
       
    86 "Bath":1,
       
    87 //"Blox":0, //unused, has no Sky.png or Border.png
       
    88 "Brick":0,
       
    89 "Cake":0,
       
    90 "Castle":1,
       
    91 "Cave":1,
       
    92 "City":1,
       
    93 "Cheese":0,
       
    94 "Christmas":1,
       
    95 "Compost":1,
       
    96 "CrazyMission":0,
       
    97 "Deepspace":0,
       
    98 "Desert":1,
       
    99 "EarthRise":0,
       
   100 "Eyes":0,
       
   101 "Freeway":0,
       
   102 "Fruit":1,
       
   103 "Halloween":1,
       
   104 "Hell":0,
       
   105 "Hoggywood":1,
       
   106 "Island":0,
       
   107 "Jungle":1,
       
   108 "Golf":1,
       
   109 "Nature":1,
       
   110 "Olympics":1,
       
   111 "Planes":0,
       
   112 "Sheep":1,
       
   113 "Snow":1,
       
   114 "Stage":1,
       
   115 "Underwater":1};
       
   116 var girder;
       
   117 var animationInterval;
       
   118 
       
   119 on_xml_loaded = function(ex)
       
   120 {
       
   121     var resp = this.responseText;
       
   122     var r = />([^<]*).png</g;
       
   123     var x;
       
   124     while(x = r.exec(resp))
       
   125     {
       
   126         graves.push(x[1]);
       
   127     }
       
   128     on_graves_loaded();
       
   129 }
       
   130 
       
   131 on_xml_error = function()
       
   132 {
       
   133     var p = document.createElement("p");
       
   134     p.appendChild(document.createTextNode("ERROR: List of graves could not be fetched from the server!"));
       
   135     document.body.appendChild(p);
       
   136 }
       
   137 
       
   138 window.onload = function()
       
   139 {
       
   140     // Load list of graves
       
   141     if (!IS_LOCAL) {
       
   142         // Request list of graves from repository URL
       
   143         var xml=new XMLHttpRequest();
       
   144         xml.open("GET", "//hg.hedgewars.org/hedgewars/file/tip/share/hedgewars/Data/Graphics/Graves/");
       
   145         xml.addEventListener("error", on_xml_error);
       
   146         xml.onload = on_xml_loaded;
       
   147         xml.send();
       
   148     }
       
   149     else
       
   150     {
       
   151         on_graves_loaded();
       
   152     }
       
   153 }
       
   154 
       
   155 on_graves_loaded = function()
       
   156 {
       
   157     // Render girders
       
   158     var s = document.styleSheets[0].cssRules;
       
   159     for(var i=0;i<s.length;i++)
       
   160     {
       
   161         if (s[i].selectorText.toLowerCase() === ".girder")
       
   162             girder = s[i];
       
   163     }
       
   164 
       
   165     var a = document.createElement("a");
       
   166     var g = document.createElement("div");
       
   167     g.className="girder";
       
   168     a.className="grave";
       
   169     a.appendChild(document.createElement("div"));
       
   170     a.lastChild.appendChild(document.createTextNode(""));
       
   171 
       
   172     // Render graves
       
   173     var missingGraves = [];
       
   174     var img;
       
   175     var j = 0;
       
   176     var toDelete = [];
       
   177     for (var i=0;i<graves.length;i++)
       
   178     {
       
   179         var h = document.body.appendChild(a.cloneNode(true));
       
   180         if (IS_LOCAL)
       
   181             h.href = "../share/hedgewars/Data/Graphics/Graves/"+graves[i]+".png";
       
   182         else
       
   183             h.href = "//hg.hedgewars.org/hedgewars/raw-file/tip/share/hedgewars/Data/Graphics/Graves/"+graves[i]+".png";
       
   184 
       
   185         h.lastChild.style.backgroundImage = 'url("'+h.href+'")';
       
   186         h.lastChild.lastChild.data = graves[i];
       
   187         h.title = graves[i];
       
   188         h.idle = Math.floor(Math.random()*16);
       
   189         if (j%8 === 7 || i === graves.length-1)
       
   190             document.body.appendChild(g.cloneNode(false));
       
   191         j++;
       
   192     }
       
   193 
       
   194     // Quick and dirty animation
       
   195     animationInterval = setInterval(animateGraves, 128);
       
   196 
       
   197     // Theme selection drop-down list
       
   198     var form = document.body.appendChild(document.createElement("form"));
       
   199 
       
   200     var opt = document.createElement("option");
       
   201     opt.appendChild(document.createTextNode(""));
       
   202 
       
   203     var label = document.createElement("label");
       
   204     label.htmlFor = "theme_select";
       
   205     label.appendChild(document.createTextNode("Theme: "));
       
   206     form.appendChild(label);
       
   207 
       
   208     var sel = form.appendChild(document.createElement("select"));
       
   209     sel.id = "theme_select";
       
   210     sel.onchange = switchTheme;
       
   211     for(var theme in themes)
       
   212     {
       
   213         sel.appendChild(opt.cloneNode(true));
       
   214         sel.lastChild.value = theme;
       
   215         sel.lastChild.lastChild.data = theme;
       
   216         if(theme === "Nature")
       
   217             sel.lastChild.selected = true;
       
   218     }
       
   219     form.appendChild(document.createElement("br"));
       
   220 
       
   221     // Checkbox: Switch animation
       
   222     var chk = document.createElement("input");
       
   223     chk.id = "anim";
       
   224     chk.type = "checkbox";
       
   225     chk.onclick = switchAnim;
       
   226     chk.checked = true;
       
   227     form.appendChild(chk);
       
   228     label = document.createElement("label");
       
   229     label.htmlFor = "anim";
       
   230     label.appendChild(document.createTextNode("Animate graves"));
       
   231     form.appendChild(label);
       
   232 
       
   233     form.appendChild(document.createElement("br"));
       
   234 
       
   235     // Checkbox: Hide girders
       
   236     chk = document.createElement("input");
       
   237     chk.id = "hide_girders";
       
   238     chk.type = "checkbox";
       
   239     chk.onclick = hideGirders;
       
   240     chk.checked = true;
       
   241     form.appendChild(chk);
       
   242     label = document.createElement("label");
       
   243     label.htmlFor = "hide_girders";
       
   244     label.appendChild(document.createTextNode("Show girders"));
       
   245     form.appendChild(label);
       
   246 
       
   247     document.body.appendChild(form);
       
   248 
       
   249 
       
   250 }
       
   251 
       
   252 function animateGraves()
       
   253 {
       
   254     var a = document.getElementsByTagName("a");
       
   255     for (var i=0;i<a.length;i++)
       
   256     {
       
   257         if (a[i].className !== "grave")
       
   258             continue;
       
   259         // Cycle thru animation frames
       
   260 
       
   261         var maskName = a[i].title;
       
   262         // Grave
       
   263         a[i].firstChild.style.backgroundPosition=Math.floor(a[i].idle/16)*-32+"px "+(a[i].idle%16)*-32+"px";
       
   264 
       
   265         // Next frame
       
   266         a[i].idle++;
       
   267         if (a[i].idle > 15)
       
   268             a[i].idle = 0;
       
   269     }
       
   270 }
       
   271 
       
   272 // Turn on or off grave animation
       
   273 function switchAnim()
       
   274 {
       
   275     if (animationInterval)
       
   276     {
       
   277         clearInterval(animationInterval);
       
   278         animationInterval = null;
       
   279     }
       
   280     else animationInterval = setInterval(animateGraves, 128);
       
   281 }
       
   282 
       
   283 // Turn on or off girders
       
   284 function hideGirders()
       
   285 {
       
   286     var g = document.getElementsByClassName("girder");
       
   287     for(var i=0;i<g.length;i++)
       
   288         if (this.checked)
       
   289             g[i].className = "girder";
       
   290         else
       
   291             g[i].className = "girder hide";
       
   292 
       
   293 }
       
   294 
       
   295 // Select theme according to drop-down list value
       
   296 function switchTheme()
       
   297 {
       
   298     var prefix;
       
   299     if (!IS_LOCAL)
       
   300         prefix = "//hg.hedgewars.org/hedgewars/raw-file/tip";
       
   301     else
       
   302         prefix = "..";
       
   303     document.body.style.backgroundImage='url("'+prefix+'/share/hedgewars/Data/Themes/'+this.value+'/Sky.png")';
       
   304     if (themes[this.value])
       
   305         girder.style.backgroundImage='url("'+prefix+'/share/hedgewars/Data/Themes/'+this.value+'/Girder.png")';
       
   306     else
       
   307         girder.style.backgroundImage='url("'+prefix+'/share/hedgewars/Data/Graphics/Girder.png")';
       
   308 }
       
   309 //]]>
       
   310     </script>
       
   311 </head>
       
   312 <body>
       
   313 <h1>List of Hedgewars graves</h1>
       
   314 <noscript>
       
   315 <p><strong>ERROR</strong>: We're so sorry, but this webpage only works with JavaScript enabled. It seems JavaScript is disabled or not supported in your browser.<br/>
       
   316 Normally, this webpage would display an animated preview of the graves in Hedgewars.</p>
       
   317 </noscript>
       
   318 </body>
       
   319 </html>