Conversation
Co-authored-by: Tais <[email protected]> Signed-off-by: Gabi <[email protected]>
Co-authored-by: Tais <[email protected]> Signed-off-by: Gabi <[email protected]>
Co-authored-by: Tais <[email protected]> Signed-off-by: Gabi <[email protected]>
Co-authored-by: Gabi <[email protected]> Signed-off-by: Tais-A <[email protected]>
Co-authored-by: Gabi <[email protected]> Signed-off-by: Tais-A <[email protected]>
Co-authored-by: Gabi <[email protected]> Signed-off-by: Tais-A <[email protected]>
| private List<IDamageable> getEnemies() | ||
| { | ||
| var myTeam = Entity.Team; | ||
| var enemyTeam = ""; |
There was a problem hiding this comment.
Aqui a gente pode usar um método de extensão do enum Team que já tá implementado no Team.cs. Basta chamar myTeam.Opposite() que este método retornará o time oposto.
| if (_attackTimer > CooldownInSeconds) | ||
| { | ||
| Attack(); | ||
| if(isAreaAttack){ |
There was a problem hiding this comment.
Meninas, em primeiro lugar, parabéns! O código do splash damage está certo! Porém, uma crítica construtiva é a de que ele está no lugar errado.
Vou tentar esclarecer os problemas da implementação atual: imaginem que queremos criar um novo tipo de ataque com mecânica de knockback (empurra o alvo pra trás). Seguindo o modelo atual, nós teríamos que fazer uma nova variável booleana isKnockbackAttack e chegando aqui, faríamos if (isKnockbackAttack) { KnockbackAttack(); }
O problema é: e se quisermos uma carta que tenha splash damage E knockback? A gente começaria a ter problemas pq os diferentes ataques que deveriam se comportar como plugins vão ter que saber como o outro funciona.
Como eu disse, o código está certo, só está no lugar errado (na minha opinião)! O ideal seria criarmos uma nova classe pra esse novo ataque (por exemplo: SplashDamageAttackBehaviour) e movermos essa lógica pra lá. Essa nova classe implementa a interface IAttacker. Dessa forma, o AttackBehaviour vai acionar o método Attack do SplashDamageAttackBehaviour sempre que atacar um alvo, sem saber de seus detalhes de implementação (ele só armazena uma lista de IAttackers que cacheia em sua inicialização).
Daí entra a ideia de uma "arquitetura de plugins": quando quisermos criar uma nova mecânica de ataque, basta criarmos um script de ataque que implementa a interface IAttacker e nem vamos precisar mexer no AttackBehaviour, que tem única responsabilidade de acionar os behaviours de ataque (scripts que implementam o IAttacker).
Me avisem se tiver ficado confuso ou se discordarem de algo :)
Obs: tô muito feliz com o resultado, parabéns de novo!
|
|
||
| foreach (var enemy in enemies) | ||
| { | ||
| if (Vector3.Distance(transform.position, enemy.transform.position) <= distanceSplashDamage) |
There was a problem hiding this comment.
Uma pequena melhoria aqui seria comparar as distancias ao quadrado com (transform.position - enemy.transform.position).sqrMagnitude <= distanceSplashDamage * distanceSplashDamage com o ponto positivo de melhoria de performance por não ter que usar o método de raiz quadrada (internamente no Distance) que é razoavelmente mais lento que a comparação que eu sugeri, o que geralmente é importante na parte relacionada ao gameplay. Embora aqui não seja crítico dado que essa parte do código vai ser executada poucas vezes, quis aproveitar pra mostrar esse pequeno truque
Co-authored-by: Tais <[email protected]> Signed-off-by: Gabi <[email protected]>
Co-authored-by: Tais <[email protected]> Signed-off-by: Gabi <[email protected]>
|
Oi @pedrodelyra , implementamos o Splash Damage como uma classe que herda de Attack Behaviour e fizemos as alterações pra checar a distancia e o time. Só não conseguimos atualizar com a master pois está dando conflito em arquivos |
Issue #2