Heightmap Física Optimización / Mejora

Estoy trabajando en la implementación de la física que rodea a un jugador que camina en un map de alturas. Un map de alturas es una grilla de puntos que están espaciados uniformemente en los ejes x y z, con diferentes alturas. La representación física de mi jugador (lo que está expuesto a mi motor / manager de física) es simplemente una masa de puntos donde están sus pies, en lugar de complicar el problema tratándolo como una esfera o una caja.

Esta image debería ayudar a explicar aún más los maps de altura y mostrar cómo se generan triangularjs a partir de los puntos. Esta image estaría mirando hacia abajo en un map de alturas, y cada intersección sería un vértice que tiene cierta altura. Mapa de altura

Siéntase libre de pasar esto a matemáticas, física o desbordamiento de stack, pero estoy bastante seguro de que es aquí donde pertenece, ya que es una pregunta de progtwigción relacionada con los juegos.

Aquí está mi algorithm actual:

  1. Calcule la velocidad del jugador desde la input / gravedad / velocidad previa / etc.
  2. Mueva la position del jugador (nextPos = prevPos + velocity * timeSinceLastFrame)
  3. Averigua qué triángulo (¡todos los charts se hacen en triangularjs!) De mi map de alturas, la nueva position del jugador está alineada verticalmente con
  4. Usa los tres vértices de ese triángulo para calcular la ecuación para el plano en el que se encuentra ese triángulo
  5. Conecte las coorderadas x y z del jugador en la ecuación del avión para get la coorderada y para la position del jugador en ese plano
  6. Establezca la coorderada y de la position del jugador en esto (si newPos.y <y)

Todo está bien y elegante, pero me pregunto si hay algo que pueda optimizar. Por ejemplo, mi primer pensamiento es almacenar la ecuación del avión con la información del vértice del triángulo. De esta forma, todo lo que tengo que hacer es conectar los valores x y z a la ecuación para get y. Sin embargo, esto requeriría agregar 4 flotadores a cada vértice del map de alturas que es un poco ridículo en cuanto a la memory. Además, mis maps de altura son dynamics (lo que significa que las alturas cambiarán en time de ejecución), lo que significaría cambiar las ecuaciones del plano cada vez que cambie la altura de un vértice.

¿Hay una forma más rápida de calcular ese punto que desenterrar la ecuación del avión y luego conectar x y z? ¿Debo almacenar las ecuaciones de los aviones y actualizarlas en el cambio de altura de vértices o debería simplemente regenerar las ecuaciones de los planos para cada triángulo cada vez que el jugador se mueva en ese triángulo? ¿Hay una mejor manera de hacer física de altura que mantenga esta simplicidad? (Esto me parece muy simple en lo que respecta a los motores de física)

Es fácil mejorar el cálculo de la altura. Por simplicidad, consideraré que el tamaño de un cuadrado es 1 ; siempre puedes volver a este caso cambiando las coorderadas:

  x A ^ z ,'| | ,' | | ,' | M' | ,' M x | ,' x | | ,' | x'------------x-----> x BC 

Deje que M tenga coorderadas (x,z) . Primero, proyecta M en el borde AC largo de BM . Las coorderadas de M' son (1,z/x) . La interpolación lineal da la altura de M' como yM' = yC + (z/x)(yA-yC) . Finalmente, la altura de M es yM = yB + x(yM' - yB) . O:

 yM = yB + x(yC-yB) + z(yA-yC) 

Además, veo varios problemas con lo que estás haciendo.

  • nextPos = prevPos + velocity * timeSinceLastFrame es ciertamente incorrecto, debe integrar la velocidad en todo el fotogtwig transcurrido en lugar de usar solo el valor de velocidad actual. Promediar la nueva velocidad con la velocidad del cuadro anterior es casi siempre una mejor aproximación, e incluso es lo correcto en el caso de la aceleración constante (como la gravedad), ya que simula exactamente la mecánica newtoniana.

  • el tipo de triangulación de map de altura probablemente dará artefactos de representación porque las subdivisiones triangulares siempre están en la misma dirección; Una forma de compensar esto es cambiar la dirección de la diagonal de cada celda impar y par. Otra solución es usar una malla hexagonal / triangular regular en lugar de un patrón cuadrado.

  • no parece tomar en count el componente vertical de la velocidad del jugador; la distancia de caminata varía con las variaciones de elevación, por lo que si el triángulo que aterriza tiene una pendiente diferente a la que dejó, puede terminar con un error en el momento lineal. En realidad, esto se ilustra mejor con la fijación del valor y : al hacerlo, estás modificando la energía del jugador, sin compensar en otro lugar. Una solución para esto sería realizar su paso de física varias veces por cuadro para compensar tan pronto como sea posible la variación de la pendiente.