Escondendo o Lag – O que os olhos não vêem, o coração não sente

Posted by | 17/08/2013 | Programming | 12 Comments

Bom pessoal, eu sou o Vinícius Pachá, mais um dos programadores do Projeto Tilt. E estou aqui para falar um pouco do Networking das nossas armas, em especial a nossa Sniper!

Em primeiro lugar, O que é uma Sniper no nosso jogo? Bom, em termos técnicos eu diria que é uma arma de longo alcance onde o dano é instantâneo, ou seja, não existe nenhum projetil correndo pelo cenário, não existe nenhuma trajetória, nós apenas traçamos uma reta a partir do personagem na direção que ele está mirando até bater em alguma coisa.

Ok, Let’s Do This!

Definido o que é a Sniper do Tilt… Vamos programar! (Parece bem fácil né?)
1° Passo: Quando eu atirar eu mando uma mensagem chamada “FeedbackDaSniper” pra todos os players dizendo: Atirei na posicao X e na direção Y;
2° Passo: Se acertei alguém, manda uma mensagem de Dano para esse player com a quantidade de dano e se eu matei, Instantaneamente manda um feedback de que o outro player morreu;
3° Passo: Cada player assim que recebe a mensagem “FeedbackDaSniper” renderiza na tela um efeito de laser partindo da posição do tiro;

Após tudo programado fomos testar e tivemos uma surpresa…

1VersaoMatando
Quando eu mato alguém


Quando eu morro

Mesmo com todo mundo com ping por volta de 40ms, 30ms, aconteceram coisas estranhas. Para o jogador que matou, tudo era bom: ele atirava em alguem, e se acertava e havia dano suficiente para matar o alvo morria na mesma hora. Porém, para quem morria, mesmo em 30ms ele já havia mudado de posição e quando a mensagem do tiro chegava o jogador não estava mais na reta do tiro, e morria mesmo assim pois recebeu o dano do primeiro player. Para quem morria era muito frustante, a galera reclamava: “Pô, morri mas o tiro nao me acertou =( “.
Não adianta fazer um jogo multiplayer onde 1 lado fica satisfeito, porém o outro se sente injustiçado.

A importância do Feedback

Quando falamos de jogos Multiplayer e Netcode temos que encarar o nosso pior inimigo, o lag. Para quem não sabe, lag é uma entidade maligna, que refere-se ao intervalo de tempo entre o início de uma atividade e o momento em que os efeitos desta se tornam aparentes. E não adianta, sempre existiu e sempre existirá lag. Então nossa maior duvida era, como disfarçar o lag?? Então, vamos relembrar o que aconteceu, eu atirei, ele morreu pra mim, ele morreu pra ele também, porém ele não teve o Feedback de que o tiro acertou nele. Ok, achamos o problema. Então tudo que tinhamos que fazer era achar um jeito do jogador que morreu ter o feedback de que ele foi realmente atingido pelo raio da sniper para ele ficar feliz!

Como Prever o Imprevisível

Muitas vezes em jogos Multiplayer nos deparamos com ações que são imprevisíveis, ações instantaneas que só conseguiriamos prever se estivessemos dentro da mente do jogador. E a Sniper é uma arma instantanea, é impossivel prever quando o player vai apertar o botão do tiro, entao a solução que achamos foi enganar o player.
E esse foi o resultado:

2VersaoMatando
Quando eu mato alguém

2VersaoMorrendo
Quando eu morro

Vendo as 2 imagens claramente o raio da sniper está em direções diferentes, mas… Será que isso é problema?
Bom, desse jeito quem matou fica feliz, quem morreu fica “feliz”, e o jogo não parece nem um pouco lagado, então é claro que não tem problema, o mais importante é fazer com que os jogadores não sintam o lag, mesmo que ele exista.
Ta bom ta bom… mas como fizemos isso?
Ao invés de mandar uma mensagem avisando Atirei na posicao X e na Direção Y, o player assim que atira, verifica se o outro player está na reta do tiro dele e se estiver manda uma mensagem “Acertei no player X”, e quando o outro player recebe essa mensagem, ele recalcula a direção a qual a sniper deve atirar para que a sniper o acerte. Assim o lag fica escondido por causa do feedback.

É isso aí galera, se você quiser testar a nossa Sniper, faça logo sua inscrição no nosso grupo de testers www.bitcakestudio.com/testers e venha jogar conosco por www.bitcakestudio.com/tilt.
Obs: Nossos testes acontecem todas as quintas de 20:00 às 21:00

Bom Teste!

  • saulocamarotti

    Muito massa! Pergunta, o servidor de vocês que certifica se ocorreu o acerto do tiro ou é o próprio cliente que determina? Se for o cliente, como estão pensando em evitar hacks?

    • Allan Michael Smith

      Eu fiquei com a mesma duvida, as colisoes e tudo o mais estao rolando no server ou no unity? Vcs estao usando algum plugin de server?

      • Vinicius Pacha

        Nós usamos Photon, mas as colisões sao todas na própria Unity mesmo, Algumas o proprio client verifica e outras o MasterClient (é tipo um master server) que verifica! 😀

    • Vinicius Pacha

      Nós fazemos a maioria client based para diminuir a sensação de lag, fizemos vários testes e tal, um dia vou fazer um post melhor falando sobre server ou client.
      Como resolver o problema de Hacks?

      Sinceramente ainda não me preocupei com isso, se alguem se dar ao trabalho de criar um jogo para um jogo do facebook ficarei honrado e me preocuparei com isso e tentarei resolver 😀

  • otubo

    Page not found pros dois links! 🙂

    • Jefferson Bandeira

      Consertado já. 🙂

  • Raphael Santos

    E se o alvo se deslocar para trás de um obstáculo? O projétil atravessa?

    • Thiago Pachioni

      Pensei nisso tbm…a frustração ia ser maior do que se o tiro não tivesse pego haha. Nessa mesma screenshot, se ele estivesse em cima e desse um passo para tras, a linha da sniper iria passar por cima do terreno não ia?

      • Vinicius Pacha

        Sim! 😀 isso é um outro problema, uma das soluções para ele é renderizar o Efeito de Laser por cima do level ou de qualquer obstaculo ou fazer atravessar, porém por enquanto, apesar de saber que existe essa possibilidade, testando o jogo só vi acontecer algumas vezes entao ainda não parei para “enganar mais o jogador” ^^

    • bernardofbbraga

      eu já passei por isso e realmente é bem frustrante…. É como se os caras com ping alto tivessem uma vantagem…

      mas entendo que é uma limitação da solução.. sou programador tb 🙂

  • Wesley

    Dúvida, vejo vocês falando sobre o Photon, ele seria mais um server para gerenciar as partidas/jogo é isso?
    Já que ele somente gerencia isso, ainda é necessário a utilização de um outro servidor de banco (como mySQL por exemplo), para armazenar os logins dos jogadores, informações, etc…?
    Estou ansioso pelos próximos posts, to gostando bastante dessa série focada em programação.

    • Vinicius Pacha

      Então o Photon é serve como um meio de comunicação entre os players In Game, ou seja, Quando eu atiro eu aviso pro Photon que estou atirando e o Photon avisa para os outros Players. Para generiamento de pessoas usamos uma aplicação em Rails e um BD(Oracle, MySQL, Postgres, etc) nosso para podermos guardar coisas como, Login, Level, XP. Espero ter esclarecido 😀