Baixe o app para aproveitar ainda mais
Prévia do material em texto
GAME ENGINEGAME ENGINE TÓPICOS ESPECIAIS NOTÓPICOS ESPECIAIS NO UNITYUNITY Autor: Me. George Santiago Alves Revisor : I van Dimitry R . Zyr ianof f IN IC IAR introdução Introdução O Unity é uma plataforma de desenvolvimento de jogos que disponibiliza diversos recursos para as mais variadas categorias de desenvolvedores, de estúdios AAA a equipes independentes. Desse modo, os usuários podem usar as diversas funcionalidades da plataforma para criar conteúdo de alta qualidade em praticamente qualquer tipo de jogo eletrônico. Assim, nesta unidade de aprendizagem, serão abordados conceitos gerais sobre o funcionamento dos serviços para projetar jogos multijogadores, além disso, será possível ver na prática a relação entre jogabilidade e mecânica. Para isso, será desenvolvido um protótipo para testar os principais conceitos trabalhados ao longo da unidade. Por �m, abordaremos o conceito de di�culdade progressiva e a implementação de otimizações para re�nar a jogabilidade do protótipo desenvolvido. Os chamados multiplayer games (jogos multijogadores) são constituídos por um conjunto de fatores especí�cos que os diferenciam de outros modos de jogo. Segundo Rabin (2012), existem três fatores primordiais no desenvolvimento de multiplayer games , sendo eles: temporização de evento, I/O compartilhada e conectividade. Nas próximas subseções será descrito cada um desses fatores e como o Unity disponibiliza os seus serviços para que o usuário trabalhe com jogos multijogadores. Temporização de Evento Os jogos eletrônicos multijogadores trabalham com o conceito de sincronização de eventos, seja baseado em turnos ou em tempo real. Os jogos baseados em turnos são aqueles que restringem o movimento, turno ou ação a um único jogador, assim, todos os outros esperam pelo seu turno. De maneira geral, temos os jogos de tabuleiro ou cartas com uma jogabilidade projetada para jogadas baseada em turnos, como exemplo, temos: Magic: The Gathering Arena (Figura 4.1), Pokémon card game, Xadreze Yu-Gi-Oh Duel ServiçosServiços MultijogadoresMultijogadores Links. Mas, esse modo de jogo não se restringe apenas a jogos de tabuleiro ou cartas, outros gêneros como RPG (Role-Playing Games), RTS (Real-Time Strategy) e FPS (First-Person Shooter) podem exibir uma jogabilidade baseada em turnos, como exemplo, temos: League Of Angels III, Worms, Dragon awaken, Wartune, Ouroboros Project, XCOM 2, entre outros. Esse tipo de jogo tolera variações de períodos de latência e largura de banda variável. De maneira sucinta, latência é o tempo que um pacote de informações leva para ser enviado da sua origem a seu destino. Já a largura de banda é uma medida que determina a capacidade de transmissão, por exemplo, da conexão ou rede de internet. A velocidade de uma conexão é proporcional à largura de banda, ou seja, é a velocidade com que os dados trafegam através de uma rede. Jogos em tempo real são aqueles com eventos simultâneos entre os jogadores. Todas as ações durante o jogo são baseadas em interações simultâneas, por isso, é necessária uma arbitragem de eventos. São condições ou regras para determinar os eventos em jogo. Por exemplo, um determinado artefato é registrado apenas para o primeiro jogador que pegar o objeto no mundo do jogo, ou, aquele que cruzar a linha de chegada. A jogabilidade é marcada por ações que podem afetar diretamente a partida de outro jogador. Como exemplo, temos: World of Warcraft (Figura 4.2), Runescape, Ragnarök Online, Battle�eld, Call of duty, Counter-Strike, entre outros. Figura 4.1 - Magic: The Gathering Arena Fonte: Švelch (2019, p. 11). Esses jogos são projetados com condições rígidas de latência e largura de banda, uma vez que necessitam de reações rápidas. I/O compartilhada I/O é uma sigla em inglês para Input/Output (entrada/saída), que, quando aplicada ao compartilhamento de informações em jogos, permite que vários jogadores tenham interações em apenas um único dispositivo. Por exemplo, podemos atribuir diferentes teclas em um teclado para várias entradas de dados. Ou, a cada turno, um jogador assume temporariamente o controle total sobre a entrada de dados. O compartilhamento de tela é um conceito amplamente utilizado em jogos desde a era dos arcades. As partidas entre jogadores podem ser em tela cheia ou dividida. Em tela cheia, o jogador tem completa visibilidade do campo de jogo, por exemplo, em uma partida de xadrez, cada jogador terá o seu turno e controle total sobre o controle, nesse caso, um único dispositivo de entrada (teclado, mouse, joystick) é su�ciente. Mas, nada impede que outros dispositivos de entrada sejam adicionados à partida. Em jogos de tela dividida, temos o ponto de vista de cada jogador, assim, a tela é separada em visões personalizadas de cada jogador. São exemplos de jogos em tela dividida: Super Mario Kart (Figura 4.3), Goldeneye Figura 4.2 - Interface do jogo World of Warcraft Fonte: Campedelli (2009, p. 30). 007, Halo, Borderlands 2, Gears of War 4, Rocket League, Call of Duty 4: Modern Warfare, entre outros. Outro aspecto a ser levado em consideração a projetar jogos em tela dividida é a interface do jogo, que precisa conter o estado atual de cada jogador. Além disso, é necessário mesclar os efeitos sonoros, visto que existe apenas um sistema de áudio no jogo. Conectividade Quando se projeta um jogo eletrônico que tem modos multijogador on-line , é necessário levar em consideração a sua conectividade. Jogos em turnos trabalham com �exíveis requisitos de latência, pois a transferência de dados entre jogadores não precisa ser em tempo real. Para Rabin (2012), as formas aceitáveis de conectividade para jogos baseados em turnos são a transferência dos dados via FTP, e-mail ou salvando o arquivo em um disco removível e o transferindo para o outro jogador. Entretanto, é possível utilizar as categorias de conectividade presentes em jogos em tempo real. São elas: conexão direta, rede de circuito comutado e por pacotes. Na conexão direta, é realizada uma conexão entre os dispositivos, o que garante uma conexão com baixa latência, mas, a largura de banda depende do tipo de conexão entre os Figura 4.3 - Tela dividida no jogo Super Mario Kart Fonte: Sales (2013, p. 30). dispositivos. Por exemplo, temos normalmente as conexões via cabo serial, USB ( Universal Serial Bus ), Wireless, Infravermelho e Bluetooth. A rede de circuito comutado é uma rede que aloca um conjunto de recursos para transmitir a informação durante toda a transmissão. Esse tipo de conexão é utilizado em jogos com tráfego de dados constantes, como os jogos em tempo real. No entanto, segundo Rabin (2012, p. 582) a rede de circuito comutado "mantém um meio de baixa latência consistente, mas é curto em largura de banda e distribuição de jogadores (apenas dois jogadores; jogos por chamada de conferência)”. Além disso, essa rede resolve os problemas com a distribuição dos jogadores, mas, retira os benefícios da baixa latência de um circuito direto. Essencialmente, pode-se utilizar um fornecedor de saibamais Saiba mais Em ambientes on-line , é necessário compreender o funcionamento dos vários protocolos especializados que facilitam e protegem a comunicação entre os vários dispositivos conectados em rede. Uma das categorias mais utilizadas em jogos é o chamado ambiente ponto a ponto, que, pela falta de um servidor centralizado, precisa distribuir a segurança da rede entre os participantes. Para compreender o funcionamento de uma rede ponto a ponto, bem como as terminologias e conceitos utilizados no desenvolvimento de jogos on- line , acesse o link a seguir. ACESSAR https://www.cos.ufrj.br/uploadfile/1382061138.pdf acesso à internet (ISP) para que o circuito do dispositivo se conecte a uma conexão de internet, que por sua vez, transmite o pacote de dados a outro dispositivo. Na rede comutada por pacotes, os dados são transferidos através de redes diferentes. Cada pacote de dados é divididoem blocos de dados para que esses possam ser transmitidos de maneira e�ciente e mais rápida. Em ambientes on-line , é necessário compreender que as con�gurações de rede dependem de inúmeros fatores, que podem ser: tipos diferentes de hardware, protocolos e meios de transmissão. Independente desses requisitos, o Unity possui recursos para trabalhar com as demandas de projetos multijogadores. A seguir discutiremos esses recursos. Multijogador e Rede no Unity Até a versão 2018.3 o Unity fornecia recursos próprios especializados para trabalhar com ambientes virtuais. O UNet é um conjunto de recursos que inclui APIs e camadas de comunicação para jogos on-line , mas, que a partir da versão 2018.4 foi descontinuado. Os jogos que estão em processo de desenvolvimento avançado ou aqueles lançados comercialmente e que utilizam recursos ou serviços baseados no UNet terão correções e manutenção até o �nal de 2020. Atualmente, a engine em sua versão estável 2019.2.19 encontra-se em processo de transição para os novos recursos em desenvolvimento. Estima-se que a versão estável da engine para esses novos serviços acompanhe uma janela de lançamento com correções e atualizações entre 2020 e 2022. A curto prazo, a Unity incluirá uma nova estrutura de pilha de protocolos, com uma camada de transporte para envio e recebimento de informações baseado em UDP ( User Datagram Protocol ), além disso, será fornecida uma componente para que o usuário faça as con�gurações direto da interface de desenvolvimento. A engine passará a utilizar servidores de jogo dedicado (DGS) para jogos em tempo real. Por isso, a Unity Technologies �rmou um acordo para a aquisição da Multiplay Ltd., uma plataforma de hospedagem de jogos que utiliza uma tecnologia escalável para suporte de vários jogadores simultaneamente. Além disso, a Multiplay fornece ferramentas para que desenvolvedores, desde estúdios AAA ou independentes, possam criar experiências on-line de alto desempenho. Atualmente, a empresa fornece serviços para jogos populares com alta demanda de usuários, como PUBG e Titanfall 2. Desse modo, a Unity passa a integrar a tecnologia da Multiplay ao ecossistema de desenvolvimento da engine. Atualmente, as primeiras versões estáveis com integração entre as tecnologias serão disponibilizadas nas primeiras versões do Unity em 2020. saibamais Saiba mais O Unity é um mecanismo de jogo que está em constante atualização, buscando incluir novas ferramentas para facilitar o desenvolvimento de jogos. Entretanto, essas mudanças podem tornar obsoletos recursos amplamente utilizados pela comunidade. Entre eles, temos o UNet, um conjunto de recursos e serviços criados pela Unity em meados de 2015, mas, que atualmente, em sua versão 2019.2.19, encontra-se em processo de transição para uma nova estrutura voltada ao desenvolvimento de jogos multijogadores. Para acompanhar esses novos recursos, acesse o link a seguir. ACESSAR Além do Multiplay, a Unity �rmou uma parceria com o Google Cloud, onde ambos fornecerão um conjunto de ferramentas chamado Open Match que https://unity3d.com/partners/google/connectedgames?_ga=2.244121733.1626570215.1579990182-403567331.157418010 inclui bibliotecas com protocolos cliente-servidor para implementação automatizada. O Open Match é um projeto aberto que permite contribuições da comunidade. Para isso, a empresa disponibilizou um repositório GitHub. O projeto visa fornecer um serviço totalmente gerenciado, permitindo que os desenvolvedores possam ajustar o equilíbrio entre a latência, tempo de espera e habilidade sem precisar implementar uma lógica personalizada. Além disso, em versões futuras, o serviço de gerenciamento direto da interface do Unity fornecerá opções para acompanhar todo o projeto em rede, como incluir apenas os pacotes para o servidor baseado nas necessidades do jogo. Atualmente, é possível testar a primeira versão do recurso, um servidor alocado que aguarda a contagem necessária de jogadores para conectar os clientes ao servidor. O usuário poderá gerenciar via interface no Unity a contagem de jogadores simultâneos em uma partida. praticar Vamos Praticar Leia o excerto a seguir. “Os jogos multiplayer envolvem estudos e recursos ligados com percepção, hardware, software, interface do usuário, fatores humanos e aplicações. Para a elaboração de um jogo multiplayer é necessário ter algum domínio sobre: dispositivos, convencionais ou não, de entrada e saída, computadores ou processadores de alto desempenho, processamento grá�co, sistemas paralelos e multiusuário, modelagem geométrica, simulação em tempo real, interação, detecção de colisão, avaliação, impacto social, projeto de interfaces, e aplicações simples e distribuídas” (KUBO, 2006, p. 13). De acordo com o texto e os conhecimentos acerca do desenvolvimento de jogos multijogadores, analise as a�rmativas a seguir. I. Latência é o tempo que um pacote de informações leva para ser enviado da sua origem a seu destino. II. A largura de banda é uma medida que determina a capacidade de transmissão. III. A velocidade de uma conexão é proporcional à largura de banda, ou seja, é a velocidade com que os dados trafegam através de uma rede. IV. Jogos em tempo real são aqueles que restringem o movimento, turno ou ação a um único jogador. Está correto o que se a�rma em: a) I, II e III, apenas. b) I, II e IV, apenas. c) II, III e IV, apenas. d) I e II, apenas. e) II e IV, apenas. A jogabilidade é um componente que descreve e de�ne o gênero de um jogo, por exemplo, em Super Mario Bros (Figura 4.4) de 1985, o personagem principal, Mario, precisa percorrer um ambiente contendo passagens secretas, obstáculos, inimigos, moedas e ampli�cadores. Observe que a jogabilidade é independente do ambiente onde os eventos ocorrem. É um conceito que está diretamente ligado ao modo em que o jogador irá "jogar" o jogo. É constituído por características que in�uenciam a mecânica do game. Por isso, caso a jogabilidade seja alterada, a forma com que o jogador interage também mudará, assim, o jogo perde, inicialmente, o seu propósito primário. A mecânica, por sua vez, é um conjunto de regras que de�ne a interação entre o usuário e o ambiente do jogo. Se relacionarmos jogabilidade com mecânica, temos que a mecânica é um sistema de baixo nível, onde uma única interação dentro do jogo pode ser considerada uma mecânica. Por exemplo, no jogo Super Mario Bros, caso o usuário aperte a tecla A, Mario pula. Essa interação pode ser considerada uma mecânica, assim como as outras interações durante o jogo. Já a jogabilidade é um conceito abstrato, Mecânica de Jogo IMecânica de Jogo I que pode ser considerado um sistema de alto nível, onde a experiência do jogador é o resultado entre a mecânica e as suas próprias ações. Em outras palavras, a jogabilidade são todas as interações entre a mecânica(s) do jogo. Assim, as regras, os objetivos, os desa�os e a narrativa são elementos em que o jogador terá interação constante durante o jogo, que pode ser de�nida como jogabilidade. A mecânica, basicamente, é a maneira com a qual será fornecida a jogabilidade para que o jogador tenha interações ao longo do jogo. Para ilustrar ainda mais esses conceitos, precisamos recorrer ao jogo Tetris de 1986. Figura 4.4 - Super Mario Bros Fonte: Santos (2012, p. 43). Figura 4.5 - Tetris Fonte: Teixeira (2015, p. 44). O jogo Tetris é um dos mais populares e in�uentes do mundo, suas regras são baseadas em puzzles . Pelas suas regras simples, podemos observar nitidamente o conceito de mecânica e jogabilidade. Bem, o jogo possui basicamente quatro mecânicas básicas. A primeira é o sistema de rotação das peças que aparecem em tela, podendo surgir em qualquer ângulo de rotação. A segunda é a randomização das peças, a ordem e sequência dos blocos é totalmente aleatória. O que faz o jogo ter regras simples, mas, ainda, ser desa�ador. O terceiro é o sistema de pontuação, que aumenta conforme aspeças são eliminadas do jogo. Por último, temos a mobilidade, que é a capacidade do usuário em manipular as peças. O usuário pode rotacioná-las para empilhar de uma maneira que forme uma linha horizontal, assim, elimina a camada inferior de peças. É possível observar que o jogo Tetris possui mais de uma mecânica, portanto, a jogabilidade é um conjunto de mecânicas que de�ne a forma de interação entre o jogador e o jogo. Essas mecânicas determinam a complexidade do jogo. Por exemplo, em Tetris, o jogador terá poucas interações durante a partida, portanto, o jogo tem uma jogabilidade simples. Entretanto, segundo Rabin (2012), existe divergência entre vários autores sobre os conceitos de jogabilidade e mecânica. Por isso, por via de regra, não existe, atualmente, uma de�nição correta quanto aos conceitos previamente estabelecidos. À vista disso, iremos projetar um protótipo no Unity para testarmos a mecânica e a jogabilidade em um ambiente especí�co. Nos tópicos subsequentes, iremos dar continuidade ao protótipo, mas, criando uma di�culdade progressiva e fazendo os ajustes necessários para re�nar o jogo. Vamos lá? Inicialmente precisamos de�nir a nossa mecânica e jogabilidade. O jogo consiste em uma arena contendo múltiplos elementos que o usuário precisa coletar. Para isso, o jogador poderá mover o personagem no eixo horizontal e vertical. Mas, existem obstáculos para impedir que o mesmo consiga coletar todos os artefatos em cena. Além disso, a câmera principal precisa estar em uma inclinação sobre a arena. Durante o desenvolvimento do protótipo, tente imaginar novas mecânicas para alterar a jogabilidade. No �nal da unidade, faremos uma breve discussão acerca da in�uência de novas mecânicas para o protótipo. O primeiro passo será criar um novo projeto 3D no Unity, de�na o nome como: 3D catch. Feito isso, acesse a guia Project > Scenes. Dentro da pasta, crie uma nova cena chamada ‘Level1’, após isso, dê um duplo clique na cena criada. Criando o Nível 1 O nosso nível é composto por uma estrutura formada em cubos, seu layout será semelhante a uma arena quadrada. Para isso, precisamos criar: 4 paredes. 1 plano. Para criarmos essa estrutura, basta adicionar na cena um plano e um cubo. O cubo será uma parede, que chamaremos de wall, para de�nir o tamanho basta rede�nir os valores do componente Transform. É uma boa prática criar um pasta na cena para organizar todos os elementos. Por exemplo, criar uma pasta chamada ‘Walls’ para organizar os objetos paredes (wall). A escala do plano nas direções X, Y e Z será de 1/10 da escala usada para dimensionar as paredes. Após escolher o tamanho do cubo, basta duplicá-lo para redimensionar e posicionar em cena as outras paredes. Observe a Figura 4.6 para compreender a estrutura do nível 1. Figura 4.6 - Estrutura do nível 1 Fonte: Elaborada pelo autor. Para a construção dessa cena, foi usada a escala padrão de X, Y e Z nos valores 2, 2 e 2 para o nosso piso (plano). Assim, cada parede precisa seguir a escala 1/10 dos valores previamente estabelecidos para o plano. Mas, é possível escolher outros valores e criar seu próprio estágio. Criando o Player O passo seguinte será criar o player, que, inicialmente, será representado por uma esfera. Assim, adicione na cena um 3D Object sphere. Selecione a esfera e renomeie-a como Player. Para a sua posição inicial, de�nimos 1, 0.5 e 1 para XYZ. O valor de 0.5 em Y garante que o nosso Player estará acima do solo. Feito isso, precisamos adicionar os componentes para sujeitar o Player às leis da física do nosso jogo. Assim, adicione um corpo rígido (Rigidbody) em nosso Player. Inicialmente, deixaremos as con�gurações-padrão. Outro componente adicionado automaticamente pela engine é o Collider, ou colisor, responsável pela área física ocupada pelo Player. Se desligarmos o colisor, o comportamento do nosso personagem será similar a um fantasma. Veja a Figura 4.7 para compreender a estrutura e posição inicial do nosso Player. Você pode estar pensando que a nossa cena está bem genérica, sem qualquer de�nição de forma, cor ou tamanho. Assim, temos uma cena composta apenas por objetos embutidos da engine. Entretanto, estamos construindo um protótipo para validar um conceito, diante disso, a estética do jogo está sendo negligenciada. Mas, é possível criar e adicionar um material em nossos objetos em cena. Além disso, é possível importar elementos da AssetStore. Movimento Básico do Player Após criar o layout e o personagem, precisamos fazer o Player se deslocar pelo nível. Antes de criar o script, precisamos criar uma nova pasta na guia Project chamada ‘Scripts’, assim, todos os recursos do nosso jogo serão organizados. Feito isso, em nossa pasta ‘Scripts’, crie um novo script chamado ‘PlayerController’. O próximo passo é enviar o Script criado ao nosso Player e abri-lo no ambiente de programação do Visual Studio (basta dar um duplo clique no nome do script). Agora, observe o nosso algoritmo de movimento a seguir. Figura 4.7 - Player Fonte: Elaborada pelo autor. using System.Collections; using System.Collections.Generic; using UnityEngine; public class PlayerController : MonoBehaviour { public float speed; void Update() { flo at moveHorizontal = Input.GetAxis("Horizontal"); float moveVertical = Input.GetAxis("Vertical"); Vector3 movement = new Vector3(moveHorizontal, 0.0f, moveVertical); GetComponent<Rigidbody>().AddForce(movement * speed * Time.deltaTime); } } Primeiramente, declaramos a nossa variável pública Speed (velocidade), o Public nos permite ajustar a velocidade do Player direto do Inspector. Em Update, declaramos duas variáveis locais do tipo �oat: moveHorizontal e moveVertical. Essas variáveis assumem valores temporariamente dependendo dos comandos de entrada do usuário. Em seguida, temos que adicionar uma força para mover o nosso Player. Mas antes é necessário criar um novo Vetor com três dimensões que será responsável por mover o nosso personagem no espaço tridimensional. O vetor 3D assumirá os valores de entrada do usuário para os movimentos horizontal ou vertical. Observe que é atribuído valor zero na direção cima e baixo, isto porque o Player só poderá se mover em apenas duas dimensões. Por �m, adicionamos uma força usando a propriedade AddForce do componente Rigidbody. Para calcular a força aplicada ao nosso personagem, precisamos usar três parâmetros: Time.DeltaTime, speed e movement. O Time.DeltaTime contém o tempo em segundos desde o último frame. Multiplicar o vetor de movimentação com essa variável faz com que convertamos a movimentação de um valor baseado na renderização de quadros para um valor em segundos. O speed será ajustado posteriormente e o movement é o valor de entrada do usuário. Salve o arquivo e retorne à interface do Unity. Agora, execute a cena e use as teclas WASD ou setas para movimentar o personagem. O que acontece? Nada! Sabe por quê? Simples, não de�nimos o valor para a variável speed. Selecione o Player, no Inspector, localize a variável speed e atribua o valor 1000. Feito isso, execute novamente o projeto. O nosso personagem pode se mover pelo ambiente. Adicionando Iluminação na Cena A etapa seguinte é adicionar um componente responsável pela iluminação do nosso jogo. Para seguir o padrão de organização estabelecido anteriormente, precisamos criar uma pasta para esses componentes. Basta criar um objeto vazio e renomear para 'Lights'. Observe que já existe em cena um objeto chamado Directional Light, a engine adiciona o componente automaticamente em cada cena criada. Selecione o objeto Directional Light e nomeie-o para Main Light, faça-o uma subclasse do objeto Lights. Agora, selecione o Main Light e altere os valores de rotação para 30, 60 e 0 (X, Y e Z). Esses valores vão inclinar a luz sobre a arena. Feito isso, nas propriedades do componente, de�na o tipo de sombra para Soft Shadows (sombras suaves dos objetos) e a resolução para as mesmas em Very High Resolution.Em seguida, duplique o objeto ‘Main Light’ e renomeie-o como ‘Fill Light’. Com ‘Fill light’ selecionado, vá ao Inspector e altere a cor para um tom azulado (valor hexadecimal #003FFF). Agora, diminua a intensidade da cor para 0.5 e, em tipo de sombra de�na como 'No Shadows'. Por �m, altere o ângulo de rotação do ‘Fill Light’ para -30, -60 e 0 (X, Y e Z). Os parâmetros atribuídos do ‘Fill Light’ o de�nem como uma luz de preenchimento, visto que suavizam as sombras da luz principal. Entretanto, para que essa fonte secundária não inter�ra diretamente na luz principal, é necessário de�nir um valor baixo para o parâmetro de intensidade da luz. Para a nossa cena, atribuímos o valor da intensidade de iluminação em 0.5, assim, a luz de preenchimento interfere na luz principal. Observe a Figura 4.8 para visualizar o efeito de iluminação em nossa arena. Ajustando o Ângulo da Câmera Voltando ao nosso projeto, podemos observar que a visão da nossa câmera não condiz com as regras estabelecidas anteriormente, a câmera principal precisa ser inclinada sobre a arena. Assim, selecione o objeto 'Main Camera', em inspector, e ajuste os valores: Position: 0, 10 e -10 para X, Y e Z. Rotation: 45, 0 e 0 para X, Y e Z. Esses valores garantem que a câmera principal esteja em uma inclinação sobre a arena. Para de�nir a melhor posição de visualização, basta arrastar a câmera pela cena. Figura 4.8 - Iluminação Fonte: Elaborada pelo autor. Fazendo a Câmera Seguir o Player Se executarmos o projeto, podemos observar que a câmera principal permanece estática. Poderíamos deixar assim que já teríamos um protótipo para testar as regras básicas do jogo. Entretanto, iremos implementar um método no qual a câmera seguirá o jogador enquanto o mesmo se movimenta pela arena. Para isso, crie um novo script chamado 'CameraMovement', após isso, adicione o script à câmera principal do jogo. Agora, clique duas vezes no nome do script para abri-lo no Visual Studio. Observe o algoritmo a seguir. using System.Collections; using System.Collections.Generic; using UnityEngine; public class CameraMovem : MonoBehaviour { public GameObject player; private Vector3 offset; void Start() { offset = transform.position; } void Update() { transform.position = player.transform.position + offset; } } Esse algoritmo acessa as informações de outro objeto no jogo, em particular, o Player. Assim, criamos uma variável pública para anexarmos o objeto Player. A próxima variável é um Vector3 que chamamos de o�set, que, será o valor da posição da câmera no espaço tridimensional. Na função Start (), atribuímos à variável o�set a posição do objeto anexado a esse script, a câmera. Além disso, atribuímos um deslocamento (o�set) adicional a esse movimento. Salve o algoritmo e retorne à engine. Na função Update (), de�nimos a posição da câmera com base na posição do personagem. Acesse a câmera principal, no Inspector > 'CameraMovement', arraste o objeto 'Player' para a variável de mesmo nome (Figura 4.9). Figura 4.9 - Settings Player Fonte: Elaborada pelo autor. Feito isso, clique no botão play para executar o projeto. Movimente o Player e observe o movimento da câmera seguindo o seu movimento. Não esqueça de salvar o projeto. saibamais Saiba mais O conceito de mecânica e jogabilidade é discutido desde a década de 1980, entretanto, não existe um consenso de�nitivo entre os autores. Mesmo existindo características básicas que as diferencia, é possível a�rmar que o limite entre a jogabilidade e a mecânica é mínimo. São conceitos que se relacionam. Por isso, é necessário compreender a visão dos autores e desenvolvedores sobre ambos os elementos. Assim, para aprofundar o conhecimento, acesse o link a seguir. ACESSAR Nesta primeira parte do protótipo, implementamos a mecânica básica do jogo. Por enquanto, não existe nenhum elemento que altere o comportamento do nosso ‘Player’. Entretanto, no tópico seguinte, iremos discutir como a di�culdade é um elemento que pode in�uenciar na jogabilidade de um jogo. praticar Vamos Praticar https://www.sbgames.org/sbgames2017/papers/ArtesDesignFull/175536.pdf Leia o excerto a seguir. "[…] Essa variável serve para garantir que o objeto em questão seja rotacionado na mesma velocidade, independente da capacidade de processamento do computador no qual o código será executado" (PASSOS et al., 2009, p. 24). O Unity utiliza um atributo de uma classe especí�ca para tratar, por exemplo, da movimentação do personagem. Assim, assinale a alternativa que corresponde à variável conceituada anteriormente. a) Time.deltaTime. b) Time.timeScale. c) Time.�xedTime. d) Time.realtimeSinceStartup. e) Time.captureDeltaTime. A próxima etapa no desenvolvimento do nosso protótipo é �nalizar a sua construção e criar níveis com di�culdade progressiva. A di�culdade em um jogo é diretamente proporcional ao seu balanceamento, que pode ser conceituado como um conjunto de regras que equilibra a di�culdade, diversão e recompensa em um jogo eletrônico. Entretanto, esse conceito não é tão simples, pois, nem sempre é possível quanti�car matematicamente o equilíbrio em um jogo. A jogabilidade de�ne as interações entre o jogo e o jogador, logo, a jogabilidade é um componente que depende das escolhas do jogador. Assim, as escolhas precisam ter um equilíbrio, caso contrário, o Player pode descobrir uma estratégia dominante e limitar suas ações em decorrência desse desequilíbrio. Por isso, os jogos on-line estão em constante atualização, alterando o equilíbrio do jogo para gerar novas formas de jogo. Antes de de�nir a progressão em nosso protótipo, precisamos �nalizar sua construção, que será abordada nos próximos subtópicos. Criando artefatos para a arena Mecânica de Jogo IIMecânica de Jogo II Nesta etapa, criaremos os itens que o personagem coletará durante a partida. Para isso, precisamos adicionar na cena um objeto. Antes de adicionar os elementos em cena, precisamos criar uma pasta na guia Hierarchy. Crie a pasta e renomeie-a para ‘Itens’. Feito isso, adicione um 3D Object cubo à cena. Faça-o subclasse do objeto 'Itens'. Selecione o 'item' criado, no Inspector > Tag > Add Tag > crie uma nova Tag chamada 'Item'. Feito isso, volte à interface do objeto 'Item' e atribua a Tag 'Item' para o mesmo. Em seguida, com o objeto 'item' selecionado, adicione um Rigidbody e duplique o objeto três vezes. Observe a Figura 4.10 para ver a distribuição dos itens em cena. Você pode alterar a posição dos itens, basta arrastar os mesmos para qualquer lugar da arena. Não esqueça de rede�nir o Transform dos itens. Os valores do parâmetro Scale foi de 1, 1 e 1 para X, Y e Z. 3.2 Mecânica para Coletar os Itens e Exibir a Pontuação na Interface Para essa etapa, precisamos que o Player colete e saiba a sua pontuação atual. Para isso, precisamos modi�car o algoritmo do Player. Agora, abra o script 'PlayerController'. Observe as implementações feitas no algoritmo do Player. Figura 4.10 - Itens em cena Fonte: Elaborada pelo autor. using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; public class PlayerController : MonoBehaviour { public float speed; private int count; public Text countText; private void Start() { count = 0; CountText(); } void Update() { float moveHorizontal = Input.GetAxis("Horizontal"); float moveVertical = Input.GetAxis("Vertical"); Vector3 movement = new Vector3(moveHorizontal, 0.0f, moveVertical); GetComponent<Rigidbody>().AddForce(movement * speed * Time.deltaTime); } void CountText() { countText.text = "Score: " + count.ToString(); } void OnTriggerEnter(Collider other) { if (other.gameObject.tag == "Item") { other.gameObject.SetActive(false); count++; CountText(); } } } O primeiro passo é adicionar a biblioteca using UnityEngine.UI, responsável pelos elementos da interface do usuário. Após isso, declaramos duas variáveis: count e countText. O count é umavariável que armazena a pontuação do Player, enquanto o countText é responsável por exibir a pontuação na interface do usuário. Anteriormente não tínhamos o método Start(). Para as novas implementações será necessário adicioná-lo, uma vez que precisamos inicializar a variável count e a função CountText(). A função OnTriggerEnter é responsável pelo comportamento entre a colisão do Player e os Itens. Ou seja, a cada colisão entre o Player e um objeto que tenha a Tag 'Item' atribuída, o objeto será automaticamente removido da cena. Após isso, é aumentada a contagem da pontuação em +1. Por �m, precisamos criar uma função chamada CountText(), que monitora e atualiza a pontuação na interface do usuário. Para isso, a função acessa o componente text em um objeto anexado à variável e atribui o valor atual da pontuação. Salve o script e retorne ao Unity. Selecione os 'Itens' na cena e marque a opção isTrigger, que, quando habilitada, faz com que o objeto não sofra uma colisão tangível. Em vez disso, o gatilho envia uma mensagem para o sistema de eventos quando um corpo rígido atravessa outro collider. Isso possibilita saber quando o objeto atravessou, assim, eliminando o item e aumentando a pontuação. Agora, precisamos habilitar a opção Is Kinematic no Rigidbody dos itens. Caso esteja marcada, as forças e colisões não afetarão o objeto. Isso evita que os objetos em cena caiam pelo piso. Em seguida, precisamos criar um Text na cena. Automaticamente, a engine cria um Canvas. Selecione o objeto Text criado e de�na sua posição para o canto superior esquerdo. Os valores para as posições de X, Y e Z são, respectivamente, -190, 100 e 0. Por último, precisamos arrastar o objeto Text para a caixa de mesmo nome no script do Player (Figura 4.11). Salve o projeto e clique em play. Movimente o personagem na arena para coletar os itens. Observe que a cada colisão o item desaparece e a pontuação aumenta em +1. Obstáculos Por enquanto, o jogador pode coletar os itens na arena, entretanto, não existe nenhuma di�culdade em realizar essa ação. Desse modo, criaremos uma espécie de alçapão com uma mola e, caso o Player tenha uma colisão com o mesmo, este o lançará no ar, tendo a possibilidade de ultrapassar os limites da arena. Figura 4.11 - Itens em cena Fonte: Elaborada pelo autor. Como de costume, precisamos criar um objeto vazio e chamá-lo de ‘Traps’, responsável por organizar as armadilhas da arena. Feito isso, adicione em cena um 3D Object Quad, chame-o de Trap. Lembre de fazer do objeto Trap uma subclasse do objeto ‘Traps’. Em seguida, selecione o objeto Trap, crie uma nova tag chamada ‘hazard’ e atribua ao objeto selecionado. Feito isso, precisamos alterar a posição do objeto em cena. Selecione-o e em Inspector altere o valor de X no Rotation para 90 (mudando o ângulo de visualização do objeto). Para garantir que a armadilha estará acima do solo, em Position, no parâmetro Y, de�na o valor para 0.1. Observe na cena que o objeto não está visível. Precisamos alterar a sua cor, selecione-o, em Inspector, localize o componente Mesh Render e em Element 0 altere o material para Sprite-Default. Agora, adicione um Box collider no objeto ‘Trap’ e habilite a opção isTrigger. Observe como �cou o objeto na cena (Figura 4.12). O próximo passo é modi�car a função OnTriggerEnter () do Player para implementar uma nova interação entre o jogador e a armadilha. Para isso, abra o Script do Player. Observe o algoritmo OnTriggerEnter () com as modi�cações. Figura 4.12 - Trap Fonte: Elaborada pelo autor. void OnTriggerEnter(Collider other) { if (other.gameObject.tag == "Item") { other.gameObject.SetActive(false); count = count + 1; CountText(); } if (other.gameObject.tag == "hazard") { other.gameObject.SetActive(false); Vector3 jump = new Vector3(0.0f, 30, 0.0f); GetComponent<Rigidbody>().AddForce(jump * speed * Time.deltaTime); } } A modi�cação realizada no script nos diz que, caso o Player sofra uma colisão contra um objeto que tenha a tag ‘hazard’, será lançado no ar. Após isso, a armadilha será desabilitada. Salve o script e retorne ao Unity, clique em play. Observe o comportamento e interação entre o Player e os objetos em cena. Níveis Diante do exposto, quais parâmetros podem ser modi�cados para aumentar ou diminuir a complexidade do jogo? Ou melhor, como criamos novos níveis com uma di�culdade crescente? O primeiro ponto é observar os elementos implementados em nosso Level1, que é composto por: um personagem, três itens coletáveis e uma armadilha. O primeiro nível de um jogo precisa demonstrar as mecânicas básicas e a jogabilidade para o usuário. Assim, normalmente, o primeiro nível (ou os primeiros minutos de um jogo) é constituído por um tutorial, guiando o jogador pelo ambiente do jogo. E para o nosso protótipo? O primeiro nível precisa demonstrar ao jogador que o mesmo precisa mover o personagem na arena para coletar os itens e passar assim para o próximo nível. Por isso, é recomendado não ter obstáculos, armadilhas ou interações com elementos muito agressivos no início do jogo. Para ilustrar as possibilidades de progressão, faremos um pequeno roteiro para os 5 primeiros níveis do protótipo desenvolvido. Level1: demonstrar as mecânicas básicas para o jogador. O nível é constituído por 3 elementos coletáveis. O usuário precisa coletar todos os itens para prosseguir ao próximo nível. Level2: o número de elementos coletáveis permanece inalterado, mas, é acrescentada uma armadilha visível em cena. A primeira interação entre o jogador e a armadilha precisa ser inevitável, demonstrando, assim, o seu funcionamento para o mesmo. Level3: o nível é constituído por 4 elementos coletáveis, mas, um deles, na cor vermelha, é uma maldição. A maldição deixa o personagem mais lento, novamente, a interação com esse elemento é inevitável. Level4: todos os elementos do level3 são utilizados nesse nível, entretanto, é acrescentado um cronômetro decrescente. O jogador precisa coletar todos os itens antes do tempo esgotar. Por isso, a maldição foi demonstrada no nível anterior. Level5: �nalmente o jogo começa, é acrescentado vários elementos em cena para o jogador coletar em um tempo especí�co. Além disso, o mesmo precisa enfrentar diversos obstáculos em cena. Observe que esse pequeno roteiro de�ne uma progressão bem básica e intuitiva que pode ser implementada em nosso projeto. Entretanto, é possível acrescentar diversos elementos para alterar o comportamento do jogo. Por exemplo, podemos colocar armadilhas invisíveis, armadilhas na parede, ter níveis sem paredes, incontáveis tipos de maldição no jogo (diminuir pontuação, diminuir tempo total, aumentar o número de armadilhas, acelerar o tempo, entre outros), criar um sistema que elimina partes do piso conforme o tempo, criar níveis com pontes ou buracos, entre outros. Como exercício, busque na loja de Assets do Unity ativos para tornar o protótipo mais esteticamente agradável. Além disso, crie um sistema para transição de cenas e implemente os 5 primeiros níveis conforme apresentado anteriormente. reflita Re�ita Elementos aleatórios em jogos são, naturalmente, indispensáveis, visto que a sua existência torna o jogo mais natural, aumentando assim a sua imprevisibilidade. Entretanto, em jogos multijogador, é necessário que exista um balanceamento adequado para que o fator sorte não substitua, totalmente, a parte da habilidade do jogador. Levando em consideração os assuntos abordados ao longo da unidade sobre o Unity, re�ita sobre o papel do fator aleatoriedade na construção de desa�os em jogos multiplayer. Neste último tópico, faremos algumas alterações em nosso protótipo para garantir um melhor desempenho. O primeiro ponto é sobre a movimentação do personagem. Primeiramente, substituímos o método Update pelo FixedUpdate. A diferença é que ele não depende do número de frames por segundos, usando um intervalo de tempo �xo. Observe as alterações no algoritmode movimento do Player. void FixedUpdate() { float moveHorizontal = Input.GetAxis("Horizontal"); float moveVertical = Input.GetAxis("Vertical"); Vector3 movement = new Vector3(moveHorizontal, 0.0f, moveVertical); GetComponent<Rigidbody>().AddForce(movement * speed * Time.deltaTime); } Re�namentosRe�namentos A próxima alteração é no script CameraMovement. Precisamos substituir Update por LateUpdate. O LateUpdate é atualizado a cada Frame por segundo, após o Update ser chamado. A ordem de execução das funções Update são FixedUpdate > Update > LateUpdate. Lembra-se do algoritmo usado na movimentação do Player? Usamos o FixedUpdate, assim, garantimos que a câmera será movimentada, apenas, quando o Player se mover. Na função LateUpdate (), de�nimos a posição da câmera com base na posição do personagem. Com as alterações, veja como �cou o nosso método. void LateUpdate() { transform.position = player.transform.position + offset; } Além dos pontos observados, precisamos compreender que existe no Unity, basicamente, dois tipos de collider: estáticos e dinâmicos. O collider estático é usado em objetos que não têm movimentação ativa em uma cena, diferente do collider dinâmico, que é atribuído a objetos que se movem. Quando usamos um collider do tipo estático, a engine armazena-os em cache para que a aplicação obtenha uma otimização de desempenho. Entretanto, se atribuirmos um collider estático para um objeto que tem sua posição alterada de forma dinâmica, o Unity fará o armazenamento constante no cache gerando, assim, um problema de desempenho. indicações Material Complementar FILME Videogames: O Filme Ano: 2014 Comentário: Videogames é um documentário lançado em 15 de outubro de 2014, relacionando a in�uência dos jogos na sociedade. Mas, vai além da in�uência, o documentário percorre os principais fatos históricos acerca dos jogos eletrônicos. Cada capítulo contém informações profundas na visão dos maiores desenvolvedores da história da indústria dos videogames. Para conhecer mais sobre o �lme, acesse o trailer a seguir. TRA ILER LIVRO A Arte de Game Design Jesse Schell Editora: Elsevier ISBN: 10: 8535241981 ISBN-13: 978-8535241983 Comentário: A Arte de Game Design em suas mais de 500 páginas traz inúmeros conceitos aprofundados sobre o desenvolvimento de jogos eletrônicos. A obra é uma das maiores referências na área de game design. O autor fornece os fundamentos da produção de jogos usando conceitos básicos da psicologia. Assim, consegue demonstrar que um bom desenvolvedor precisa ver o seu jogo de várias perspectivas. conclusão Conclusão O desenvolvimento de jogos eletrônicos está intimamente relacionado a inúmeras áreas do conhecimento, incluindo a computação grá�ca, inteligência arti�cial, rede de computadores, interação homem-máquina, modelagem, entre outros. Não apenas em áreas da ciência da computação, a produção de jogos requer conhecimentos de disciplinas da psicologia, das ciências sociais e humanas. Todas essas áreas e conceitos precisam se relacionar mutuamente em um jogo para criar experiências únicas aos seus usuários. Assim, podemos observar que a área de jogos é dinâmica. Logo, é necessário que os desenvolvedores se mantenham em atualização constante. A Unity é um mecanismo de jogo que está em constante evolução, implementando inúmeros recursos a cada atualização. Em vista disso, faz-se mais do que necessário buscar informações e aperfeiçoamento nas novas tecnologias implementadas na plataforma. referências Referências Bibliográ�cas CAMPEDELLI, G. Bem-vindos a Azeroth : aspectos da economia lúdica nos mundos fantásticos. 2009. Dissertação (Mestrado em Estudo dos Meios e da Produção Mediática) - Escola de Comunicações e Artes, Universidade de São Paulo, São Paulo, 2009. CORDEIRO, M. A. da S.; PEREIRA, M. F. Mecânicas de Jogo: uma exploração da experiência interativa na série Metal Gear Solid. In: SBGAMES, XVI, 2017, Curitiba. Proceedings [...] . Curitiba: SBC, 2017. Disponível em: https://www.sbgames.org/sbgames2017/papers/ArtesDesignFull/175536.pdf . Acesso em: 15 fev. 2020. KUBO, M. M. FMMG : um framework para jogos multiplayer móveis. Pós- Doutorado em Engenharia da Computação e Sistemas Digitais, Escola Politécnica (EP), Universidade de São Paulo, São Paulo, 2006. PACHECO, B. de M. Protocolos seguros para jogos em redes peer-to-peer . 2013. Dissertação (Mestrado em Engenharia de Sistemas e Computação) - COPPE, Universidade Federal do Rio de Janeiro, Rio de Janeiro, 2013. Disponível em: https://www.cos.ufrj.br/upload�le/1382061138.pdf . Acesso em: 15 fev. 2020. PASSOS, E. B. et al. Tutorial: desenvolvimento de jogos com Unity 3D. In: BRAZILIAN SYMPOSIUM ON GAMES AND DIGITAL ENTERTAINMENT, 2009, Rio de Janeiro. Anais [...]. Rio de Janeiro: MediaLab UFF, 2009. p. 1-30. RABIN, S. Introdução ao Desenvolvimento de Games Vol. II . São Paulo: Cengage Learning, 2012. SALES, M. O. Jogos textuais interativos na escola : efeitos dos Role-Playing Games na sala de aula. 2013. 132 f. Dissertação (Mestrado em Psicologia Cognitiva) — Programa de Pós-Graduação em Psicologia Cognitiva, Universidade Federal de Pernambuco, Recife, 2013. SANTOS, L. V. V. dos. A nacionalidade em jogo : representações do Brasil em jogos digitais. 2012. Dissertação (Mestrado em Cultura e Sociedade) – Programa Multidisciplinar de Pós-Graduação em Cultura e Sociedade, Universidade Federal da Bahia, Salvador, 2012. https://www.sbgames.org/sbgames2017/papers/ArtesDesignFull/175536.pdf https://www.cos.ufrj.br/uploadfile/1382061138.pdf SVELCH, J. Mediatization of a card game: Magic. Media, Culture & Society , [s.l.], p. 20, 16 out. 2019. Disponível em: http://dx.doi.org/10.1177/0163443719876536 . Acesso em: 15 fev. 2020. TEIXEIRA, R. A. S. Jogos Digitais como Artifício Pedagógico na Escola Atual . 2015. 115f. Dissertação (Mestrado em Ciência da Computação) – Universidade Federal de Minas Gerais, Belo Horizonte, 2015. UNITY. Connected games . [2020]. Disponível em: https://unity3d.com/partners/google/connectedgames? _ga=2.244121733.1626570215.1579990182-403567331.157418010 . Acesso em: 15 fev. 2020. VELLOSO, L. Narrativas do jogo Tetris em um recorte tipográ�co: De sua origem ao Game Boy. In: INTERACTION SOUTH AMERICA, 2011, Belo Horizonte. Anais [...] . Belo Horizonte: [S.n.], 2011. http://dx.doi.org/10.1177/0163443719876536 https://unity3d.com/partners/google/connectedgames?_ga=2.244121733.1626570215.1579990182-403567331.157418010
Compartilhar