Skip to content

Instantly share code, notes, and snippets.

@felipap
Last active December 20, 2015 18:08
Show Gist options
  • Save felipap/6173272 to your computer and use it in GitHub Desktop.
Save felipap/6173272 to your computer and use it in GitHub Desktop.
Trabalho do Castaneda.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf8">
<title>Pong Game</title>
<link href="http://netdna.bootstrapcdn.com/bootstrap/3.0.0-rc1/css/bootstrap.min.css" rel="stylesheet">
<link href="http://netdna.bootstrapcdn.com/font-awesome/3.2.0/css/font-awesome.css" rel="stylesheet">
<style type="text/css">
body {
padding-top: 80px;
}
canvas {
outline: 1px solid #DDD;
cursor: none;
width: 100%;
}
#canvas {
position: relative;
text-align: center;
}
#canvas h3 {
display: none;
position: absolute;
top: 170px;
width: 700px;
margin-left: -350px;
left: 50%;
font-weight: normal;
}
#canvas h3.visible {
display: auto;
}
</style>
</head>
<body>
<div class="container">
<div class="row">
<div id="canvas" class="col-8">
<h3 data-msg="mouseout"><strong>canvas:hover</strong> para voltar ao jogo</h3>
<canvas width="500" height="500">Your browser does not support canvas.</canvas>
</div>
<div class="col-4">
<div class="well">
<h1><strong>4-Pong</strong></h1>
<h4>Não deixe a bola tocar na lateral!</h4>
<p>Ganha quem reduzir as traves ao seu tamanho mínimo.</p>
<button id='gmode' type="button" class="btn btn-primary" onClick="game.gmode = !game.gmode" data-toggle="button">Go GMODE</button>
<button id='gmode' type="button" class="btn btn-danger" onClick="game.hardMode()" >Go Modo <strong>HARD</strong></button>
<h3> <span class="label label-info">Score: <span id="score">0/???</span></span></h3>
</div>
<div class="alert alert-warning" style="display: none" id="errrou">
<a class="close" data-dismiss="alert" href="#">&times;</a>
<h2><a href="#" class="alert-link"><strong>Que decepção!</strong><br>Você perdeu o jogo<br> (e <strong>O JOGO</strong> também).</a></h2>
</div>
<div class="alert alert-warning" style="display: none" id="acertou">
<a class="close" data-dismiss="alert" href="#">&times;</a>
<h2><a href="#" class="alert-link">Ohhh, o aluninho ganhou? Grandes merda.</h2>
</div>
<div class="alert alert-warning" style="display: none" id="msg1">
<a class="close" data-dismiss="alert" href="#">&times;</a>
<h2><a href="#" class="alert-link">Está comprovado que existe um chinês de 8 anos de idade que pode fazer tudo melhor que você.<strong>Por que você não desiste da vida?</strong>
</div>
</div>
</div>
</div>
<script src="http://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.4.4/underscore-min.js" type="text/javascript"></script>
<script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/2.0.3/jquery.min.js" type="text/javascript"></script>
<script src="http://netdna.bootstrapcdn.com/bootstrap/3.0.0-rc1/js/bootstrap.min.js"></script>
<script type="text/javascript">
var canvas = document.querySelector("canvas");
var ctx = canvas.getContext('2d');
canvas.width = $(canvas).width(); // make canvas take full width
var min = Math.min,
max = Math.max,
abs = Math.abs;
"use strict";
Number.prototype.btw = function (a, b) {
// Return true if this is between a,b
return (a<b)?(this>=a&&this<=b):(this>=b&&this<=a);
}
Number.prototype.close = function (a, dev) {
// Return true if this is within dev from a
return Math.abs(this-a)<=dev;
}
Number.prototype.sign = function () {
return this?(this<0?-1:1):0;
}
var rainbow = function (numOfSteps, step) {
var b, c, f, g, h, i, q, r;
h = step / numOfSteps;
i = ~~(h * 6);
f = h * 6 - i;
q = 1 - f;
switch (i % 6) {
case 0:
r = 1; g = f; b = 0; break;
case 1:
r = q; g = 1; b = 0; break;
case 2:
r = 0; g = 1; b = f; break;
case 3:
r = 0; g = q; b = 1; break;
case 4:
r = f; g = 0; b = 1; break;
case 5:
r = 1; g = 0; b = q;
}
c = "#" + ("00" + (~~(r * 255)).toString(16)).slice(-2) + ("00" + (~~(g * 255)).toString(16)).slice(-2) + ("00" + (~~(b * 255)).toString(16)).slice(-2);
return c;
};
var Ball = function (x, y, vel) {
var size = 8,
vel_x = (vel||1)*(3+Math.random()*5)/5, // .2 to 1 of vel
vel_y = (vel||1)*(3+Math.random()*5)/5, // .2 to 1 of vel
x = Math.max(x, size),
y = Math.max(y, size);
this.tic = function (clock, tframe) {
var _x = x, _y = y; // save old
var collided = false;
x = max(0, min(x+vel_x, canvas.width-size));
y = max(0, min(y+vel_y, canvas.height-size));
// Check for collisions in the trajectory.
// In that case, move the ball back and invert velocity.
// Notice bar.crosses parameters are different for the different
// orientation of the bars.
for (var i=0, bar=game.bars[0]; i<game.bars.length; bar=game.bars[++i]) {
if (bar instanceof HorizontalBar) {
if (bar.crosses(_x, _y, x+size, y)) { // collision!
y = (vel_y>0)?(bar.y-size):(bar.y+bar.size_y+1);
// x-Distortion based on collision position to the bar
dx = (x-bar.x-bar.size_x/2)/(bar.size_x/2);
vel_y *= -1;
vel_x += vel*dx; // don't ask me why!
$(bar).trigger('collision', {type:'horizontal'});
collided = true;
}
} else if (bar instanceof VerticalBar) {
if (bar.crosses(_x, _y, x, y+size)) { // collision!
x = (vel_x>0)?(bar.x-size):(bar.x+bar.size_x+1);
// x-Distortion based on collision position to the bar
dy = (y-bar.y-bar.size_y/2)/(bar.size_y/2);
vel_x *= -1;
vel_y += vel*dy; // don't ask me why!
$(bar).trigger('collision', {type:'vertical'});
collided = true;
}
}
}
// Limit velocities!
vel_x = vel_x.sign()*min(vel*2, Math.abs(vel_x))
vel_y = vel_y.sign()*min(vel*2, Math.abs(vel_y))
if (!collided) {
if (0 == y || y == canvas.height-size) {
$(game).trigger('lost');
vel_y *= -1
}
else if (0 == x || x == canvas.width-size) {
$(game).trigger('lost')
vel_x *= -1
}
}
}
this.draw = function (context) {
context.fillStyle = rainbow(canvas.width, x); "rgb(200,0,0)";
context.fillRect(x,y,size,size);
}
};
var VerticalBar = function (size_x, size_y, cMin, cMax, x, vel) {
var y = cMin,
x = min(x, canvas.width-size_x),
cMin = min(cMin, canvas.height-size_y),
cMax = min(cMax, canvas.height);
this.tic = function (tframe) {
y = max(cMin, min(y+vel, cMax-size_y));
if (cMin == y || y == cMax-size_y)
vel *= -1
}
this.moveTo = function (a, b) {
y = b-size_y/2;
}
this.crosses = function (a, b, p, q) {
//console.log('crosses (%s): %s is in (%s, %s)',(x+size_x).btw(a, p), x+size_x, a, p)
return (x.btw(a, p) || (x+size_x).btw(a, p)) && // cross in the x axis
(b.btw(y, y+size_y) || q.btw(y, y+size_y)); // cross in the y axis
}
this.draw = function (context) {
context.fillStyle = "rgb(150,150,150)";
context.fillRect(x, y, size_x, size_y);
}
this.decreaseSize = function (am) {
size_y = max(50, size_y-(am||5));
}
this.__defineGetter__('x', function(){ return x; })
this.__defineGetter__('y', function(){ return y; })
this.__defineGetter__('size_x', function(){ return size_x; })
this.__defineGetter__('size_y', function(){ return size_y; })
};
var HorizontalBar = function (size_x, size_y, cMin, cMax, y, vel) {
var x = cMin,
y = min(y, canvas.height-size_y),
cMin = min(cMin, canvas.width-size_x),
cMax = min(cMax, canvas.width);
this.tic = function (tframe) {
x = max(cMin, min(x+vel, cMax-size_x));
if (cMin == x || x == cMax-size_x)
vel *= -1
}
this.moveTo = function (a, b) {
x = a-size_x/2;
}
this.crosses = function (a, b, p, q) {
return (y.btw(b, q) || (y+size_y).btw(b, q)) && // cross in the y axis
(a.btw(x, x+size_x) || p.btw(x, x+size_x)); // cross in the x axis
}
this.draw = function (context) {
context.fillStyle = "rgb(150,150,150)";
context.fillRect(x, y, size_x, size_y);
}
this.decreaseSize = function (am) {
size_x = max(50, size_x-(am||5));
}
this.__defineGetter__('x', function(){ return x; })
this.__defineGetter__('y', function(){ return y; })
this.__defineGetter__('size_x', function(){ return size_x; })
this.__defineGetter__('size_y', function(){ return size_y; })
};
var game_started = false,
barMaxSize = 100,
barMinSize = 50,
barDecStep = 25,
maxScore = (barMaxSize-barMinSize)*4/barDecStep;
$("#score").html('0/'+maxScore);
function Game() {
var ball, bars, score;
this.gmode = false;
var frate = 60;
function clear(canvas) {
ctx.fillStyle = "rgba(255,255,255,1)";
ctx.fillRect(0, 0, canvas.width, canvas.height);
}
this.reset = function () {
console.log('call')
score = 0;
ball = new Ball(70, 70, frate/5);
var w = canvas.width, h = canvas.height;
bars = [
new VerticalBar(6, barMaxSize, 0, h, 3, frate/15),
new VerticalBar(6, barMaxSize, 0, h, w-3-6, frate/15),
new HorizontalBar(barMaxSize, 6, 0, w, 3, frate/15),
new HorizontalBar(barMaxSize, 6, 0, w, h-3-6, frate/15),
]
$(bars).bind('collision', function (evt) {
console.log('collision')
evt.target.decreaseSize(5);
++score;
console.log(score)
if (score === maxScore) {
$(game).trigger('won');
}
$("#score").html(''+score+'/'+(barMaxSize-barMinSize)*4/barDecStep);
})
}
$(this).bind('lost', function () {
if (this.gmode)
return;
ball = null;
bars = [];
window.game_started = false;
console.log('Lost game!');
$("#errrou").slideDown().delay(5000).slideUp();
game.reset();
})
$(this).bind('won', function () {
$("#acertou").slideDown().delay(5000).slideUp();
setTimeout(this.reset, 2000);
});
this.hardMode = function () {
for (var i=0; i<bars.length; i++) {
bars[i].decreaseSize(1000);
}
}
this.start = function () {
this.reset();
(function Draw () {
if (game_started && window.mouseover) {
clear(canvas);
ball.tic();
for (var i=0; i<bars.length; i++)
if (!window.mouseover)
bars[i].tic();
ball.draw(ctx);
for (var i=0; i<bars.length; i++)
bars[i].draw(ctx);
} else {
ctx.fillStyle = "rgba(255,255,255,.1)";
ctx.fillRect(0, 0, canvas.width, canvas.height);
}
setTimeout(Draw, window.mousedown?750:frate);
})();
}
this.__defineGetter__('ball', function(){return ball;});
this.__defineGetter__('bars', function(){return bars;});
}
var game = new Game();
game.start();
function listenCanvas(label, global, value) {
$(canvas).bind(label, function (evt) {
window[global]=value;
});
}
listenCanvas('mousedown', 'mousedown', true);
listenCanvas('mouseup', 'mousedown', false);
listenCanvas('mouseover', 'mouseover', true);
listenCanvas('mouseleave', 'mouseover', false);
$(canvas).bind('mousemove', function() {window.mouseover=true; window.game_started=true; });
$(canvas).bind('mouseleave', function () {
$("[data-msg=mouseout]").fadeIn();
})
$(canvas).bind('mouseover', function () {
$("[data-msg=mouseout]").fadeOut();
})
$('body').bind('mousemove', function (evt) {
var rect = canvas.getBoundingClientRect();
var mousePos = { x: evt.clientX - $(canvas).offset().left, y: evt.clientY - $(canvas).offset().top };
for (var i=0; i<game.bars.length; i++)
game.bars[i].moveTo(mousePos.x, mousePos.y)
});
</script>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment