After I worked more on the collision system I added a system to get Bitren to act out the movement before and after collision hence removing the need to compensate forces.
var VirtualPosition = Vector3(0,0,0)
var VelocityDelta = 1
func MoveAndCollide(AppliedForces,delta):
VelocityDelta = 1
VirtualPosition = position #Helps give a more accurate position of where the object is during collisions without actually moving the object
var WasCollision = Collide(AppliedForces,delta)
var Collisions = 0
while WasCollision == true && VelocityDelta > 0 && Collisions < 10: #More than ten collisions is proof of compression
WasCollision = Collide(AppliedForces,delta)
Collisions += 1
if VelocityDelta > 0:
position += (Velocity*delta * Meter)*VelocityDelta
func Collide(AppliedForces,delta):
PhysicsDetector.target_position=(Velocity*delta * Meter)*VelocityDelta
PhysicsDetector.force_shapecast_update()
if PhysicsDetector.is_colliding():
var CollisionPoint = MovePointOnCourse(PhysicsDetector.get_collision_point(0) * Vector3(0,1,1),VirtualPosition,(Velocity*delta * Meter)*VelocityDelta) #It moves the collision point to the course of the object since the collision point is not in a useful position
var CollisionNormal = PhysicsDetector.get_collision_normal(0) * Vector3(0,1,1)
#Plays out movement prior to collision
var PositionDuringCollision = CollisionPoint + CollisionNormal * Volume / 2
VelocityDelta -= GetTimeToDestination(PositionDuringCollision,VirtualPosition,(Velocity*delta * Meter)*VelocityDelta)
VirtualPosition = PositionDuringCollision
#Adds collision force
var Radians = atan2(CollisionNormal.y,CollisionNormal.z)
var DotProduct=-2*(Velocity.z*cos(Radians)+Velocity.y*sin(Radians))
Velocity = Vector3(0,Velocity.y+DotProduct*sin(Radians),Velocity.z+DotProduct*cos(Radians))
#Velocity+=AppliedForces #Compensate Forces No longer needed
return true
return false
func MovePointOnCourse(Point,Origin,Direction):
# Shows how many frames in the future it takes the object to get to one of the collision point vectors
var DeltaTime = GetTimeToDestination(Point,Origin,Direction)
# Handle cases where Delta y or z not greater than zero or equalls infinity and chooses the smallest one the best fits the conditions
return Origin + Direction * DeltaTime
func GetTimeToDestination(Point,Origin,Direction):
# Shows how many frames in the future it takes the object to get to one of the collision point vectors
var DeltaTime = Vector3(0,(Point.y - Origin.y) / Direction.y,(Point.z - Origin.z) / Direction.z)
# Handle cases where Delta y or z not greater than zero or equalls infinity and chooses the smallest one the best fits the conditions
if DeltaTime.z > 0 && not is_inf(DeltaTime.z) && (DeltaTime.z < DeltaTime.y || not DeltaTime.y > 0):
return DeltaTime.z
elif DeltaTime.y > 0 && not is_inf(DeltaTime.y) && (DeltaTime.y < DeltaTime.z || not DeltaTime.z > 0):
return DeltaTime.y
else:
return 0