From: Chip Black Date: Tue, 23 Aug 2011 08:36:53 +0000 (-0500) Subject: Initial commit, v1.0.0 X-Git-Tag: v1.0.0 X-Git-Url: http://git.bytex64.net/?a=commitdiff_plain;h=refs%2Ftags%2Fv1.0.0;p=Hacks.git Initial commit, v1.0.0 --- 7f476a519a8abeecf6c1e19e4e91635ea324d608 diff --git a/COPYING b/COPYING new file mode 100644 index 0000000..840acd4 --- /dev/null +++ b/COPYING @@ -0,0 +1,22 @@ +Copyright (c) 2011, The Dominion of Awesome +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/HacksSelectorCanvas.js b/HacksSelectorCanvas.js new file mode 100644 index 0000000..6eb4405 --- /dev/null +++ b/HacksSelectorCanvas.js @@ -0,0 +1,79 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "HacksSelector", + kind: "Control", + nodeTag: "canvas", + className: "hacks-selector", + style: "opacity: 0", + width: "748px", + height: "192px", + index: 0, + published: { + hacksList: null + }, + hacksThumbs: {}, + rendered: function() { + this.inherited(arguments); + var node = this.hasNode(); + node.width = 748; + node.height = 192; + this.ctx = node.getContext('2d'); + this.ctx.fillStyle = 'white'; + this.fadeGradient = this.ctx.createLinearGradient(0, 0, 0, 128); + this.fadeGradient.addColorStop(0.6, 'rgba(0,0,0,0)'); + this.fadeGradient.addColorStop(1.0, 'rgba(255,255,255,0.5)'); + }, + setHacksList: function(newHacksList) { + this.hacksList = newHacksList; + for (var i = 0; i < this.hacksList.length; i++) { + if (this.hacksThumbs[this.hacksList[i]]) + continue; + var img = new Image(); + img.src = "hacks/" + this.hacksList[i] + "/thumbnail.png"; + img.onload = this.draw.bind(this); + this.hacksThumbs[this.hacksList[i]] = img; + } + }, + show: function() { + if (this.hideTimer) + clearTimeout(this.hideTimer); + this.hideTimer = setTimeout(function() { + this.setStyle('opacity: 0; -webkit-transition: opacity 0.5s linear'); + }.bind(this), 1500); + this.setStyle('opacity: 1.0; -webkit-transition: opacity 0.25s linear'); + }, + draw: function() { + this.ctx.clearRect(0, 0, 750, 256); + if (!this.hacksList) return; + for (var i = -2; i <= 3; i++) { + var frac = this.index - Math.floor(this.index); + var x = 311 + (i - frac) * 146; + var j = Math.floor(this.index) + i; + if (j < 0 || j > this.hacksList.length - 1) + continue; + var h = this.hacksList[j]; + + this.ctx.save(); + this.ctx.translate(x, 0); + this.ctx.drawImage(this.hacksThumbs[h], 0, 0); + this.ctx.scale(1, -1); + this.ctx.translate(0, -256); + this.ctx.beginPath(); + this.ctx.fillStyle = this.fadeGradient; + this.ctx.rect(0, 0, 128, 128); + this.ctx.fill(); + this.ctx.globalCompositeOperation = 'source-in'; + this.ctx.drawImage(this.hacksThumbs[h], 0, 0); + this.ctx.restore(); + + this.ctx.save(); + this.ctx.shadowColor = 'white'; + this.ctx.shadowBlur = '3'; + this.ctx.beginPath(); + this.ctx.arc(374, 160, 5, 0, Math.PI * 2); + this.ctx.fill(); + this.ctx.restore(); + } + } +}); diff --git a/Main.css b/Main.css new file mode 100644 index 0000000..1fe2ca5 --- /dev/null +++ b/Main.css @@ -0,0 +1,29 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +@font-face { + font-family: PCSenior; + src: url(fonts/pcsenior.ttf); +} + +.hacks-selector { + position: absolute; + bottom: 64px; + margin-left: -374px; + left: 50%; +} + +.info { + position: absolute; + left: 0; + bottom: 0; + width: 100%; + padding: 24px; + font-size: 24px; + -webkit-transition-property: opacity; + -webkit-transition-duration: 0.6s; + color: #303030; +} + +.info.dark { + color: #AFAFAf; +} diff --git a/Main.js b/Main.js new file mode 100644 index 0000000..eb02da9 --- /dev/null +++ b/Main.js @@ -0,0 +1,139 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Main", + kind: "VFlexBox", + style: "background-color: black", + components: [ + {kind: "ApplicationEvents", onWindowActivated: "windowActivated", onWindowDeactivated: "windowDeactivated"}, + {name: "hacksCarousel", kind: "Carousel", flex: 1, onGetLeft: "getLeft", onGetRight: "getRight", onScroll: "scrolling", onScrollStart: "startScroll", onScrollStop: "stopScroll"}, + //{name: "hacksSelector", kind: "HacksSelector"} + {name: "info", kind: "HFlexBox", className: "info", style: "opacity: 0", showing: false, components: [ + {name: "title"}, + {kind: "Spacer"}, + {name: "notice", className: "notice"} + ]} + ], + hacksList: [ + {name: "Nimbus", kind: "Nimbus", dark: false}, + {name: "Landscape", kind: "Landscape", dark: false}, + {name: "Munch", kind: "Munch", dark: true}, + {name: "Orbit", kind: "Orbit", dark: false}, + {name: "Pixelfade", kind: "Pixelfade", dark: true}, + //{name: "Swarm", kind: "Swarm", dark: false}, // crashy + //{name: "Spinner.CGA", kind: "XSpinnerCGA", dark: true}, // no webfont support + {name: "Spinner", kind: "XSpinner", dark: true} + ], + create: function() { + this.inherited(arguments); + /* + this.index = localStorage.getItem('hack.index'); + if (!this.index) + this.index = 0; + */ + this.index = 0; + this.lastScrollPos = 0; + this.$.hacksCarousel.setCenterView(this.getHack(this.index)); + //this.$.hacksSelector.setHacksList(this.hacksList); + }, + ready: function() { + this.startHack(); + window.addEventListener('resize', this.resizeHack.bind(this), false); + this.setNotice('Swipe for more...'); + this.setTitle(this.hacksList[this.index].name); + }, + setTitle: function(title) { + this.$.title.setContent(title); + this.infoFade(); + }, + setNotice: function(notice) { + this.$.notice.setContent(notice); + this.infoFade(); + }, + infoFade: function() { + this.$.info.setStyle('opacity: 1'); + this.$.info.show(); + + clearTimeout(this.noticeTimer); + this.noticeTimer = setTimeout(function() { + this.$.info.setStyle('opacity: 0'); + setTimeout(function() { + this.$.info.hide(); + this.setNotice(''); + this.setTitle(''); + }.bind(this), 600); + }.bind(this), 5000); + }, + windowActivated: function() { + this.startHack(); + }, + windowDeactivated: function() { + this.stopHack(); + }, + startHack: function(direction) { + var view = this.$.hacksCarousel.fetchView(direction || 'center'); + //enyo.log('starting view ' + view); + if (view) + view.start(); + //localStorage.setItem('hack.index', this.index); + }, + stopHack: function(direction) { + var view = this.$.hacksCarousel.fetchView(direction || 'center'); + //enyo.log('stopping view ' + view); + if (view) + view.stop(); + }, + resizeHack: function() { + var view = this.$.hacksCarousel.fetchView('center'); + + //enyo.log('resizing view ' + view); + if (view) + view.resize(window.innerWidth, window.innerHeight); + }, + hackHidden: function(direction) { + var view = this.$.hacksCarousel.fetchView(direction); + //enyo.log('view ' + view + ' hidden'); + if (view) + view.hidden(); + }, + getHack: function(index) { + return {kind: this.hacksList[index].kind}; + }, + getLeft: function(inSender, inSnap) { + if (inSnap && this.index > 0) { + this.index--; + this.hackHidden('right'); + this.setTitle(this.hacksList[this.index].name); + this.$.info.addRemoveClass('dark', this.hacksList[this.index].dark); + } + if (this.index == 0) + return null; + else + return this.getHack(this.index - 1); + }, + getRight: function(inSender, inSnap) { + if (inSnap && this.index < this.hacksList.length) { + this.index++; + this.hackHidden('left'); + this.setTitle(this.hacksList[this.index].name); + this.$.info.addRemoveClass('dark', this.hacksList[this.index].dark); + } + if (this.index == this.hacksList.length - 1) + return null; + else + return this.getHack(this.index + 1); + }, + scrolling: function(inSender) { + if (inSender.scrollLeft == 0 || inSender.scrollLeft == inSender.getBoundaries().right) + this.startHack(); + //this.$.hacksSelector.index = this.index + ((inSender.scrollLeft - this.lastScrollPos) / window.innerWidth); + //this.$.hacksSelector.draw(); + }, + startScroll: function(inSender) { + this.stopHack(); + }, + stopScroll: function(inSender) { + this.lastScrollPos = this.$.hacksCarousel.scrollLeft; + this.startHack(); + } +}); diff --git a/appinfo.json b/appinfo.json new file mode 100644 index 0000000..7c95063 --- /dev/null +++ b/appinfo.json @@ -0,0 +1,11 @@ +{ + "id": "com.dominionofawesome.hacks", + "version": "1.0.0", + "vendor": "The Dominion of Awesome", + "type": "web", + "main": "index.html", + "title": "Hacks!", + "icon": "icon.png", + "uiRevision": 2, + "dockMode": true +} diff --git a/depends.js b/depends.js new file mode 100644 index 0000000..6e775a3 --- /dev/null +++ b/depends.js @@ -0,0 +1,14 @@ +enyo.depends( + "Main.js", + "Main.css", + //"HacksSelector.js", + "hacks/Hack.js", + "hacks/Nimbus/Nimbus.js", + "hacks/Landscape/Landscape.js", + "hacks/Munch/Munch.js", + "hacks/Orbit/Orbit.js", + "hacks/Pixelfade/Pixelfade.js", + //"hacks/Swarm/Swarm.js", + //"hacks/XSpinnerCGA/XSpinnerCGA.js", + "hacks/XSpinner/XSpinner.js" +); diff --git a/hacks/Hack.js b/hacks/Hack.js new file mode 100644 index 0000000..28cfad7 --- /dev/null +++ b/hacks/Hack.js @@ -0,0 +1,14 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Hack", + kind: "VFlexBox", + stop: function() { + }, + start: function() { + }, + resize: function() { + }, + hidden: function() { + } +}); diff --git a/hacks/Landscape/Landscape.js b/hacks/Landscape/Landscape.js new file mode 100644 index 0000000..590cb2c --- /dev/null +++ b/hacks/Landscape/Landscape.js @@ -0,0 +1,33 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Landscape", + kind: "Hack", + style: "background-color: #2ab40f", + components: [ + {name: "clouds", style: "height: 200px; background-image: url(hacks/landscape/clouds.png)"}, + {name: "mountains", style: "height: 200px; background-image: url(hacks/landscape/mountains.png)"}, + {name: "trees", style: "height: 200px; background-image: url(hacks/landscape/trees.png)"} + ], + create: function() { + this.inherited(arguments); + this.n = 0; + }, + start: function() { + if (!this.timer) + this.timer = setInterval(this.draw.bind(this), 33); + }, + stop: function() { + clearInterval(this.timer); + this.timer = null; + }, + draw: function() { + this.n--; + if (this.n == -1600) + this.n = 0; + + this.$.clouds.applyStyle("background-position", (this.n * 1.5) + "px top"); + this.$.mountains.applyStyle("background-position", (this.n * 2.5) + "px top"); + this.$.trees.applyStyle("background-position", (this.n * 7.5) + "px top"); + } +}); diff --git a/hacks/Landscape/clouds.png b/hacks/Landscape/clouds.png new file mode 100644 index 0000000..7c7fe85 Binary files /dev/null and b/hacks/Landscape/clouds.png differ diff --git a/hacks/Landscape/mountains.png b/hacks/Landscape/mountains.png new file mode 100644 index 0000000..99a5a51 Binary files /dev/null and b/hacks/Landscape/mountains.png differ diff --git a/hacks/Landscape/trees.png b/hacks/Landscape/trees.png new file mode 100644 index 0000000..c395192 Binary files /dev/null and b/hacks/Landscape/trees.png differ diff --git a/hacks/Munch/Munch.js b/hacks/Munch/Munch.js new file mode 100644 index 0000000..2acc90a --- /dev/null +++ b/hacks/Munch/Munch.js @@ -0,0 +1,49 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: 'Munch', + kind: 'Hack', + pack: "center", + align: "center", + style: "background-color: black", + components: [ + {kind: enyo.Control, nodeTag: "canvas", name: "display", width: "512px", height: "512px"} + ], + + t: 0, + timer: null, + + rendered: function() { + var node = this.$.display.hasNode(); + node.width = 256; + node.height = 256; + this.ctx = node.getContext('2d'); + this.ctx.fillStyle = 'black'; + this.ctx.fillRect(0, 0, 255, 255); + this.ctx.fillStyle = 'rgba(0,0,0,0.075)'; + this.ctx.strokeStyle = '#00FF00'; + this.draw(); + }, + + draw: function() { + this.ctx.fillRect(0, 0, 256, 256); + this.ctx.beginPath(); + for (var x = 0; x < 256; x++) { + var y = x ^ this.t; + this.ctx.moveTo(x, y); + this.ctx.lineTo(x+1, y+1); + } + this.ctx.stroke(); + this.t = (this.t + 1) % 255; + }, + + start: function() { + if (this.timer) return; + this.timer = setInterval(this.draw.bind(this), 20); + }, + + stop: function() { + clearInterval(this.timer); + this.timer = null; + } +}); diff --git a/hacks/Nimbus/Nimbus.js b/hacks/Nimbus/Nimbus.js new file mode 100644 index 0000000..f8ed719 --- /dev/null +++ b/hacks/Nimbus/Nimbus.js @@ -0,0 +1,85 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Drop", + constructor: function() { + this.live = false; + }, + start: function(w, h, perspective) { + this.x = Math.random() * w; + this.y = (Math.random() * h) / perspective; + this.t = (new Date()).getTime(); + this.live = true; + }, + draw: function(ctx, t) { + var dt = t - this.t; + if (dt < 100) { + ctx.save(); + ctx.globalAlpha = 0.25; + ctx.beginPath(); + ctx.moveTo(this.x, 0); + ctx.lineTo(this.x, this.y); + ctx.stroke(); + ctx.restore(); + } else if (dt < 750) { + ctx.save(); + ctx.globalAlpha = (1.0 - ((dt - 500) / 250)); + ctx.beginPath(); + ctx.arc(this.x, this.y, Math.sqrt(dt) * 5, 0, 2 * Math.PI, false); + ctx.stroke(); + ctx.restore(); + } else { + this.live = false; + } + } +}); + +enyo.kind({ + name: "Nimbus", + kind: "Hack", + style: "background-color: white", + drop_c: 0, + drops: [], + perspective: 0.3, + components: [ + {name: "raindrops", nodeTag: "canvas"} + ], + rendered: function() { + this.raindrops = this.$.raindrops.hasNode(); + this.ctx = this.raindrops.getContext('2d'); + this.resize(window.innerWidth, window.innerHeight); + + for (var i = 0; i < 100; i++) + this.drops.push(new Drop()); + }, + start: function() { + if (!this.timer) + this.timer = setInterval(this.draw.bind(this), 50); + }, + stop: function() { + clearInterval(this.timer); + this.timer = null; + }, + resize: function(w, h) { + this.raindrops.width = this.w = w; + this.raindrops.height = this.h = h; + + this.ctx.fillStyle = 'rgba(255,255,255,0.7)'; + this.ctx.strokeStyle = 'rgb(128,128,128)'; + this.ctx.lineWidth = '2'; + }, + draw: function() { + if (Math.random() > 0.3) { + this.drops[this.drop_c].start(this.w, this.h, this.perspective); + this.drop_c = (this.drop_c + 1) % 100; + } + var now = (new Date()).getTime(); + this.ctx.fillRect(0, 0, this.w, this.h); + this.ctx.save(); + this.ctx.scale(1.0, this.perspective); + for (var i = 0; i < this.drops.length; i++) + if (this.drops[i].live) + this.drops[i].draw(this.ctx, now); + this.ctx.restore(); + } +}); diff --git a/hacks/Orbit/Orbit.js b/hacks/Orbit/Orbit.js new file mode 100644 index 0000000..0bc7fac --- /dev/null +++ b/hacks/Orbit/Orbit.js @@ -0,0 +1,65 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Orbit", + kind: "Hack", + pack: "center", + align: "center", + style: "background-color: lightgray", + components: [ + {kind: "Control", nodeTag: "canvas", name: "canvas", width: "250px", height: "250px"} + ], + rendered: function() { + var canvas = this.$.canvas.hasNode(); + canvas.width = 250; + canvas.height = 250; + this.context = canvas.getContext('2d'); + + this.center_x = canvas.width / 2; + this.center_y = canvas.height / 2; + this.radius = 100; + this.zr = 0; + this.xr = 0; + + this.chromeball = new Image(); + this.chromeball.onload = this.setReady.bind(this); + this.chromeball.src = "hacks/orbit/chrome_ball.png"; + }, + setReady: function() { + this.ready = true; + this.engine(); + }, + start: function() { + if (this.ready && !this.timer) + this.timer = setInterval(this.engine.bind(this), 20); + }, + stop: function() { + clearInterval(this.timer); + this.timer = null; + }, + engine: function() { + this.context.clearRect(this.center_x - this.radius - 25, this.center_y - this.radius - 25, this.radius * 2 + 50, this.radius * 2 + 50); + this.zr += 0.1; + this.xr += 0.05; + var objects = []; + for (var i = 0; i < 8; i++) { + var czr = this.zr + i * Math.PI/4; + var cxr = this.xr + Math.PI + i * Math.PI/4; + var cx = this.center_x + this.radius * Math.sin(czr); + var cy = this.center_y + this.radius * Math.cos(czr) * Math.cos(this.xr); + var r = 20 + 10 * Math.cos(czr) * Math.cos(this.xr + Math.PI/2); + + objects.push({ + x: cx - r, + y: cy - r, + s: r * 2 + }); + } + // Sort by size to simulate z-ordering + objects.sort(function(a,b) { + return a.s - b.s; + }); + for (var i = 0; i < 8; i++) + this.context.drawImage(this.chromeball, objects[i].x, objects[i].y, objects[i].s, objects[i].s); + } +}); diff --git a/hacks/Orbit/chrome_ball.png b/hacks/Orbit/chrome_ball.png new file mode 100644 index 0000000..6614330 Binary files /dev/null and b/hacks/Orbit/chrome_ball.png differ diff --git a/hacks/Pixelfade/Pixelfade.js b/hacks/Pixelfade/Pixelfade.js new file mode 100644 index 0000000..b91d5d2 --- /dev/null +++ b/hacks/Pixelfade/Pixelfade.js @@ -0,0 +1,148 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Pixelfade", + kind: "Hack", + style: "background-color: yellow; background-position: center center", + components: [ + {name: "canvas", nodeTag: "canvas", onclick: "canvasClick"}, + {name: "wallpaperService", kind: "PalmService", + service: 'palm://com.palm.systemservice', + method: 'getPreferences', + onSuccess: "gotWallpaper"} + ], + create: function() { + this.inherited(arguments); + this.$.wallpaperService.call({ + keys: ['wallpaper'], + subscribe: false + }); + }, + rendered: function() { + this.canvas = this.$.canvas.hasNode(); + this.context = this.canvas.getContext('2d'); + this.resize(window.innerWidth, window.innerHeight); + this.context.fillRect(0, 0, this.canvas.width, this.canvas.height); + + this.faders = []; + for (var i = 0; i < 10; i++) { + var img = new Image(); + img.src = "hacks/Pixelfade/pixelfade" + i + ".gif"; + this.faders.push(img); + } + }, + start: function() { + this.resize(window.innerWidth, window.innerHeight); + + if (this.timer) + clearInterval(this.timer); + this.fade_val = 9; + this.fade_dir = -1; + this.fade_end = -1; + this.timer = setInterval(this.fade_all.bind(this), 50); + + if (!this.spotTimer) + this.spotTimer = setInterval(this.do_fade_spot.bind(this), 3000); + }, + stop: function() { + clearInterval(this.timer); + this.timer = null; + clearInterval(this.spotTimer); + this.spotTimer = null; + clearTimeout(this.fadeInTimer); + this.fadeInTimer = null; + }, + resize: function(w, h) { + this.canvas.style.width = w + 'px'; + this.canvas.style.height = h + 'px'; + this.canvas.width = w; + this.canvas.height = h; + this.context.fillColor = 'black'; + this.context.fillRect(0, 0, w, h); + }, + hidden: function() { + this.context.fillRect(0, 0, this.canvas.width, this.canvas.height); + }, + canvasClick: function(inSender, inEvent) { + clearTimeout(this.fadeInTimer); + clearInterval(this.spotTimer); + this.spotTimer = setInterval(this.do_fade_spot.bind(this), 3000); + this.fader_go(inEvent.clientX, inEvent.clientY); + }, + gotWallpaper: function(inSender, inResponse) { + enyo.log("got background: " + JSON.stringify(inResponse)); + this.setStyle('background-image: url(' + inResponse.wallpaper.wallpaperFile + '); background-alignment: center center'); + }, + do_fade_spot: function() { + var x = Math.floor(Math.random() * this.canvas.width); + var y = Math.floor(Math.random() * this.canvas.height); + this.fader_go(x, y); + }, + fade_all: function() { + this.context.clearRect(0, 0, this.canvas.width, this.canvas.height); + if (this.fade_val == this.fade_end) { + clearInterval(this.timer); + this.timer = null; + if (this.fade_dir == -1) + this.context.clearRect(0, 0, this.canvas.width, this.canvas.height); + else + this.context.fillRect(0, 0, this.canvas.width, this.canvas.height); + } else { + for (var x = 0; x < this.canvas.width; x += 64) { + for (var y = 0; y < this.canvas.height; y += 64) { + this.context.drawImage(this.faders[this.fade_val], x, y); + } + } + } + this.fade_val += this.fade_dir; + }, + fader_go: function(x, y) { + this.context.clearRect(0, 0, this.canvas.width, this.canvas.height); + this.fader_count = 0; + this.time_faders(x, y); + this.faderptr = new Array(10); + for (var i=0; i < 10; i++) + this.faderptr[i] = 0; + this.t0 = (new Date()).getTime(); + this.faderRunning = true; + clearInterval(this.timer); + this.timer = setInterval(this.fader.bind(this), 50); + }, + time_faders: function(xpos, ypos) { + this.fadertimes = []; + for (var y = 0; y < this.canvas.height; y += 64) { + for (var x = 0; x < this.canvas.width; x += 64) { + var xd = x - xpos; + var yd = y - ypos; + this.fadertimes.push({ + t: 125 - Math.sqrt(xd*xd + yd*yd) / 8, + x: x, + y: y + }); + } + } + this.fadertimes.sort(function(a, b) { return a.t - b.t }); + }, + fader: function() { + var tnow = (new Date()).getTime(); + var td = (tnow - this.t0) / 8.0; + for (var i = 0; i < 10; i++) { + while (this.faderptr[i] < this.fadertimes.length && this.fadertimes[this.faderptr[i]].t < td - i * 10) { + var xpos = this.fadertimes[this.faderptr[i]].x; + var ypos = this.fadertimes[this.faderptr[i]].y; + this.context.clearRect(xpos, ypos, 64, 64); + this.context.drawImage(this.faders[i], xpos, ypos); + this.faderptr[i]++; + } + } + if (this.faderptr[9] >= this.fadertimes.length) { + clearTimeout(this.timer); + this.fadeInTimer = setTimeout(function() { + this.fade_val = 9; + this.fade_dir = -1; + this.fade_end = -1; + this.timer = setInterval(this.fade_all.bind(this), 50); + }.bind(this), 750); + } + } +}); diff --git a/hacks/Pixelfade/pixelfade0.gif b/hacks/Pixelfade/pixelfade0.gif new file mode 100644 index 0000000..5521700 Binary files /dev/null and b/hacks/Pixelfade/pixelfade0.gif differ diff --git a/hacks/Pixelfade/pixelfade1.gif b/hacks/Pixelfade/pixelfade1.gif new file mode 100644 index 0000000..f4dda0e Binary files /dev/null and b/hacks/Pixelfade/pixelfade1.gif differ diff --git a/hacks/Pixelfade/pixelfade2.gif b/hacks/Pixelfade/pixelfade2.gif new file mode 100644 index 0000000..20ef3ed Binary files /dev/null and b/hacks/Pixelfade/pixelfade2.gif differ diff --git a/hacks/Pixelfade/pixelfade3.gif b/hacks/Pixelfade/pixelfade3.gif new file mode 100644 index 0000000..d586808 Binary files /dev/null and b/hacks/Pixelfade/pixelfade3.gif differ diff --git a/hacks/Pixelfade/pixelfade4.gif b/hacks/Pixelfade/pixelfade4.gif new file mode 100644 index 0000000..dd226d9 Binary files /dev/null and b/hacks/Pixelfade/pixelfade4.gif differ diff --git a/hacks/Pixelfade/pixelfade5.gif b/hacks/Pixelfade/pixelfade5.gif new file mode 100644 index 0000000..c7f2eed Binary files /dev/null and b/hacks/Pixelfade/pixelfade5.gif differ diff --git a/hacks/Pixelfade/pixelfade6.gif b/hacks/Pixelfade/pixelfade6.gif new file mode 100644 index 0000000..c4633ce Binary files /dev/null and b/hacks/Pixelfade/pixelfade6.gif differ diff --git a/hacks/Pixelfade/pixelfade7.gif b/hacks/Pixelfade/pixelfade7.gif new file mode 100644 index 0000000..5bc10e1 Binary files /dev/null and b/hacks/Pixelfade/pixelfade7.gif differ diff --git a/hacks/Pixelfade/pixelfade8.gif b/hacks/Pixelfade/pixelfade8.gif new file mode 100644 index 0000000..93cef76 Binary files /dev/null and b/hacks/Pixelfade/pixelfade8.gif differ diff --git a/hacks/Pixelfade/pixelfade9.gif b/hacks/Pixelfade/pixelfade9.gif new file mode 100644 index 0000000..f72f9f9 Binary files /dev/null and b/hacks/Pixelfade/pixelfade9.gif differ diff --git a/hacks/Swarm/Swarm.js b/hacks/Swarm/Swarm.js new file mode 100644 index 0000000..cfe7f32 --- /dev/null +++ b/hacks/Swarm/Swarm.js @@ -0,0 +1,137 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "Pixel", + constructor: function(canvas) { + this.x = Math.random() * canvas.width; + this.y = Math.random() * canvas.height; + this.vx = Math.random() * 20.0 - 10.0; + this.vy = Math.random() * 20.0 - 10.0; + this.lastupdate = (new Date()).getTime(); + }, + accel: function(x, y) { + this.vx += x; + if (this.vx > 200.0) + this.vx = 200.0; + else if (this.vx < -200.0) + this.vx = -200.0; + this.vy += y; + if (this.vy > 200.0) + this.vy = 200.0; + else if (this.vy < -200.0) + this.vy = -200.0; + }, + update: function() { + var now = (new Date()).getTime(); + var dt = (now - this.lastupdate) / 75.0; + this.x += this.vx * dt; + this.y += this.vy * dt; + this.lastupdate = now; + }, + draw: function(ctx) { + ctx.beginPath(); + ctx.moveTo(this.x,this.y); + ctx.lineTo(this.x - this.vx / 4.0, this.y - this.vy / 4.0); + ctx.stroke(); + ctx.closePath(); + } +}); + +enyo.kind({ + name: "Swarm", + kind: "Hack", + align: "stretch", + pack: "stretch", + components: [ + {name: "canvas", nodeTag: "canvas", style: "background-color: gray", + onmousemove: "mouseMove", onmousedown: "mouseDown"} + ], + npixels: 100, + pixels: [], + rendered: function() { + this.canvas = this.$.canvas.hasNode(); + this.resize(); + this.mx = this.canvas.width / 2; + this.my = this.canvas.width / 2; + for (var x = 0; x < this.npixels; x++) + this.pixels.push(new Pixel(this.canvas)); + //this.stopTime = (new Date()).getTime(); + this.engine(); + }, + start: function() { + if (this.stopTime) { + var delta = (new Date()).getTime() - this.stopTime; + for (var i = 0; i < this.npixels; i++) + this.pixels[i].lastupdate += delta; + this.stopTime = null; + } + if (!this.timer) + this.timer = setInterval(this.engine.bind(this), 20); + }, + stop: function() { + this.stopTime = (new Date()).getTime(); + clearInterval(this.timer); + this.timer = null; + }, + resize: function(w, h) { + this.canvas.width = w; + this.canvas.height = h; + //this.canvas.style.width = w + 'px'; + //this.canvas.style.height = h + 'px'; + this.context = this.canvas.getContext('2d'); + this.context.strokeStyle = '#000000'; + this.context.lineCap = 'round'; + this.context.lineWidth = 1.5; + }, + mouseMove: function(inSender, inEvent) { + this.mx = inEvent.clientX; + this.my = inEvent.clientY; + }, + mouseDown: function(inSender, inEvent) { + this.mouseMove(inSender, inEvent); + // Apply force to each pixel outwards from the mouse + for (var i = 0; i < this.npixels; i++) { + // Get the direction + var dx = this.pixels[i].x - inEvent.clientX; + var dy = this.pixels[i].y - inEvent.clientY; + var mag = Math.sqrt(dx*dx + dy*dy); + dx /= mag; + dy /= mag; + + // Apply force. + this.pixels[i].accel(dx * 40.0, dy * 40.0); + } + }, + engine: function() { + // Clear the canvas + this.context.clearRect(0, 0, this.canvas.width, this.canvas.height); + // Update all pixel objects + for (var i = 0; i < this.npixels; i++) { + // Get distance + var dx = this.mx - this.pixels[i].x; + var dy = this.my - this.pixels[i].y; + var d = Math.sqrt(dx*dx + dy*dy); + + // Apply acceleration to pixels towards the mouse cursor + var ax = dx / 50.0; + var ay = dy / 50.0; + + // Apply a drag proportional to the distance from the cursor + if (d > 100.0) { + ax += -this.pixels[i].vx * (d - 100.0) / 2000.0; + ay += -this.pixels[i].vy * (d - 100.0) / 2000.0; + } + + // And a "chaotic" acceleration inversely proportional + // to the distance from the cursor + ax += (Math.random() * 160.0 - 80.0) / d; + ay += (Math.random() * 160.0 - 80.0) / d; + + this.pixels[i].accel(ax,ay); + this.pixels[i].update(); + this.pixels[i].draw(this.context); + } + + this.context.strokeRect(this.mx - 10, this.my - 10, 20, 20); + } +}); diff --git a/hacks/XSpinner/XSpinner.js b/hacks/XSpinner/XSpinner.js new file mode 100644 index 0000000..9fd0a33 --- /dev/null +++ b/hacks/XSpinner/XSpinner.js @@ -0,0 +1,80 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "XSpinner", + kind: "Hack", + style: "background-color: black; color: #00FF00; font-family: Courier, sans-serif; font-size: 12px", + pack: "center", + align: "center", + components: [ + {style: "border: 2px solid green; padding: 4px", components: [ + {name: "terminal", nodeTag: "pre", style: "margin: 0"}, + {nodeTag: "pre", style: "margin: 0", +content: "SESSION 1 80x24 CAPS NUM SCR RAVE"} + ]} + ], + create: function() { + this.inherited(arguments); + this.w = 80; + this.h = 24; + this.delay = 20; + this.rate = 360.0 / 1000.0; + this.cw = this.w / 2; + this.ch = this.h / 2; + }, + rendered: function() { + this.terminal = this.$.terminal.hasNode(); + this.blinker = document.getElementById('spinner_blinker'); + this.blink_active = true; + this.spinner(); + }, + start: function() { + if (!this.timer) { + this.timer = setInterval(this.spinner.bind(this), this.delay); + this.blinkerTimer = setInterval(this.blink.bind(this), 500); + } + }, + stop: function() { + clearInterval(this.timer); + clearInterval(this.blinkerTimer); + this.timer = null; + this.blinkerTimer = null; + }, + spinner: function() { + // Get date + var ms = (new Date()).getMilliseconds(); + var r = ms * this.rate; + var a = Math.tan((r / 180.0) * Math.PI); + var b = Math.tan(((r+90) / 180.0) * Math.PI); + + var t = ''; + for (var j=0; j < this.h; j++) { + for (var i=0; i < this.w; i++) { + if ((r > 90 && r <= 180) || (r > 270 && r < 360) || r == 0) { + if ((j-this.ch) * 2 > a * (i-this.cw) && (j-this.ch) * 2 < b * (i-this.cw) || + (j-this.ch) * 2 < a * (i-this.cw) && (j-this.ch) * 2 > b * (i-this.cw) ) { + t += '*'; + } else { + t += ' '; + } + } else { + if ((j-this.ch) * 2 > a * (i-this.cw) && (j-this.ch) * 2 > b * (i-this.cw) || + (j-this.ch) * 2 < a * (i-this.cw) && (j-this.ch) * 2 < b * (i-this.cw) ) { + t += '*'; + } else { + t += ' '; + } + } + } + t += "\n"; + } + this.terminal.innerHTML = t; + }, + blink: function() { + if (this.blink_active) + this.blinker.style.color = '#00FF00'; + else + this.blinker.style.color = 'black'; + this.blink_active = !this.blink_active; + } +}); diff --git a/hacks/XSpinnerCGA/XSpinnerCGA.js b/hacks/XSpinnerCGA/XSpinnerCGA.js new file mode 100644 index 0000000..9ff7634 --- /dev/null +++ b/hacks/XSpinnerCGA/XSpinnerCGA.js @@ -0,0 +1,78 @@ +/* Copyright 2011 The Dominion of Awesome + * See COPYING for licensing information */ +enyo.kind({ + name: "XSpinnerCGA", + kind: "Hack", + style: "background-color: black", + pack: "center", + align: "center", + components: [ + {style: "border: 2px solid green; padding: 4px", components: [ + {name: "terminal", nodeTag: "pre", style: "margin: 0; font-family: PCSenior; font-size: 16px"} + ]} + ], + create: function() { + this.inherited(arguments); + this.w = 40; + this.h = 24; + this.delay = 20; + this.rate = 360.0 / 1000.0; + this.cw = this.w / 2; + this.ch = this.h / 2; + }, + rendered: function() { + this.terminal = this.$.terminal.hasNode(); + this.blinker = document.getElementById('spinner_blinker'); + this.blink_active = true; + this.spinner(); + }, + start: function() { + if (!this.timer) { + this.timer = setInterval(this.spinner.bind(this), this.delay); + this.blinkerTimer = setInterval(this.blink.bind(this), 500); + } + }, + stop: function() { + clearInterval(this.timer); + clearInterval(this.blinkerTimer); + this.timer = null; + this.blinkerTimer = null; + }, + spinner: function() { + // Get date + var ms = (new Date()).getMilliseconds(); + var r = ms * this.rate; + var a = Math.tan((r / 180.0) * Math.PI); + var b = Math.tan(((r+90) / 180.0) * Math.PI); + + var t = ''; + for (var j=0; j < this.h; j++) { + for (var i=0; i < this.w; i++) { + if ((r > 90 && r <= 180) || (r > 270 && r < 360) || r == 0) { + if ((j-this.ch) * 2 > a * (i-this.cw) && (j-this.ch) * 2 < b * (i-this.cw) || + (j-this.ch) * 2 < a * (i-this.cw) && (j-this.ch) * 2 > b * (i-this.cw) ) { + t += '*'; + } else { + t += ' '; + } + } else { + if ((j-this.ch) * 2 > a * (i-this.cw) && (j-this.ch) * 2 > b * (i-this.cw) || + (j-this.ch) * 2 < a * (i-this.cw) && (j-this.ch) * 2 < b * (i-this.cw) ) { + t += '*'; + } else { + t += ' '; + } + } + } + t += "\n"; + } + this.terminal.innerHTML = t; + }, + blink: function() { + if (this.blink_active) + this.blinker.style.color = '#00FF00'; + else + this.blinker.style.color = 'black'; + this.blink_active = !this.blink_active; + } +}); diff --git a/icon.png b/icon.png new file mode 100644 index 0000000..f5d77e6 Binary files /dev/null and b/icon.png differ diff --git a/icon_48.png b/icon_48.png new file mode 100644 index 0000000..6a77b6a Binary files /dev/null and b/icon_48.png differ diff --git a/index.html b/index.html new file mode 100644 index 0000000..95db2f1 --- /dev/null +++ b/index.html @@ -0,0 +1,14 @@ + + + + +Hacks! + + + + + +