matemática triângulo para desenvolvimento de jogos
-
03-07-2019 - |
Pergunta
Eu estou tentando fazer um triângulo (triângulo isósceles) para mover ao redor da tela e, ao mesmo tempo girá-lo levemente quando um usuário pressiona uma tecla direcional (como a direita ou esquerda).
Gostaria que o nariz (ponto superior) do triângulo para levar o triângulo em todos os momentos. (Como que os asteróides velho jogo).
O meu problema é com a matemática por trás disso. Em cada intervalo de tempo X, eu quero o triângulo para mover-se em "algum sentido", eu preciso de ajuda para encontrar essa direção (x e y incrementos / decréscimos).
posso encontrar o ponto central (Centróide) do triângulo, e eu tenho o mais alto x um y pontos, então eu tenho um vetor linha para trabalhar, mas não um indício a respeito de "como" trabalhar com ele .
Eu acho que tem algo a ver com os velhos métodos seno e cosseno e a quantidade (ângulo) que o triângulo tenha sido rodado, mas eu sou um enferrujado pouco sobre essas coisas.
Qualquer ajuda é muito apreciada.
Solução
O arco tangente (tangente inversa) de vy / vx, onde vx e vy são os componentes de seu (centroid-> ponta) vetor, dá-lhe o ângulo do vetor está enfrentando.
O arco tangente clássica dá-lhe um ângulo normalizado para -90 ° Felizmente, a biblioteca padrão deve proive uma função atan2 () que leva vx e vy separadamente como parâmetros e retorna um ângulo entre 0 ° e 360 ??°, ou -180 ° e + 180 ° graus. Ele também irá lidar com o caso especial em que vx = 0, o que resultaria em uma divisão por zero se você não fosse cuidadoso. Consulte http://www.arctangent.net/atan.html ou apenas pesquisar para "arco tangente". Edit:. Eu usei graus no meu post para maior clareza, mas Java e muitas outras línguas / bibliotecas funcionam em radianos, onde 180 ° = p Você também pode simplesmente adicionar vx e vy a pontos do triângulo para torná-lo mover-se no "forward" direção, mas certifique-se que o vetor é normalizado (vx² + vy² = 1), então a velocidade vai depender de suas do triângulo tamanho.
Outras dicas
@ Marcos:
Eu tentei escrever uma cartilha sobre vetores, coordenadas, pontos e ângulos nesta caixa de resposta duas vezes, mas mudei de idéia em ambas as ocasiões, porque levaria muito tempo e eu tenho certeza que existem muitos tutoriais lá fora, explicando coisas melhor do que eu puder.
O seu centróide e coordenadas "ponta" não são vetores; isto é, não há nada a ser adquirida a partir de pensar neles como vetores.
O vector que quiser, vForward = PTIP - pCentroid, pode ser calculado subtraindo-se as coordenadas do canto "ponta" do ponto baricentro. O atan2 () deste vetor, ou seja, atan2 (tipY-centY, tipX-centX), dá-lhe o ângulo de seu triângulo está "enfrentando".
Como para o que é em relação a, não importa. Sua biblioteca provavelmente vai usar a convenção de que o aumento do eixo X (---> o direito / direção leste na presumivelmente todos os 2D gráficos que você já viu) é de 0 ° ou 0p. O aumento Y (topo, norte) direcção corresponderá a 90 ° ou p (1/2).
Parece-me que você precisa para armazenar o ângulo de rotação do triângulo e, possivelmente, é a velocidade atual.
x' = x + speed * cos(angle)
y' = y + speed * sin(angle)
Note que o ângulo é em radianos, não graus!
Radians = graus * RadiansInACircle / DegreesInACircle
RadiansInACircle = 2 * pi
DegressInACircle = 360
Para os locais dos vértices, cada um está localizado a uma certa distância e ângulo a partir do centro. Adicione o ângulo de rotação atual antes de fazer este cálculo. É a mesma matemática como para descobrir o movimento.
Aqui está um pouco mais:
Vectors representam deslocamento. Deslocamento, tradução, movimento ou o que você quiser chamá-lo, não tem sentido sem um ponto de partida, é por isso que eu me referi ao "forward" vector acima como "a partir do centróide", e é por isso que o "vector centróide", o vector com que os componentes x / y do ponto de centróide não faz sentido. Esses componentes dará o deslocamento do ponto baricentro da origem. Em outras palavras, pOrigin + vCentroid = pCentroid. Se você começar a partir do ponto 0, em seguida, adicione um vetor que representa o deslocamento do ponto de centróide, você começa o ponto baricentro.
Note que:
vector + vector = vetor
(Adição de dois deslocamentos dá-lhe um terceiro deslocamento, diferente)
ponto + vector = ponto
(Movendo / deslocando um ponto dá-lhe um outro ponto)
ponto + ponto = ???
(Adicionando dois pontos não faz sentido, no entanto:)
ponto - ponto = vetor
(A diferença de dois pontos é o deslocamento entre eles)
Agora, esses deslocamentos podem ser pensado em (pelo menos) duas maneiras diferentes. O que você já está familiarizado com o retangular sistema (x, y), onde os dois componentes de um vetor representam o deslocamento nas direções x e y, respectivamente. No entanto, você também pode usar polar coordenadas, (r, T). Aqui, T representa o sentido do deslocamento (em ângulos em relação a um ângulo de zero arbitrária) e r, a distância.
Aqui o (1, 1) vector, por exemplo. Ela representa um movimento de uma unidade para a direita e uma unidade para cima no sistema de coordenadas que estamos todos acostumados a ver. O equivalente polar deste vector seria (1,414, 45 °); o mesmo movimento, mas representado como um "deslocamento de 1,414 unidades na direcção 45 ° -angle. (Mais uma vez, utilizando um sistema conveniente de coordenadas polares onde a direcção este é de 0 ° e ângulos aumentar sentido anti-horário.)
A relação entre as coordenadas polares e rectangulares são:
T = atan2 (y, x)
r = sqrt (x² + y²) (agora você vê onde o triângulo retângulo vem em?)
e, inversamente,
x = r * cos (T)
Agora, uma vez que um segmento de linha traçada a partir do centróide do seu triângulo para o canto "ponta" representaria a direção do triângulo está "enfrentando", se fôssemos para obter um vector paralelo a essa linha (por exemplo, vForward = PTIP -. pCentroid ), que do vetor T coordenada corresponderia ao ângulo que seu triângulo está enfrentando
Leve o vetor (1, 1) de novo. Se este era vForward, então isso teria significado que xey coordenadas do seu ponto de "ponta" eram mais ambos 1 do que os de seu centróide. Digamos que o baricentro está ligado (10, 10). Isso coloca a "ponta" canto mais em (11, 11). (Lembre-se, PTIP = pCentroid + vForward , acrescentando "+ pCentroid" para ambos os lados da equação anterior). Agora em qual direção é esse triângulo enfrentando? 45 °, certo? Essa é a T coordenada do nosso (1, 1) vetor!
manter o centróide na origem. usar o vector a partir do centroide do nariz como o vector de direcção. http://en.wikipedia.org/wiki/Coordinate_rotation#Two_dimensions vai rodar este vetor. construir os outros dois pontos a partir deste vector. traduzir os três pontos para onde eles estão na tela e desenhar.
double v; // velocity
double theta; // direction of travel (angle)
double dt; // time elapsed
// To compute increments
double dx = v*dt*cos(theta);
double dy = v*dt*sin(theta);
// To compute position of the top of the triangle
double size; // distance between centroid and top
double top_x = x + size*cos(theta);
double top_y = y + size*sin(theta);
Eu posso ver que eu preciso para aplicar as fórmulas comuns de rotação 2d ao meu triângulo para obter o meu resultado, Im apenas ter um pouco de dificuldade com as relações entre os diferentes componentes aqui.
aib , afirmou que:
O arco de tangente (tangente inversa) de vy / vx, vy onde vx e são o componentes do seu (centroid-> tip) vetor, dá-lhe o ângulo do vetor está enfrentando.
é vx e vy x e y coords da centriod ou a ponta? Eu acho que estou ficando confuso quanto à terminologia de um "vector" aqui. Fiquei com a impressão de que a Vector foi apenas um ponto em 2D (neste caso) espaço que representou direção.
Portanto, neste caso, como é o vetor da centroid-> tip calculado? É apenas o centriod?
meyahoocomlorenpechtel declarou:
Parece-me que você precisa para loja o ângulo de rotação do triângulo e possivelmente é a velocidade atual.
O que é o ângulo de rotação em relação ao? A origem do triângulo, ou a própria janela do jogo? Além disso, para futuras rotações, é o ângulo do ângulo a partir da última rotação ou a posição original do triângulo?
Obrigado a todos pela ajuda até agora, eu realmente aprecio isso!
você vai querer o vértice superior para ser o centróide, a fim de alcançar o efeito desejado.
Em primeiro lugar, gostaria de começar com o centróide em vez de calculá-lo. Você sabe a posição do centróide e o ângulo de rotação do triângulo, eu iria usar isso para calcular as posições dos vértices. (Peço desculpas antecipadamente por quaisquer erros de sintaxe, eu só começou a se envolver em Java.)
// ponto de partida
double tip_x = 10;
double tip_y = 10;
should be
double center_x = 10;
double center_y = 10;
// detalhes triângulo
int width = 6; //base
int height = 9;
deve ser uma matriz de três pares de ângulo, à distância.
angle = rotation_angle + vertex[1].angle;
dist = vertex[1].distance;
p1_x = center_x + math.cos(angle) * dist;
p1_y = center_y - math.sin(angle) * dist;
// and the same for the other two points
Note que eu sou subtraindo a distância Y. Você está sendo desarmado pelo fato de que o espaço na tela é invertido. Em nossas mentes Y aumenta à medida que você subir - mas coordenadas de tela não funciona dessa maneira
.A matemática é muito mais simples se você acompanhar as coisas como posição e ângulo de rotação em vez de derivar o ângulo de rotação.
Além disso, em sua parte final do código que você está modificando o local pelo ângulo de rotação. O resultado será que o seu navio se transforma pelo ângulo de rotação a cada ciclo de atualização. Eu acho que o objetivo é algo como Asteroids, não um gato que persegue a sua cauda!