in advanced 3 (new series) when testing the circle collision with the "plank" i did the same code as chili but the distance (between point and line) gives different results than what chili does. i can't figure out why....
collision code found in Ball.h in functions
bool IsCollidingWithLine(const Vec2& p0, const Vec2& p1) const
and
void ProcessCollision(const Vec2& wall, const Vec2& p0, const Vec2& p1)
here is my code (branch "Advanced3")
https://github.com/xEyad/advmath/tree/Advanced3
thanks in advance for the help.
advanced 3 vector collision

 Posts: 4153
 Joined: February 28th, 2013, 3:23 am
 Location: Oklahoma, United States
Re: advanced 3 vector collision
There is a disconnect between the physics and the graphics. I can't seem to find the disconnect though. Also, there is an error in the way you are getting the wall normal. The normal of the plank should be facing away from the plank surface back toward the ball spawn point. The way you have it now, it's pointing from free > anchor. To rotate the normal by 90 degrees, you an swap the X and Y components and negate the resulting X or Y.
Vec2 normal = Vec2{(anchor.y  free.y), (anchor.x  free.x ) }.GetNormalized();
or
Vec2 normal = Vec2{(anchor.y  free.y), (anchor.x  free.x ) }.GetNormalized();
Since you are working in a coordinate system with +Y is UP, the first one rotates anticlockwise and the second one rotates clockwise if I remember correctly.
Here's the reflection formula for reference:
d  n * ( dot_product( n, d ) * 2.f )
d = vel
n = normal
With _Vec2::operator* overloaded, you could do
Vec2 normal = Vec2{(anchor.y  free.y), (anchor.x  free.x ) }.GetNormalized();
or
Vec2 normal = Vec2{(anchor.y  free.y), (anchor.x  free.x ) }.GetNormalized();
Since you are working in a coordinate system with +Y is UP, the first one rotates anticlockwise and the second one rotates clockwise if I remember correctly.
Here's the reflection formula for reference:
d  n * ( dot_product( n, d ) * 2.f )
d = vel
n = normal
With _Vec2::operator* overloaded, you could do
Code: Select all
// Variable named right because the current vector points to the right
auto const right = wall.GetNormalized();
auto const normal = Vec2( right.y, right.x );
vel = normal * ( ( normal * vel ) * 2.f ) )
If you think paging some data from disk into RAM is slow, try paging it into a simian cerebrum over a pair of optical nerves.  gameprogrammingpatterns.com

 Posts: 4153
 Joined: February 28th, 2013, 3:23 am
 Location: Oklahoma, United States
Re: advanced 3 vector collision
Ok, so after a little bit of playing around I think I have an answer for you.
The vertices of the plank you generate each time you move the free side, and you base it on the free side's new position. Then you do your transformations on the vertices even though they have already been transformed when you create the new model. Basically, the vertices are being translated twice. The vertices should be offsets from the position, which makes things difficult because you based your position from the middle of the plank and this position doesn't move when the free side moves.
For the collision, you base the collision off of the free and anchor relation, but for drawing, you are basing the translation from the Entity::pos vector and the vertices are based on the free and anchor positions.
The vertices of the plank you generate each time you move the free side, and you base it on the free side's new position. Then you do your transformations on the vertices even though they have already been transformed when you create the new model. Basically, the vertices are being translated twice. The vertices should be offsets from the position, which makes things difficult because you based your position from the middle of the plank and this position doesn't move when the free side moves.
For the collision, you base the collision off of the free and anchor relation, but for drawing, you are basing the translation from the Entity::pos vector and the vertices are based on the free and anchor positions.
If you think paging some data from disk into RAM is slow, try paging it into a simian cerebrum over a pair of optical nerves.  gameprogrammingpatterns.com

 Posts: 4153
 Joined: February 28th, 2013, 3:23 am
 Location: Oklahoma, United States
Re: advanced 3 vector collision
Figured out a way to use a skew matrix to draw the plank and have the collisions work using the free and anchor points.
Code: Select all
Drawable GetDrawable()const override
{
auto d = Drawable( GetModel(), GetColor() );
d.GetTransform() =
Mat3f::SkewY( ( anchor.y  free.y ) / length )*
Mat3f::Scale( GetScale(), GetScale() ) *
Mat3f::Translate( GetPos() );
return d;
}
Code: Select all
static constexpr Matrix SkewY( T skew )noexcept
{
constexpr auto zero = T( 0 );
constexpr auto one = T( 1 );
return{
one, skew, zero,
zero, one, zero,
zero, zero, one
};
}
Code: Select all
bool Ball::IsCollidingWithLine(const Vec2& p0, const Vec2& p1) const
{
auto sq = []( float a )constexpr { return a * a; };
auto const& q = GetPos();
auto u = q  p0;
auto v = ( p1  p0 ).Normalize();
auto t = dot_product( u, n );
auto p = p0 + ( v * t );
auto distSq = ( q  p ).LenSq();
auto radSq = sq( radius );
return distSq <= radSq;
}
void Ball::ProcessCollision(const Vec2& wall, const Vec2& p0, const Vec2& p1)
{
if( IsCollidingWithLine( p0, p1 ) )
{
auto const normal = Vec2( wall.y, wall.x ).Normalize();
vel = reflect( normal, vel );
}
}
Code: Select all
constexpr Vec2 reflect( Vec2 const& n, Vec2 const& d )noexcept
{
return d  n * ( dot_product( n, d ) * 2.f );
}
If you think paging some data from disk into RAM is slow, try paging it into a simian cerebrum over a pair of optical nerves.  gameprogrammingpatterns.com