¿Cómo puedo extender btCollisionAlgorithm para permitir la colisión con un terreno vóxel?

8

Estoy usando Bullet e intento hacer un algoritmo de colisión que genere puntos de contacto fuera de un terreno basado en cubos junto con la respuesta de colisión adecuada. También planeo extender esto para incluir formas que no sean cajas, sin embargo, eso no es vital en este momento. Descubrí que usar una malla triangular es demasiado RAM para mapas grandes.

He intentado el procedimiento descrito por Byte56 aquí , sin embargo, tengo varias preguntas sobre la implementación de esto con Bullet:

  • ¿Cómo se genera una forma de colisión para el mundo? ¿Usas una forma personalizada? ¿Qué configuras m_shapeTypepara estar en él?
  • ¿O todavía utilizas una caja del tamaño del mundo?
  • ¿Cómo se asegura de que se liberen los puntos de contacto?
  • ¿Cómo se modifica exactamente processCollision?

Qué he hecho:

  • He creado un terrenoShape that extendsbtBoxShape , the only difference being thatm_shapeType = CUSTOM_CONVEX_SHAPE_TYPE`, para poder registrar un nuevo algoritmo de colisión con el despachador de objetos con solo esta forma.
  • btRigidBodyExtendí la clase de una manera similar a Byte56 en su pregunta (vea el enlace en el segundo párrafo), sin embargo, checkCollisionWith(CollisionObject * co)devuelve verdadero si algún vóxel en el AABB de cono es aire.
  • He extendido la btCollisionAlgorithmclase, de manera similar a btCompoundCollisionAlgorithm, processCollisionhaciendo lo siguiente:

    1. Verifique los objetos en colisión pasados ​​como argumentos y determine cuál es el terreno y cuál es la entidad.
    2. Borre los múltiples algoritmos secundarios.
    3. Llamada resultOut->setPersistantManifold(resultOut)
    4. Genere nuevas formas de caja y transformaciones en el AABB ocupado por la entidad en colisión, y luego llame m_dispatcher->findAlgorithm. Almacene el algoritmo de forma, transformación y encontrado en una estructura de Algoritmo Infantil para cada vóxel dentro de la AABB.
    5. Iterar sobre todos los algoritmos secundarios, llamando proccessCollision.
    6. Iterar sobre todos los algoritmos secundarios, eliminando cualquiera ahora fuera del AABB de la entidad en colisión. (llamando ~btCollisionAlgorithm()entonces m_dispatcher->freeCollisionAlgorithm())
    7. Llamada resultOut->refreshContactPoints().

Lo que funciona: processCollisionse llama cuando el AABB del jugador se cruza con vóxeles no aéreos.

Lo que no: la respuesta de colisión es simplemente extraña ... La entidad del jugador comienza a levitar hacia arriba. Si se topa con algo, rebota violentamente. A veces, no puede seguir moviéndose en un eje después de tropezar con algo. Lo que sospecho que está sucediendo es que los puntos de contacto no se liberan después de la respuesta de colisión, posiblemente debido a que la entidad del jugador siempre está en el AABB del objeto mundial. Tengo curiosidad por ver si estoy ladrando el árbol correcto con respecto a processCollision?

SnapperTT
fuente
¿Resolviste esto? Estoy teniendo un problema muy similar.
timoxley
Un poco tarde, lo siento, no vi tu pregunta. Si aún no lo ha resuelto, ¿ha intentado el dibujo de depuración de sus cuerpos de física? El AABB que está utilizando para detectar la colisión no limita el cuerpo físico que está utilizando. Entonces, para cuando detecte la colisión, su objeto ya está muy adentro. Esto explica por qué sus reacciones de colisión son tan extrañas.
MichaelHouse
1
Vea mi última respuesta a mi pregunta: gamedev.stackexchange.com/questions/27405/…
MichaelHouse

Respuestas:

1

Desafortunadamente, no pude obtener resultados confiables del método descrito en la respuesta a la que hace referencia . Al igual que usted, obtendría eventos flotantes extraños, o situaciones en las que eliminar un vóxel provocaría que los objetos que flotaran sobre ellos permanecieran flotando en el aire, o que una extraña pluma oscilante cayera al suelo. Abandoné esa estrategia por una nueva estrategia.

Comencé a crear mallas de colisión personalizadas para cada fragmento de terreno vóxel. Lo hago con el BvhTriangleMeshShape. Esto funciona bastante bien:

ingrese la descripción de la imagen aquí

Hay más detalles sobre la aplicación de las mallas de colisión costumbre aquí .

MichaelHouse
fuente