function on_message(self, message_id, message, sender)
-- Handle collision
if message_id == hash("contact_point_response") then
-- Get the info needed to move out of collision. We might
-- get several contact points back and have to calculate
-- how to move out of all accumulatively:
if message.distance > 0 then
-- First, project the penetration vector on
-- accumulated correction
local proj = vmath.project(self.correction, message.normal * message.distance)
if proj < 1 then
-- Only care for projections that does not overshoot.
local comp = (message.distance - message.distance * proj) * message.normal
-- Apply compensation
go.set_position(go.get_position() + comp)
-- Accumulate the corrections done
self.correction = self.correction + comp
end
end
end
end
But i can’t figure out a corect value to self.correction variable.
self.correction in the code is a vector that holds the accumulated compensation needed to move an object out of a collision. It should be zeroed at each update() so the next round of collisions can be accumulated.
It is needed because if there are multiple collisions each collision holds data for that collision only and you need a way to combine the penetration vectors. Simply adding them won’t be correct. This is one way of doing that.
In your game example, do each of these little guys solve collisions separately?
If so, the order they solve will have an impact. For example, one character could first solve against the yellow circle and move out of it, then be pushed into the circle when solved against another character.
What you a trying to achieve called “group behavior” and combined from multiple behaviors: obstacle avoidance, separation, flocking, etc.
Read Chapter 3 “How to Create Autonomously Moving Game Agents” from “Programming Game AI by Example” book by Mat Buckland.
Is there some reason why you don’t want to use dynamic collision objects? It seems like that would solve the problem—just apply a force in the direction of movement and you are done.