2011-01-15 16 views
5

Tengo un objeto con el que me gustaría hacer seguir una curva bezier y ahora estoy un poco perdido en cuanto a cómo hacerlo en función del tiempo en lugar de los puntos que forman la curva.¿Mover un objeto en la dirección de una curva bezier?

. :: Sistema actual ::. Cada objeto en mi gráfico de escena está hecho de vectores de posición, rotación y escala. Estos vectores se utilizan para formar sus matrices correspondientes: escala, rotación y traducción. Que luego se multiplican en ese orden para formar la matriz de transformación local. Una transformación mundial (generalmente la matriz de identidad) se multiplica luego por la transformación de matriz local.

class CObject 
{ 
public: 
// Local transform functions 
Matrix4f GetLocalTransform() const; 
void SetPosition(const Vector3f& pos); 
void SetRotation(const Vector3f& rot); 
void SetScale(const Vector3f& scale); 

    // Local transform 
    Matrix4f m_local; 
    Vector3f m_localPostion; 
    Vector3f m_localRotation; // rotation in degrees (xrot, yrot, zrot) 
    Vector3f m_localScale; 
} 

Matrix4f CObject::GetLocalTransform() 
{ 
    Matrix4f out(Matrix4f::IDENTITY); 

    Matrix4f scale(), rotation(), translation(); 

    scale.SetScale(m_localScale); 
    rotation.SetRotationDegrees(m_localRotation); 
    translation.SetTranslation(m_localTranslation); 

    out = scale * rotation * translation; 
} 

La gran pregunta que tengo son

1) ¿Cómo puedo orientar mi objeto hacer frente a la tangente de la curva de Bezier?

2) ¿Cómo muevo ese objeto a lo largo de la curva sin solo colocar la posición de los objetos a la de un punto en la cumbre bezier?

Heres una visión general de la función hasta ahora

void CNodeControllerPieceWise::AnimateNode(CObject* pSpatial, double deltaTime) 
{ 
    // Get object latest pos. 
    Vector3f posDelta = pSpatial->GetWorldTransform().GetTranslation(); 

    // Get postion on curve 
    Vector3f pos = curve.GetPosition(m_t); 

    // Get tangent of curve 
    Vector3f tangent = curve.GetFirstDerivative(m_t); 

} 

Editar: lo siento no es muy clara. He estado trabajando en esto por años y está haciendo que mi cerebro se convierta en papilla.

Quiero que el objeto se una a la curva y quede orientado en la dirección de la curva.

En cuanto al movimiento, quiero objetar seguir la curva en función del tiempo, de esta manera se crea un movimiento suave a lo largo de la curva.

+0

Tengo la curva en su forma completa. Obtengo una posición en la curva basada en el valor de t (Véase la función AnimateNode), que se encuentra entre 0 y 1. La función "curve.GetPosition (m_t)" se basa en la ecuación paramétrica de la curva. – Sent1nel

Respuesta

2

Debe tener una curva en forma paramétrica y usar un vector derivado para evaluar la rotación de su objeto (ángulo de rotación = ángulo derivado) como dijo @etarion.

Para mover el objeto en una curva con la velocidad deseada (creo que es lo que piensas) cada paso de simulación debes calcular la distancia que debe recorrer el punto en este paso.

La estimación más simple es dist = derivative.length()*TIMER_STEP. Cuando sepa que el dist debe atravesarse en el paso actual y t0 - el parámetro actual de la curva puede simplemente aumentar t0 mediante un pequeño valor epsilon y comprobar que la distancia recorrida es aún menor que la estimada. Repita esto hasta que la distancia recorrida (mientras aumenta t0) sea> = estimada. Este será el nuevo T0 parámetro actual para el siguiente paso

EDIT:

no se dio cuenta primero se encuentra en 3d. En el espacio 3D, no puede definir inequívocamente la posición de un objeto en una curva, incluso si conoce la posición inicial. Solo imagine que su curva es una línea, el objeto aún puede rotar alrededor de la línea. Este ángulo no está definido por una curva.

Haría algo como esto. Atemos un vector al objeto para que al comienzo del movimiento (parámetro de curva t = 0 por ejemplo) la dirección del vector del objeto coincida con el vector derivado. Luego, durante el movimiento, este vector debería coincidir con la derivada en cada punto de una curva. Entonces conocerá este vector de objeto y podrá configurar su objeto de acuerdo con este vector. Pero aún tendrás un grado de libertad.

Por ejemplo, puede decir que el objeto no gira alrededor de este vector.

Conociendo el vector del objeto y el ángulo de rotación a su alrededor, puede restaurar la orientación del objeto en el mundo 3D.

PS: este vector de objeto y un ángulo de rotación a su alrededor se llama cuaternión, por lo que puede usar cuaternión matemática (¡copie simplemente la fórmula requerida) para calcular la matriz de rotación de objetos! aquí están las fórmulas http://www.euclideanspace.com/maths/geometry/rotations/conversions/quaternionToMatrix/index.htm

+0

No estoy seguro de qué significa usted y 'etarion' para establecer la rotación.¿Es el "ángulo derivado" la tangente de la curva? Si es así, ¿cómo convierto ese vector, la tangente, en ángulos eulares para usar con la función "pSpatial-> SetRotation (Vector3f (?,?));" ? – Sent1nel

+0

He actualizado la respuesta – Andrew

+0

Esto no es exactamente lo que hice, pero fue de gran ayuda. Voy a publicar mi solución en unos días. Necesito dormir ahora. – Sent1nel

2

Necesita una formulación paramétrica de su curva.

La gran pregunta que tengo son

1) ¿Cómo puedo orientar mi objeto a la cara la tangente de la curva de Bezier?

Si tiene la curva en forma paramétrica, la dirección tangencial es la derivada de la posición wrt. t.

2) ¿Cómo puedo mover ese objeto a lo largo de la curva sin sólo la creación de objetos posición a la de un punto de la cuba bézier?

no estoy seguro que consigo su pregunta - que le aumenta t en su forma paramétrica en un pequeño paso y la posición de actualización y dirección. Todavía tienes un grado de libertad allí, por cierto, la dirección de "arriba" no está determinada por la curva, por lo que tendrás que ocuparte de eso también.

0

Supongo que tiene todos los puntos que necesita para definir la curva de bezier. Luego puede calcular cada punto en esa curva. Calcule un punto adecuado teniendo en cuenta la velocidad a la que debe viajar el objeto, y el tiempo de cuadro y debe tener un movimiento consistente.

El vector formado por los puntos del último y el fotograma actual se puede usar como una estimación aproximada de la tangente en la mayoría de los casos; p.ej. cuando la curva no se dobla demasiado.

Editar: también hay un vistazo aquí en how to calculate the length of a bezier curve. Tendrá que transformar eso, para que pueda calcular un punto en su curva (o más bien t) para una longitud determinada. Luego solo mueva las distancias equitativamente en relación con el tiempo y debería estar bien.

0

Un enfoque es calcular una pirámide de puntos. La capa inferior es tus puntos de control transformados. Ahora, para una t dada, y para cada par de puntos adyacentes, cree un nuevo punto que esté en este segmento de línea ponderado por t. Este nuevo conjunto de puntos forma la siguiente capa en la pirámide. Repita hasta que la capa actual tenga solo 1 punto. Este punto es tu posición. Tenga en cuenta que la segunda capa desde la parte superior tiene 2 puntos y determina la línea tangente.

Cuestiones relacionadas