Jogo IA AStar Jquery / CSS / Html / Web

Jogo IA AStar Jquery / CSS / Html / Web

Tela1

Hoje, vamos saborear uma Web Salada que deverá ser preparada com o mínimo de Inteligência pelo desenvolvedor. Mas para que a salada fique saborosa e não perca a consistência é preciso que contenha os temperos JQUERY e CSS na composição.

 Tela2

A receita leva um tempo para preparar, mas o resultado é muito apetitoso. A Web Salada pode ser preparada em qualquer editor de textos (recomendamos pelo menos o notepad ++), mas fica muito bonita e colorida se preparada e servida em uma vasilha da marca ECLIPSE.

“A* Ghost Pathrun é um jogo criado para ambiente Web com a técnica de Inteligência Artificial (A*)”

Tela3

Configuração inicial de ambiente Randômico. Dificuldade / Objetivo também randômico.

O jogo é baseado na técnica de IA : A* Pathfiding, onde até 3 fantasmas podem seguir o mesmo objetivo (Você) simultâneamente…

O objetivo do jogo é capturar os monstros que estão no cemitério,, mas é preciso ter cuidado para não utilizar a sua mágica nas lápides ou nos fantasmas… ou poderá perder suas chances…

Gerado em um ambiente WEB a linguagem escolhida para desenvolvimento do game foi o JavaScript, em união com a biblioteca jquery-1.7.1.min

O game está dividido em 3 arquivos principais:

pathrun.html = Esqueleto e chamadas do game.
pathrun.css = Configura todo o Ambiente e Sprites.
pathrun.js = Interação e funcionalidades do game.

Cada clique do mouse aciona a função de busca do A*,fazendo que surja mais um fantasma a sua procura.

Tela4

Para configuração do pathfiding a tela foi divida em blocos de 32×32 pixels e todos os sprites foram
configurados com o mesmo tamanho dos blocos, facilitando o calculo de posicionamento.

Ao Iniciar o game, carregam-se : Variáveis globais; Arquivos de som;

Nesmo momento também são chamadas as configurações de ambiente no arquivo css.

Inicia-se o processo de construção do ambiente e então mostra a primeira mensagem do jogo:

“ELIMINE OS MONSTROS, MAS NAO DEIXE OS FANTASMAS TE PEGAREM.”

Ao iniciar o game, o primeiro processo randômico de criação do cenário é consolidado com as implementações do path fiding PathfindingSearch().

Inicia-se então as variáveis padrão do jogo e os textos de informação do painel direito da tela.

Os [nodes] do grid do cenário vão se formando um a um e conforme as configurações randômicas criadas definem cada bloco como cenário padrão, monstro, lápide de cemitério ou posição inicial dos fantasmas.

Tela5

Cada clique na tela chama a função PathfindingSearch.prototype.cellClicked() Que executa as rotinas  de verificação do bloco clicado e aciona o A* criando um fantasma e iniciando o processo de Pathfiding pelo mesmo…

As verificações de bloco e a função de A* e Pathfiding repetem-se até não restarem chances para o jogador, ou o clique tenha sido feito em um bloco com um fantasma ou todos os monstros tenham sido capturados.

————————————–

Para preparar o game siga os passos a seguir :

1) INSTALE O NOTEPAD ++ (SE DESEJAR)

2) ABRA O NOTEPAD, O EDITOR DE TEXTOS DE SUA PREFERENCIA OU ALGUMA IDE DE SEU USO

3) CRIE UM NOVO ARQUIVO COM A EXTENSÃO .HTML (Pode ser pathrun.html)

4) COPIE O CÓDIGO ABAIXO PARA ESTE ARQUIVO (ESTE CÓDIGO VAI SER SERVIR COMO MOLDURA PARA O JOGO, ALÉM DE CHAMAR AS ESTRUTURAS DE CSS E JQUERY)

pathrun.html

<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
        <link rel="stylesheet" type="text/css" media="screen, projection" href="pathrun.css" />
    </head>
    <div id="outer-container">  
    
    <div id="top-Nav">  
        <h1 align='center'>A* GHOST PATHRUN</h1>   
    </div>  
    
    <div style="clear: both">  
    </div>  
    
    <div id="left-sidebar">  
    </div>  
        
    <div id="content-container">  
        <div align='center' style="float:middle;">
        </div>
        
        <div id="content" align='center'>
            <div id="main">
                <div id="search_tiles">Carregando...</div>
            </div>
        </div>
        
        <div id="footer">
        </div>
        
        <script type='text/javascript' src='jquery-1.7.1.min.js'></script>
        <script type='text/javascript' src='jquery.jWebAudio.js'></script>
        <script type='text/javascript' src='pathrun.js'></script>  
    </div>  


    <div align='center' id="right-sidebar">  
        <h2>
        <input id="selectObstaculoFrequencia" name="selectObstaculoFrequencia"           value=".1"         type="hidden">
        <input id="selectTilesSize"              name="selectTilesSize"                   value="20"         type="hidden">
        <br />
        <input type="button" id="btnGenerate" value="TENTE NOVAMENTE" />
        <br />
        <br> <h2 id='labelchances'>Chances : 5 <h2></br>
        <br> <h2 id='labeltentativas'>Tentativas : 0 <h2></br>
        <br> <h2 id='labelmonstro'> Monstros : X <h2></br>
        <br> <h2 id='labelpontuacao'>Pontuação : 0 <h2></br>
        <br> <h2 id='labelnfantasmas'>Fantasmas : 0 <h2></br>
        <h3>
        <br> Clique para eliminar os monstros antes que os fantasmas te alcancem... </br>
        <br> Você perde a chance a cada clique errado. Você tem apenas 5 chances de erro.. </br>
        </h1>
        </h3>  
    </div>  
    
    <div style="clear: both">  
    </div>  
        
    </div> 
    <div id="footer">  
        <h3>Puc-PR - Desenvolvimento de Jogos Digitais - Enzo A. Marchiorato - Disciplina : IA para Jogos</h3>  
    </div>  

</html>

5) CRIE AGORA UM ARQUIVO COM O NOME DE (pathrun.js)

6) COPIE O CÓDIGO ABAIXO PARA ESTE ARQUIVO (ESTE CÓDIGO VAI CHAMAR AS BIBLIOTECAS DO JQUERY, GAME QUERY E AS FUNÇÕES DO JOGO)

pathrun.js

var OBSTACULO = 0;
var chances = 5;
var tentativas = 0;
var pontuacao = 0;
var nfantasmas = 1;
var monstro = 1;
var monstroindice = 1;


var byebye = document.createElement('audio');
var source = document.createElement('source');
var hahaha = document.createElement('audio');
var source2 = document.createElement('source');
var ghostwalk = document.createElement('audio');
var source3 = document.createElement('source');
var monstrofala = document.createElement('audio');
var source4 = document.createElement('source');
var monstromorre = document.createElement('audio');
var source5 = document.createElement('source');
var playerdie = document.createElement('audio');
var source6 = document.createElement('source');
var step = document.createElement('audio');
var source7 = document.createElement('source');

source.src = 'sounds/byebye.wav';
source2.src = 'sounds/hahaha.wav';
source3.src = 'sounds/ghostwalk.wav';
source4.src = 'sounds/monstrofala.wav';
source5.src = 'sounds/monstromorre.wav';
source6.src = 'sounds/playerdie.wav';
source7.src = 'sounds/step.wav';

byebye.appendChild(source);
hahaha.appendChild(source2);
ghostwalk.appendChild(source3);
monstrofala.appendChild(source4);
monstromorre.appendChild(source5);
playerdie.appendChild(source6);
step.appendChild(source7);

performance = window.performance;

// FUNCAO PRINCIPAL
$(function() {

    hahaha.play();
    
    alert('ELIMINE OS MONSTROS, MAS NAO DEIXE OS FANTASMAS TE PEGAREM.'); // ALERTA INICIAL
    
    var $tiles = $("#search_tiles"),
        $selecionarObstaculoFrequencia = $("#selectObstaculoFrequencia"), // FREQUENCIA DE APARICAO DO TILE
        $selecionarTilesSize = $("#selectTilesSize"), // TAMANHO DO TILE
        $procurarDiagonal = $("#searchDiagonal"),
        $checkMaisProximo = $("#checkMaisProximo");

    var opts = {
        obstaculoFrequencia: $selecionarObstaculoFrequencia.val(),
        tilesSize: $selecionarTilesSize.val(),
        diagonal: $procurarDiagonal.is("checked"),
        closest: $checkMaisProximo.is("checked")
        };

  
    var tiles = new PathfindingSearch($tiles, opts, astar.search);

    $("#btnGenerate").click(function() {
           tiles.initialize();
    });

});

var css = { origem: "origem", destino: "destino", obstaculo: "obstaculo", ativo: "ativo", monstro1: "monstro1", monstro2: "monstro2", monstro3: "monstro3", monstro4: "monstro4"};

function PathfindingSearch($pathfinding, options, implementation) {
    this.$pathfinding = $pathfinding;
    this.search = implementation;
    this.opts = $.extend({obstaculoFrequencia:0.1, debug:true, tilesSize:10}, options);
    this.initialize();
}
PathfindingSearch.prototype.setOption = function(opt) {
    this.opts = $.extend(this.opts, opt);
};

PathfindingSearch.prototype.initialize = function() {
    tentativas = 0; // RESETA
    chances = 5; // RESETA
    pontuacao = 0; // RESETA
    nfantasmas = 1; // RESETA
    monstro = 1; // RESETA
    monstroindice = 1; // RESETA
    
    document.getElementById("labeltentativas").innerHTML = "Tentativas : " + tentativas;
    document.getElementById("labelchances").innerHTML = "Chances : " + chances;
    document.getElementById("labelpontuacao").innerHTML = "Pontuacao : " + pontuacao;
    document.getElementById("labelnfantasmas").innerHTML = "Fantasmas : " + nfantasmas;
    document.getElementById("labelmonstro").innerHTML = "Monstros : " + monstro;
    
    this.tiles = [];
    var self = this,
        nodes = [],
       $pathfinding = this.$pathfinding;

    $pathfinding.empty();
    step.play();

    var cellWidth = ($pathfinding.width()/this.opts.tilesSize)-2,
        cellHeight = ($pathfinding.height()/this.opts.tilesSize)-2,
        $cellTemplate = $("<span />").addClass("tiles_item").width(cellWidth).height(cellHeight),
        origemSet = false;

    for(var x = 0; x < this.opts.tilesSize; x++) {
        var $row = $("<div class='clear' />"),
            nodeRow = [],
            tilesRow = [];


        for(var y = 0; y < this.opts.tilesSize; y++) {
            var id = "cell_"+x+"_"+y,
                $cell = $cellTemplate.clone();
            $cell.attr("id", id).attr("x", x).attr("y", y);
            $row.append($cell);
            tilesRow.push($cell);

            var ismonstro = Math.floor((Math.random() * 20) + 0);

            var isObstaculo = Math.floor(Math.random()*(1/self.opts.obstaculoFrequencia));
            
            if(isObstaculo === 0) { //DESENHA OS TILES NORMAIS ***************************************************************************
                nodeRow.push(OBSTACULO);
                $cell.addClass(css.obstaculo);
            }
            else if(ismonstro === 0) { //DESENHA OS MONSTROS ***************************************************************************
                //nodeRow.push(OBSTACULO);
                $cell.addClass(css.monstro2);
                monstro = monstro + 1;
                document.getElementById("labelmonstro").innerHTML = "Monstros : " + monstro;
            }
            else  { // DESENHA OS OBSTACULOS *********************************************************************************************
                var cell_weight = ($("#generateWeights").prop("checked") ? (Math.floor(Math.random() * 3)) * 2 + 1 : 1);
                nodeRow.push(cell_weight);
                $cell.addClass('weight1');
                if (!origemSet) {
                    $cell.addClass(css.origem);
                    origemSet = true;// APARECE O FANTASMA NA ORIGEM
                }
            }
        }

        $pathfinding.append($row);

        this.tiles.push(tilesRow);
        nodes.push(nodeRow);
    }

    this.pathfinding = new Pathfinding(nodes);

    this.$cells = $pathfinding.find(".tiles_item");
    this.$cells.click(function() {
        self.cellClicked($(this));
    });
};

//--------------------------------------------------------------------------------------------------

PathfindingSearch.prototype.cellClicked = function($end) {
    tentativas = tentativas + 1; // DETECTA E REALIZA AÇÃO PARA O CLIQUE DO MOUSE NO TABULEIRO
    document.getElementById("labeltentativas").innerHTML = "Tentativas : " + tentativas;
    var end = this.nodeFromElement($end);

//------------------------------------------------------------------------------------------------    
    if($end.hasClass(css.obstaculo) || $end.hasClass(css.origem) || $end.hasClass(css.wheight1)) {
        hahaha.play();
        chances = chances - 1;
        document.getElementById("labelchances").innerHTML = "Chances : " + chances;
        if (chances < 1){
            alert ("GAME OVER - PERDEU TODAS AS CHANCES"); 
            window.location.reload();
        }
        return;
    }

    if($end.hasClass(css.ativo)) {
        monstrofala.play();
        alert ("GAME OVER - PEGO PELO FANTASMA"); 
        window.location.reload();
    }
    
    //------------------------------------------------------------------------------------------------
    if($end.hasClass(css.monstro2)) {
        monstromorre.play();
        monstro = monstro - 1
        document.getElementById("labelmonstro").innerHTML = "Monstros : " + monstro;
        pontuacao = pontuacao + 100
        document.getElementById("labelpontuacao").innerHTML = "Pontuacao : " + pontuacao;
        //this.$pathfinding.find("." + css.destino).removeClass(css.monstro).addClass(css.obstaculo);
        this.$pathfinding.find("." + css.destino).removeClass(css.monstro2).addClass('weight1');
        this.$pathfinding.find("." + css.origem).removeClass(css.monstro2).addClass('weight1');
        //$cell.addClass('weight1');
        //alert ("ITEM"); 
        if (monstro < 1){
            step.play();
            alert ("VOCÊ ALCANÇOU O OBJETIVO COM " + pontuacao + " PONTOS" ); 
            window.location.reload();
        }
    }
//------------------------------------------------------------------------------------------------
    if (tentativas > 29){
        playerdie.play();
        alert ("GAME OVER - 30 TENTATIVAS"); 
        window.location.reload();
    }
    
//------------------------------------------------------------------------------------------------    
    this.$cells.removeClass(css.destino);
    $end.addClass("destino");
    var $origem = this.$cells.filter("." + css.origem),
        origem = this.nodeFromElement($origem);

    var sTime = performance ? performance.now() : new Date().getTime();

    var path = this.search(this.pathfinding, origem, end, {
        closest: this.opts.closest
    });
    var fTime = performance ? performance.now() : new Date().getTime(),
        duration = (fTime-sTime).toFixed(2);

    if(path.length === 0) {
        $("#message").text("couldn't find a path (" + duration + "ms)");
        this.animateNoPath();
        //alert('Assim não vale !!!.');  
    }
    else {
        $("#message").text("search took " + duration + "ms.");
        this.animatePath(path);
    }
//------------------------------------------------------------------------------------------------
};

//--------------------------------------------------------------------------------------------------

PathfindingSearch.prototype.nodeFromElement = function($cell) {
    return this.pathfinding.tiles[parseInt($cell.attr("x"))][parseInt($cell.attr("y"))];
};

PathfindingSearch.prototype.animatePath = function(path) {
    var tiles = this.tiles,
        timeout = 5000 / tiles.length,
        elementFromNode = function(node) {
        return tiles[node.x][node.y];
    };

    var self = this;

    var removeClass = function(path, i) {
        if(i >= path.length + 10) {
            return setorigemClass(path, i); // LIMPA AS CLASSES DOS FANTASMAS
        }
    
        elementFromNode(path[i]).removeClass(css.ativo); // EXCLUI UMA CLASSE DE FANTASMA NO ULTIMO TILE DO PATH
    
        setTimeout(function() {
            removeClass(path, i+1);
            nfantasmas = nfantasmas - 1; // diminiu 1 do numero de fantasmas
            document.getElementById("labelnfantasmas").innerHTML = "Fantasmas : " + nfantasmas; // Mostras número de Fantasmas
        }, timeout*path[i].getCost());
    };
    
    var setorigemClass = function(path, i) {//REM--------------------------------------------------------------------------------
        if(i === path.length) {//REM---------------------------------------------------------------------------------------------
            self.$pathfinding.find("." + css.origem).removeClass(css.origem);//REM-----------------------------------------------
            elementFromNode(path[i-1]).addClass(css.origem);//REM----------------------------------------------------------------
        }//REM-------------------------------------------------------------------------------------------------------------------
            
    };
   
   var addClass = function(path, i) {
        if(i >= path.length) {
            return removeClass(path, 0); // LIMPA AS CLASSES DOS FANTASMAS
        }

        elementFromNode(path[i]).addClass(css.ativo); // INCLUI UMA CLASSE DE FANTASMA NO TILE ATUAL DO PATH
    
        setTimeout(function() {
            ghostwalk.play(); // SOM DO PASSO DO FANTASMA
            addClass(path, i+1);
            nfantasmas = nfantasmas + 1; // aumenta do numero de fantasmas
            document.getElementById("labelnfantasmas").innerHTML = "Fantasmas : " + nfantasmas; // Mostras número de Fantasmas
        }, timeout*path[i].getCost());
    };

    addClass(path, 0);
    this.$pathfinding.find("." + css.origem).removeClass(css.origem); //SETA O DESTINO
    this.$pathfinding.find("." + css.destino).removeClass(css.destino).addClass(css.origem); //SETA NOVA ORIGEM
};

(function(definition) {
    if(typeof module === 'object' && typeof module.exports === 'object') {
        module.exports = definition();
    } else if(typeof define === 'function' && define.amd) {
        define([], definition);
    } else {
        var exports = definition();
        window.astar = exports.astar;
        window.Pathfinding = exports.Pathfinding;
    }
})(function() {


function pathTo(node){
    var curr = node,
        path = [];
    while(curr.parent) {
        path.push(curr);
        curr = curr.parent;
    }
    return path.reverse();
}

function getHeap() {
    return new BinaryHeap(function(node) {
        return node.f;
    });
}

var astar = {
    init: function(pathfinding) {
        for (var i = 0, len = pathfinding.nodes.length; i < len; ++i) {
            var node = pathfinding.nodes[i];
            node.f = 0;
            node.g = 0;
            node.h = 0;
            node.visited = false;
            node.closed = false;
            node.parent = null;
        }
    },

    search: function(pathfinding, origem, end, options) {
    
        astar.init(pathfinding);

        options = options || {};
        var heuristic = options.heuristic || astar.heuristics.manhattan,
            closest = options.closest || false;

        var openHeap = getHeap(),
            closestNode = origem; 
        
        origem.h = heuristic(origem, end);

        openHeap.push(origem);

        while(openHeap.size() > 0) {

            var currentNode = openHeap.pop();

            if(currentNode === end) {
                return pathTo(currentNode);
            }

               currentNode.closed = true;

             var neighbors = pathfinding.neighbors(currentNode);

            for (var i = 0, il = neighbors.length; i < il; ++i) {
                var neighbor = neighbors[i];

                if (neighbor.closed || neighbor.isObstaculo()) {
                    continue;
                }

                var gScore = currentNode.g + neighbor.getCost(currentNode),
                    beenVisited = neighbor.visited;

                if (!beenVisited || gScore < neighbor.g) {

                    neighbor.visited = true;
                    neighbor.parent = currentNode;
                    neighbor.h = neighbor.h || heuristic(neighbor, end);
                    neighbor.g = gScore;
                    neighbor.f = neighbor.g + neighbor.h;

                    if (closest) {
                         if (neighbor.h < closestNode.h || (neighbor.h === closestNode.h && neighbor.g < closestNode.g)) {
                            closestNode = neighbor;
                        }
                    }

                    if (!beenVisited) {
                        openHeap.push(neighbor);
                    }
                    else {
                        openHeap.rescoreElement(neighbor);
                    }
                }
            }
        }

        return [];
    },
    heuristics: {
        manhattan: function(pos0, pos1) {
            var d1 = Math.abs(pos1.x - pos0.x);
            var d2 = Math.abs(pos1.y - pos0.y);
            return d1 + d2;
        },
    }
};


function Pathfinding(tilesIn, options) {
    // MONTA O GRID PRINCIPAL DO CENARIO
    options = options || {};
    this.nodes = [];
    this.tiles = [];
    for (var x = 0; x < tilesIn.length; x++) {
        this.tiles[x] = [];

        for (var y = 0, row = tilesIn[x]; y < row.length; y++) {
            var node = new TilesNode(x, y, row[y]);
            this.tiles[x][y] = node;
            this.nodes.push(node);
            
        }
    }
}
//----------- RETORNA OS NODES DOS FANTASMAS ----------------------

Pathfinding.prototype.neighbors = function(node) {
    var ret = [],
        x = node.x,
        y = node.y,
        tiles = this.tiles;

    // West
    if(tiles[x-1] && tiles[x-1][y]) {
        ret.push(tiles[x-1][y]);
    }

    // East
    if(tiles[x+1] && tiles[x+1][y]) {
        ret.push(tiles[x+1][y]);
    }

    // South
    if(tiles[x] && tiles[x][y-1]) {
        ret.push(tiles[x][y-1]);
    }

    // North
    if(tiles[x] && tiles[x][y+1]) {
        ret.push(tiles[x][y+1]);
    }

    return ret;
};

//-------------------------------------------------------------------------------

function TilesNode(x, y, weight) {
    this.x = x;
    this.y = y;
    this.weight = weight;
}

TilesNode.prototype.getCost = function() {
    return this.weight;
};

TilesNode.prototype.isObstaculo = function() {
    return this.weight === 0;
};

function BinaryHeap(scoreFunction){
    this.content = [];
    this.scoreFunction = scoreFunction;
}

BinaryHeap.prototype = {
    push: function(element) {
        this.content.push(element);

        this.sinkDown(this.content.length - 1);
    },
    pop: function() {
        var result = this.content[0];
        var end = this.content.pop();
        if (this.content.length > 0) {
            this.content[0] = end;
            this.bubbleUp(0);
        }
        return result;
    },
    remove: function(node) {
        var i = this.content.indexOf(node);
        var end = this.content.pop();

        if (i !== this.content.length - 1) {
            this.content[i] = end;

            if (this.scoreFunction(end) < this.scoreFunction(node)) {
                this.sinkDown(i);
            }
            else {
                this.bubbleUp(i);
            }
        }
    },
    size: function() {
        return this.content.length;
    },
    rescoreElement: function(node) {
        this.sinkDown(this.content.indexOf(node));
    },
    sinkDown: function(n) {
        var element = this.content[n];
        while (n > 0) {
            var parentN = ((n + 1) >> 1) - 1,
                parent = this.content[parentN];
            if (this.scoreFunction(element) < this.scoreFunction(parent)) {
                this.content[parentN] = element;
                this.content[n] = parent;
                n = parentN;
            }
            else {
                break;
            }
        }
    },
    bubbleUp: function(n) {
        var length = this.content.length,
            element = this.content[n],
            elemScore = this.scoreFunction(element);

        while(true) {
            var child2N = (n + 1) << 1,
                child1N = child2N - 1;
            var swap = null,
                child1Score;
            if (child1N < length) {
                var child1 = this.content[child1N];
                child1Score = this.scoreFunction(child1);
                if (child1Score < elemScore){
                    swap = child1N;
                }
            }
            if (child2N < length) {
                var child2 = this.content[child2N],
                    child2Score = this.scoreFunction(child2);
                if (child2Score < (swap === null ? elemScore : child1Score)) {
                    swap = child2N;
                }
            }
            if (swap !== null) {
                this.content[n] = this.content[swap];
                this.content[swap] = element;
                n = swap;
            }
           else {
                break;
            }
        }
    }
};

return {
    astar: astar,
    Pathfinding: Pathfinding
};

});

7) AGORA CRIE UM ARQUIVO COM O NOME (pathrun.css). ESSE AQUIVO CONTÉM TODA A CONFIGURAÇÃO VISUAL DO GAME E CHAMADAS DE SOM E SPRITES.

pathrun.css

html, body {
    height:100%;
    margin:0;
}
/* CORPO */  
body {  
    margin: 0px;  
    padding: 0px;  
}  

.clearfix {
  *zoom: 1;
}
.clearfix:before, .clearfix:after {
  display: table;
  content: "";
}
.clearfix:after {
  clear: both;
}

/* h1 */  
h1 {  
    margin: 0px;  
    padding: 0px;  
    font-family: Georgia;  
    font-size: 25px;  
    color: YELLOW;  
}

h2 {
    margin: 0px;  
    padding: 0px;  
    font-family: Georgia;  
    font-size: 25px;  
    color: lightblue;  
}

h3 {
    margin: 0px;  
    padding: 0px;  
    font-family: Georgia;  
    font-size: 15px;  
    color: yellow;  
}

#outer-container {  
    width: 100%;  
    margin: 0 auto;  
}

.links {
    clear:both;
    background: rgba(0, 0, 0, .1);
    padding: 4px;
    padding-left: 20px;
    padding-bottom:5px;
}
.links a {
    padding: 3px;
    color: #339;
}
.buttons { 
    float:right;
    position:relative;
    right: 10px;
    top: 10px;
}
.buttons a {
    text-decoration: none;
}

#pathfinding {
    overflow-x:scroll;
    width: 90%;
    font-size: .8em;
    margin:0 auto;
    white-space:pre;
    border:none;
}
#content {
    margin:0 auto;
    width:98%;
}


#header {  
    width: 100%;  
    height: 30px;  
    background-color: blue;  
    background:#fafafa url('imagens/backtopmenu.png') repeat;
}  

#footer {
    width:100%;  
    background-color: red;  
    font-size:8px;
    font-family: Georgia;    
    background:#fafafa url('imagens/backdownmenu.png') repeat;
}

#content-container {  
    width: 70%;  
    height: 610px;  
    background-color: green;  
    margin: 2px 0px 2px 0px;  
    float: left;  
    background:#fafafa url('imagens/backmapa.png') repeat;
} 


#left-sidebar {  
    width: 5%;  
    height: 610px;  
    background-color: navy;  
    margin: 2px 2px 2px 0px;  
    float: left;  
    background:#fafafa url('imagens/backleftmenu.png') repeat;
}  
  
#right-sidebar {  
    width: 24%;
    height: 610px;  
    background-color: navy;  
    margin: 2px 0px 2px 2px;  
    float: right;  
    background:#fafafa url('imagens/backrightmenu.png') repeat;
}  
  
#top-Nav {  
    width: 100%;  
    background-color: black;  
    margin: 2px 0px 0px 0px;  
    background:#fafafa url('imagens/backtopmenu.png') repeat;
} 


#header a, #footer a {
    font-size:.9em;
    font-family: Georgia;
}
ul.basics {
    list-style-type:none;
}
ul.basics li {
    margin-bottom: .45em;
}
.result-panel {
    width:80%;
    padding:10px;
    margin:10px;
    -moz-border-radius: 5px;
    -webkit-border-radius: 5px;
    border: 1px solid #000;
}
pre {
    padding-left:10px;
    border-left: solid 5px #99b;
}
.result-panel pre {
    border-left: solid 5px #b99;
}
.result-panel pre span {
    font-size:1.4em;
    color: #f11;
    font-weight:bold;
}
pre span.key {
    color: #f11;
    font-weight:normal;
}


.left {
    float:left;
}
.right {
    float: right;
}
.clear:after {
    content: ".";
    display: block;
    height: 0;
    clear: both;
    visibility: hidden;
}

#message {
    color:#f00;
    font-size:1.2em;
}
#controls {
    border: dashed 3px #9999BB;
    border-left:none;
    border-right:none;
    margin-bottom: 25px;
    padding:5px 0;
    width:650px;
}
#search_tiles  {
    width:650px;
    height:650px;
    position: relative;
}

.tiles_item {
    display: block;
    border: 0px solid #bbb;
    float: left;
    line-height:12px;
    font-size:10px;
    
}
.tiles_item.monstro1 {
  background-color: #000000;
  background:#fafafa url('imagens/monstro1.png') repeat;
  cursor: url('imagens/capture.png'), default;
}
.tiles_item.monstro2 {
  background-color: #000000;
  background:#fafafa url('imagens/monstro2.png') repeat;
  cursor: url('imagens/capture.png'), default;
}
.tiles_item.monstro3 {
  background-color: #000000;
  background:#fafafa url('imagens/monstro3.png') repeat;
  cursor: url('imagens/capture.png'), default;
}
.tiles_item.monstro4 {
  background-color: #000000;
  background:#fafafa url('imagens/monstro4.png') repeat;
  cursor: url('imagens/capture.png'), default;
}

.tiles_item.obstaculo {
  background-color: #000000;
  background:#fafafa url('imagens/obstaculo.png') repeat;
  cursor: url('imagens/cuidado.png'), default;
}
.tiles_item.weight1 {
  background-color: #ffffff;
  background:#fafafa url('imagens/terrain.png') repeat;
  cursor: url('imagens/procura.png'), default;
}
.tiles_item.weight3 {
  background-color: #D6EAFF;
}
.tiles_item.weight5 {
  background-color: #ABD1FF;
}
.tiles_item.origem {
    background-color: #FF703F;
    background:#fafafa url('imagens/origem.png') repeat;
    cursor: url('imagens/aguarda.png'), default;
}
.tiles_item.ativo {
    background-color: #FF703F;
    background:#fafafa url('imagens/ativo.png') repeat;
    cursor: url('imagens/cuidado.png'), default;
}
.tiles_item.destino {
    background:#fafafa url('imagens/destino.png') repeat;
    cursor: url('imagens/aguarda.png'), default;

}
#weightsKey {
  display: none;
}

8) SALVE OS ARQUIVOS CRIADOS EM UMA MESMA PASTA E DESCOMPACTE O SEGUINTE ARQUIVO DA BIBLIOTECA DO JQUERY E DO GAMEQUERY (jquery-1.7.1.min.zip).

jquery-1.7.1.min.zip

9) AGORA, CRIE UMA PASTA COM O NOME DE [imagens] E SALVE AS IMAGENS ABAIXO DENTRO DA PASTA [imagens],  (ESTAS SERÃO AS ANIMAÇÕES E SPRITES  APLICADAS NOS OBJETOS DO GAME).

aguarda ativo backdownmenu backleftmenu backmapa backrightmenu backtopmenu capture capture0 cuidado destino destino2 itensrestantes killgui monstro1 monstro2 monstro3 monstro4 obstaculo origem procura terrain

10) AGORA, CRIE UMA PASTA COM O NOME DE [sounds] E SALVE OS ARQUIVOS ABAIXO DENTRO DA PASTA [sounds],  (ESTES SERÃO OS EFEITOS SONOROS DO GAME).

byebye.wav

ghostwalk.wav

hahaha.wav

monstrofala.wav

monstromorre.wav

playerdie.wav

step.wav

11) AGORA É SÓ CLICAR 2X NO ARQUIVO pathrun.html QUE VOCÊ CRIOU E PRONTO, O JOGO DEVE ESTAR FUNCIONANDO REDONDINHO.

12) AGORA EXPERIMENTE ALTERAR ALGUNS COMPONENTES DA RECEITA, ESTUDE O CÓDIGO, FAÇA IMPLEMENTAÇÕES E CRIE SEU PRÓPRIO GAME WEB COM TÉCNICA DE IA (A*) UTILIZANDO HTML, JQUERY E CSS….

SEGUE FONTE COMPLETO ABAIXO

Jogo IA AStar Jquery CSS Html Web.zip

Anúncios

Deixe um comentário

Preencha os seus dados abaixo ou clique em um ícone para log in:

Logotipo do WordPress.com

Você está comentando utilizando sua conta WordPress.com. Sair / Alterar )

Imagem do Twitter

Você está comentando utilizando sua conta Twitter. Sair / Alterar )

Foto do Facebook

Você está comentando utilizando sua conta Facebook. Sair / Alterar )

Foto do Google+

Você está comentando utilizando sua conta Google+. Sair / Alterar )

Conectando a %s