Calcular el rumbo de la bicicleta a partir del rumbo y la velocidad de la rueda delantera

10

Tengo un simple juego de bicicleta de arriba hacia abajo al que estoy tratando de agregar dirección. Me gustaría saber cómo uso el rumbo de la rueda delantera para determinar el rumbo y la velocidad de la bicicleta.

void Update () 
{
    //Get input from user Vertical: 0 to 1, Horizontal -1 to 1
    float forwardInput = Input.GetAxis("Vertical");
    float sidewaysInput = Input.GetAxis("Horizontal") * m_steeringAmount;

    // Turn front wheel
    m_frontWheelTransform.localEulerAngles = new Vector3(0, sidewaysInput, 90);

    // get speed and drag
    float   speed           = m_velocity.magnitude;
    Vector3 forwardDrag     = -m_forwardDragConstant * m_velocity * speed;

    // calculate acceleration 
    float engineForce       = forwardInput * m_enginePower;
    Vector3 forwardTraction = transform.forward * engineForce;
    Vector3 forwrdForce     = forwardTraction + forwardDrag;
    Vector3 acceleration    = forwrdForce / m_mass;

    // update velocity and position
    m_velocity += acceleration * Time.deltaTime;
    transform.localPosition += m_velocity * Time.deltaTime;
}

He tratado de aplicar la velocidad de la bicicleta a la rueda delantera y trasera y usar la diferencia de las posiciones para determinar el rumbo de la bicicleta, pero el arrastre hacia adelante lo hace confuso.

Editar basado en el comentario de madshogo

ingrese la descripción de la imagen aquí

usuario346443
fuente
Estoy en mi teléfono en este momento, así que solo daré una breve respuesta: las ruedas son tangentes a un círculo ficticio a lo largo del cual avanza la bicicleta, por lo tanto, la bicicleta gira. El centro del círculo está en la intersección de las líneas ortogonales a cada rueda. Si las ruedas son rectas (la bicicleta no gira), entonces estas líneas se cruzan infinitamente lejos (son paralelas) dando como resultado un círculo de radio infinito, es decir, una línea. Eventualmente, esto le brinda la trayectoria que la bicicleta debe seguir (el círculo) o su curvatura, lo que se adapte a sus necesidades.
jrsala
Gracias por la respuesta madshogo. ¿Podría echar un vistazo al diagrama que he agregado y decirme si eso es correcto? La línea roja es el rumbo de la bicicleta. Saludos
usuario346443
Oh, espera, la rueda delantera no es tangente al círculo en tu dibujo. En mi cabeza, ambas ruedas eran tangentes. Eso cambia algunas cosas.
jrsala
¿Has visto la página de Wikipedia sobre física de bicicletas ? Tiene fórmulas útiles para el radio de giro que tienen en cuenta la inclinación.
sam hocevar

Respuestas:

3

Ok, estoy de vuelta con los resultados!

bicicleta animada

Intenté dos enfoques:

  • Uso de la mecánica de sólidos para derivar una ecuación diferencial que rige el movimiento de los centros de las ruedas: las entradas del sistema "bicicleta" son el par en la rueda trasera y el ángulo de la rueda delantera, y las salidas son la cinemática de los centros de las ruedas. Pero me di por vencido, ¡fue difícil!

  • Tratando de adivinar lo que sucede desde un punto de vista geométrico cuando la rueda trasera "empuja" la rueda delantera hacia adelante con la rueda delantera no recta. Este método produce directamente una ecuación de incrementos infinitesimales (ver más abajo) de la que puede obtener una ecuación diferencial real. No he intentado manipular esta primera ecuación para obtener la EDO, pero supongo que habría obtenido esa misma EDO utilizando la mecánica de sólidos. Simplemente se siente bien.

Anotaciones e hipótesis:

Estamos en el plano con los vectores base ex y ey .

A es el centro de la rueda trasera. B es el centro de la rueda delantera. La longitud de la moto L es la distancia entre A y B . El ángulo entre ey y el vector AB es φ . El ángulo entre AB y la rueda delantera es θ .

Justificación intuitiva:

Suponemos que, en un cierto instante t , A (t) tiene una velocidad V (t) colineal con AB . Por lo tanto, para un paso de tiempo infinitesimal dt ,

A (t + dt) = A (t) + V (t) .dt .

También suponemos que, en el tiempo t , la rueda delantera no se desplaza, es decir, la velocidad de B es colineal con la dirección de la rueda delantera, es decir, forma un ángulo θ con AB . Llamamos a el vector unitario que forma un ángulo θ con AB , es decir, el vector unitario con la misma dirección que la rueda delantera.

Por lo tanto, en t + dt ,

B (t + dt) = B (t) + λ.Uθ

para un cierto λ positivo real, tal que la longitud de la bicicleta L se conserva:

distancia (A (t + dt), B (t + dt)) = L

Cálculos:

Esta última ecuación se traduce en

norm² (B (t) + λ.Uθ - A (t) - V (t) .dt) = L²

pero B (t) , por definición, es A (t) + L.Uφ , de modo que λ debe satisfacer la ecuación

norm² (L.Uφ + λ.Uθ - V (t) .dt) = L² .

La solución, por supuesto, es independiente de φ ya que el problema es el mismo cuando la bicicleta apunta hacia una y positiva . Por lo tanto, si llamamos a R la matriz de rotación con ángulo , λ debe ser la solución positiva de

norm² (L.ey; + λ.Uθ - RV (t) .dt) = L² .

Después de algunos cálculos, si llamamos a v la norma de V , obtienes

λ = L. (sqrt (1 - (sin (θ). (1-v.dt / L)) ²) - cos (θ)) + v.dt.cos (θ) .

Aquí está el pseudocódigo que usé para obtener la animación anterior (en lugar de usar , uso u = U (θ + φ) porque era más simple):

// I start at i=1 because i=0 contains the initial values
for (int i=1; i<=N; i++)
{
    // the array in which I stored the successive A points
    Aarray[i] = Aarray[i-1] + dt*V;
    float lambda = L*( sqrt(1 - (sin(theta)*(1-v*dt/L))**2) - cos(theta) )
                   + cos(theta)*v*dt;
    // the array in which I stored the successive B points
    Barray[i] = Barray[i-1] + lambda*u;
    // the AB vector normalized
    AiBiUnit = (Barray[i] - Aarray[i])/L;
    // Refreshing the velocity of A
    V = v*AiBiUnit;
    // Refreshing u.
    // u is indeed a unit vector separated from AiBiUnit by an angle theta,
    // so you get it by rotating the newly computed AiBiUnit by an angle
    // of +theta:
    u = AiBiUnit.rotate(theta);
}

Si repite mucho y / o aumenta el ángulo de dirección, la trayectoria es un círculo, que es coherente, creo.

jrsala
fuente