
ããã«ã¡ã¯ãHabrïŒ ãã®èšäºã§ã¯ãWebGLã²ãŒã Digital Tripã®éçºã«ãããç§èªèº«ã®çµéšãå
±æããããšæããŸãã WebGLã«å ããŠãã²ãŒã ã¯WebAudio APIãWebSocketsãgetUserMediaãVibration APIãDeviceOrientationãªã©ã®ãã¯ãããžãŒã䜿çšããthree.jsãhedtrackr.jsãsocket.ioã©ã€ãã©ãªãªã©ã䜿çšããŸãããã®èšäºã§ã¯ãæãè峿·±ãå®è£
ã®è©³çްã«ã€ããŠèª¬æããŸãã ã²ãŒã ãšã³ãžã³ãã¢ãã€ã«ã䜿çšããå¶åŸ¡ãWebã«ã¡ã©ã®å¶åŸ¡ã«ã€ããŠèª¬æããŸãããŸããdogecoinããŒã¢ã³ãšé£åããŠãnode.jsã®ããã¯ãšã³ãã«ã€ããŠããã€ã説æããŸãã
èšäºã®æåŸã«ã䜿çšããã©ã€ãã©ãªãGitHubã®ãœãŒã¹ã³ãŒããã²ãŒã ã®èª¬æãããã³ã²ãŒã èªäœãžã®ãªã³ã¯ããããŸãã
ç«ã®äžã§èå³ã®ããæ¹ãã©ããã
ã²ãŒã ãã¬ã€ã¯éåžžã«ã·ã³ãã«ã§ããæå®ãããè»éã«æ²¿ã£ãŠé£è¡ããã³ã€ã³ãšããŒãã¹ãåéããç³ãããããŸãã ãã¬ã€ã€ãŒã®ããžã·ã§ã³ã¯3ã€ã®ãªãã·ã§ã³ã«å¶éãããŠããŸãã ããŒãã¹ã«ã¯ãã·ãŒã«ãïŒHTML5ïŒãã¹ããŒããŠã³ïŒç«ïŒãã©ã€ããªã¹ãã¢ïŒåïŒã®3çš®é¡ããããŸãã ã²ãŒã ã®çµããã«ãåãåã£ãã³ã€ã³ããã²ã³ã€ã³ãŠã©ã¬ããã«åŒãåºãããšãã§ããŸãã

ã²ãŒã ã®éçºã®ç®çã¯ããã©ãŠã¶ã®æ©èœã«ã€ããŠè©±ããã¹ãã«ãã¢ããã°ã¬ãŒãããçµéšãå
±æããããã»ã¹ã楜ããããšã§ãã
次ã«ãå®è£
ã®æ©èœã«ã€ããŠè©³ãã説æããŸãã
ã²ãŒã ãšã³ãžã³ãšè©³çް
ã°ããŒãã«å€æ°DTã¯ããŠãŒãã£ãªãã£é¢æ°ãã¯ã©ã¹ã³ã³ã¹ãã©ã¯ã¿ãŒãã€ã³ã¹ã¿ã³ã¹ãããã³ãã³ãã©ãŒé¢æ°ãããŸããŸãªãã©ã¡ãŒã¿ãŒãªã©ã«ã¢ã¯ã»ã¹ã§ããåå空éãšããŠäœ¿çšãããŸãã
ããªããŒããŒ
3ã€ã®ã¹ã¯ãªãããããŒãžã«æ¥ç¶ãããŠããŸãã
<script src="js/vendor/jquery.min.js"></script> <script src="js/vendor/yepnope.1.5.4-min.js"></script> <script src="js/myYepnope.min.js"></script>
ä»ã®ã¹ã¯ãªãããããŒãããã«ã¯ã
yepnopeãªãœãŒã¹
ããŒããŒã䜿çšããŸãã
myYepnope.jsãå®è¡ãããšããã©ãŠã¶ãŒã¯WebGLãµããŒãã確èªããŸãã
var isWebGLSupported, canvas = document.getElementById('checkwebgl'); if (!window.WebGLRenderingContext) {
ãã©ãŠã¶ãWebGLããµããŒãããŠããå ŽåãmyYepnopeã¯ãªãœãŒã¹ã®èªã¿èŸŒã¿ã衚瀺ãã颿°ãå®çŸ©ããæ®ãã®ã¹ã¯ãªãããèªã¿èŸŒã¿ãŸãã
ããã§ãããªããŒããŒãæ©èœãå§ããŸãã èŠèŠçã«ã¯ãããã¯ã²ãŒã ã®ãŒãããéå§ã€ã³ã¿ãŒãã§ã€ã¹ã§ãããèªã¿èŸŒã¿ã«äŒŽã£ãŠãŒããååŸãæžå°ããŸãã

ãŒãã广ã¯ãcssããããã£
-webkit-filter: blur()
ã䜿çšããŠå®çŸãããŸãã ããããã£ã¯å®å
šã«ã¢ãã¡ãŒã·ã§ã³åãããŠããŸãã Firefoxã§ã¯ãsvgãã£ã«ã¿ãŒã䜿çšããããã®ååŸã¯css-property
filter: 'url()'
圢åŒã§åçã«å€æŽãããŠé©çšãã
filter: 'url()'
ã
data url
ã¹ã¯ãªããã«ãã£ãŠçæãããè² è·ã®20ïŒ
ããšã«æŽæ°ãããŸãã
ã³ãŒã if (isWebGLSupported) { var $body = $('body'), $cc = $('.choose_control'), maxBlur = 100, steps = 4, isWebkitBlurSupported; if ($body[0].style.webkitFilter === undefined) { isWebkitBlurSupported = false; $cc.css({filter: "url('data:image/svg+xml;utf8,<svg xmlns=\"http://www.w3.org/2000/svg\"><filter id=\"blur-overlay\"><feGaussianBlur stdDeviation=\"" + maxBlur + "\"/></filter></svg>#blur-overlay')"}); } else { isWebkitBlurSupported = true; $body[0].style.webkitFilter = 'blur(' + maxBlur + 'px)'; } $('#loader').css({display: 'table'}); $cc.css({display: 'table'}); yepnope.loadCounter = 0; yepnope.percent = 0; yepnope.showLoading = function (n) { yepnope.percent += maxBlur/steps; yepnope.loadCounter += 1; $(".loader").animate({minWidth: Math.round(yepnope.percent)+"px"}, { duration: 1000, progress: function () { var current = parseInt($(".loader").css("minWidth"), 10) * 100/maxBlur; $("title").html(Math.floor(current) + "% " + "digital trip"); if (isWebkitBlurSupported) { $body[0].style.webkitFilter = 'blur('+ (maxBlur - current)+ 'px)'; } if (!isWebkitBlurSupported && current % 20 === 0) { $cc.css({filter: "url('data:image/svg+xml;utf8,<svg xmlns=\"http://www.w3.org/2000/svg\"><filter id=\"blur-overlay\"><feGaussianBlur stdDeviation=\"" + (maxBlur - maxBlur/(steps+1)*n) + "\"/></filter></svg>#blur-overlay')"}); } if (current === 100) { $("title").html("digital trip"); if (!isWebkitBlurSupported && current % 20 === 0) $cc.css({filter: "url('data:image/svg+xml;utf8,<svg xmlns=\"http://www.w3.org/2000/svg\"><filter id=\"blur-overlay\"><feGaussianBlur stdDeviation=\"" + 0 + "\"/></filter></svg>#blur-overlay')"}); } }, complete: function () { if (n === steps) { DT.runApp(); } } }); }; yepnope([{ load: [ "js/vendor/three.min.js", "js/DT.min.js", "../socket.io/socket.io.js" ], callback: {} }]); } else { $('#nogame').css({display: 'table'}); }
ããŒãåŸã3ã€ã®å¶åŸ¡æ¹æ³ã®ãããããéžæããŠã²ãŒã ãéå§ã§ããŸãã
ã€ãã³ã
ã²ãŒã å
ã®ãªããžã§ã¯ãéã®çžäºäœçšã¯ãæšæºããã³ã«ã¹ã¿ã ã€ãã³ãã«åºã¥ããŠããŸãã
ã€ãã³ããªã¹ã'blur' //ãã©ãŒã«ã¹ã®åªå€±
'focus' //ãã©ãŒã«ã¹ã®å€èг
'socketInitialized' // socket.ioãåæåãã
'externalObjectLoaded' //å€éšã¢ãã«ã®ããŒããçµäº
'startGame' //ã²ãŒã ãéå§
'pauseGame' //äžæåæ¢
'resumeGame' //ã²ãŒã ãåé
'gameOver' //ã²ãŒã ã®çµäº
'resetGame' //ã²ãŒã ãã©ã¡ãŒã¿ããªã»ãã
'updatePath' //ã²ãŒã 空éå
ã®äœçœ®ãæŽæ°ããŸãïŒãã€ãïŒ
'update' //ã²ãŒã ãªããžã§ã¯ããæŽæ°ãã
'changeSpeed' //å€éšé床ã®å€æŽ
'showHelth' //ãã«ã¹ã®å€åã衚瀺
'showInvulner' //è匱æ§ã®å€åã衚瀺ïŒã·ãŒã«ãïŒ
'showScore' //倿Žç¹ã衚瀺
'showFun' //æžéã¢ãŒãã®å€æŽã®è¡šç€ºïŒcatïŒ
'changeHelth' //å¥åº·ã®å€å
'bump' //ãªããžã§ã¯ããšã®è¡çª
'blink' //çãç¹æ»
'hit' //ç³ãšã®è¡çª
'changeScore' //ãã€ã³ãããšã«å€æŽ
'catchBonus' //ãã£ããããŒãã¹
'makeInvulner' //äžæ»èº«ã¢ãŒãã®å€æŽïŒã·ãŒã«ãïŒ
'makeFun' //æžéã¢ãŒããæå¹ã«ããïŒcatïŒ
'showBonuses' //ãã£ãããããããŒãã¹ã®åæ
'stopFun' //ç«ã¢ãŒãããªãã«ãã
'paymentCheck' //æ¯æãã®ã¯ã©ã€ã¢ã³ããã§ãã¯ã¹ããŒã¿ã¹
'paymentMessage' //æ¯æãã¡ãã»ãŒãžãåä¿¡
'transactionMessage' //ãã©ã³ã¶ã¯ã·ã§ã³ã¡ãã»ãŒãžãåä¿¡
'checkup' //ãã§ãã¯ãéå§
document
èŠçŽ ã§ã€ãã³ããçºçããé©åãªãã³ãã©ãŒãåŒã³åºããŸããæ¬¡ã«äŸã瀺ããŸãã
DT.$document.trigger('gameOver', {cause: 'death'}); DT.$document.on('gameOver', function (e, data) { if (data.cause === 'death') { DT.audio.sounds.gameover.play(); } });
ã€ãã³ã
'blur'
ãš
'focus'
ã¯
window
ããªã¬ãŒãããã²ãŒã ã§ãŠã£ã³ããŠã®ãã©ãŒã«ã¹ã倱ããããšãã«ãµãŠã³ãããªãã«ããäžæåæ¢ããªã³ã«ããŸãã
DT.$window.on('blur', function() { if (DT.game.wasStarted && !DT.game.wasPaused && !DT.game.wasOver) { DT.$document.trigger('pauseGame', {}); } DT.setVolume(0); });
ã²ãŒã ã¯ãŒã«ãã®åæå
three.js
ãããžã§ã¯ãã§ã¯ããã¹ãŠãæšæºã§ããã·ãŒã³ãã«ã¡ã©ãã²ãŒã ã¹ããŒã¹ãå
æºãèæ¯ãäœæãããŸãã
ã·ãŒã³
DT.scene = new THREE.Scene();
ã«ã¡ã©
DT.splineCamera = new THREE.PerspectiveCamera( 84, window.innerWidth / window.innerHeight, 0.01, 1000 );
åçã¹ããŒã¹ã¯ãTHREE.Curvesã»ããã®TorusKnotã«ãŒãã«æ²¿ã£ããã€ãã§ã
var extrudePath = new THREE.Curves.TorusKnot(); DT.tube = new THREE.TubeGeometry(extrudePath, 100, 3, 8, true, true);
å
æº
DT.lights = { light: new THREE.PointLight(0xffffff, 0.75, 100), directionalLight: new THREE.DirectionalLight(0xffffff, 0.5) };
ã·ãŒã ã¬ã¹ãªæ¥ç¶ãå®çŸããããã«ãåãè²ã®å¢çç·ãæã€å
é¢ã«åŒã䌞ã°ãããåçãåãããéã³å Žã®åšãã®ç圢ã®èæ¯ã
èæ¯
var geomBG = new THREE.SphereGeometry(500, 32, 32), matBG = new THREE.MeshBasicMaterial({ map: THREE.ImageUtils.loadTexture('img/background5.jpg'), }), worldBG = new THREE.Mesh(geomBG, matBG); worldBG.material.side = THREE.BackSide;
ã¯ã©ã¹
ã²ãŒã ã«ã¯ããã€ãã®äž»èŠãªã¯ã©ã¹ããããŸãïŒã²ãŒã ïŒ
DT.Game
ïŒããã¬ã€ã€ãŒïŒ
DT.Player
ïŒããã³ã²ãŒã ãªããžã§ã¯ãïŒ
DT.GameObject
ïŒã ãããã«ã¯ãã€ãã³ãã®ããªã¬ãŒã«å¯Ÿå¿ããŠå¯Ÿå¿ãããã³ãã©ãŒã«ãã£ãŠåŒã³åºãããç¬èªã®ã¡ãœããïŒæŽæ°ããã³ããªã©ïŒããããŸãã ã²ãŒã ãªããžã§ã¯ãã«ã¯ãããŸããŸãªãã©ã¡ãŒã¿ãŒïŒé床ãå é床ïŒã宿°ïŒ
wasStarted
ã®æå°è·é¢ãšãã®ç¶æ
ã«é¢ããæ
å ±ïŒ
wasStarted
ã
wasPaused
ïŒãå«ãŸããŸãããã¬ãŒã€ãŒãªããžã§ã¯ãã«ã¯ããã¬ãŒã€ãŒã®çŸåšã®ç¶æ
ïŒã¹ã³ã¢ãã©ã€ããäžæ»èº«ç¶æ
ïŒãããã³ãã¬ãŒã€ãŒã¢ãã«ã®ç¶æ
ã«é¢ããæ
å ±ãå«ãŸããŸãïŒçäœãçäœã®åšãã®ãªã³ã°ïŒå¥åº·ç¶æ
ã瀺ã茪éïŒãïŒä»ã®ãã¹ãŠã®ãªããžã§ã¯ãã¯ãã²ãŒã ãªããžã§ã¯ãã®ãµãã¯ã©ã¹ïŒç²åããã¬ãŒã€ãŒã®çŸãããŒãã¹ïŒã§ãã
å
éšã¢ãã«ãšå€éšã¢ãã«
ã²ãŒã ã«ã¯2çš®é¡ã®ã¢ãã«ããããŸãïŒthree.jsããŒã«ã䜿çšããŠäœæãããå
éšïŒåçŽïŒã¢ãã«ïŒçäœããã«ã¹ã€ã³ãžã±ãŒã¿ãŒïŒãªã³ã°/茪éïŒãç³ãšã³ã€ã³ïŒãšå€éšïŒè€éãªïŒã¢ãã«ïŒçäœã®åšãã®ããŒãã¹ãšHTML5ã·ãŒã«ãïŒãèªã¿èŸŒãŸããŸã察å¿ãã
ããŒããŒã«ãã.obj圢åŒã
çäœã¯ãã¬ãŒã€ãŒã®ãªããžã§ã¯ãã®äžéšã§ããã2ã€ã®ãªããžã§ã¯ãã衚ããŸããä»ã®ãªããžã§ã¯ããšã®è¡çªãèšç®ããããã®ç©ççãªçäœïŒã·ãŒã³ã«ã¯è¿œå ãããŸããïŒ
çäœ
this.sphere = new THREE.Mesh(new THREE.SphereGeometry(0.5, 32, 32), new THREE.MeshPhongMaterial({}));
FireworksããŒãã£ã¯ã«ã·ã¹ãã çšã®ãšã³ãžã³ããŒã¹ã®ããŒãã£ã¯ã«ã·ã¹ãã ã

ããŒãã£ã¯ã«ã·ã¹ãã
this.emitter = Fireworks.createEmitter({nParticles : 100}) .effectsStackBuilder() .spawnerSteadyRate(30) .position(Fireworks.createShapePoint(0, 0, 0)) .velocity(Fireworks.createShapePoint(0, 0, 0)) .lifeTime(0.2, 0.7) .renderToThreejsParticleSystem({ ... }) .back() .start();
ããŒãã¹ã¢ãã«ã¯ãåãæ°ã®é ç¹ãæã€2ã€ã®ãªããžã§ã¯ãã®åœ¢åŒã§èªã¿èŸŒãŸããŸãïŒå€æçšïŒã
ã¢ãã«ãªã¹ã DT.listOfModels = [{ name: 'bonusH1', scale: 0.1, rotaion: new THREE.Vector3(0, 0, 0), color: 0xff0000, }, { name: 'bonusI', scale: 0.02, rotaion: new THREE.Vector3(0, 0, 0), color: 0x606060, '5': 0xffffff, 'html': 0xffffff, 'orange': 0xD0671F, 'shield': 0xC35020, }, { name: 'bonusE1', scale: 0.75, rotaion: new THREE.Vector3(0, 0, 0), color: 0x606060, }, { name: 'bonusH2', scale: 0.1, rotaion: new THREE.Vector3(0, 0, 0), color: 0xff0000, }, { name: 'shield', scale: 0.16, rotaion: new THREE.Vector3(0, 0, 0), color: 0x606060, }, { name: 'bonusE2', scale: 0.75, rotaion: new THREE.Vector3(0, 0, 0), color: 0x606060, } ];
ããŒãããŒã㌠var manager = new THREE.LoadingManager(), loader = new THREE.OBJLoader(manager); manager.onProgress = function (item, loaded, total) { console.info('loaded item', loaded, 'of', total, '('+item+')'); }; DT.listOfModels.forEach(function (el, i, a) { loader.load('objects/' + el.name + '.obj', function ( object ) { object.traverse( function ( child ) { var color = el[child.name] || el.color; child.material = new THREE.MeshPhongMaterial({ color: color, shading: THREE.SmoothShading, emissive: new THREE.Color(color).multiplyScalar(0.5), shininess: 100, }); }); if (i === 1) { a[i].object = object } else { a[i].object = object.children[0]; } DT.$document.trigger('externalObjectLoaded', {index: i}); }); });
ããŒãåŸãå€éšã¢ãã«ã¯ãªã³ã¯
DT.listOfModels[index].object
å©çšå¯èœã«ãªããããŒãã¹ã³ã³ã¹ãã©ã¯ã¿ãŒã§äœ¿çšãããŸãã
倿ïŒå€æïŒãšåŸåŠç
ã²ãŒã ã«ã¯ããã€ãã®å€æããããŸããã²ãŒã ã®çµäºæã®ãã«ã¹ã€ã³ãžã±ãŒã¿ãããŒãã¹ãã°ãªãããšãã§ã¯ãïŒãŸãã¯å£ãããã¬ãã®ãšãã§ã¯ãïŒã§ãã
å¥åº·ææšãšããŒãã¹å€æã¯
morphTargetsã«åºã¥ããŠã
ãŸã ã

ãªããžã§ã¯ããäœæãããšããæšæºç¶æ
ã¯ãã®ãªããžã§ã¯ãã®ãžãªã¡ããªã«ä¿åãããŸãã æ®ãã®ç¶æ
ã¯ãç¹å¥ãªãžãªã¡ããªããããã£
morphTargets
ä¿åãããŸãã ãªããžã§ã¯ãã®çŸåšã®ç¶æ
ã¯ããªããžã§ã¯ãã®
morphTargetInfluences
ã¬ãã«ã«ãã£ãŠæ±ºå®ãããŸãã
çã®åšå²ã®ãã«ã¹ã€ã³ãžã±ãŒã¿ïŒãªã³ã°/茪éïŒã¯2ã€ã®ãªããžã§ã¯ãã§ãããããã®ãžãªã¡ããªã¯180ã®é ç¹ïŒå
åŽãšå€åŽã«60ïŒã§æ§æãããŠããŸãã
ãªã³ã°/茪éã¯ãåã5ã4ãããã³äžè§åœ¢ã§ãé ç¹ã®æ°ã¯åžžã«180ã®ãŸãŸã§ãã
åç¶æ
ã®é ç¹ã®æ°ãåãã§ããããããã®åº§æšãã¯ãã«ãïŒç®çã®å€æã«åŸã£ãŠïŒãæ£ãããå€åããããšãéèŠã§ããããã§ãªãå Žåãå€æã¯æ£ããæ©èœããªããããŸã£ããæ©èœããŸããã
ãã®ããã«ããã«ã¹ã€ã³ãžã±ãŒã¿ã®ãžãªã¡ããªïŒãªã³ã°/茪éïŒãäœæããç¹å¥ãªé¢æ°ãäœæãããŸããã
ãã«ã¹ã€ã³ãžã±ãŒã¿ã®ãžãªã¡ã㪠DT.createGeometry = function (circumradius) { var geometry = new THREE.Geometry(), x, innerradius = circumradius * 0.97, n = 60; function setMainVert (rad, numb) { var vert = []; for (var i = 0; i < numb; i++) { var vec3 = new THREE.Vector3( rad * Math.sin((Math.PI / numb) + (i * ((2 * Math.PI)/ numb))), rad * Math.cos((Math.PI / numb) + (i * ((2 * Math.PI)/ numb))), 0 ); vert.push(vec3); } return vert; } function fillVert (vert) { var nFilled, nUnfilled, result = []; nFilled = vert.length; nUnfilled = n/nFilled; vert.forEach(function (el, i, arr) { var nextInd = i === arr.length - 1 ? 0 : i + 1; var vec = el.clone().sub(arr[nextInd]); for (var j = 0; j < nUnfilled; j++) { result.push(vec.clone().multiplyScalar(1/nUnfilled).add(el)); } }); return result; }
åãçç±ã§ãããŒãã¹ã¢ãã«ã¯2ã€ã®.objãªããžã§ã¯ãã®åœ¢åŒã§ã€ã³ããŒãããããšãã£ã¿ãŒã§ç¹å®ã®æ¹æ³ã§äºåã«å€æŽãããŸãïŒäºæ³ããã倿ïŒå€æïŒã¢ãã¡ãŒã·ã§ã³ã«å¿
èŠã§ãããã®ããã«3ds MaxãšBlenderã䜿çšããŸããã

ãªããã¢ãã«ã«ã¯è峿·±ãç¹ã1ã€ãããŸãã éåžžã®ç¶æ
ã§ã¯ãåã¯ã¢ãã¡ãŒã·ã§ã³åãããŸãïŒåå²ãããŠéããããŸãïŒã ãã®å Žåã2çµã®é ç¹ïŒéããåãšéããåïŒããã®é ç¹ã®åœ±é¿ã«åçŽã«å€åããããŸãã
three.jsã®ããã¥ã¡ã³ãã«ããã°ãåé ç¹ã»ããã®
morphTargetInfluenceå€ã¯[0ã1]ã®ç¯å²å
ã«ããå¿
èŠããããŸãã ãã®å Žåã1ãã倧ããåã䜿çšãããšãããã€ããŒã€ã³ãã«ãšã³ã¹ãã®åœ±é¿ãçºçããŸãã ãã®ãããããšãã°ãå€5ã®morphTargetInfluenceãç«ã¢ãã«ã®é ç¹ã»ããã«é©çšãããšãã¢ãã«ã¯ãè£è¿ããã«ãªããŸãã åã¢ãã«ã®å Žåããå£ãéããŠãããããã«èŠããŸãã
ãã®åäœã¯ã远å ã®å€éšã¢ãã«ã®ã€ã³ããŒããåé¿ããããªãããããŒãã¹ã®åžåã®å¹æã«åºã¥ããŠããŸãã
ã²ãŒã ã®çµãããã¢ãã¡ãŒã·ã§ã³åããããã«äœ¿çšãããã°ãªãã广ïŒãŸãã¯å£ãããã¬ãã®å¹æïŒã¯ã
ã·ã§ãŒããŒã䜿çšããåŸåŠçã®äŸã§ãã

ãšãã§ã¯ããäœæ
ã³ãŒã DT.effectComposer = new THREE.EffectComposer( DT.renderer ); DT.effectComposer.addPass( new THREE.RenderPass( DT.scene, DT.splineCamera ) ); DT.effectComposer.on = false; var badTVParams = { mute:true, show: true, distortion: 3.0, distortion2: 1.0, speed: 0.3, rollSpeed: 0.1 } var badTVPass = new THREE.ShaderPass( THREE.BadTVShader ); badTVPass.on = false; badTVPass.renderToScreen = true; DT.effectComposer.addPass(badTVPass);
ãã¬ãŒã ããšã«ã¬ã³ããªã³ã°ããŸã
ã³ãŒã DT.$document.on('update', function (e, data) { if (DT.effectComposer.on) { badTVPass.uniforms[ "distortion" ].value = badTVParams.distortion; badTVPass.uniforms[ "distortion2" ].value = badTVParams.distortion2; badTVPass.uniforms[ "speed" ].value = badTVParams.speed; badTVPass.uniforms[ "rollSpeed" ].value = badTVParams.rollSpeed; DT.effectComposer.render(); badTVParams.distortion+=0.15; badTVParams.distortion2+=0.05; badTVParams.speed+=0.015; badTVParams.rollSpeed+=0.005; }; });
ã€ãã³ã
'gameOver'
åŸã«å¹æãæå¹ã«ãªããŸã
ã³ãŒã DT.$document.on('gameOver', function (e, data) { DT.effectComposer.on = true; });
察å¿ããã€ãã³ããçºçãããšãªã»ãããããŸã
ã³ãŒã DT.$document.on('resetGame', function (e, data) { DT.effectComposer.on = false; badTVParams = { distortion: 3.0, distortion2: 1.0, speed: 0.3, rollSpeed: 0.1 } });
åŸåŠçã䜿çšãããšããã¬ãŒã ã®ã¬ã³ããªã³ã°æéã倧å¹
ã«å¢å ãããããã²ãŒã ã®çµäºæã«åŸåŠçãçæé䜿çšãããŸãã
鳿¥œã®èŠèŠå
鳿¥œã¯ãæŒå¥ç©ºéå
ã®ç²åïŒã»ããïŒã®èåã«ãã£ãŠèŠèŠåãããŸãã
ãã®ããã«ãæãŸããå¯èŠåé »åºŠãæ±ºå®ãããŸããã ç®çã®åšæ³¢æ°ã®é³ã®ååšã¬ãã«ïŒ
DT.audio.valueAudio
ïŒã¯ãçŸåšãèŠèŠåãããã¡ãŒã§æ¬¡ã®ããã«å®çŸ©ãããŠããŸã
ã³ãŒã var getFrequencyValue = function(frequency, bufferIndex) { if (!DT.isAudioCtxSupp) return; var nyquist = DT.audio.context.sampleRate/2, index = Math.round(frequency/nyquist * freqDomain[bufferIndex].length); return freqDomain[bufferIndex][index]; }; var visualize = function(index) { if (!DT.isAudioCtxSupp) return; freqDomain[index] = new Uint8Array(analysers[index].frequencyBinCount); analysers[index].getByteFrequencyData(freqDomain[index]); DT.audio.valueAudio = getFrequencyValue(DT.audio.frequency[index], index); };
DT.audio.valueAudio
ã®å€ã¯ãããŒãã£ã¯ã«ã®éæåºŠã®ç¶æ
ãæŽæ°ããããã«äœ¿çšãããŸãã
ã³ãŒã DT.$document.on('update', function (e, data) { DT.dust.updateMaterial({ isFun: DT.player.isFun, valueAudio: DT.audio.valueAudio, color: DT.player.sphere.material.color }); });
updateMaterial
ã¡ãœãã
updateMaterial
ïŒ
ã³ãŒã DT.Dust.prototype.updateMaterial = function (options) { if (!this.material.visible) { this.material.visible = true; } this.material.color = options.isFun ? options.color : new THREE.Color().setRGB(1,0,0); this.material.opacity = 0.5 + options.valueAudio/255; return this; };
WebAudio APIã®è©³çްã«ã€ããŠã¯ã
ãã¡ããã芧ãã ãã ã
ãã¡ãã³ã³ã¢ãã¡ãŒã·ã§ã³
ãã¡ãã³ã³ã®ããžã¿ã«æ
è¡ã¯ãããã©ã«ãã§ã¯ç«ã®çœé»ç»åã§ãã
ã¹ããŒã¢ãŒãïŒç«ã¢ãŒãïŒã§ã¯ãã¢ã€ã³ã³ã®è²ãå€ããå§ããŸãã
Firefoxã§ããªãã眮ãããšãã§ããå Žå
<link rel="icon" type="image/gif" href="fav.gif">
ãã®æ¹æ³ã¯Chromeã§ã¯æ©èœããŸããã Chromeã§ã¯ãåçãªãã¡ãã³ã³pngã¹ããŒãã£ã³ã°ã䜿çšãããŸããã
äžè¬çãªå®è£
ã¯æ¬¡ã®ããã«ãªããŸãã
ã³ãŒã var favicon = document.getElementsByTagName('link')[1], giffav = document.createElement('link'), head = document.getElementsByTagName('head')[0], isChrome = navigator.userAgent.indexOf('Chrome') !== -1; giffav.setAttribute('rel', 'icon'); giffav.setAttribute('type', 'image/gif'); giffav.setAttribute('href', 'img/fav.gif'); DT.$document.on('update', function (e, data) { if (isChrome && DT.player.isFun && DT.animate.id % 10 === 0) favicon.setAttribute('href', 'img/' + (DT.animate.id % 18 + 1) + '.png'); }); DT.$document.on('showFun', function (e, data) { if (!data.isFun) { if (isChrome) { favicon.setAttribute('href', 'img/0.png'); } else { $(giffav).remove(); head.appendChild(favicon); } } else { if (!isChrome) { $(favicon).remove(); head.appendChild(giffav); } } });
'update'
'showFun'
ãªããžã§ã¯ãã®ç¶æ
ãæŽæ°ããã€ãã³ãã
'showFun'
ã·ãŒã«ã¢ãŒãã®éå§ã®ã€ãã³ãïŒæžéïŒã
DT.player.isFun
ã·ãŒã«ã¢ãŒãã®ç¶æ
ã
DT.animate.id
çŸåšã®ãã¬ãŒã ïŒãã¬ãŒã ïŒã®çªå·ã ãã¡ãã³ã³ã«ã¯19ã®ãªãã·ã§ã³ããããŸãããæ®å¿µãªãããSafariã«ã¯ãã¡ãã³ã³ã¢ãã¡ãŒã·ã§ã³ã¯ãããŸããã
ã¢ãã€ã«ã³ã³ãããŒã©ãŒ
ã²ãŒã ã«ã¯ã¢ãã€ã«ããã€ã¹ãå¶åŸ¡ããæ©èœããããŸãã
ã¢ãã€ã«ããã€ã¹ãã³ã³ãããŒã©ãŒãšããŠæ¥ç¶ããã«ã¯ããªã³ã¯ããã©ããã
ãã©ã°ã€ã³ã«ãã£ãŠçæãããQRã³ãŒãã䜿çšããå¿
èŠããã
ãŸã ã
å¶åŸ¡ã¯ããžã£ã€ãã¹ã³ãŒããšã€ãã³ã
'deviceOrientation'
ã䜿çšããŠå®è¡ãããŸãã ãžã£ã€ãã¹ã³ãŒãããªãå ŽåããŸãã¯ãžã£ã€ãã¹ã³ãŒãã«ã¢ã¯ã»ã¹ã§ããªãå Žåãå¶åŸ¡ãã¿ã³ãæŒãããšã«ããå¶åŸ¡ã䜿çšãããŸãã
ãã©ãŒã«ããã¯ãšãã³ãã©ãŒïŒ
'deviceOrientation'
ãµããŒãã®ç¢ºèªã¯ã
'deviceOrientation'
ããµããŒãããããã€ã¹ïŒããšãã°HTC One VïŒããããŸãããã€ãã³ãèªäœã¯çºçããªãããã
eventSupported
ãšã¯
eventSupported
ã
setTimeout
ãä»ããŠå®è£
ãããŸãã å®éãããæéééã®éãã€ãã³ããçºçããã®ãåŸ
ã£ãŠããŸãïŒééããªãçºçããã¯ãã§ãïŒãçºçããªãå Žåãã€ãã³ãã¯ãµããŒããããŠããªããšå€æããŸãã ãã®ãããªãã§ãã¯ã¯å®éã«ã¯ããã¯ã§ãã
äžéšã®é»è©±ïŒWindows PhoneæèŒã®HTCãªã©ïŒã§ã¯ãæšæºãã©ãŠã¶ãŒïŒã¢ãã€ã«IEïŒã¯
'touchstart'
ã€ãã³ãããµããŒãããŠããŸããããããé«ãã¬ãã«ã®
'click'
ã€ãã³ãããµããŒãããŠã
'click'
ã
'click'
ã€ãã³ãã䜿çšããå Žåã®å¿çæéïŒ300ããªç§ïŒã¯
'touchstart'
ã®å¿çæéãããã¯ããã«é·ãããã®ãããªããã€ã¹ã䜿çšããç£èŠã«å¿
èŠãªå¿çã¬ãã«ãæäŸã§ããªãããããã®ãããªããã€ã¹ã®ãµããŒããæåŠããŸããã
ãšããã§ãHDDãæèŒããäžéšã®Macbook Proã¢ãã«ã®ãŠãŒã¶ãŒã¯ããžã£ã€ãã¹ã³ãŒããåããŠããããããã®ã¢ãŒãã§ã©ãããããã䜿çšã§ããŸãã
Android 4.0以äžãæèŒããããã€ã¹ã®ãŠãŒã¶ãŒã«ã¯ãå°ããªããŒãã¹ããããŸããç³ã«ééããå ŽåïŒæ¯å100ããªç§ïŒãŸãã¯ã³ã€ã³ãæŸã£ãå ŽåïŒæ¯å10ããªç§ïŒã®ã³ã³ãããŒã©ãŒã®å¿çã§ãã ãããè¡ãã«ã¯ãVibration APIã䜿çšããŸãïŒææ°ã®æšæºãã©ãŠã¶ãŒãã¢ãã€ã«ChromeãŸãã¯Firefoxãå¿
èŠã§ãïŒã
ãã¡ãããVibration APIã®è©³çްã
ã芧ãã ãã ã
ããã€ã¹ã®åŸããå¶åŸ¡ããå ŽåããŠãŒã¶ãŒã¯é·æéç»é¢ã«è§Šããªãããšããããããã€ã¹ãããã¯ãããç»é¢ã空çœã«ãªãããã©ãŠã¶ãŒããžã£ã€ãã¹ã³ãŒãããã®ããŒã¿éä¿¡ã忢ããŸãã ãã®åäœãé²ãããã«ããªãŒãã£ãªã«ãŒãã§ããããã¯ã䜿çšãããŸããã10ç§éã®ãµã€ã¬ã³ããã©ãã¯ã¯ãåšæçã«åçããããã¿ã³ãæŒããããšéå§ãåéãäžæåæ¢ããŸãã
<audio id="audioloop" src="../sounds/loop.mp3" onended="this.play();" autobuffer></audio>
$('#btnSphere').on('touchstart',function () { socket.emit('click', {'click':'pause'}); $('#audioloop').trigger('play'); });
åæã«ãAndroid OSãæèŒããããã€ã¹ã§ã¯ãé³å£°ã«ãŒãã1ç§ã«ãªããiOSãæèŒããããã€ã¹ã§ã¯ãããé·ããã©ãã¯ãå¿
èŠã«ãªããŸãã iOSã§ã¯ãSafariãã©ãŠã¶ãŒã¯ç¡éã«ãã©ãã¯ãåçããããµã€ã¯ã«æ°ã¯çŽ100ã§ããããã10ç§ã®ãã©ãã¯é·ãéžæãããŸããã
ãŠã§ãã«ã¡ã©å¶åŸ¡
Webcamã³ã³ãããŒã«ã¯
getUserMedia()
ã¡ãœããã«åºã¥ããŠããŸãã
Webã«ã¡ã©å¶åŸ¡ã®äŸãããã€ãèŠãŠããŸããã 1ã€ã®ãªãã·ã§ã³ã¯ããã®
äŸã®ããã«ä»®æ³ããŒãæŒãããš
ã§ã ã

æ£ç¢ºæ§ãäžååã§ããããšã倿ãããããæåŠããŸããã
å¥ã®ãªãã·ã§ã³ã¯ããããã¢ã³ã°ã«ãš
headtrackr.jsã©ã€ãã©ãªã䜿çšããããšã§ãã ããã¯ããè峿·±ãããšã倿ããéŠã䌞ã°ããŠç·åŒµãåãããã®ã«åœ¹ç«ã¡ãŸããããè§åºŠã¯åžžã«æ£ããæ±ºå®ãããŠããŸããã§ããã ãã®çµæãWebã«ã¡ã©ã䜿çšããŠå¶åŸ¡ããããã«ãé ã®äœçœ®ãšç»é¢ã®äžå€®ã«å¯Ÿããçžå¯Ÿçãªåãã䜿çšãããŸãïŒheadtrackr.jsã䜿çšïŒã
ãã®å¶åŸ¡æ¹æ³ã¯ãããŒããŒããã¢ãã€ã«ããã1æ¡è€éã§ãããããWebã«ã¡ã©å¶åŸ¡ã¢ãŒãã§ã®ã²ãŒã é床ãäœäžããŸãã
ããã¯ãšã³ã
ã²ãŒã ãµãŒããŒã¯node.jsã§å®è¡ãããŸãã 䜿çšãããã¢ãžã¥ãŒã«ã¯ãexpressãsocket.ioãmongooseãnode-dogecoinãããã³hookshotã§ãã
ããã§ã¯ãã¹ãŠãéåžžã«ç°¡åã§ããsocket.ioã¯ãã©ã³ã¹ããŒããæäŸããexpressã¯ã«ãŒããšéçãæ
åœããmongooseã¯ã¯ã©ã€ã¢ã³ããããŒã¿ããŒã¹ã«ä¿åããŸãã ããã¯ã·ã§ããã¯ãVPSãžã®å€æŽããã°ããå±éããããã«äœ¿çšãããŸãã
app.use('/webhook', hookshot('refs/heads/master', 'git pull'));
ããã¯ãšã³ãã§æãè峿·±ãã®ã¯ãåããµãŒããŒã«ãããã€ãããdogecoinããŒã¢ã³ãšã®çžäºäœçšã§ãã ããã¯æ¬æ ŒçãªdogecoinãŠã©ã¬ããã§ãããnode-dogecoinã¢ãžã¥ãŒã«ã䜿çšããŠæ¬¡ã®ããã«çžäºäœçšãè¡ãããŸãã
dogecoin.exec('getbalance', function(err, balance) { console.log(err, balance); });
ããã«ããµãŒããŒã¯ã¯ã©ã€ã¢ã³ãã®äžæ£ããã§ãã¯ããŸãã ããã§ã¯ãã¯ã©ã€ã¢ã³ãããã€ã€ã«ããã³ã€ã³ã®æ°ããã§ãã¯ããããã®ã»ãã·ã§ã³äžã«åéã§ããã³ã€ã³ã®æå€§æ°ãšæ¯èŒãããŸãã
ã³ãŒã var checkCoins = function (timeStart, timeEnd, coinsCollect) { var time = (timeEnd - timeStart)/1000, maxCoins = calcMaxCoins(time);
ãŸãã1ã€ã®UIDïŒCookieïŒãš1ã€ã®IPããã®2ã€ã®æãè¿ãã²ãŒã éã®æéã䜿çšããŠã1ã€ã®IPããã®æ¯æãåæ°ã®æ€èšŒãå®è£
ããŸããã³ãŒã var checkClient = function (clients, currentClient) { console.log("Handle clients from Array[" + clients.length + "]") var IPpaymentsCounter = 0, UIDpaymentsCounter = 0, IPtimeCounter = 60 * 1000, checkup = null; clients.forEach(function(client, i) { if (client.clientIp === currentClient.clientIp && client.paymentRequest) { IPpaymentsCounter += client.paymentRequest; if (currentClient.timeEnd && currentClient.cientId !== client.cientId) { Math.min(IPtimeCounter, currentClient.timeEnd - client.timeEnd); } } if (client.cookieUID === currentClient.cookieUID && client.paymentRequest) { UIDpaymentsCounter += client.paymentRequest; }
ããã¯ã䟿å®ã®ååã«åºã¥ãåçŽãªé²åŸ¡ã§ãããããã«
ãã®èšäºã§ã¯ãéçºäžã«åºäŒã£ãæãè峿·±ãç¹ããªã¹ãããŸããããã®æ
å ±ãã圹ã«ç«ãŠã°å¹žãã§ãããã¹ãŠã®éçºã¯GitHubã§å®è¡ãããŸãããã³ãŒãã¯ãã¡ãã«ãããŸãããªã³ã¯ïŒgithubãããžã§ã¯ããã²ãŒã ã®èª¬æãã²ãŒã ã®äœ¿çšããŒã«ãšã©ã€ãã©ãªïŒ