<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	xmlns:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd"
	xmlns:media="http://search.yahoo.com/mrss/"
>

<channel>
	<title>Abrindo o Jogo &#187; Programação</title>
	<atom:link href="http://abrindoojogo.com.br/category/programacao/feed" rel="self" type="application/rss+xml" />
	<link>http://abrindoojogo.com.br</link>
	<description></description>
	<lastBuildDate>Mon, 06 Feb 2012 10:00:08 +0000</lastBuildDate>
	<language>pt-br</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0.1</generator>
	<copyright>Copyright © Abrindo o Jogo 2011 </copyright>
	<managingEditor>contato@abrindoojogo.com.br (Abrindo o Jogo)</managingEditor>
	<webMaster>contato@abrindoojogo.com.br (Abrindo o Jogo)</webMaster>
	<ttl>1440</ttl>
	<image>
		<url>http://abrindoojogo.com.br/files/logoItunes_144.jpg</url>
		<title>Abrindo o Jogo</title>
		<link>http://abrindoojogo.com.br</link>
		<width>144</width>
		<height>144</height>
	</image>
	<itunes:subtitle>PodAbrir - o Podcast do Abrindo o Jogo.</itunes:subtitle>
	<itunes:summary>Dicas e opiniões sobre a indústria dos games, abordando desde o desenvolvimento até o mercado.</itunes:summary>
	<itunes:keywords>jogos, game, development, desenvolvimento, indie, programming</itunes:keywords>
	<itunes:category text="Games &#38; Hobbies">
		<itunes:category text="Video Games" />
	</itunes:category>
	<itunes:category text="Technology" />
	<itunes:author>Abrindo o Jogo</itunes:author>
	<itunes:owner>
		<itunes:name>Abrindo o Jogo</itunes:name>
		<itunes:email>contato@abrindoojogo.com.br</itunes:email>
	</itunes:owner>
	<itunes:block>no</itunes:block>
	<itunes:explicit>no</itunes:explicit>
	<itunes:image href="http://abrindoojogo.com.br/files/logoItunes_600.jpg" />
		<item>
		<title>Tutorial HTML 5 &#8211; Parte 1/3</title>
		<link>http://abrindoojogo.com.br/tutorial-html-5-parte-13</link>
		<comments>http://abrindoojogo.com.br/tutorial-html-5-parte-13#comments</comments>
		<pubDate>Wed, 11 Jan 2012 21:35:07 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[HTML 5]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Tutorial]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://abrindoojogo.com.br/?p=3748</guid>
		<description><![CDATA[Prometido no ano passado, finalmente o tutorial de HTML 5 chegou! Neste tutorial em 3 partes veremos o básico sobre como usar o objeto &#60;canvas&#62; em conjunto com técnicas que permitem a criação de jogos de forma semelhante ao que já fazemos em outras linguagens. Nesta parte 1 aprenderemos como inicializar o canvas e carregar e [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2011/10/HTML5-logo.png"><img class="alignleft size-thumbnail wp-image-3349" title="HTML5-logo" src="http://abrindoojogo.com.br/wp-content/uploads/2011/10/HTML5-logo-150x150.png" alt="" width="150" height="150" /></a>Prometido no ano passado, finalmente o tutorial de HTML 5 chegou! Neste tutorial em 3 partes veremos o básico sobre como usar o objeto &lt;canvas&gt; em conjunto com técnicas que permitem a criação de jogos de forma semelhante ao que já fazemos em outras linguagens.</p>
<p>Nesta parte 1 aprenderemos como inicializar o canvas e carregar e exibir imagens.</p>
<p><span id="more-3748"></span>A primeira coisa que precisamos saber para criar jogos em HTML 5 é&#8230; bem, HTML! É necessário o conhecimento básico de tags e de como criar pelo menos uma página vazia para conter o jogo.</p>
<p>A segunda coisa é um pouco de CSS, que serve para configurar os elementos inseridos na página (bordas, cores, tamanhos, etc). Jogos mais avançados em HTML utilizam muitos elementos fora do &lt;canvas&gt;, que vamos ver nesse tutorial, tirando proveito de outros elementos HTML para apresentar dados e de CSS para formatar este dados.</p>
<p>Finalmente, precisamos saber também Javascript (JS) para fazer a programação da lógica do jogo. A sintaxe é parecida com Java ou C++ e oferece suporte a objetos, embora não seja de fato uma linguagem orientada a objetos. Não oferece, por exemplo, recurso para herança, embora seja possível simular isto com construções mais avançadas.</p>
<p>Vou assumir que você entende pelo menos o mínimo de HTML e CSS e que sabe incluir scripts em uma página. Mas a necessidade disto é tão pequena para este tutorial que é até possível você aprender o necessário só estudando os exemplos.</p>
<p>Dito isso, vamos em frente.</p>
<h2>O elemento &lt;canvas&gt;</h2>
<p>Uma das novidades que a versão 5 da HTML trouxe foi a tag &lt;canvas&gt;, que cria na página um elemento que permite o desenho direto. Antes disso, para exibir imagens era preciso inserir um elemento &lt;img&gt; para cada uma. Ess elemento cria um objeto gráfico no navegador para armazenar e apresentar a imagem &#8211; este tipo de objeto consome recursos do sistema. Se todas imagens fossem sprites animados, teríamos um página bem pesada para o navegador renderizar. Com o canvas, no entanto, podemos desenhar nele todas imagens necessárias e o navegador só vai renderizar o canvas &#8211; como se fosse uma única imagem.</p>
<p>Além disso, com o canvas podemos desenhar primitivas gráficas, como linhas, retângulos e texto, além de ter efeitos de composição na aplicação das imagens. A grosso modo, o canvas é como uma imagem cujo conteúdo pode ser modificado. Utilizamos ele como se fosse a tela, desenhando nele cada quadro do jogo.</p>
<p>A inclusão de um elemento canvas na página é feita com a tag &lt;canvas&gt;&gt;. No exemplo de código abaixo temos uma página HTML que contém esta tag e também um elemento &lt;div&gt; acima do canvas, dentro do qual vai uma informação textual.</p>

<div class="wp_syntax"><div class="code"><pre class="xml" style="font-family:monospace;">&nbsp;
        <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;script</span> <span style="color: #000066;">src</span>=<span style="color: #ff0000;">&quot;aoj/aojcanvas.js&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><span style="color: #808080; font-style: italic;">&lt;!--mce:0--&gt;</span><span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/script<span style="color: #000000; font-weight: bold;">&gt;</span></span></span>
<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;div</span> <span style="color: #000066;">id</span>=<span style="color: #ff0000;">&quot;info&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>Abrindo o Jogo - exemplo de uso do elemento canvas<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/div<span style="color: #000000; font-weight: bold;">&gt;</span></span></span></pre></div></div>

<p>Note que esta página inclui dois arquivos externos:</p>
<p><strong>css/estilos.css</strong>: Contém o código CSS de formatação dos elementos. Esse código se refere aos elementos pelo seu ID, sendo que o div possui o ID &#8220;info&#8221; e o canvas possui o ID &#8220;Canvas1&#8243;.</p>
<p>O conteúdo deste arquivo é o seguinte:</p>

<div class="wp_syntax"><div class="code"><pre class="css" style="font-family:monospace;">body <span style="color: #00AA00;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">margin</span><span style="color: #00AA00;">:</span> <span style="color: #933;">0px</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">border</span><span style="color: #00AA00;">:</span> <span style="color: #993333;">none</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">background-color</span><span style="color: #00AA00;">:</span> <span style="color: #000000; font-weight: bold;">black</span><span style="color: #00AA00;">;</span>
<span style="color: #00AA00;">&#125;</span>
<span style="color: #cc00cc;">#canvas1</span> <span style="color: #00AA00;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">position</span><span style="color: #00AA00;">:</span> <span style="color: #993333;">absolute</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">left</span><span style="color: #00AA00;">:</span> <span style="color: #933;">50%</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">top</span><span style="color: #00AA00;">:</span> <span style="color: #933;">50%</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">margin-left</span><span style="color: #00AA00;">:</span> <span style="color: #933;">-480px</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">margin-top</span><span style="color: #00AA00;">:</span> <span style="color: #933;">-300px</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">background-color</span><span style="color: #00AA00;">:</span> <span style="color: #993333;">white</span><span style="color: #00AA00;">;</span>
<span style="color: #00AA00;">&#125;</span>
<span style="color: #cc00cc;">#info</span> <span style="color: #00AA00;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">background-color</span><span style="color: #00AA00;">:</span> <span style="color: #000000; font-weight: bold;">blue</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">color</span><span style="color: #00AA00;">:</span> <span style="color: #993333;">yellow</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">font-family</span><span style="color: #00AA00;">:</span> Arial<span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">font-size</span><span style="color: #00AA00;">:</span> <span style="color: #933;">14px</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">font-weight</span><span style="color: #00AA00;">:</span> <span style="color: #993333;">bold</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">padding</span><span style="color: #00AA00;">:</span> <span style="color: #933;">5px</span><span style="color: #00AA00;">;</span>
    <span style="color: #000000; font-weight: bold;">text-align</span><span style="color: #00AA00;">:</span> <span style="color: #993333;">center</span><span style="color: #00AA00;">;</span>
<span style="color: #00AA00;">&#125;</span></pre></div></div>

<p>Basicamente o código deste arquivo muda o fundo da página para preto, centraliza o canvas na tela e aplica estilo de fundo, cor e fonte ao div que apresenta o texto. É comum colocarmos os arquivos de estilo dentro de uma pasta &#8220;css&#8221;.</p>
<p><strong>aoj/aojcanvas.js</strong>: este arquivo de script possui o código para inicialização e uso do canvas, contendo algumas rotinas criadas para facilitar a programação. Veremos como usar o canvas a seguir.</p>
<h2>Usando o elemento canvas</h2>
<p>Para obter uma referência ao elemento canvas, usamos o comando document.getElementById(), passando o ID que especificamos para nosso canvas. Obtemos a referência e atribuímos para uma variável, assim:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">    <span style="color: #003366; font-weight: bold;">var</span> _aojCanvas <span style="color: #339933;">=</span> document.<span style="color: #660066;">getElementById</span><span style="color: #009900;">&#40;</span>canvasId<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Para desenhar algo nele, precisamos obter um contexto gráfico, o que é feito com o método getContext do canvas. Esse método requer um parâmetro que, atualmente, só pode ser &#8220;2d&#8221;.</p>
<p>Depois de obter o contexto, atribuindo ele a uma variável, usamos os métodos dele para desenhar. Veja abaixo:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">window.<span style="color: #000066;">onload</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> _aojCanvas <span style="color: #339933;">=</span> document.<span style="color: #660066;">getElementById</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'canvas1'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #003366; font-weight: bold;">var</span> ctx <span style="color: #339933;">=</span> _aojCanvas.<span style="color: #660066;">getContext</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'2d'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">beginPath</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// inicia um desenho.</span>
    ctx.<span style="color: #660066;">fillStyle</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">'blue'</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// especifica a cor de preenchimento.</span>
    ctx.<span style="color: #660066;">strokeStyle</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">'red'</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// especifica a cor de contorno.</span>
    ctx.<span style="color: #660066;">rect</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">200</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// especifica um retângulo.</span>
    ctx.<span style="color: #660066;">rect</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">220</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// especifica outro retângulo.</span>
    ctx.<span style="color: #660066;">stroke</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// contorna o desenho (dois retângulos).</span>
    ctx.<span style="color: #660066;">fill</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// preenche o desenho (dois retângulos).</span>
    ctx.<span style="color: #660066;">beginPath</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// inicia outro desenho.</span>
    ctx.<span style="color: #660066;">strokeStyle</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">'black'</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// muda a cor de contorno.</span>
    ctx.<span style="color: #660066;">rect</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// especifica um retângulo.</span>
    ctx.<span style="color: #660066;">stroke</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// contorna o desenho (um retângulo).</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>O código acima desenha dois retângulos preenchidos de azul dentro do canvas. Cada desenho é iniciado com beginPath. Se este método não fosse chamado na segunda vez, o terceiro retângulo especificado ainda seria parte do primeiro desenho e o comando stroke iria contornar os três retângulos.</p>
<p>Perceba que o código foi colocado dentro de uma função atribuída ao evento onload da janela, para que seja executado apenas depois dela carregar completamente. Isso é importante porque se não for feito, o código executaria assim que fosse baixado &#8211; o que poderia ocorrer antes mesmo da declaração do canvas ter sido carregada &#8211; o que resultaria em erro porque o objeto canvas não existira ainda na página.</p>
<h2>Métodos de atalho</h2>
<p>A utilização do canvas para desenhar é algo de baixo nível. São precisos vários comandos para desenhar um retângulo na tela, por exemplo.</p>
<p>Para facilitar a programação, é interessante criar funções auxiliares que incluem todas chamadas necessárias para realizar determinadas ações. Assim criamos uma biblioteca própria. O arquivo aojcanvas.js é um exemplo de biblioteca deste tipo, embora incompleta.</p>
<p>Vejamos algumas funções deste arquivo para entender essa prática:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> aojSetCanvas<span style="color: #009900;">&#40;</span>canvasId<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    _aojCanvas <span style="color: #339933;">=</span> document.<span style="color: #660066;">getElementById</span><span style="color: #009900;">&#40;</span>canvasId<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #003366; font-weight: bold;">function</span> aojFillStyle<span style="color: #009900;">&#40;</span>optionalNewValue<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> ctx <span style="color: #339933;">=</span> _aojCanvas.<span style="color: #660066;">getContext</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'2d'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>optionalNewValue<span style="color: #009900;">&#41;</span>
        ctx.<span style="color: #660066;">fillStyle</span> <span style="color: #339933;">=</span> optionalNewValue<span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">return</span> ctx.<span style="color: #660066;">fillStyle</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #003366; font-weight: bold;">function</span> aojFillRect<span style="color: #009900;">&#40;</span>x<span style="color: #339933;">,</span> y<span style="color: #339933;">,</span> w<span style="color: #339933;">,</span> h<span style="color: #339933;">,</span> optionalFillStyle<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> ctx <span style="color: #339933;">=</span> _aojCanvas.<span style="color: #660066;">getContext</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'2d'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">beginPath</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>optionalFillStyle<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        ctx.<span style="color: #660066;">fillStyle</span> <span style="color: #339933;">=</span> optionalFillStyle<span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
    ctx.<span style="color: #660066;">rect</span><span style="color: #009900;">&#40;</span>x<span style="color: #339933;">,</span> y<span style="color: #339933;">,</span> w<span style="color: #339933;">,</span> h<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">fill</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>A função aojSetCanvas() é usada para informar à nossa biblioteca qual elemento canvas desejamos usar &#8211; podemos ter mais de um canvas na nossa página. Passamos o ID como parâmetro e o elemento é obtido é armazenado em uma variável global, acessível para todas as demais funções.</p>
<p>aojFillStyle() permite obter o estilo de preenchimento atual, e também modificá-lo. Se for passado um parâmetro, ele é usado para modificar o estilo, que em seguida é retornado. Se não for passado o parâmetro, o estilo atual não é modificado, apenas retornado.</p>
<p>E a função aojFillRect() serve para desenhar um retângulo preenchido. Ela pode usar o estilo previamente definido, mas também aceita um quarto parâmetro opcional que, se informado, é usado como estilo para o retângulo.</p>
<p>Este tipo de comando permite mudar nosso exemplo para o seguinte:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">window.<span style="color: #000066;">onload</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    aojSetCanvas<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'canvas1'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    aojFillRect<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">200</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'blue'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// preenche um retângulo azul.</span>
    aojFillRect<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">220</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'blue'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// preenche outro retângulo azul.</span>
    aojStrokeRect<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">200</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'red'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// contorna um retângulo vermelho.</span>
    aojStrokeRect<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">220</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">10</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'red'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// contorna outro retângulo vermelho.</span>
    aojStrokeRect<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'black'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// contorna um retângulo preto.</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Este exemplo ficaria ainda mais claro e resumido se criássemos uma função para desenhar um retângulo preenchido e já contornado. Até que ponto devemos ir na criação de nossa própria biblioteca de funções vai depender da natureza de cada projeto &#8211; aqueles procedimento que são repetidos muitas vezes são os que devem ser transformados em funções. Não recomendo tentar criar uma porção de funções de antemão porque você acabará com muitas que nunca vai utilizar, e mesmo assim não eliminará o risco de precisar de uma que não lembrou.</p>
<h2>Desenhando imagens no canvas</h2>
<p>É importante saber como desenhar primitivas gráficas no canvas, mas o principal recurso ainda é a apresentação de imagens, afinal, quase todo jogo é feito de sprites.</p>
<p>Para carregar uma imagem, basta criar um objeto do tipo Imagem e atribuir a URL do arquivo para o atributo &#8220;src&#8221;. Opcionalmente podemos atribuir uma função para o atributo onload &#8211; esta função será chamada quando o arquivo de imagem for carregado. Este é um recurso importante de usar em jogos com muitas imagens, para garantir que todas tenham sido carregadas antes de iniciar o jogo.</p>
<p>Novamente, para facilitar o trabalho, criamos uma função na nossa biblioteca:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> aojNewImage<span style="color: #009900;">&#40;</span>imgURL<span style="color: #339933;">,</span> optionalLoadCallback<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> img <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> Image<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    img.<span style="color: #660066;">src</span> <span style="color: #339933;">=</span> imgURL<span style="color: #339933;">;</span>
    img.<span style="color: #000066;">onload</span> <span style="color: #339933;">=</span> optionalLoadCallback<span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">return</span> img<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Esta função recebe a URL do arquivo da imagem e opcionalmente uma função de callback, que será chamada quando a imagem for carregada.</p>
<p>Para desenhar uma imagem no canvas, temos outra função:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> aojDrawImage<span style="color: #009900;">&#40;</span>img<span style="color: #339933;">,</span> x<span style="color: #339933;">,</span> y<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> ctx <span style="color: #339933;">=</span> _aojCanvas.<span style="color: #660066;">getContext</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'2d'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">drawImage</span><span style="color: #009900;">&#40;</span>img<span style="color: #339933;">,</span> x <span style="color: #339933;">-</span> img.<span style="color: #660066;">width</span> <span style="color: #009966; font-style: italic;">/ 2, y - img.height /</span> <span style="color: #CC0000;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>_aojShowImageCenter<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        ctx.<span style="color: #660066;">arc</span><span style="color: #009900;">&#40;</span>x<span style="color: #339933;">,</span> y<span style="color: #339933;">,</span> <span style="color: #CC0000;">2</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">0</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">2</span><span style="color: #339933;">*</span>Math.<span style="color: #660066;">PI</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        ctx.<span style="color: #660066;">fill</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Nesta função, apenas as duas primeiras linhas são responsáveis por desenhar a imagem no canvas. O IF é usado para desenhar um círculo no ponto (x,y) onde a imagem é desenhada, de forma a enxergarmos onde fica esse ponto. É útil para debugar posicionamento.</p>
<h2>Transformações geométricas</h2>
<p>O canvas oferece métodos para aplicar transformações geométricas no que é desenhado nele. Por exemplo, podemos rotacionar ou aumentar e diminuir uma imagem no momento de desenhá-la.</p>
<p>É importante saber, no entanto, que uma vez especificada uma transformação, ela fica em efeito para tudo que for desenhado depois. Portanto, depois de aplicar uma rotação, por exemplo, e desenhar a imagem desejada, é preciso aplicar a rotação inversa para deixar o canvas no estado normal antes de desenhar as próximas imagens.</p>
<p>Abaixo está uma função para desenhar uma imagem com transformação de escala. Como parâmetros ela recebe o objeto imagem, a posição (x, y) onde ele deve ser desenhado e os fatores de escala sx e sy.</p>
<p>Veja que para o efeito ser aplicado corretamente é preciso usar uma outra transformação em conjunto &#8211; a translação. Fazemos a translação para que a posição da imagem seja transferida para a origem (ponto (0,0)) e então a escala é aplicada. Depois de desenhada a imagem, desfazemos a escala e a translação aplicando estas transformações com o valor inverso.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> aojDrawImageScale<span style="color: #009900;">&#40;</span>img<span style="color: #339933;">,</span> x<span style="color: #339933;">,</span> y<span style="color: #339933;">,</span> sx<span style="color: #339933;">,</span> sy<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> ctx <span style="color: #339933;">=</span> _aojCanvas.<span style="color: #660066;">getContext</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'2d'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">translate</span><span style="color: #009900;">&#40;</span>x<span style="color: #339933;">,</span> y<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">scale</span><span style="color: #009900;">&#40;</span>sx<span style="color: #339933;">,</span> sy<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">drawImage</span><span style="color: #009900;">&#40;</span>img<span style="color: #339933;">,</span> <span style="color: #339933;">-</span>img.<span style="color: #660066;">width</span> <span style="color: #009966; font-style: italic;">/ 2, -img.height /</span> <span style="color: #CC0000;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">scale</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">1</span><span style="color: #339933;">/</span>sx<span style="color: #339933;">,</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">/</span>sy<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    ctx.<span style="color: #660066;">translate</span><span style="color: #009900;">&#40;</span><span style="color: #339933;">-</span>x<span style="color: #339933;">,</span> <span style="color: #339933;">-</span>y<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>_aojShowImageCenter<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        ctx.<span style="color: #660066;">arc</span><span style="color: #009900;">&#40;</span>x<span style="color: #339933;">,</span> y<span style="color: #339933;">,</span> <span style="color: #CC0000;">2</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">0</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">2</span><span style="color: #339933;">*</span>Math.<span style="color: #660066;">PI</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        ctx.<span style="color: #660066;">fill</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>No arquivo aojcanva.js existem outras funções deste tipo. Este arquivo e os demais estão no Zip no final da página.</p>
<h2>Conclusão</h2>
<p>Neste artigo vimos o basico da utilização do canvas para mostrar imagens.</p>
<p>No site abaixo há um guia de referência do canvas para ser impresso, com todos os comandos. O Autor (Jacob Seidelin) também escreveu um livro sobre jogos em HTML 5.<br />
<a href="http://blog.nihilogic.dk/2009/02/html5-canvas-cheat-sheet.html" target="_blank">http://blog.nihilogic.dk/2009/02/html5-canvas-cheat-sheet.html</a></p>
<p>No próximo artigo veremos como implementar um game loop e utilizar o teclado e mouse.</p>
<ul>
<li><a href="http://www.abrindoojogo.com.br/files/tutorial-html5/01/" target="_blank">Visualizar o exemplo funcionando</a></li>
<li><a href="http://abrindoojogo.com.br/wp-content/uploads/2012/01/AoJ-tutorial-HTML5-01.zip">Baixar o código fonte do exemplo</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/tutorial-html-5-parte-13/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>How-to: Configuração do Google PlayN</title>
		<link>http://abrindoojogo.com.br/tutorial-de-configuracao-do-google-playn</link>
		<comments>http://abrindoojogo.com.br/tutorial-de-configuracao-do-google-playn#comments</comments>
		<pubDate>Thu, 10 Nov 2011 04:54:53 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[HTML 5]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Técnico]]></category>
		<category><![CDATA[how-to]]></category>

		<guid isPermaLink="false">http://abrindoojogo.com.br/?p=3407</guid>
		<description><![CDATA[Google vem desenvolvendo a certo tempo uma biblioteca para criação de jogos que promete facilitar o desenvolvimento multiplataforma. A PlayN, como é chamada hoje, permite o desenvolvimento de jogos utilizando a linguagem Java e uma API própria, e gera automaticamente o código do jogo em HTML5, Android e Flash. Parece incrível e é, mas a [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2011/11/ImgPlayN1.png"><img class="alignleft size-full wp-image-3423" title="ImgPlayN" src="http://abrindoojogo.com.br/wp-content/uploads/2011/11/ImgPlayN1.png" alt="" width="200" height="200" /></a>Google vem desenvolvendo a certo tempo uma biblioteca para criação de jogos que promete facilitar o desenvolvimento multiplataforma. A <strong>PlayN</strong>, como é chamada hoje, permite o desenvolvimento de jogos utilizando a linguagem Java e uma API própria, e gera automaticamente o código do jogo em HTML5, Android e Flash.</p>
<p>Parece incrível e é, mas a configuração do ambiente ainda é um desafio para quem não está acostumado a trabalhar com Git, Maven, Ant e outros diretamente. Nesse curto passo a passo mostramos como configurar PlayN no Eclipse.</p>
<p><span id="more-3407"></span></p>
<p>O projeto PlayN está passando por modificações neste exato momento. Por isso este passo a passo acabou demorando mais do que eu gostaria &#8211; depois que prometi ele, o PlayN simplesmente parou de funcionar em função da atualização da API do Android. Hoje este problema está resolvido, mas para isso o PlayN não vem mais com o pacote de samples &#8211; demonstrações do uso da plataforma. Eles poderão ser baixados separadamente em breve &#8211; quando ocorrer, informamos aqui.</p>
<h3>[ATUALIZAÇÃO]</h3>
<p>O PlayN está agora disponível no Maven Central, que é um repositório público. Isso facilita muito o processo todo, já que não é preciso baixar todos os fontes do PlayN para a máquina para poder utilizá-lo &#8211; só é preciso criar um novo projeto do tipo Maven e basear ele no arquétipo desejado do Maven Central.</p>
<p>Incluí abaixo o how-to para criar um novo projeto do PlayN no NetBeans, que é mais amigável que o Eclipse, mas o processo é praticamente o mesmo para ambos.</p>
<p>Todo o processo é feito em uma máquina limpa, sem nada previamente instalado. Utilizei o Netbeans 7.0.1 recém instalado e com todas atualizações aplicadas.</p>
<p>Os dados para o arquétipo de projeto são os seguintes:</p>
<div>
<ul>
<li>group: com.googlecode.playn</li>
<li>artefato: playn-archetype</li>
<li>versão: 1.0.1</li>
</ul>
</div>
<div>
<ul>
<li><a href="https://docs.google.com/present/view?id=dgmf7xht_617gd44jvfz" target="_blank">Clique aqui para ver a apresentação.</a></li>
</ul>
</div>
<p><strong>Segue post original.</strong></p>
<p>Este how-to está longe de ser à prova de falhas &#8211; muita coisa depende da configuração da sua máquina se você já tiver o Eclipse ou Maven instalado. Se você não tem nada disso, é provável que a coisa funcione sem problemas.</p>
<p>Um problema que tive foi o Eclipse rodar com JRE, que é run-time do Java para usuários finais, não para desenvolvimento. E com isso não conseguir compilar algumas coisas. Se você desconfiar que seu problema é esse, recomendo desinstalar temporariamente o JRE e deixar instalado apenas o JDK (versão de desenvolvimento do Java). Se o Eclipse não iniciar, por não achar mais o Java, abra o arquivo eclipse.ini (que fica na pasta do Eclipse) e acrescente a ele as seguintes linhas (são duas):</p>
<pre>-vm
C:\Program Files\Java\jdk1.7.0_01\jre\bin\client\jvm.dll</pre>
<p>O caminho do Java pode variar conforme sua configuração, principalmente a versão.</p>
<ul>
<li><a href="https://docs.google.com/present/view?id=dgmf7xht_546sm5qzdx" target="_blank">Clique aqui para ver a apresentação do how-to e boa sorte</a>.</li>
</ul>
<p>Sites citados:</p>
<ul>
<li><a href="http://eclipse.org/" target="_blank">Eclipse</a></li>
</ul>
<ul>
<li><a href="https://developers.google.com/playn/" target="_blank">PlayN</a>
<ul>
<li>Endereço do repositório para obter o PlayN:
<p>https://code.google.com/p/playn</li>
</ul>
</li>
</ul>
<ul>
<li><a href="http://code.google.com/eclipse/" target="_blank">Plugin do Google para o Eclipse</a>
<ul>
<li>Endereço para instalação de novo software no Eclipse:
<p>http://dl.google.com/eclipse/plugin/3.7</li>
</ul>
</li>
</ul>
<ul>
<li>Plugin de integração do Maven com o Web Tools Plataform do Eclipse
<ul>
<li>Endereço para instalação de novo software no Eclipse:
<p>http://download.jboss.org/jbosstools/updates/m2eclipse-wtp</li>
</ul>
</li>
</ul>
<ul>
<li><a href="http://developer.android.com/sdk/eclipse-adt.html" target="_blank">Plugin ADT (Android Development Tools) para Eclipse</a> (não necessário para o tutorial acima)
<ul>
<li>Endereço para instalação de novo software no Eclipse:
<p>https://dl-ssl.google.com/android/eclipse/</li>
</ul>
</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/tutorial-de-configuracao-do-google-playn/feed</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Joypad no Java com JInput</title>
		<link>http://abrindoojogo.com.br/joypad-no-java-com-jinput</link>
		<comments>http://abrindoojogo.com.br/joypad-no-java-com-jinput#comments</comments>
		<pubDate>Wed, 17 Aug 2011 14:34:55 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://abrindoojogo.com.br/?p=2663</guid>
		<description><![CDATA[Dependendo do tipo de jogo, a experiência do jogador só fica completa com um controle de jogo, joypad ou joystick. Sem contar ainda com a necessidade que alguns jogos possuem de controles especiais (guitarras, etc). Neste post técnico veremos como usar a biblioteca JInput para dar suporte a controles de jogo no Java. Já vimos [...]]]></description>
			<content:encoded><![CDATA[<p><a rel="attachment wp-att-2666" href="http://abrindoojogo.com.br/joypad-no-java-com-jinput/java_controller"><img class="alignleft size-medium wp-image-2666" title="java_controller" src="http://abrindoojogo.com.br/wp-content/uploads/2011/08/java_controller-300x300.png" alt="" width="144" height="144" /></a>Dependendo do tipo de jogo, a experiência do jogador só fica completa com um controle de jogo, joypad ou joystick. Sem contar ainda com a necessidade que alguns jogos possuem de controles especiais (guitarras, etc). Neste post técnico veremos como usar a biblioteca JInput para dar suporte a controles de jogo no Java.<span id="more-2663"></span></p>
<p>Já vimos aqui como criar um game loop básico no post <a href="http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-parte-1-de-2" target="_blank">Game Loop com taxa constante de pulsos</a>. Utilizaremos agora uma estrutura muito semelhante, de forma que é interessante dar uma olhada naquele post se você ainda não leu.</p>
<p>Nosso projeto terá duas classes apenas, a Main, que carrega o “jogo” (não é de fato um jogo&#8230;) e a classe Jogo, que possui um game loop onde ficamos verificando se alguma tecla, botão do mouse ou do joypad foi pressionada, mostrando a informação correspondente na tela.</p>
<p>A classe Main é simples, como podemos ver abaixo:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
</pre></td><td class="code"><pre class="java" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Main <span style="color: #009900;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> main<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> args<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        Jogo j <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Jogo<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        j.<span style="color: #006633;">run</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>Basicamente ela cria um objeto do tipo Jogo e executa ele, chamando seu método “run”. A classe Jogo, então, é que contém todo o código interessante. Veremos seu código e a seguir a explicação dos pontos que usam o JInput (os demais pontos são explicados no post citado acima).</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
</pre></td><td class="code"><pre class="java" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.awt.Graphics2D</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.awt.image.BufferStrategy</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">javax.swing.JFrame</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">javax.swing.WindowConstants</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">net.java.games.input.Component</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">net.java.games.input.Controller</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">net.java.games.input.ControllerEnvironment</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Jogo <span style="color: #000000; font-weight: bold;">extends</span> <span style="color: #003399;">JFrame</span> <span style="color: #009900;">&#123;</span>
&nbsp;
    BufferStrategy bs<span style="color: #339933;">;</span>
    Controller<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> cs<span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> Jogo<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> initialize<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        setTitle<span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;Exemplo de uso do JInput&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        setDefaultCloseOperation<span style="color: #009900;">&#40;</span><span style="color: #003399;">WindowConstants</span>.<span style="color: #006633;">EXIT_ON_CLOSE</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        setSize<span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">800</span>, <span style="color: #cc66cc;">600</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        setIgnoreRepaint<span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">true</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        setVisible<span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">true</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        createBufferStrategy<span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        bs <span style="color: #339933;">=</span> getBufferStrategy<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
        ControllerEnvironment ce <span style="color: #339933;">=</span> ControllerEnvironment.<span style="color: #006633;">getDefaultEnvironment</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        cs <span style="color: #339933;">=</span> ce.<span style="color: #006633;">getControllers</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> run<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        initialize<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #000000; font-weight: bold;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">true</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            update<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            render<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> update<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000000; font-weight: bold;">for</span> <span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> i <span style="color: #339933;">=</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span> i <span style="color: #339933;">&amp;</span>lt<span style="color: #339933;">;</span> cs.<span style="color: #006633;">length</span><span style="color: #339933;">;</span> i<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            cs<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">poll</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> render<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #003399;">Graphics2D</span> g <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">Graphics2D</span><span style="color: #009900;">&#41;</span> bs.<span style="color: #006633;">getDrawGraphics</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        g.<span style="color: #006633;">clearRect</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span>, <span style="color: #cc66cc;">0</span>, getWidth<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, getHeight<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
        <span style="color: #000000; font-weight: bold;">for</span> <span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> i <span style="color: #339933;">=</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span> i <span style="color: #339933;">&amp;</span>lt<span style="color: #339933;">;</span> cs.<span style="color: #006633;">length</span><span style="color: #339933;">;</span> i<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            g.<span style="color: #006633;">drawString</span><span style="color: #009900;">&#40;</span>i <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot;. &quot;</span> <span style="color: #339933;">+</span> cs<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getName</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot;, &quot;</span> <span style="color: #339933;">+</span> cs<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getType</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, <span style="color: #cc66cc;">50</span>, <span style="color: #cc66cc;">80</span> <span style="color: #339933;">+</span> i <span style="color: #339933;">*</span> <span style="color: #cc66cc;">20</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            <span style="color: #003399;">Component</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> cmps <span style="color: #339933;">=</span> cs<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getComponents</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            <span style="color: #000000; font-weight: bold;">for</span> <span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> c <span style="color: #339933;">=</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span> c <span style="color: #339933;">&amp;</span>lt<span style="color: #339933;">;</span> cmps.<span style="color: #006633;">length</span><span style="color: #339933;">;</span> c<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                g.<span style="color: #006633;">drawString</span><span style="color: #009900;">&#40;</span>c <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot;. &quot;</span> <span style="color: #339933;">+</span> cmps<span style="color: #009900;">&#91;</span>c<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getName</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot; = &quot;</span> <span style="color: #339933;">+</span> cmps<span style="color: #009900;">&#91;</span>c<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getPollData</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, <span style="color: #cc66cc;">50</span> <span style="color: #339933;">+</span> i <span style="color: #339933;">*</span> <span style="color: #cc66cc;">200</span>, <span style="color: #cc66cc;">180</span> <span style="color: #339933;">+</span> c <span style="color: #339933;">*</span> <span style="color: #cc66cc;">20</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            <span style="color: #009900;">&#125;</span>
        <span style="color: #009900;">&#125;</span>
        g.<span style="color: #006633;">dispose</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        bs.<span style="color: #006633;">show</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<h2 dir="ltr">Usando o JInput</h2>
<p>Quando incluímos a biblioteca JInput no nosso projeto (veremos como fazer isso no final), temos algumas classes disponíveis para uso. Uma delas é ControllerEnvironment, que permite obter uma lista de todos controles disponíveis no sistema. Isto é feito da seguinte forma:</p>
<p>ControllerEnvironment ce = ControllerEnvironment.getDefaultEnvironment();<br />
Controller[] cs = ce.getControllers();</p>
<p>Interessante notar que a JInput trata o teclado e o mouse como controles, de forma que o vetor acima terá pelo menos estes dois itens. Se você tiver um ou mais controle de jogo conectado ao sistema, então mais itens serão adicionados ao vetor, um para cada controle.</p>
<p>Cada controle é constituído de componentes. No teclado os componentes são as teclas; em um controle de jogo, os componentes são os eixos e os botões. Uma vez que temos um objeto do tipo Coltroller, podemos obter a lista de componentes que ele possui, com o código abaixo:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
</pre></td><td class="code"><pre class="java" style="font-family:monospace;"><span style="color: #003399;">Component</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> cmps <span style="color: #339933;">=</span> controle.<span style="color: #006633;">getComponents</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">for</span> <span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> c <span style="color: #339933;">=</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span> c <span style="color: #339933;">&amp;</span>lt<span style="color: #339933;">;</span> cmps.<span style="color: #006633;">length</span><span style="color: #339933;">;</span> c<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span>cmps<span style="color: #009900;">&#91;</span>c<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getName</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot; = &quot;</span> <span style="color: #339933;">+</span> cmps<span style="color: #009900;">&#91;</span>c<span style="color: #009900;">&#93;</span>.<span style="color: #006633;">getPollData</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>Este código obtem um vetor de componentes do controle e para cada um deles exibe o nome e os dados lidos no último pooling. Estes dados correspondem ao estado do componente. Por exemplo, se for um botão, pode vir 1 (pressionado) ou 0 (solto); se for um joystick analógico, virá um valor entre -1.0 e 1.0, sendo que 0.0 significa que o joystick está no centro. São estes dados que vamos utilizar para comandar as ações do jogo.</p>
<p>Veja que, seguindo a melhor prática para leitura de dispositivos de entrada, o JInput não trabalha com eventos, mas sim com pooling. A diferença é que com eventos, quando uma tecla do teclado é pressionada, por exemplo, é gerado um evento que o jogo deve anteder &#8211; nem sempre será a melhor hora para fazer isso &#8211; podemos estar no meio da atualização da tela, por exemplo. Com o pooling a coisa se inverte: é o jogo que lê o estado do teclado quando desejar, verificando, então, se a tecla desejada está pressionada ou não.</p>
<p>Como JInput fazemos a leitura do estado de um objeto do tipo Controller chamando seu método “pool”. Veja dentro do método “update” da classe Jogo onde percorremos o vetor de controles chamando “pool” para cada um deles. Isso faz com que a cada volta do game loop os dados atualizados dos controles estejam disponíveis.</p>
<p>No método “render” percorremos novamente o vetor de controles e para cada um, obtermos o vetor de componentes. Então percorremos todos componentes mostrando na tela seu nome e seu estado atual.</p>
<h2 dir="ltr">Incluindo JInput no projeto</h2>
<p>Finalmente, vejamos como incluir a JInput no nosso projeto. <a href="http://java.net/projects/jinput/downloads" target="_blank">Baixe a biblioteca mais recente no site</a> e dentro do ZIP você vai encontrar o arquivo jinput.jar, que é a biblioteca em Java, e vários arquivos dll e so, que são as partes nativas. Estas partes devem ser distribuídas junto com seu jogo e são a ponte entre o código Java que usamos acima e a manipulação de baixo nível do hardware em cada plataforma (.dll no Windows e .so no Linux).</p>
<p>Digamos que seu projeto esteja armazenado em uma pasta chamada MeuProjeto. Dentro dela deve ter a pasta de códigos fonte (src) e quando você compila e constrói, surgem as pastas build e dist (que é onde está o jogo pronto para ser distribuído). Se não existir, crie dentro de MeuJogo uma pasta lib e dentro dela coloque o jinput.jar. Os arquivos .dll e .so vão diretamente dentro de MeuJogo.</p>
<p>Agora utilize um comando do seu IDE para importar a biblioteca para o projeto. No NetBeans faça assim:</p>
<ol>
<li>Clique com o botão direito do mouse no projeto;</li>
<li>No menu selecione propriedades;</li>
<li>Na janela de propriedades vá na seção “Bibliotecas” e clique em “Adicionar JAR/pasta”;</li>
<li>Localize o jinput.jar que está dentro da pasta lib e pronto, confirme tudo.</li>
</ol>
<p>Ao construir (dar build), será criada uma pasta lib dentro de dist, com o jinput lá dentro. Mas será preciso copiar as dll e so manualmente. Então é só distribuir o conteúdo da pasta dist.</p>
<h2 dir="ltr">Conclusão</h2>
<p>Usar um controle de jogo pode melhorar muito a experiência do usuário com certos jogos, principalmente nos gêneros de tiro, luta, corrida e plataforma.</p>
<p>Mas mesmo em jogos onde o teclado e o mouse são a melhor opção, o JInput é uma boa escolha porque facilita também o acesso a estes dispositivos. Criar do zero um pool para teclado e mouse é meio chato &#8211; demora pra dar o resultado desejado. O Jinput já tem tudo pronto.</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2011/08/JogoComJoypad.zip">Clique aqui para baixar o código fonte deste post</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/joypad-no-java-com-jinput/feed</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>Metaballs em Actionscript</title>
		<link>http://abrindoojogo.com.br/metaballs-em-actionscript</link>
		<comments>http://abrindoojogo.com.br/metaballs-em-actionscript#comments</comments>
		<pubDate>Wed, 10 Nov 2010 15:48:11 +0000</pubDate>
		<dc:creator>Henrique.Vilela</dc:creator>
				<category><![CDATA[ActionScript 3.0]]></category>
		<category><![CDATA[Programação]]></category>

		<guid isPermaLink="false">http://abrindoojogo.com.br/?p=1956</guid>
		<description><![CDATA[Olá pessoal, Hoje vou falar um pouco sobre as Metaballs - que nada mais são do que modelos gráficos de aparência orgânica, usados para simular vários tipos de objetos não-sólidos, incluindo líquidos. Para quem procura uma definição matemática formal, recomendo a leitura do artigo na Wikipedia. Para quem procura apenas uma forma simples de gerar [...]]]></description>
			<content:encoded><![CDATA[<p><em><a href="http://abrindoojogo.com.br/wp-content/uploads/2010/11/metaballs.jpg"><img class="alignleft size-full wp-image-2015" title="metaballs" src="http://abrindoojogo.com.br/wp-content/uploads/2010/11/metaballs.jpg" alt="" width="191" height="183" /></a></em>Olá pessoal,</p>
<p>Hoje vou falar um pouco sobre as <em>Metaballs </em>- que nada mais são do que modelos gráficos de aparência orgânica, usados para simular vários tipos de objetos não-sólidos, incluindo líquidos.</p>
<p>Para quem procura uma definição matemática formal, recomendo a leitura do <a href="http://en.wikipedia.org/wiki/Metaballs" target="_blank">artigo na Wikipedia</a>. Para quem procura apenas uma forma simples de gerar este tipo de forma em Actionscript, mostrarei alguns passos simples para atingir resultados bastante interessantes.</p>
<p><span id="more-1956"></span></p>
<p>O primeiro passo é criar uma instância de BitmapData. Apesar de ser possível criar <em>Metaballs</em> vetorialmente, utilizando os recursos desta classe torna o processo bem mais simples.</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">BitmapData</span> = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">BitmapData</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">stage</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">stageWidth</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">stage</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">stageHeight</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">addChild</span><span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Bitmap</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">bitmapData</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span></pre></td></tr></table></div>

<p>As <em>Metaballs</em> são círculos em sua essência, e para criá-las vamos criar alguns em nosso <em>bitmap</em>.</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #6699cc; font-weight: bold;">var</span> circle<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Sprite</span> = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Sprite</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
circle<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">graphics</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">beginFill</span><span style="color: #000000;">&#40;</span>0x000000<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
circle<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">graphics</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">drawCircle</span><span style="color: #000000;">&#40;</span><span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">20</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> i<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">;</span> i <span style="color: #000066; font-weight: bold;">&amp;</span>lt<span style="color: #000066; font-weight: bold;">;</span> <span style="color: #000000; font-weight:bold;">100</span><span style="color: #000066; font-weight: bold;">;</span> i<span style="color: #000066; font-weight: bold;">++</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#123;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">matrix</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Matrix</span> = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Matrix</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">matrix</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">translate</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">Math</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">random</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span> <span style="color: #000066; font-weight: bold;">*</span> <span style="color: #004993;">stage</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">stageWidth</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">Math</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">random</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span> <span style="color: #000066; font-weight: bold;">*</span> <span style="color: #004993;">stage</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">stageHeight</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">draw</span><span style="color: #000000;">&#40;</span>circle<span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">matrix</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>Até então, temos apenas vários círculos bem definidos espalhados de forma randômica. O próximo passo é “misturá-los”, aplicando <em>Blur</em>.</p>
<p>O <em>Blur</em> faz com que as áreas entre os círculos próximos fiquem mais escuras. Áreas entre círculos muito próximos ficam mais escuras do as áreas entre círculos mais afastados, e é isto que cria  efeito esperado.</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #6699cc; font-weight: bold;">var</span> blur<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">BlurFilter</span> = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">BlurFilter</span><span style="color: #000000;">&#40;</span><span style="color: #000000; font-weight:bold;">10</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">10</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">10</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">applyFilter</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">rect</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Point</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">,</span> blur<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span></pre></td></tr></table></div>

<p>O passo final é deixar a figura bem definida novamente, utilizando para isso a função <em>threshold</em>. Primeiramente a função é utilizada para transformar todos os pixels escuros para preto e posteriormente todos os pixels claros para branco, eliminando assim todos os tons de cinza.</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">threshold</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">rect</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Point</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #990000;">&quot;&amp;gt;&quot;</span><span style="color: #000066; font-weight: bold;">,</span> 0xFF666666<span style="color: #000066; font-weight: bold;">,</span> 0xFFFFFFFF<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">threshold</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">bitmapData</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">rect</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Point</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #990000;">&quot;&amp;lt;&quot;</span><span style="color: #000066; font-weight: bold;">,</span> 0xFFFFFFFF<span style="color: #000066; font-weight: bold;">,</span> 0xFF000000<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;&amp;</span>lt<span style="color: #000066; font-weight: bold;">;/</span>code<span style="color: #000066; font-weight: bold;">&amp;</span>gt<span style="color: #000066; font-weight: bold;">;</span></pre></td></tr></table></div>

<p>A partir daí, é só usar a criatividade. Apenas como exemplo, usei as <em>Metaballs</em> para simular uma espécie de lava que entra em erupção a cada 10 segundos.</p>
<p><object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" width="586" height="290" codebase="http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=6,0,40,0"><param name="src" value="http://abrindoojogo.com.br/wp-content/uploads/2010/11/Metaballs.swf" /><param name="bgcolor" value="#ffffff" /><embed type="application/x-shockwave-flash" width="586" height="290" src="http://abrindoojogo.com.br/wp-content/uploads/2010/11/Metaballs.swf" bgcolor="#ffffff"></embed></object></p>
<address>Postado por Henrique Vilela<br />
</address>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/metaballs-em-actionscript/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Integrador de Verlet Parte 1 &#8211; Introdução</title>
		<link>http://abrindoojogo.com.br/integrador-de-verlet-parte-1-introducao</link>
		<comments>http://abrindoojogo.com.br/integrador-de-verlet-parte-1-introducao#comments</comments>
		<pubDate>Thu, 21 Oct 2010 21:33:03 +0000</pubDate>
		<dc:creator>Regis Machado</dc:creator>
				<category><![CDATA[ActionScript 3.0]]></category>
		<category><![CDATA[Programação]]></category>

		<guid isPermaLink="false">http://www.abrindoojogo.com.br/?p=1762</guid>
		<description><![CDATA[por: Regis Machado Olá pessoal esse é o meu primeiro post como colaborador aqui no Abrindo o Jogo, e pra isso eu vou mostrar como funcionam os verlet points, que são bem legais de usar e tem como simular uma física legal e descomplicada, ou criar um sistema de partículas simples. &#8220;O Integrador Verlet é [...]]]></description>
			<content:encoded><![CDATA[<address><a href="http://abrindoojogo.com.br/wp-content/uploads/2010/10/verletCloth1.png"><img class="alignleft size-full wp-image-1816" title="verletCloth" src="http://abrindoojogo.com.br/wp-content/uploads/2010/10/verletCloth1.png" alt="" width="128" height="145" /></a>por: Regis Machado</address>
<p>Olá pessoal esse é o meu primeiro post como colaborador aqui no Abrindo o Jogo, e pra isso eu vou mostrar como funcionam os verlet points, que são bem legais de usar e tem como simular uma física legal e descomplicada, ou criar um sistema de partículas simples.</p>
<p><span id="more-1762"></span></p>
<blockquote><p><em><strong>&#8220;O Integrador Verlet </strong>é um metodo numérico usado para simular a equação de movimento de Newton&#8217;s. É usada frequentemente para calcular trajetorias de particulas em simulações de dinâmica molecular e video games&#8221;</em>.-Wikipedia</p></blockquote>
<p>O ponto de verlet que vou mostrar aqui é um vetor onde mantem armazenada a sua ultima posição e a posição atual e a partir da diferença entre essas duas posições ele calcula sua movimentação futura,  se pensarmos na parte física, se um corpo em um momento <strong>T0</strong> está na posição <strong>x</strong> e em um segundo momento <strong>T1</strong> está na posição <strong>x1</strong>, o seu deslocamento no tempo-espaço <strong>D(x1-x)</strong> pode (não obrigatoriamente) ser considerado como sua velocidade de deslocamento no futuro.</p>
<p>Para demonstrar isto, vou apresentar a implementação em AS3 (uma linguagem que eu gosto muito de trabalhar para fazer jogos). A IDE que vou usar é o <em>FlashDevelop </em>e vocês podem utilizar o <a href="http://evertonbaumgarten.wordpress.com/cursos/curso-actionscrpt-3-0-modulo-3/">tutorial</a> aqui do Abrindo o Jogo para baixar e instalar.</p>
<p>Essa primeira parte vai ser composta de 3 classes, a classe principal, a  classe <em>VerletPoint</em>, e o <em>VerletStick </em>uma classe criado pelo <a title="yoambulante" href="www.yoambulante.com/">yoambulante</a> que nessa primeira parte vai nos ajudar muito a ver o poder e simplicidade dos verlet points.</p>
<p>Primeiro a Classe VPoint que implementa o integrador de verlet:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #9900cc; font-weight: bold;">class</span> VerletPoint <span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #6699cc; font-weight: bold;">var</span> oldx<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #6699cc; font-weight: bold;">var</span> oldy<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> VerletPoint <span style="color: #000000;">&#40;</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000000;">&#41;</span> <span style="color: #000000;">&#123;</span>
&nbsp;
setPos<span style="color: #000000;">&#40;</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">,</span><span style="color: #004993;">y</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/* informa a posição do ponto*/</span>
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> setPos<span style="color: #000000;">&#40;</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span><span style="color: #000000;">&#123;</span>
<span style="color: #0033ff; font-weight: bold;">this</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span> = oldx = <span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">this</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span> = oldy = <span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/*Atualiza a posição do ponto, de acordo com o integrador de Verlet*/</span>
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> refresh<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span> <span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #6699cc; font-weight: bold;">var</span> tempx<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> tempy<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">x</span> <span style="color: #000066; font-weight: bold;">+</span>= <span style="color: #004993;">x</span> <span style="color: #000066; font-weight: bold;">-</span> oldx<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #004993;">y</span> <span style="color: #000066; font-weight: bold;">+</span>= <span style="color: #004993;">y</span> <span style="color: #000066; font-weight: bold;">-</span> oldy<span style="color: #000066; font-weight: bold;">;</span>
oldx = tempx<span style="color: #000066; font-weight: bold;">;</span>
oldy = tempy<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/* função que desenha o ponto na tela */</span>
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> <span style="color: #004993;">render</span><span style="color: #000000;">&#40;</span>g<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Graphics</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span><span style="color: #000000;">&#123;</span>
&nbsp;
 g<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">beginFill</span><span style="color: #000000;">&#40;</span>0xff8989<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
 g<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">drawCircle</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">,</span><span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">,</span><span style="color: #000000; font-weight:bold;">2</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
 g<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">endFill</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>E a classe que criada pelo yoambulante para limitar a movimentação entre dois pontos de verlet:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #9900cc; font-weight: bold;">class</span> VerletStick<span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #6699cc; font-weight: bold;">var</span> pointa<span style="color: #000066; font-weight: bold;">:</span>VPoint<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #6699cc; font-weight: bold;">var</span> pointb<span style="color: #000066; font-weight: bold;">:</span>VPoint<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #6699cc; font-weight: bold;">var</span> _lenght<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> VerletStick<span style="color: #000000;">&#40;</span>a<span style="color: #000066; font-weight: bold;">:</span>VPoint<span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">b</span><span style="color: #000066; font-weight: bold;">:</span>VPoint<span style="color: #000066; font-weight: bold;">,</span> lenght<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #000066; font-weight: bold;">-</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#41;</span> <span style="color: #000000;">&#123;</span>
&nbsp;
pointa = a<span style="color: #000066; font-weight: bold;">;</span>
pointb = <span style="color: #004993;">b</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">if</span><span style="color: #000000;">&#40;</span>lenght == <span style="color: #000066; font-weight: bold;">-</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#123;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> dx<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = a<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span> <span style="color: #000066; font-weight: bold;">-</span> <span style="color: #004993;">b</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> dy<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = a<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span> <span style="color: #000066; font-weight: bold;">-</span> <span style="color: #004993;">b</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">;</span>
_lenght = <span style="color: #004993;">Math</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">sqrt</span><span style="color: #000000;">&#40;</span>dx <span style="color: #000066; font-weight: bold;">*</span> dx <span style="color: #000066; font-weight: bold;">+</span> dy <span style="color: #000066; font-weight: bold;">*</span> dy<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span><span style="color: #0033ff; font-weight: bold;">else</span><span style="color: #000000;">&#123;</span>
_lenght = lenght<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> contract<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span> <span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #6699cc; font-weight: bold;">var</span> dx<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = pointb<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span> <span style="color: #000066; font-weight: bold;">-</span> pointa<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> dy<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = pointb<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span> <span style="color: #000066; font-weight: bold;">-</span> pointa<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> h<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #004993;">Math</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">sqrt</span><span style="color: #000000;">&#40;</span>dx <span style="color: #000066; font-weight: bold;">*</span> dx <span style="color: #000066; font-weight: bold;">+</span> dy <span style="color: #000066; font-weight: bold;">*</span> dy<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> diff<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = _lenght <span style="color: #000066; font-weight: bold;">-</span> h<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #6699cc; font-weight: bold;">var</span> offx<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #000000;">&#40;</span>diff <span style="color: #000066; font-weight: bold;">*</span> dx <span style="color: #000066; font-weight: bold;">/</span> h<span style="color: #000000;">&#41;</span> <span style="color: #000066; font-weight: bold;">*</span> <span style="color: #000066; font-weight: bold;">.</span>5<span style="color: #000066; font-weight: bold;">;</span> <span style="color: #009900; font-style: italic;">// or /2</span>
<span style="color: #6699cc; font-weight: bold;">var</span> offy<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Number</span> = <span style="color: #000000;">&#40;</span>diff <span style="color: #000066; font-weight: bold;">*</span> dy <span style="color: #000066; font-weight: bold;">/</span> h<span style="color: #000000;">&#41;</span> <span style="color: #000066; font-weight: bold;">*</span> <span style="color: #000066; font-weight: bold;">.</span>5<span style="color: #000066; font-weight: bold;">;</span><span style="color: #009900; font-style: italic;">// or /2</span>
pointa<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span> <span style="color: #000066; font-weight: bold;">-</span>= offx<span style="color: #000066; font-weight: bold;">;</span>
pointa<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span> <span style="color: #000066; font-weight: bold;">-</span>= offy<span style="color: #000066; font-weight: bold;">;</span>
pointb<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span> <span style="color: #000066; font-weight: bold;">+</span>= offx<span style="color: #000066; font-weight: bold;">;</span>
pointb<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span> <span style="color: #000066; font-weight: bold;">+</span>= offy<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> <span style="color: #004993;">render</span><span style="color: #000000;">&#40;</span>g<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Graphics</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span> <span style="color: #000000;">&#123;</span>
g<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">lineStyle</span><span style="color: #000000;">&#40;</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000066; font-weight: bold;">,</span>0xff00ff<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
g<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">moveTo</span><span style="color: #000000;">&#40;</span>pointa<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">,</span>pointa<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
g<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">lineTo</span><span style="color: #000000;">&#40;</span>pointb<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">x</span><span style="color: #000066; font-weight: bold;">,</span> pointb<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">y</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>E finalmente a nossa classe main que ira fazer a mágica</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
</pre></td><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #9900cc; font-weight: bold;">class</span> Main <span style="color: #0033ff; font-weight: bold;">extends</span> <span style="color: #004993;">Sprite</span><span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> Main<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span>
<span style="color: #000000;">&#123;</span>
  <span style="color: #0033ff; font-weight: bold;">if</span> <span style="color: #000000;">&#40;</span><span style="color: #004993;">stage</span><span style="color: #000000;">&#41;</span> <span style="color: #004993;">init</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
  <span style="color: #0033ff; font-weight: bold;">else</span> <span style="color: #004993;">addEventListener</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">Event</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">ADDED_TO_STAGE</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">init</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #339966; font-weight: bold;">function</span> <span style="color: #004993;">init</span><span style="color: #000000;">&#40;</span>e<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Event</span> = <span style="color: #0033ff; font-weight: bold;">null</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span><span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #004993;">removeEventListener</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">Event</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">ADDED_TO_STAGE</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">init</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
createPoints<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span><span style="color: #009900; font-style: italic;">//função encarregada de criar os Vpoints;</span>
<span style="color: #004993;">addEventListener</span><span style="color: #000000;">&#40;</span><span style="color: #004993;">Event</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">ENTER_FRAME</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">render</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #009900; font-style: italic;">//constante com o numero de verlets points que será gerado</span>
<span style="color: #0033ff; font-weight: bold;">private</span> const NUM_POINTS<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">int</span> = <span style="color: #000000; font-weight:bold;">10</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #009900; font-style: italic;">//vetor com os pontos, somente flashplayer 10+</span>
<span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #6699cc; font-weight: bold;">var</span> pontos<span style="color: #000066; font-weight: bold;">:</span>Vector<span style="color: #000066; font-weight: bold;">.</span>VerletPoint<span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #6699cc; font-weight: bold;">var</span> sticks<span style="color: #000066; font-weight: bold;">:</span>Vector<span style="color: #000066; font-weight: bold;">.</span>VerletStick<span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> createPoints<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span> <span style="color: #000000;">&#123;</span>
&nbsp;
pontos = <span style="color: #0033ff; font-weight: bold;">new</span> Vector<span style="color: #000066; font-weight: bold;">.</span>VerletPoint<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
sticks = <span style="color: #0033ff; font-weight: bold;">new</span> Vector<span style="color: #000066; font-weight: bold;">.</span>VerletStick<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> i<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">int</span> = <span style="color: #000000; font-weight:bold;">0</span> <span style="color: #000066; font-weight: bold;">;</span> i <span style="color: #000066; font-weight: bold;">&amp;</span>amp<span style="color: #000066; font-weight: bold;">;</span>lt<span style="color: #000066; font-weight: bold;">;</span> NUM_POINTS<span style="color: #000066; font-weight: bold;">;</span> i<span style="color: #000066; font-weight: bold;">++</span> <span style="color: #000000;">&#41;</span> <span style="color: #000000;">&#123;</span>
pontos<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">push</span><span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">new</span> VerletPoint<span style="color: #000000;">&#40;</span><span style="color: #000000; font-weight:bold;">25</span><span style="color: #000066; font-weight: bold;">*</span><span style="color: #000000;">&#40;</span>i<span style="color: #000066; font-weight: bold;">+</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">,</span><span style="color: #000000; font-weight:bold;">25</span><span style="color: #000066; font-weight: bold;">*</span><span style="color: #000000;">&#40;</span>i<span style="color: #000066; font-weight: bold;">+</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> a<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">int</span> = <span style="color: #000000; font-weight:bold;">1</span> <span style="color: #000066; font-weight: bold;">;</span> a <span style="color: #000066; font-weight: bold;">&amp;</span>amp<span style="color: #000066; font-weight: bold;">;</span>lt<span style="color: #000066; font-weight: bold;">;</span> NUM_POINTS<span style="color: #000066; font-weight: bold;">;</span> a<span style="color: #000066; font-weight: bold;">++</span> <span style="color: #000000;">&#41;</span> <span style="color: #000000;">&#123;</span>
sticks<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">push</span><span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">new</span> VerletStick<span style="color: #000000;">&#40;</span>pontos<span style="color: #000000;">&#91;</span>a<span style="color: #000066; font-weight: bold;">-</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">,</span> pontos<span style="color: #000000;">&#91;</span>a<span style="color: #000000;">&#93;</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> <span style="color: #004993;">render</span><span style="color: #000000;">&#40;</span>e<span style="color: #000066; font-weight: bold;">:</span><span style="color: #004993;">Event</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span><span style="color: #0033ff; font-weight: bold;">void</span> <span style="color: #000000;">&#123;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">this</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">graphics</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">clear</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span> <span style="color: #009900; font-style: italic;">//limpa a tela</span>
pontos<span style="color: #000000;">&#91;</span><span style="color: #000000; font-weight:bold;">0</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">.</span>setPos<span style="color: #000000;">&#40;</span><span style="color: #004993;">mouseX</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #004993;">mouseY</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span> <span style="color: #009900; font-style: italic;">//seta o ponto 0 com a posição do mouse</span>
<span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #0033ff; font-weight: bold;">each</span><span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> s<span style="color: #000066; font-weight: bold;">:</span>VerletStick <span style="color: #0033ff; font-weight: bold;">in</span> sticks<span style="color: #000000;">&#41;</span> <span style="color: #000000;">&#123;</span>
s<span style="color: #000066; font-weight: bold;">.</span>contract<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span> <span style="color: #009900; font-style: italic;">//atualiza os sticks</span>
s<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">render</span><span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">this</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">graphics</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #0033ff; font-weight: bold;">each</span> <span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> p<span style="color: #000066; font-weight: bold;">:</span>VerletPoint <span style="color: #0033ff; font-weight: bold;">in</span> pontos<span style="color: #000000;">&#41;</span> <span style="color: #000000;">&#123;</span>
p<span style="color: #000066; font-weight: bold;">.</span>refresh<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span> <span style="color: #009900; font-style: italic;">//atualiza os pontos</span>
p<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">render</span><span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">this</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">graphics</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #000000;">&#125;</span>
&nbsp;
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>A versão final em Flash vocês podem conferir aqui:</p>
<p><object style="width: 500px; height: 300px;" classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" width="500" height="300" codebase="http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=6,0,40,0"><param name="src" value="http://abrindoojogo.com.br/files/Integrador_Verlet.swf" /><param name="bgcolor" value="#59bef7" /><embed style="width: 500px; height: 300px;" type="application/x-shockwave-flash" width="500" height="300" src="http://abrindoojogo.com.br/files/Integrador_Verlet.swf" bgcolor="#59bef7"></embed></object></p>
<p>Espero que tenham gostado se alguem tiver problemas comenta que eu tento resolver o mais rápido possivel.</p>
<p>Até a segunda parte do nosso Integrador de Verlet.</p>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/integrador-de-verlet-parte-1-introducao/feed</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Anti-Invaders &#8211; um projeto didático.</title>
		<link>http://abrindoojogo.com.br/anti-invaders-um-projeto-didatico</link>
		<comments>http://abrindoojogo.com.br/anti-invaders-um-projeto-didatico#comments</comments>
		<pubDate>Wed, 30 Jun 2010 00:54:10 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Padrão de Projeto]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Projeto de Jogo]]></category>
		<category><![CDATA[Projeto de Software]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://blog.abrindoojogo.com.br/?p=1565</guid>
		<description><![CDATA[Este post é o primeiro de uma série que vai documentar a evolução de um projeto inteiro, desde o game design até o produto final. O projeto tem o objetivo de ser didático e por isso foi escolhido um jogo de navinha (shooter) e será desenvolvido utilizando a tecnologia Java. Neste post conheceremos a primeira [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2010/07/blog2.png"><img class="alignleft size-full wp-image-1580" title="blog2" src="http://abrindoojogo.com.br/wp-content/uploads/2010/07/blog2.png" alt="" width="150" height="150" /></a>Este post é o primeiro de uma série que vai documentar a evolução de um projeto inteiro, desde o game design até o produto final. O projeto tem o objetivo de ser didático e por isso foi escolhido um jogo de navinha (shooter) e será desenvolvido utilizando a tecnologia Java. Neste post conheceremos a primeira versão do GDD e a história de fundo do jogo.</p>
<p><span id="more-1576"></span>O nome do jogo é <strong>Anti-Invaders</strong>. É um jogo de tiro espacial como vários outros que apareceram ao longo do tempo. É um gênero bem conhecido e de implementação relativamente simples, por isso mesmo uma boa escolha para um projeto didático.</p>
<p>A idéia é mostrar umprojeto simples porém completo, desenvolvido com protótipos e releases e comentando cada evolução em posts semanais. Serão decisões de game design, de arquitetura de software e de implementação que, no final, darão uma visão completa do processo.</p>
<p>Acredito que será útil principalmente para quem está iniciando e não tem, ainda, noção clara do processo como um todo.</p>
<p>Iniciaremos, então, com a primeira versão do GDD (Game Design Document), criado com base <a href="http://blog.abrindoojogo.com.br/trabalhar-com-jogos-e-uma-questao-de-sorte-parte-1-de-3/">neste post do Everton</a>, embora bem simplificado. Algumas seções não foram preenchidas &#8211; nelas está anotado o que deveria ser colocado alí. O foco deste documento é na história de base, fases (tamanho do jogo) e controles. Clique no link abaixo para baixar o PDF.</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2010/06/gdd_anti_invaders.pdf">GDD_Anti_Invaders</a></p>
<p>Semana que vem teremos um protótipo do jogo para ter idéia do que querermos fazer.</p>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/anti-invaders-um-projeto-didatico/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Criando um Applet básico</title>
		<link>http://abrindoojogo.com.br/criando-um-applet-basico</link>
		<comments>http://abrindoojogo.com.br/criando-um-applet-basico#comments</comments>
		<pubDate>Sat, 21 Nov 2009 01:22:57 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://blog.abrindoojogo.com.br/?p=1078</guid>
		<description><![CDATA[A tecnologia Java ficou originalmente conhecida pelo Applets, palavra que significa pequenos aplicativos. São programas que rodam embutidos dentro de outro &#8211; no caso, em navegadores da web. Embora os applets tenham também dado ao Java o stigma de linguagem lenta, hoje, com a evolução da tecnologia, eles são um opão para a criação de [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/11/applet1.png"><img class="alignleft size-full wp-image-1092" title="Applet" src="http://abrindoojogo.com.br/wp-content/uploads/2009/11/applet1.png" alt="" width="199" height="150" /></a>A tecnologia Java ficou originalmente conhecida pelo Applets, palavra que significa pequenos aplicativos. São programas que rodam embutidos dentro de outro &#8211; no caso, em navegadores da web. Embora os applets tenham também dado ao Java o stigma de linguagem lenta, hoje, com a evolução da tecnologia, eles são um opão para a criação de webgames. Neste post vamos ver o mínimo para ter um applet com game loop.</p>
<p><span id="more-1078"></span>Um applet Java é uma classe derivada de JApplet, que por sua vez é um painel. Ou seja, não temos uma janela para nosso programa e sim um painel, que será embutido na janela de outro programa, no caso, um navegador da web.</p>
<p>Isso não nos permite obter um BufferStrategy para a janela, mas podemos ter o mesmo efeito criando um objeto do tipo Canvas, que é uma área de desenho que possui contexto gráfico, e criar um BufferStrategy para ele. Daí para frente usamos ele para fazer <a href="http://blog.abrindoojogo.com.br/passive-vs-active-rendering-parte-1-de-2/">active rendering</a> normalmente.</p>
<p>Outro ponto específico é que por rodar dentro de outro programa, não podemos trancar nossa thread principal com um loop infinito, como fizemos em <a href="http://blog.abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-parte-1-de-2/">outros exemplos</a> aqui no blog. Isso é resolvido de forma simples implementando a interface Runnable na nossa classe e executando ela em uma thread separada.</p>
<p>Veja no código abaixo um applet simples que a cada volta do loop muda a cor da tela.</p>
<p><strong>Arquivo Main.java</strong></p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> exemploapplet;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">import</span> java.awt.Canvas;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span><span style="color: #0000e6;">import</span> java.awt.Color;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span></span><span style="color: #0000e6;">import</span> java.awt.Graphics2D;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span></span><span style="color: #0000e6;">import</span> java.awt.image.BufferStrategy;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span></span><span style="color: #0000e6;">import</span> javax.swing.JApplet;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Main <span style="color: #0000e6;">extends</span> JApplet <span style="color: #0000e6;">implements</span> Runnable<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>    </span><span style="color: #0000e6;">int</span> x;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>    </span>Canvas canvas;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>    </span>BufferStrategy bs;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>    </span>@Override<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">016</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> init()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">018</span>        </span>canvas = <span style="color: #0000e6;">new</span> Canvas();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">019</span>        </span>setIgnoreRepaint(<span style="color: #0000e6;">true</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">020</span>        </span><span style="color: #0000e6;">this</span>.add(canvas);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>        </span>Thread t = <span style="color: #0000e6;">new</span> Thread(<span style="color: #0000e6;">this</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>        </span>t.start();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> run()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span>        </span>canvas.createBufferStrategy(<span style="color: #000000;">2</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">028</span>        </span>bs = canvas.getBufferStrategy();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">029</span>        </span><span style="color: #0000e6;">while</span> (<span style="color: #0000e6;">true</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">030</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">031</span>            </span>Thread.yield();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">032</span>            </span>update();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">033</span>            </span>render();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">034</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">035</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">036</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">037</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> update()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">038</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">039</span>        </span><span style="color: #0000e6;">if</span> (++x &gt; <span style="color: #000000;">255</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">040</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">041</span>            </span>x = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">042</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">043</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">044</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">045</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> render()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">046</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">047</span>        </span>Graphics2D g = (Graphics2D) bs.getDrawGraphics();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">048</span>        </span><span style="color: #0000e6;">if</span> (g != <span style="color: #0000e6;">null</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">049</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">050</span>            </span>g.setColor(<span style="color: #0000e6;">new</span> Color(x, x, x));<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">051</span>            </span>g.fillRect(<span style="color: #000000;">0</span>, <span style="color: #000000;">0</span>, getWidth(), getHeight());<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">052</span>            </span>g.dispose();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">053</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">054</span>        </span>bs.show();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">055</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">056</span></span>}</pre>
<p>Em um applet não inicializamos variáveis nem criamos objetos no constructor. Isso porque a classe do applet pode ser criada muito antes de ser utilizada. Aliás, pode ser criada e acabar nem sendo utilizada porque, por exemplo, o usuário fechou o programa externo antes disso ocorrer. Carregar recursos no contructor do applet poderia levar a processamento realizado à toa nestes casos.</p>
<p>O que faz, então, é implementar o método ini(), herdado de JApplet, e fazer a inicialização nele. Esse método é chamado pelo programa externo quando o applet for ativado e iniciar sua execução.</p>
<p>No método init do exemplo acima o que fazemos é criar um objeto Canvas e adicioná-lo ao applet, além de desligar o repaint automatico do applet (porque vamos fazer active rendering). Também criamos uma thread nova para nossa classe e colocamos ela para rodar.</p>
<p>Quando a thread roda, ela chama o método run() da nossa classe. Nele criamos o BufferStrategy configurado para double buffering e obtemos uma referência a ele na variável &#8220;bs&#8221;. Veja que o BufferStrategy é criado para o objeto Canvas.</p>
<p>Em seguida entramos no loop infinito do jogo (game loop), que fica chamando update() e render(). Esse loop não possui controle de pulsos e frames, portanto vai rodar na velocidade máxima que a máquina suportar.</p>
<p>O método update simplesmente incrementa a variável x a cada vez que é chamado, zerando-a quando ela passa de 255. Essa variável será utilizada para determinar a cor a ser aplicada na tela.</p>
<p>A mudança da cor é feita no método render(), que desenha na tela utilizando o BufferStrategy obtido anteriormente. Primeiro é executado um setColor() passando para ele um objeto Color criado utilizando a variável x nas posições referentes às componentes vermelha (R), verde (G) e azul (B) da cor. Assim, teremos vários tons de ciz desde o preto (0, 0, 0) até o branco (255, 255, 255). Um fillRect() preenche com a cor selecionada a área total da tela.</p>
<p>O applet pode ser visualizada aqui: <a href="http://sites.google.com/site/nornberg/exemploapplet" target="_blank">http://sites.google.com/site/nornberg/exemploapplet</a></p>
<h2>Incluindo o applet em HTML</h2>
<p>A seguir está um exemplo de página HTML com a tag &lt;OBJECT&gt;, que é utilizada para incluir o applet.</p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span>&lt;html&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span></span>&lt;head&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>    </span>&lt;title&gt;ExemploApplet&lt;/title&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span>&lt;/head&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span></span>&lt;body&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>    </span>&lt;center&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>        </span>&lt;object<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>            </span>width=<span style="color: #ce7b00;">"640"</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>            </span>height=<span style="color: #ce7b00;">"480"</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>            </span>type=<span style="color: #ce7b00;">"application/x-java-applet"</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>            </span>classid=<span style="color: #ce7b00;">"java:exemploapplet/Main.class"</span>&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>            </span>&lt;param name=<span style="color: #ce7b00;">"code"</span> value=<span style="color: #ce7b00;">"exemploapplet/Main.class"</span> /&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>            </span>&lt;param name=<span style="color: #ce7b00;">"archive"</span> value=<span style="color: #ce7b00;">"ExemploApplet.jar"</span> /&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>        </span>&lt;/object&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>    </span>&lt;/center&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">016</span></span>&lt;/body&gt;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span></span>&lt;/html&gt;</pre>
<p>Esta tag carrega o applet pelo menos no Internet Explorer, Mozilla Firefox e Google Chrome (últimas versões). Onde está &#8220;exemploapplet/Main.class&#8221; você pode substituir pelo caminho da sua classe (pacotes e classe separados por barra. Por ponto deve funcioanr também). O parâmetro &#8220;archive&#8221; contém o caminho para o JAR do applet (gerado pelo NetBeans com o comando &#8220;construir&#8221;).</p>
<p>Isso é só o básico, para dar a fundamentação a quem nunca criou um applet. Em próximos posts mostrarei como incluir imagens e sons no JAR, para utilizá-los de dentro do applet.</p>
<p><a href="http://blog.abrindoojogo.com.br/como-obter-os-codigos-fonte-dos-artigos/">Baixe o código fonte deste artigo.</a></p>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/criando-um-applet-basico/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Threads, apenas um exemplo</title>
		<link>http://abrindoojogo.com.br/threads-apenas-um-exemplo</link>
		<comments>http://abrindoojogo.com.br/threads-apenas-um-exemplo#comments</comments>
		<pubDate>Thu, 08 Oct 2009 01:43:30 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://blog.abrindoojogo.com.br/?p=862</guid>
		<description><![CDATA[Threads são partes de um programa que executam paralelamente. Com seu uso é possível executar simultâneamente duas ou mais rotinas. Atualmente, com o barateamento dos processadores de vários núcleos (multi core), seu uso fica mais justificado. Embora eu não recomende trabalhar com threads, convém entender o que elas representam na prática. Antes de tudo vou [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/threads.png"><img class="alignleft size-full wp-image-875" title="Threads" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/threads.png" alt="Threads" width="200" height="150" /></a><em>Threads</em> são partes de um programa que executam paralelamente. Com seu uso é possível executar simultâneamente duas ou mais rotinas. Atualmente, com o barateamento dos processadores de vários núcleos (<em>multi core</em>), seu uso fica mais justificado. Embora eu não recomende trabalhar com <em>threads</em>, convém entender o que elas representam na prática.</p>
<p><span id="more-862"></span>Antes de tudo vou ressaltar: não recomendo trabalhar com <em>threads</em> a menos que seja o desenvolvimento de um jogo AAA, o qual não é foco deste site (digamos um Batman: Asilo Arkhan). Jogos assim, exigem intenso processamento de I.A., física e gráficos e possuem, em geral, muito dinheiro para serem feito. Isso justifica a utilização de uma forma de programação mais complexa. Ainda mais que estes jogos em geral são criados em C++, uma das piores linguagens para trabalhar com <em>threads</em>. Mesmo no Java, cujo uso é relativamente simples (como veremos abaixo), depurar um programa com <em>thread</em> é um inferno.</p>
<p>Além disso, projetar o código para tirar proveito de <em>threads</em> é tarefa para arquitetos competentes &#8211; caso contrário você vai criar um código complexo, difícil de depurar e manter e, provavelmente, vai cair em <em>dead locks</em> e outros problemas de concorrência . E ainda corre o risco de acabar com um código pouco eficiente, apesar do esforço adicional.</p>
<p>Fica então o aviso: o código abaixo serve para efeito de exemplo e não deve ser base para um jogo do mundo real.</p>
<p>Bom, se depois do que foi dito acima você ainda não desistiu de ler sobre <em>threads</em>, vamos em frente &#8211; o fato é que o conceito por trás delas, e sua correta utilização, são importantes para tirar todo proveito de uma CPU com múltiplos núcleos. Vamos ver como fazer isso com o <em>gameloop</em> desenvolvidos nos meus artigos anteriores. Se você não leu, filtre os posts pela tag <strong>Java </strong>e leia-os antes, ok?</p>
<h2>Modularizando o jogo</h2>
<p>Começo criando duas classes especializadas em atualizar a lógica do jogo (lembra do <em>update</em>?) e em atualizar a tela (lembra do <em>render</em>?). Chamarei elas de Controlador e Renderizador, respectivamente. Seu código está abaixo. Basicamente, eu tirei as rotinas update() e render() da minha classe do jogo e coloquei em classes separadas.</p>
<p><strong>Arquivo Controlador.java</strong></p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.thread;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">import</span> javax.swing.JFrame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Controlador<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>    </span>Contador contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>    </span>JFrame frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>    </span>Nave nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>    </span><span style="color: #0000e6;">public</span> Controlador(JFrame frame, Contador contador, Nave nave)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>        </span><span style="color: #0000e6;">this</span>.frame = frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>        </span><span style="color: #0000e6;">this</span>.contador = contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>        </span><span style="color: #0000e6;">this</span>.nave = nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">016</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">018</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> update()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">019</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">020</span>        </span>contador.contaPulso();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>        </span>nave.x += <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>        </span><span style="color: #0000e6;">if</span> (nave.x &gt; frame.getWidth() + <span style="color: #000000;">30</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>            </span>nave.x = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span></span>}</pre>
<p><strong>Arquivo Renderizador.java</strong></p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.thread;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">import</span> java.awt.Color;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span><span style="color: #0000e6;">import</span> java.awt.Graphics2D;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span></span><span style="color: #0000e6;">import</span> java.awt.image.BufferStrategy;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span></span><span style="color: #0000e6;">import</span> javax.swing.JFrame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Renderizador<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>    </span>BufferStrategy bs;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>    </span>Contador contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>    </span>JFrame frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>    </span>Nave nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">boolean</span> terminado = <span style="color: #0000e6;">false</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">016</span>    </span><span style="color: #0000e6;">public</span> Renderizador(JFrame frame, BufferStrategy bs,<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span>                        </span>Contador contador, Nave nave)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">018</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">019</span>        </span><span style="color: #0000e6;">this</span>.frame = frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">020</span>        </span><span style="color: #0000e6;">this</span>.bs = bs;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>        </span><span style="color: #0000e6;">this</span>.contador = contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>        </span><span style="color: #0000e6;">this</span>.nave = nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> render()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span>        </span>contador.contaFrame();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">028</span>        </span>Graphics2D g = (Graphics2D) bs.getDrawGraphics();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">029</span>        </span>g.setColor(Color.black);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">030</span>        </span>g.fillRect(<span style="color: #000000;">0</span>, <span style="color: #000000;">0</span>, frame.getWidth(), frame.getHeight());<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">031</span>        </span><span style="color: #0000e6;">int</span> x = nave.x;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">032</span>        </span><span style="color: #0000e6;">int</span> y = nave.y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">033</span>        </span><span style="color: #0000e6;">for</span> (<span style="color: #0000e6;">int</span> i = <span style="color: #000000;">0</span>; i &lt; nave.qtd; i++)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">034</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">035</span>            </span>g.setColor(Color.yellow);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">036</span>            </span>g.drawLine(x, y, x - <span style="color: #000000;">20</span>, y - <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">037</span>            </span>g.drawLine(x, y, x - <span style="color: #000000;">20</span>, y + <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">038</span>            </span>g.drawLine(x - <span style="color: #000000;">20</span>, y - <span style="color: #000000;">5</span>, x - <span style="color: #000000;">20</span>, y + <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">039</span>            </span>y += <span style="color: #000000;">15</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">040</span>            </span><span style="color: #0000e6;">if</span> (y &gt; <span style="color: #000000;">550</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">041</span>            </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">042</span>                </span>y = nave.y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">043</span>                </span>x += <span style="color: #000000;">15</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">044</span>            </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">045</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">046</span>        </span>g.setColor(Color.white);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">047</span>        </span>g.drawString(<span style="color: #ce7b00;">"Pulsos: "</span> + contador.getPulsosPorSegundo() +<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">048</span>                     </span><span style="color: #ce7b00;">"  Frames: "</span> + contador.getFramesPorSegundo() +<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">049</span>                     </span><span style="color: #ce7b00;">"          naves: "</span> + nave.qtd, <span style="color: #000000;">10</span>, <span style="color: #000000;">20</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">050</span>        </span>g.dispose();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">051</span>        </span>bs.show();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">052</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">053</span></span>}</pre>
<p>Veja que essas classes recebem &#8220;de fora&#8221;, no momento de sua construção, os objetos necessários para seu funcionamento. Ou seja, elas não possuem dados próprios, encapsulando apenas o algoritmo. Para que elas compartilhem os mesmos dados, criei também uma classe separada para armazenar os dados da nave:</p>
<p><strong>Arquivo Nave.java</strong></p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.thread;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Nave<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>    </span><span style="color: #0000e6;">int</span> x;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>    </span><span style="color: #0000e6;">int</span> y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>    </span><span style="color: #0000e6;">int</span> qtd;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span></span>}</pre>
<p>A classe do jogo em sí é exatamente igual à classe JogoLoopSimples vista em um artigo anterior, só que sem update() e sem render() e com o <em>gameloop</em> modificado conforme abaixo:</p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> gameloop()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>        </span>initialize();<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">004</span>        </span></span><span style="color: #ff0000;">Controlador c = new Controlador(this, contador, nave);
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">005</span>        Renderizador r = new Renderizador(this, bs, contador, nave);</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>        </span><span style="color: #0000e6;">while</span> (<span style="color: #0000e6;">true</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>        </span>{<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">008</span>            </span></span><span style="color: #ff0000;">c.update();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">009</span>            r.render();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>    </span>}</pre>
<p>Além disso, mais uma pequena modificação: ao sair do programa (pressionar ESC), envio para o console os dados de pulsos e frames, para registro. Isso é feito com um System.out.println() chamado na rotina keyPressed():</p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> keyPressed(KeyEvent e)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>        </span><span style="color: #0000e6;">if</span> (e.getKeyCode() == KeyEvent.VK_ESCAPE)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span>        </span>{<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">005</span>            </span></span><span style="color: #ff0000;">System.out.println("Pulsos: " + contador.getPulsosPorSegundo() +
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">006</span>                                "  Frames: " + contador.getFramesPorSegundo() +
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">007</span>                                "          naves: " + nave.qtd);</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>            </span>System.exit(<span style="color: #000000;">0</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>        </span>...</pre>
<p style="text-align: left;">Executando o programa assim, temos o seguinte resultado:</p>
<p style="text-align: center;"><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread01a.png"><img class="size-full wp-image-864 aligncenter" title="Thread01a" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread01a.png" alt="Thread01a" width="502" height="214" /></a></p>
<p style="text-align: center;"><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread01b.png"><img class="size-full wp-image-865 aligncenter" title="Thread01b" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread01b.png" alt="Thread01b" width="279" height="222" /></a></p>
<p style="text-align: left;">Reconhece a tela? É o mesmo protótipo da nave dos outros posts. Mas perai&#8230; Uau! 460 fps! Não eram apenas 40! Como foi que ficou mais rápido?</p>
<p>Simples: troquei de máquina&#8230; Veja: essa é uma máquina bem mais rápida e tem um processador de dois núcleos como podemos ver no painel do gerenciador de tarefas. Note outra coisa também: apesar do jogo estar programado de forma a rodar o mais rápido possível (sem limitação de pulsos), ele utiliza apenas 50% do processamento da máquina. Nos gráficos pode-se ver claramente que o jogo está ocupando praticamente todo núcleo da esquerda, enquanto o da direita está ocioso (quase ocioso, na verdade, está atendendo o S.O. e processos de fundo, como o antivirus).</p>
<p>Abaixo da tela está a saída do console do NetBeans, mostrando o número de pulsos e frames registrados ao fechar o programa.</p>
<h2>A soma das partes</h2>
<p>Modifiquemos agora nosso gameloop <strong>comentando o update()</strong>. Assim vamos ver quantos frames conseguimos se eliminarmos o trabalho de atualizar a lógica do jogo.</p>
<p>A saída é a seguinte:</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread02a.png"><img class="aligncenter size-full wp-image-866" title="Thread02a" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread02a.png" alt="Thread02a" width="468" height="199" /></a></p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread02b.png"><img class="aligncenter size-full wp-image-867" title="Thread02b" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread02b.png" alt="Thread02b" width="278" height="222" /></a>Veja que temos zero pulsos, já que update() nunca foi executada. Mas a quantidade de frames não mudou. Ou seja, o impacto de processamento da nossa lógica é muito pequeno. Vejamos o contrário. Vamos <strong>comentar o render()</strong>.</p>
<p>Resultado abaixo:</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread03a.png"><img class="aligncenter size-full wp-image-868" title="Thread03a" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread03a.png" alt="Thread03a" width="468" height="199" /></a><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread03b.png"><img class="aligncenter size-full wp-image-872" title="Thread03b" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread03b.png" alt="Thread03b" width="278" height="222" /></a>Pois é, sem o render() não aparece a tela. Mas o programa está lá, rodando, como podemos ver pelo processamento. Ao pressionar ESC basta olhar para a saída para ver a quantidade de pulsos e&#8230; Caraca! Mais de três milhões e meio de pulsos por segundo! Realmente, a parte (bem) mais pesada é a atualização da tela. A atualização da lógica (nesse caso, pelo menos) é tão efêmera que esse computador consegue realizar mais de 3.000.000 em um segundos contra apenas 460 atualizações da tela no mesmo tempo.</p>
<h2>Analisando os resultados, entram as Threads</h2>
<p>A primeira coisa importante é ver como o render() segura o jogo quando usamos esse tipo de <em>gameloop</em>, que é o mais simples. A cada volta do laço temos um update() (muito rápido) e um render(), que demora e faz com que o próximo update() acabe demorando a ser executado.</p>
<p>Mas o que conta para este post é o seguinte: reveja as imagens acima e preste atenção no processamento. Ele nunca passa de 50%. Ou seja, meu jogo não está tirando tudo da minha máquina nova! Praticamente ele só usa o núcleo da esquerda, enquanto o outro fica com pouco processamento, oriundo das tarefas do sistema. Isso é bom, na verdade. Mas e se eu precisasse de mais processamento? Teria uma forma de usar o outro núcleo? Tem sim, com <em>threads</em>.</p>
<p>Você sabe que o S.O. é multitarefa, ou seja, executa vários programas ao mesmo tempo. Você pode ver um vídeo e ouvir música ao mesmo simultâneamente, porque o S.O dá um pouco de processador para o vídeo e um pouco para a música. É a mesma CPU, porém dividida entre dois programas.</p>
<p>Se tem mais de uma CPU (mais de um núcleo, como na máquina acima), o S.O. pode dar um núcleo inteiro para o vídeo e o outro núcleo para a música, ao invés de dividir a mesma CPU. Isso torna as coisas mais ágeis ainda.</p>
<p>As <em>threads</em> permitem ter esta multitarefa dentro do mesmo programa. Por exemplo, você cria uma <em>thread</em> para carregar os dados do jogo e outra para rodar uma animação. Assim, o S.O. dá um pouco de processamento para cada uma,  e o resultado é que você pode mostrar uma animação enquanto os dados são carregados.</p>
<p>A modificação que faço a seguir no código vai permitir colocar o Controlador em uma <em>thread</em> e o Renderizador em outra, de forma a executarem paralelamente e, de quebra, rodar cada um em um núcleo, utilizando todo o poder da máquina. Se o render() sozinho dá 460 frames e update(), também sozinho, dá 3.000.000, agora deverei obter o jogo rodando simultâneamente com 3.000.000 pulsos e 460 frames.</p>
<p>Vamos ver se funciona:</p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Controlador <span style="color: #ff0000;">implements Runnable</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>    </span>Contador contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span>    </span>JFrame frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>    </span>Nave nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>    </span><span style="color: #0000e6;">public</span> Controlador(JFrame frame, Contador contador, Nave nave)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>        </span><span style="color: #0000e6;">this</span>.frame = frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>        </span><span style="color: #0000e6;">this</span>.contador = contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>        </span><span style="color: #0000e6;">this</span>.nave = nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">014</span>    </span></span><span style="color: #ff0000;">public void run()
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">015</span>    {
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">016</span>        while (true)
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">017</span>        {
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">018</span>            Thread.yield();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">019</span>            update();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">020</span>        }
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">021</span>    }</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> update()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>        </span>...<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Renderizador <span style="color: #ff0000;">implements Runnable</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">028</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">029</span>    </span>BufferStrategy bs;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">030</span>    </span>Contador contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">031</span>    </span>JFrame frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">032</span>    </span>Nave nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">033</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">boolean</span> terminado = <span style="color: #0000e6;">false</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">034</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">035</span>    </span><span style="color: #0000e6;">public</span> Renderizador(JFrame frame, BufferStrategy bs, Contador contador, Nave nave)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">036</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">037</span>        </span><span style="color: #0000e6;">this</span>.frame = frame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">038</span>        </span><span style="color: #0000e6;">this</span>.bs = bs;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">039</span>        </span><span style="color: #0000e6;">this</span>.contador = contador;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">040</span>        </span><span style="color: #0000e6;">this</span>.nave = nave;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">041</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">042</span>
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">043</span>    </span></span><span style="color: #ff0000;">public void run()
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">044</span>    {
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">045</span>        while (!terminado)
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">046</span>        {
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">047</span>            Thread.yield();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">048</span>            render();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">049</span>        }
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">050</span>    }</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">051</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">052</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> render()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">053</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">054</span>        </span>...</pre>
<p>Modifiquei o código das classes Controlador e Renderizador para que implementem a interface Runnable do Java. Para isso, também declarei o método run() e dentro dele coloquei um laço. O Renderizador tem um laço que fica chamando render(). O Controlador tem um laço que fica chamando o update().</p>
<p>Agora a modificação no <em>gameloop</em>:</p>
<pre><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> gameloop()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>        </span>initialize();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span>        </span>Controlador c = <span style="color: #0000e6;">new</span> Controlador(<span style="color: #0000e6;">this</span>, contador, nave);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>        </span>Renderizador r = <span style="color: #0000e6;">new</span> Renderizador(<span style="color: #0000e6;">this</span>, bs, contador, nave);<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">006</span>        </span></span><span style="color: #ff0000;">Thread t;
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">007</span>        t = new Thread(c);
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">008</span>        t.start();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">009</span>        t = new Thread(r);
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">010</span>        t.start();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>    </span>}</pre>
<p>Aqui está o uso das <em>threads</em>, finalmente. Basta criar um objeto do tipo Thread informando para ele um objeto do tipo Runnable (o Renderizador, por exemplo). Depois chamamos o método start() da <em>thread</em> e ela vai chamar o método run() do objeto que lhe foi passado. O método run() será executado em paralelo ao resto do programa. Então, estamos colocando o laço do render() e o laço do update() para rodarem em paralelo.</p>
<p>Curioso para ver o resutado? Está abaixo:</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread04a.png"><img class="aligncenter size-full wp-image-863" title="Thread04a" src="http://abrindoojogo.com.br/wp-content/uploads/2009/10/thread04a.png" alt="Thread04a" width="468" height="199" /></a></p>
<p>Voilá! Um milhão e oitocentos mil pulsos e 459 frames. E usado 100% da CPU. Veja que agora os dois núcleos estão absolutamente carregados &#8211; a linha do gráfico está &#8220;cravada&#8221; no topo.</p>
<p>Mas porque deu valores menores do que quando rodamos cada um separadamente? Bom, é que a CPU ainda precisa atender os tais processos de fundo, S.O., antivirus, etc. Eles devem estar rodando no mesmo núcleo do update(), o que fez ele executar mais lentamente. Mas foi uma boa escolha do S.O., já que esse é o processo mais leve. Inteligentes estas máquinas modernas, não?</p>
<p>De qualquer forma, é um desempenho muito acima da primeira versão que eu mostrei.</p>
<h2>Conclusão</h2>
<p>Não usem <em>threads</em>.</p>
<p>Pelo menos não até chegar a um ponto onde não tenha mais o quê otimizar no código de vocês e ainda assim o jogo esteja lento. Uma minoria de jogos atuais faz uso intensivo de <em>threads</em> (menos de 20, pelo que sei), e todos especialistas concordam que não é fácil.</p>
<p>O que fiz no código acima, compartilhar um objeto (a nave) entre duas <em>threads</em> rodando paralelamente é perigoso. Nesse caso uma delas atualiza os dados e a outra apenas lê. Mas se duas <em>threads</em> atualizarem os mesmos dados ao mesmo tempo, as consequencias serão imprevisíveis. O Java facilita porque possui formas de sincronizar dados, impedindo sua leitura simultaneamente por duas <em>threads</em>. Mas não adianta sincronizar tudo, senão uma <em>thread</em> vai acabar esperando pela outra para poder acessar os dados e vão acabar rodando em sequencia, ao invés de em paralelo.</p>
<p>Por outro lado, o Java, por sí,  já tira proveito de processadores de múltiplos núcleos. Existem outros processos que a máquina virtual faz, como coleta de lixo e otimização interativa do código. A JVM (Máquina Virtual Java) faz uso de <em>threads</em> para separar e rodar em paralelo estas operações, melhorando o desempenhdo do seu programa sem você ter que fazer nada.</p>
<p>Bom, fica aí um exemplo de uso de <em>threads</em> para quem não conhecia.</p>
<p><a href="http://blog.abrindoojogo.com.br/como-obter-os-codigos-fonte-dos-artigos/">Baixe o código fonte deste artigo.</a></p>
<div id="_mcePaste" style="overflow: hidden; position: absolute; left: -10000px; top: 1850px; width: 1px; height: 1px;">&lt;pre style=&#8221;font-family:Monospaced,monospace;color:#000000&#8243;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;001&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;package&lt;/span&gt; abrindoojogo.exemplos.thread;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;002&lt;/span&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;003&lt;/span&gt;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;public&lt;/span&gt; &lt;span style=&#8221;color:#0000e6;&#8221;&gt;class&lt;/span&gt; Nave&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;004&lt;/span&gt;&lt;/span&gt;{&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;005&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;int&lt;/span&gt; x;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;006&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;int&lt;/span&gt; y;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;007&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;int&lt;/span&gt; qtd;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;008&lt;/span&gt;&lt;/span&gt;}&lt;/pre&gt;</div>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/threads-apenas-um-exemplo/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>GameLoop com taxa constante de pulsos – parte 2 de 2</title>
		<link>http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-%e2%80%93-parte-2-de-2</link>
		<comments>http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-%e2%80%93-parte-2-de-2#comments</comments>
		<pubDate>Sat, 26 Sep 2009 02:18:00 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://blog.abrindoojogo.com.br/?p=743</guid>
		<description><![CDATA[No artigo anterior vimos o game loop em sua forma mais simples, que tem o problema de ter a taxa de pulsos e frames presas uma a outra. Isso faz o jogo correr mais lentamente em CPUs lentas e acelerar em CPU mais poderosas, impedindo uma velocidade estável em todas plataformas. Neste artigo veremos como [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop1.png"><img class="alignleft size-full wp-image-729" title="GameLoop" src="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop1.png" alt="GameLoop" width="200" height="150" /></a>No artigo anterior vimos o game loop em sua forma mais simples, que tem o problema de ter a taxa de pulsos e frames presas uma a outra. Isso faz o jogo correr mais lentamente em CPUs lentas e acelerar em CPU mais poderosas, impedindo uma velocidade estável em todas plataformas. Neste artigo veremos como criar um game loop que garanta uma velocidade fixa para o jogo.</p>
<p><span id="more-743"></span>Aprendemos, no post anterior, a diferença entre o pulso e o frame, sendo o primeiro relacionado à lógica do jogo e o segundo à atualização da tela. Tinhamos uma classe Main que criava um objeto do tipo JogoLoopSimples. Vamos modificar essa classe para usar agora um objeto do tipo JogoPulsoFixo.</p>
<p><strong>Arquivo Main.java</strong></p>
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.gameloop;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Main<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">static</span> <span style="color: #0000e6;">void</span> main(String[] args)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>        </span>JogoPulsoFixo jogo = <span style="color: #0000e6;">new</span> JogoPulsoFixo();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>        </span>jogo.gameloop();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span></span>}</span></pre>
<p>O game loop da classe JogoLoopSimples era assim (para relembrar):</p>
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> gameloop()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>        </span>initialize();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span>        </span><span style="color: #0000e6;">while</span> (<span style="color: #0000e6;">true</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>            </span>Thread.yield();<span style="color: #000000;">
<strong><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>            </strong></span><strong>update();</strong><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>            </span>render();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>    </span>}</span></pre>
<p>Uma chamada a update() e uma a render(), acopladas. Se render demora, update também demora e o jogo fica lento. Bem, vamos partir do seguinte pressuposto: <strong>é possível &#8220;aturar&#8221; uma taxa de frames baixa, mas uma taxa de pulsos baixa modifica a jogabilidade.</strong></p>
<p>Imagine um jogo onde uma nave se move um pixel por pulso. Se temos 60 pulsos por segundo, ao final de dois segundos a nave terá se movido 120 pixels. Mas se a taxa cair para 10 pulsos por segundo, em dois segundos a nave vai se mover apenas 20 pixels. E mais: se o computador for muito rápido, a taxa pode subir a 100 pulsos por segundo, e a nave vai andar 200 pixels em dois segundos. A jogabilidade é totalmente afetada.</p>
<p>A solução que apresento a seguir tenta manter a taxa de pulsos fixa, em detrimento da taxa de frames. Ou seja, se a máquina é lenta, priorizamos os pulsos e geramos os frames conforme der. Sempre teremos 60 pulsos por segundo, embora a taxa de frames possa cair para 10.</p>
<p>Isso causa o seguinte efeito: a nave vai se mover sempre 120 pixels em dois segundos, independente da velocidade da máquina. Mas se a máquina for lenta, a tela estará sendo atualizada apenas a 10 frames por segundo &#8211; o jogador vai ver a imagem quadro a quadro, mas a jogabilidade não fica tão comprometida, porque não há mudança na velocidade da ação.</p>
<p>E se a máquina for muito rápida, ainda assim ficaremos apenas com 60 pulsos por segundo, embora possamos estar obtendo 100 frames. A atualização da tela será bem rápida, o que é bom, e a nave continua se movendo na velocidade esperada.</p>
<p>Eu mostro abaixo a nova classe, chamada JogoPulsoFixo. Ela é derivada da classe do artigo anterior, de forma que tem tudo igual a ela. A lógica do jogo é exatamente a mesma. Só sobreescrevi o método gameloop, para modificá-lo.</p>
<p><strong>Arquivo JogoPulsoFixo.java</strong></p>
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.gameloop;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> JogoPulsoFixo <span style="color: #0000e6;">extends</span> JogoLoopSimples<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span>{<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">005</span>    </span></span><span style="color: #ff0000;">long PULSOS_DESEJADOS_POR_SEGUNDO = 60;
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">006</span>    double NANOS_ESPERADOS_POR_PULSO = Contador.NANOS_EM_UM_SEGUNDO / PULSOS_DESEJADOS_POR_SEGUNDO;</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>    </span>@Override<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> gameloop()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>        </span>initialize();<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">012</span>        </span></span><span style="color: #ff0000;">long nanoTimeDoProximoPulso = System.nanoTime();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>        </span><span style="color: #0000e6;">while</span> (<span style="color: #0000e6;">true</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>            </span>Thread.yield();<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">016</span>            </span></span><span style="color: #ff0000;">while (System.nanoTime() &gt; nanoTimeDoProximoPulso)
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">017</span>            {
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">018</span>                update();
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">019</span>                nanoTimeDoProximoPulso += NANOS_ESPERADOS_POR_PULSO;
<span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">020</span>            }</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>            </span>render();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span></span>}</span></pre>
<p>A modificação (marcada em vermelho) é simples em termos de código, mas pode ser difícil de entender como funciona. Por isso vou explicar bem detalhadamente.</p>
<p>Nas linhas 005, 006  são declaradas constantes. PULSOS_DESEJADOS_POR_SEGUNDO armazena a quantidade de pulsos que desejamos que o game rode. Nesse caso é 60. Não é necessário mais do que isso para a lógica de qualquer jogo. Alguns rodam a 30 ou 25.</p>
<p>NANOS_ESPERADOS_POR_PULSO armazena a quantidade de nanosegundos que cada pulso deve durar. Calcular isso é fácil: se queremos 60 pulsos por segundo, basta pegar a quantidade total de nanosegundos que cabem em um segundo (1e9 ou  1.000.000.000) e dividir por sessenta pulsos. Cada pulso vai durar, nesse caso, 16.666.666 nanosegundos. Em geral vai durar menos, mas queremos ter um pulso a cada 16.666.666 nanosegundos, de forma a constituir 60 por segundo.</p>
<p>Agora veja o game loop. A grande mudança é que temos um outro laço dentro dele, para chamar repetidamente update(). Funciona assim: inicializamos uma variável chamada nanoTimeDoProximoPulso com o valor no nanosegundo atual. Em seguida entramos no game loop e já caimos no loop do update. É feita a verificação para ver se o nanosegundo atual é maior do que o nanoTimeDoProximoPulso, o que certamente não será, já que acabamos de atribuir o tempo atual a esta variável.</p>
<p>Pois bem. Entramos no loop do update(), chamamos esta rotina e depois adicionamos ao nanoTimeDoProximoPulso a quantidade de nanos esperados em um pulso. Isso nos dá o momento no tempo quando deverá ser executado o próximo pulso. Não executaremos ele antes desse tempo. Por outro lado, passar muito desse tempo, executaremos ele mais de uma vez até recuperar o atraso.</p>
<p>Vamos analisar um exemplo volta a volta do game loop. Respire fundo antes de continuar lendo.</p>
<ol>
<li>Vamos assumir que tudo iniciou com o nanoTime = 0 (zero). Executamos update(), que demora 5.000.000 nanosegundos e somamos 16.666.666 na variável nanoTimeDoProximoPulso. Isso quer dizer que o próximo pulso é esperado para ocorrer nesse tempo.</li>
<li>Como update() demorou apenas 5.000.000 nanosegundos, ainda não chegamos ao 16.666.666 e saimos do loop do update. É executado em seguida o  render(), que demora mais 5.000.000 nanosegundos e voltamos ao início do game loop.</li>
<li>Nova verificação do loop do update. O tempo atual é maior do que 16.666.666? Já que update() levou 5.000.000 e render() mais 5.000.000, estamos em 10.000.000 nanosegundos, que é menor. Não entramos no loop do update, ou seja, desta vez o update() não será executado, porque ainda não está na hora esperada. Executamos o render(), que leva mais 5.000.000 nanosegundos e voltamos ao início do game loop.</li>
<li>Agora já estamos em 15.000.000, mas ainda é menor do que 16.666.666, então pulamos novamente o loop do update e vamos direto para o render. Mais 5.000.000 nanosegundos e voltamos ao início.</li>
<li>Agora sim, estamos em 20.000.000 nanosegundos e isso é maior do que o esperado para o próximo pulso, que deveria ter ocorrido em 16.666.666. Estamos atrasados, mas tudo bem &#8211; agora entramos no loop do update, executamos ele (mais 5.000.000) e somamos mais 16.666.666 na variável nanoTimeDoProximoPulso. Isso quer dizer que agora vamos esperar até o tempo chegar em 33.333.332 para executar update() novamente.</li>
</ol>
<p>Já deu para notar que update está sendo limitado. Praticamente temos três render() para cada update(). Essa é uma máquina rápida. Vamos refazer a análise em uma máquina lenta.</p>
<ol>
<li>Tudo inicia no nanoTime = 0 (zero). Executamos update(), que agora demora 10.000.000 nanosegundos e somamos 16.666.666 na variável nanoTimeDoProximoPulso.</li>
<li>Como update() demorou apenas 9.000.000 nanosegundos, ainda não chegamos ao 16.666.666 e saimos do loop do update. É executado em seguida o  render(), que demora 15.000.000 nanosegundos (placa de vídeo lenta) e voltamos ao início do game loop.</li>
<li>Nova verificação do loop do update e o tempo atual é 25.000.000, ou seja, maior que o 16.666.666 esperado para o próximo pulso. Assim, entramos no loop do update e executamos ele. Mais 10.000.000 se passam e estamos então há 35.000.000 nanosegundos de jogo. Acrescentamos novamente 16.666.666 à variável, ficando com 33.333.332, que seria a hora do próximo pulso.</li>
<li>Mas veja: já estamos em 35.000.000, ou seja, já passou a hora do segundo pulso. Então ficamos dentro do loop do update (porque 35.000.000 é maior que 33.333.332) e vamos executar update mais uma vez. Se passam mais 10.000.000 e estamos em 45.000.000. Somamos novamente 16.666.666 na variável e o próximo pulso fica então esperado para 49.999.998.</li>
<li>Ok, desta vez o tempo atual (45.000.000) é menor do que o esperado para o próximo pulso (49.999.998). Então pulamos o loop do update e vamos para o render(). Executamos ele e, devido aos seus 15.000.000 ficamos em 60.000.000 e voltamos ao início.</li>
</ol>
<p>Já deu para ver que vamos entrar novamente no loop do update porque estamos bem atrasados. Vamos acabar executando o update duas vezes novamente, ou seja, nessa máquina o update executa o dobro de vezes que o render.</p>
<p>Caramba, que explicação cheia de volta&#8230; Entendeu? Espero que sim. Caso contrário, leia novamente o exemplo. Experimente colocar o comando contador.sleep(X), onde X é um número de milisegundos, dentro das rotinas update() e render() no arquivo JogoLoopSimples. Isso vai simular rotinas demoradas. Use valores como 50 ou 100  milisegundos.</p>
<p>Esse game loop mantém a taxa de pulsos fixa (na verdade pode oscilar entre 60 e 62) e pode ser utilizado para a criação de games reais. Mas ele apresenta um problema com máquina muitissimo lentas: pode ser que o update() precise rodar 500 vezes para cada render(). Ou mais! Ou ainda, ficar rodando sem nunca chegar na taxa desejada, e assim nunca executar o update().</p>
<p>Alguma dica de como resolver isso? Se você achar uma solução envie para mim (<strong>nornberg</strong> no gmail). Depois publico um post citando as soluções que aparecerem.</p>
<p><a href="http://blog.abrindoojogo.com.br/como-obter-os-codigos-fonte-dos-artigos/">Baixe o código fonte deste artigo.</a></p>
<div id="_mcePaste" style="overflow: hidden; position: absolute; left: -10000px; top: 786px; width: 1px; height: 1px;">&lt;pre&gt;&lt;span style=&#8221;font-family:Monospaced,monospace;color:#000000&#8243;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;001&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;package&lt;/span&gt; abrindoojogo.exemplos.gameloop;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;002&lt;/span&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;003&lt;/span&gt;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;public&lt;/span&gt; &lt;span style=&#8221;color:#0000e6;&#8221;&gt;class&lt;/span&gt; JogoPulsoFixo &lt;span style=&#8221;color:#0000e6;&#8221;&gt;extends&lt;/span&gt; JogoLoopSimples&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;004&lt;/span&gt;&lt;/span&gt;{&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;005&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;long&lt;/span&gt; PULSOS_DESEJADOS_POR_SEGUNDO = &lt;span style=&#8221;color:#000000;&#8221;&gt;60&lt;/span&gt;;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;006&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;double&lt;/span&gt; NANOS_ESPERADOS_POR_PULSO = Contador.NANOS_EM_UM_SEGUNDO / PULSOS_DESEJADOS_POR_SEGUNDO;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;007&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;long&lt;/span&gt; MAX_FRAMES_PARA_PULAR = &lt;span style=&#8221;color:#000000;&#8221;&gt;2&lt;/span&gt;;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;008&lt;/span&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;009&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;public&lt;/span&gt; &lt;span style=&#8221;color:#0000e6;&#8221;&gt;void&lt;/span&gt; gameloop()&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;010&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;{&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;011&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;initialize();&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;012&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;long&lt;/span&gt; nanoTimeDoProximoPulso = System.nanoTime();&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;013&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;while&lt;/span&gt; (&lt;span style=&#8221;color:#0000e6;&#8221;&gt;true&lt;/span&gt;)&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;014&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;{&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;015&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;Thread.yield();&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;016&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;long&lt;/span&gt; pulsos = &lt;span style=&#8221;color:#000000;&#8221;&gt;0&lt;/span&gt;;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;017&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;&lt;span style=&#8221;color:#0000e6;&#8221;&gt;while&lt;/span&gt; (System.nanoTime() &amp;gt; nanoTimeDoProximoPulso &amp;amp;&amp;amp; pulsos &amp;lt; MAX_FRAMES_PARA_PULAR)&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;018&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;{&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;019&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;update();&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;020&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;nanoTimeDoProximoPulso += NANOS_ESPERADOS_POR_PULSO;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;021&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;pulsos++;&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;022&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;}&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;023&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;render();&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;024&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;}&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;025&lt;/span&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;/span&gt;}&lt;span style=&#8221;color:#000000;&#8221;&gt;&lt;br/&gt;&lt;span style=&#8217;color:#666;background-color:#DDD;border-right:1px #999 solid;margin-right:5px;padding:2px&#8217;&gt;026&lt;/span&gt;&lt;/span&gt;}&lt;/span&gt;&lt;/pre&gt;&lt;/div&gt;</div>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-%e2%80%93-parte-2-de-2/feed</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>GameLoop com taxa constante de pulsos &#8211; parte 1 de 2</title>
		<link>http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-parte-1-de-2</link>
		<comments>http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-parte-1-de-2#comments</comments>
		<pubDate>Fri, 25 Sep 2009 03:31:02 +0000</pubDate>
		<dc:creator>Luiz Nörnberg</dc:creator>
				<category><![CDATA[Java]]></category>
		<category><![CDATA[Programação]]></category>
		<category><![CDATA[Técnico]]></category>

		<guid isPermaLink="false">http://blog.abrindoojogo.com.br/?p=727</guid>
		<description><![CDATA[O coração de qualquer jogo é o game loop, um laço que fica sendo repetido durante toda execução do jogo. A cada volta desse laço temos um novo frame de jogo. Mas você sabe que a taxa de frames pode variar muito de um hardware para outro. Como manter a lógica do jogo rodando a [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop1.png"><img class="alignleft size-full wp-image-729" title="GameLoop" src="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop1.png" alt="GameLoop" width="200" height="150" /></a></p>
<p>O coração de qualquer jogo é o <em>game loop</em>, um laço que fica sendo repetido durante toda execução do jogo. A cada volta desse laço temos um novo frame de jogo. Mas você sabe que a taxa de frames pode variar muito de um hardware para outro. Como manter a lógica do jogo rodando a uma velocidade fixa, independente da variação nos frames?<br />
<span id="more-727"></span><br />
Quando jogamos, o que vemos na tela é uma sucessão de quadros que nos dá a impressão de movimento. Isso é chamado animação e tenho certeza que você já conhece seus princípios. Em geral somos levados a crer que, a cada quadro novo que vemos, algo mudou no estado do jogo. Se uma nave está se movendo, a cada quadro ela estará, digamos, um pixel para a direita.</p>
<p>É o <em>game loop</em>, o laço principal do jogo, que emite o que podemos chamar de <strong>pulsos </strong>para atualizar o estado do jogo (<em><strong>update</strong></em>) e redesenhar a imagem na tela (<em><strong>render</strong></em>). Em sua forma mais simples, a cada volta do <em>game loop</em> temos um pulso para <em>update </em>e um para <em>render</em>. Mas estas duas tarefas não precisam ser sempre sincronizadas. Na verdade, é melhor que não sejam.</p>
<p>Vamos contruir um programa de exemplo para estudar mais a fundo o <em>game loop</em>. Neste post vamos ver o <em>loop </em>mais simples e entender sua limitação. No próximo veremos como desacoplar o <em>update </em>do <em>render</em>, de forma que o <em>update </em>rode sempre a uma determinada velocidade e o <em>render </em>rode o mais rápido que puder.</p>
<p><strong>Arquivo Main.java</strong></p>
<div style="overflow: scroll; border: 1px solid #cccccc;">
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.gameloop;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Main<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">static</span> <span style="color: #0000e6;">void</span> main(String[] args)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>        </span>JogoLoopSimples jogo = <span style="color: #0000e6;">new</span> JogoLoopSimples();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>        </span>jogo.gameloop();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span></span>}</span></pre>
</div>
<p>Esta classe simplesmente cria um objeto do tipo JogoLoopSimples e chama seu método gameloop() que vai rodar o jogo. A seguir a classe do jogo em sí, que possui o game loop.</p>
<p><strong>Arquivo JogoLoopSimples</strong></p>
<div style="overflow: scroll; border: 1px solid #cccccc;">
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.gameloop;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">import</span> java.awt.Color;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span><span style="color: #0000e6;">import</span> java.awt.Dimension;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span></span><span style="color: #0000e6;">import</span> java.awt.Graphics2D;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span></span><span style="color: #0000e6;">import</span> java.awt.Toolkit;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span></span><span style="color: #0000e6;">import</span> java.awt.event.KeyEvent;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span></span><span style="color: #0000e6;">import</span> java.awt.event.KeyListener;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span></span><span style="color: #0000e6;">import</span> java.awt.image.BufferStrategy;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span></span><span style="color: #0000e6;">import</span> javax.swing.JFrame;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span></span><span style="color: #0000e6;">import</span> javax.swing.WindowConstants;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> JogoLoopSimples <span style="color: #0000e6;">extends</span> JFrame <span style="color: #0000e6;">implements</span> KeyListener<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>    </span>BufferStrategy bs;<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">016</span>    </span></span><span style="color: #ff0000;">Contador contador;</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span>    </span><span style="color: #0000e6;">int</span> nave_x, nave_y, nave_qtd;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">018</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">019</span>    </span><span style="color: #0000e6;">public</span> JogoLoopSimples()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">020</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>        </span>setUndecorated(<span style="color: #0000e6;">true</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>        </span>setSize(<span style="color: #000000;">800</span>, <span style="color: #000000;">600</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>        </span>Dimension d = Toolkit.getDefaultToolkit().getScreenSize();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>        </span>setLocation(d.width / <span style="color: #000000;">2</span> - <span style="color: #000000;">400</span>, d.height / <span style="color: #000000;">2</span> - <span style="color: #000000;">300</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>        </span>setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>        </span>setIgnoreRepaint(<span style="color: #0000e6;">true</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span>        </span>addKeyListener(<span style="color: #0000e6;">this</span>);<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">028</span>        </span></span><span style="color: #ff0000;">contador = new Contador();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">029</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">030</span>
<strong><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">031</span>    </strong></span><strong><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> gameloop()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">032</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">033</span>        </span>initialize();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">034</span>        </span><span style="color: #0000e6;">while</span> (<span style="color: #0000e6;">true</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">035</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">036</span>            </span>Thread.yield();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">037</span>            </span>update();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">038</span>            </span>render();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">039</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">040</span>    </span>}</strong><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">041</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">042</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> initialize()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">043</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">044</span>        </span>setVisible(<span style="color: #0000e6;">true</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">045</span>        </span>createBufferStrategy(<span style="color: #000000;">2</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">046</span>        </span>bs = getBufferStrategy();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">047</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">048</span>        </span>nave_x = <span style="color: #000000;">400</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">049</span>        </span>nave_y = <span style="color: #000000;">50</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">050</span>        </span>nave_qtd = <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">051</span>
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">052</span>        </span></span><span style="color: #ff0000;">contador.inicia();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">053</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">054</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">055</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> update()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">056</span>    </span>{<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">057</span>        </span></span><span style="color: #ff0000;">contador.contaPulso();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">058</span>        </span>nave_x += <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">059</span>        </span><span style="color: #0000e6;">if</span> (nave_x &gt; getWidth() + <span style="color: #000000;">30</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">060</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">061</span>            </span>nave_x = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">062</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">063</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">064</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">065</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> render()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">066</span>    </span>{<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">067</span>        </span></span><span style="color: #ff0000;">contador.contaFrame();</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">068</span>        </span>Graphics2D g = (Graphics2D) bs.getDrawGraphics();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">069</span>        </span>g.setColor(Color.black);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">070</span>        </span>g.fillRect(<span style="color: #000000;">0</span>, <span style="color: #000000;">0</span>, getWidth(), getHeight());<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">071</span>        </span><span style="color: #0000e6;">int</span> x = nave_x;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">072</span>        </span><span style="color: #0000e6;">int</span> y = nave_y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">073</span>        </span><span style="color: #0000e6;">for</span> (<span style="color: #0000e6;">int</span> i = <span style="color: #000000;">0</span>; i &lt; nave_qtd; i++)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">074</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">075</span>            </span>g.setColor(Color.yellow);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">076</span>            </span>g.drawLine(x, y, x - <span style="color: #000000;">20</span>, y - <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">077</span>            </span>g.drawLine(x, y, x - <span style="color: #000000;">20</span>, y + <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">078</span>            </span>g.drawLine(x - <span style="color: #000000;">20</span>, y - <span style="color: #000000;">5</span>, x - <span style="color: #000000;">20</span>, y + <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">079</span>            </span>y += <span style="color: #000000;">15</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">080</span>            </span><span style="color: #0000e6;">if</span> (y &gt; <span style="color: #000000;">550</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">081</span>            </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">082</span>                </span>y = nave_y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">083</span>                </span>x += <span style="color: #000000;">15</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">084</span>            </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">085</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">086</span>        </span>g.setColor(Color.white);<span style="color: #000000;">
<span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">087</span></span>        </span>g.drawString(<span style="color: #ce7b00;">"Pulsos: "</span> + <span style="color: #ff0000;">contador.getPulsosPorSegundo()</span> + <span style="color: #ce7b00;">"  Frames: "</span> + <span style="color: #ff0000;">contador.getFramesPorSegundo()</span> + <span style="color: #ce7b00;">"          naves: "</span> + nave_qtd, <span style="color: #000000;">10</span>, <span style="color: #000000;">20</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">088</span>        </span>g.dispose();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">089</span>        </span>bs.show();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">090</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">091</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">092</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> keyPressed(KeyEvent e)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">093</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">094</span>        </span><span style="color: #0000e6;">if</span> (e.getKeyCode() == KeyEvent.VK_ESCAPE)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">095</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">096</span>            </span>System.exit(<span style="color: #000000;">0</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">097</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">098</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">099</span>        </span><span style="color: #0000e6;">if</span> (e.getKeyCode() == KeyEvent.VK_UP)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">100</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">101</span>            </span>nave_y -= <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">102</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">103</span>        </span><span style="color: #0000e6;">if</span> (e.getKeyCode() == KeyEvent.VK_DOWN)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">104</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">105</span>            </span>nave_y += <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">106</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">107</span>        </span><span style="color: #0000e6;">if</span> (e.getKeyCode() == KeyEvent.VK_RIGHT)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">108</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">109</span>            </span><span style="color: #0000e6;">if</span> (nave_qtd &lt; <span style="color: #000000;">1054</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">110</span>            </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">111</span>                </span>nave_qtd += <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">112</span>            </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">113</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">114</span>        </span><span style="color: #0000e6;">if</span> (e.getKeyCode() == KeyEvent.VK_LEFT)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">115</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">116</span>            </span><span style="color: #0000e6;">if</span> (nave_qtd &gt; <span style="color: #000000;">1</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">117</span>            </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">118</span>                </span>nave_qtd -= <span style="color: #000000;">1</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">119</span>            </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">120</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">121</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">122</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">123</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> keyReleased(KeyEvent e)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">124</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">125</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">126</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">127</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> keyTyped(KeyEvent e)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">128</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">129</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">130</span></span>}</span></pre>
</div>
<p>Vejamos os métodos mais importantes. O contructor faz bastante coisa de configuração, mas tudo com relação à janela do jogo. É tirada a decoração (título, borda, etc) ficando apenas um quadro centralizado no vídeo. É centralizado baseado no tamanho da tela, obtida por meio de Toolkit.getDefaultToolkit().getScreenSize().  Boa parte desse código é parecida com o que foi mostrado no post <a href="http://blog.abrindoojogo.com.br/passive-vs-active-rendering-%E2%80%93-parte-2-de-2/">Passive VS Active Rendering</a>. Note, no entando na criação do objeto &#8220;contador&#8221;. Ele será utilizado para contar quantos pulsos e quantos <em>frames </em>obteremos. Os pontos onde ele é utilizado estão destacados em vermelho.</p>
<p>O jogo é muito simples &#8211; na verdade nem é um jogo. O método update() incrementa a variável nave_x, fazendo ela ir até a direita da tela e então recomeçar da esquerda. Quando uma tecla é pressionada, o método keyPressed modifica a variável nave_y, fazendo a posição subir ou descer, ou aumenta/diminui a variável nave_qtd, que informa quantos sprites teremos na tela.</p>
<p>O método render() limpa a tela, desenha a &#8220;nave&#8221; (um triângulo feito com linhas) dentro de um <em>loop </em>que vai repetir o desenho tantas vezes quanto for o valor de nave_qtd. Depois mostra na tela os valores de pulsos por segundo e <em>frames </em>por segundos do contador.</p>
<p>Note que toda vez que o método update() é executado, dentro dele é chamado o contador.contaPulso(). E no método render() é chamado contador.contaFrame(). Assim estamos contando quantas vezes estes dois métodos são chamados.</p>
<p>Nosso game loop é a versão mais simples possível, reproduzida abaixo.</p>
<div style="overflow: scroll; border: 1px solid #cccccc;">
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">031</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> gameloop()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">032</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">033</span>        </span>initialize();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">034</span>        </span><span style="color: #0000e6;">while</span> (<span style="color: #0000e6;">true</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">035</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">036</span>            </span>Thread.yield();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">037</span>            </span>update();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">038</span>            </span>render();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">039</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">040</span>    </span>}</span></pre>
</div>
<p>É chamado update() e depois render(), um após o outro sem nenhum controle mais elaborado. O método yield() faz o programa interromper rapidamente seu processamento para que o resto do sistema tenha tempo de CPU. Usar ele faz o programa parar um pouco para escutar o teclado. Sem ele, um pressionar de tecla pode ser perdido.</p>
<p>Finalmente vejamos o código do contador.</p>
<p><strong>Arquivo Contador.java</strong></p>
<div style="overflow: scroll; border: 1px solid #cccccc;">
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #0000e6;">package</span> abrindoojogo.exemplos.gameloop;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span></span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">class</span> Contador<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span></span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>    </span><span style="color: #0000e6;">static</span> <span style="color: #0000e6;">public</span> <span style="color: #0000e6;">double</span> NANOS_EM_UM_SEGUNDO = <span style="color: #000000;">1e9</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>    </span><span style="color: #0000e6;">protected</span> <span style="color: #0000e6;">long</span> pulsosPorSegundo;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>    </span><span style="color: #0000e6;">protected</span> <span style="color: #0000e6;">long</span> framesPorSegundo;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>    </span><span style="color: #0000e6;">protected</span> <span style="color: #0000e6;">long</span> nanoTimeAnterior;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>    </span><span style="color: #0000e6;">protected</span> <span style="color: #0000e6;">long</span> pulsosContados;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>    </span><span style="color: #0000e6;">protected</span> <span style="color: #0000e6;">long</span> framesContados;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> inicia()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>        </span>nanoTimeAnterior = System.nanoTime();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>        </span>pulsosContados = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">016</span>        </span>framesContados = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span>        </span>pulsosPorSegundo = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">018</span>        </span>framesPorSegundo = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">019</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">020</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> contaPulso()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>        </span>pulsosContados++;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>        </span>verifica();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> contaFrame()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">028</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">029</span>        </span>framesContados++;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">030</span>        </span>verifica();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">031</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">032</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">033</span>    </span><span style="color: #0000e6;">protected</span> <span style="color: #0000e6;">void</span> verifica()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">034</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">035</span>        </span><span style="color: #0000e6;">if</span> (System.nanoTime() - nanoTimeAnterior &gt; NANOS_EM_UM_SEGUNDO)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">036</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">037</span>            </span>pulsosPorSegundo = pulsosContados;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">038</span>            </span>framesPorSegundo = framesContados;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">039</span>            </span>pulsosContados = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">040</span>            </span>framesContados = <span style="color: #000000;">0</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">041</span>            </span>nanoTimeAnterior = System.nanoTime();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">042</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">043</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">044</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">045</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> sleep(<span style="color: #0000e6;">long</span> miliSecondsToSleep)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">046</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">047</span>        </span><span style="color: #0000e6;">try</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">048</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">049</span>            </span>Thread.sleep(miliSecondsToSleep);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">050</span>        </span>} <span style="color: #0000e6;">catch</span> (Exception e)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">051</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">052</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">053</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">054</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">055</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">long</span> getPulsosPorSegundo()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">056</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">057</span>        </span><span style="color: #0000e6;">return</span> pulsosPorSegundo;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">058</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">059</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">060</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">long</span> getFramesPorSegundo()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">061</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">062</span>        </span><span style="color: #0000e6;">return</span> framesPorSegundo;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">063</span>    </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">064</span></span>}</span></pre>
</div>
<p>O trabalho desta classe é interessante: cada vez que chamamos o método contaPulso(), ela incrementa o contador de pulsos e chama o método verifica() que testa se já passou um segundo desde a última verificação. Se sim, ele atribui a quantidade de pulsos contados para a variável pulsosPorSegundo. Assim, esta variável é atualizada a cada segundo com a quantidade de pulsos que ocorreram. Nesse momento o contador de pulsos é zerado para contar quantos pulsos ocorrerão no próximo segundo. A mesma coisa para a contagem de frames.</p>
<p>O tempo é medido em nanosegundos, que é bem menor que os milisegundos geralmente utilizados nos programas. Um segundo contém 1.000 milisegundos, ou seja, <strong>1e3</strong> (mil). E possui 1.000.000.000 nano segundos, ou seja, <strong>1e9</strong> (um milhão). Esse valor está registrado na constante NANOS_EM_UM_SEGUNDO para ser utilizado nos cálculos.</p>
<p>Essa classe oferece ainda um método utilitário chamado sleep(), que servirá para realizarmos alguns testes. Ele simplifica o uso do método sleep() de Thread, que precisa de um <em>try-catch</em> para ser usado. Ele faz o processamento parar durante os milisegundos informados.</p>
<p>Executando esse programa, obtenho o seguinte resultado (só mostro o canto da tela):</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop01.png"><img class="aligncenter size-full wp-image-732" title="GameLoop01" src="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop01.png" alt="GameLoop01" width="400" height="100" /></a>Conforme os dados do contador mostrados, tenho 47 pulsos por segundo e também 47 frames. Naturalmente estes números serão sempre iguais, porque dentro do loop chamo uma vez update() e uma vez o render().</p>
<p>Se eu desejasse 60 fps (<em>frames </em>por segundo), não seria possível. 47 é tudo que eu consigo no meu computador e ainda fica variando. Se eu pressiono a seta para direita, aumentando a quantidade de <em>sprites </em>até 1054, a taxa de <em>frames </em>cai mais um pouco.</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop02.png"><img class="aligncenter size-full wp-image-733" title="GameLoop02" src="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop02.png" alt="GameLoop02" width="400" height="100" /></a>Talvez seu computador seja bem mais rápid e mesmo aumentando os <em>sprites </em>a taxa de frames não apresente muita diferença. Vamos fazer um teste mais exagerado. Chamaremos o método contador.sleep() dentro do método render(), de forma a fazer este método demorar alguns milisegundos a mais.</p>
<div style="overflow: scroll; border: 1px solid #cccccc;">
<pre><span style="font-family: Monospaced,monospace; color: #000000;"><span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">001</span><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">002</span>
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">003</span>    </span><span style="color: #0000e6;">public</span> <span style="color: #0000e6;">void</span> render()<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">004</span>    </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">005</span>        </span>contador.contaFrame();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">006</span>        </span>Graphics2D g = (Graphics2D) bs.getDrawGraphics();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">007</span>        </span>g.setColor(Color.black);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">008</span>        </span>g.fillRect(<span style="color: #000000;">0</span>, <span style="color: #000000;">0</span>, getWidth(), getHeight());<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">009</span>        </span><span style="color: #0000e6;">int</span> x = nave_x;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">010</span>        </span><span style="color: #0000e6;">int</span> y = nave_y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">011</span>        </span><span style="color: #0000e6;">for</span> (<span style="color: #0000e6;">int</span> i = <span style="color: #000000;">0</span>; i &lt; nave_qtd; i++)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">012</span>        </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">013</span>            </span>g.setColor(Color.yellow);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">014</span>            </span>g.drawLine(x, y, x - <span style="color: #000000;">20</span>, y - <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">015</span>            </span>g.drawLine(x, y, x - <span style="color: #000000;">20</span>, y + <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">016</span>            </span>g.drawLine(x - <span style="color: #000000;">20</span>, y - <span style="color: #000000;">5</span>, x - <span style="color: #000000;">20</span>, y + <span style="color: #000000;">5</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">017</span>            </span>y += <span style="color: #000000;">15</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">018</span>            </span><span style="color: #0000e6;">if</span> (y &gt; <span style="color: #000000;">550</span>)<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">019</span>            </span>{<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">020</span>                </span>y = nave_y;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">021</span>                </span>x += <span style="color: #000000;">15</span>;<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">022</span>            </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">023</span>        </span>}<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">024</span>        </span>g.setColor(Color.white);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">025</span>        </span>g.drawString(<span style="color: #ce7b00;">"Pulsos: "</span> + contador.getPulsosPorSegundo() + <span style="color: #ce7b00;">"  Frames: "</span> + contador.getFramesPorSegundo() + <span style="color: #ce7b00;">"          naves: "</span> + nave_qtd, <span style="color: #000000;">10</span>, <span style="color: #000000;">20</span>);<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">026</span>        </span>g.dispose();<span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">027</span>        </span>bs.show();<span style="color: #000000;">
<strong><span style="color: #ff0000;"><span style="border-right: 1px solid #999999; background-color: #dddddd; margin-right: 5px; padding: 2px;">028</span>        </span></strong></span><strong><span style="color: #ff0000;">contador.sleep(50);</span></strong><span style="color: #000000;">
<span style="color: #666; background-color: #ddd; border-right: 1px #999 solid; margin-right: 5px; padding: 2px;">029</span>    </span>}</span></pre>
</div>
<p>Agora sim. O tempo de atualizar a tela (render) leva absurdos 50 ms (milisegundos). Absolutamente lento demais. A taxa de <strong>frames </strong>cai para 14 na minha máquina.</p>
<p><a href="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop03.png"><img class="aligncenter size-full wp-image-734" title="GameLoop03" src="http://abrindoojogo.com.br/wp-content/uploads/2009/09/gameloop03.png" alt="GameLoop03" width="400" height="100" /></a>Agora preste atenção na parte mais importante: <strong>a taxa de pulsos por segundo cai junto com os frames</strong>, embora apenas a rotina render() tenha recebido o tempo a mais. Isso ocorre porque como uma rotina é chamada depois da outra, em sequencia, update() tem que esperar render() executar para ser executada novamente.</p>
<p>Rodando o jogo você percebe que não é apenas a taxa de atualização da tela que fica lenta, <strong>mas o jogo todo</strong>. A nave agora leva uma eternidade para chegar até a extremidade da tela, porque temos apenas 14 pulsos de atualização da sua posição por segundo.</p>
<p>Está comprovado o problema. No próximo post a solução. Até amanhã.</p>
<p><a href="http://blog.abrindoojogo.com.br/como-obter-os-codigos-fonte-dos-artigos/">Baixe o código fonte deste artigo.</a></p>
]]></content:encoded>
			<wfw:commentRss>http://abrindoojogo.com.br/gameloop-com-taxa-constante-de-pulsos-parte-1-de-2/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

