Posted: 7th Apr 2004 22:59
Here's my last collision system, I hope you'll like it
So, how does it works ? I'll try to explain it, but since I don't speak English well, it may be a bit hard to understand me

First, I think it would be good that you test it ; you can draw a map (bitmap please, not jpeg ) or download this one : http://sensai.free.fr/attreid/map.bmp
Okay, my map is ugly and blue, but if you dislike blue, just open it with Paint and replace the blue with red (or pink if you're a Lady ^_~).
If you want to draw a map yourself, be sure that the area around the coordinates {350,350} doesn't contain anything, and that it's a 800x600 pixels image !

Okay, now, you may launch it and test it


If you're still reading, then I guess you're interrested by my collision system (or do you like my map so much ?).. So I'll do my best to explain how it works

Line 5, I load the image and put it in a memblock .. I don't remimber why I didn't load an image but loaded a bitmap .. There was maybe something in the water

Look ad the line fourty, I give informations to the coll type (position X, position Y and Radius), then there's a gosub and I take the informations from the coll type.. Interresting, isn't it ? So everything's in the gosub .. Let's see it

On the way, one can see a few functions :
mem_point() gives the color of a pixel that's stocked in a memblock
arrondit() gives the integer of a float, but add one when the first decimal number is superior or equal to five
colliz() looks around the sphere if there's a collision (gives back 1) or not (gives back 0)

Then, my dear gosub. I like gosubs. They're lovely, with their two points and ... hmm.. I should shut up ^__^
So, as you can see, at the beggining, I put several variables to 0 ; I need them empty for the collision system

As you can see, there's almost the same code twice. It's for each side (left & right) of the circle. I'll explain only the left-handed one - the first one.
I look only at the pixels which are around the circle ; not the ones which are in it (it would be far too slow)

First step, I look if the pixel is in the bitmap - if it isn't, there'll be a problem with the memblock
Second step, I look the color of the pixel => if it's superior to 0, the pixel isn't black => there's a collision on that point => I add the position to the coll.center[x,y], I increase the number of collision points (coll.nbr), and I tell there's a collision (coll.hit=1)
Okay, now, I've all the informations, what should I do ? I should use them or drink a beer. Because I'm a kind guy, I'll drink my beer later, for now, I explain you how I use the informations ^^

first step : I've to use the informations only if there's a collision
Second step : I find the center of gravity of all the collision points (I divide the sum of their positions by their number)
Third step : I ask my dear DBP the angle between the center of the sphere and the center of gravity of the collision points
Fourth step : I move the sphere along the angle until there's no collision again

And ... that's all ^^

I hope you understood what I said ^^ .. .. .. Sorry for making you sleep ^_^
I've never been good at explaining things, especially not in a foreign language
Posted: 8th Apr 2004 23:58
I don't speak English well too but I understand what you should say.
Posted: 11th Apr 2004 15:42
en gros, je fais la liste de tous les points de collision entre le bord du cercle et l'image, je cherche leur centre de gravité, je cherche l'angle entre le centre du cercle et ce centre de gravité et finalement, je recule le cercle selon cet angle jusqu'à ce qu'il n'y aie plus de collision
Posted: 11th Apr 2004 16:38
Code doesn't work. i think it might have cut part of it off.

it doesn't recognise this:
+ Code Snippet
x = arrondit(x)
y = arrondit(y)
Posted: 12th Apr 2004 16:01
Sometimes, I wonder why does the forum hates me ^^
Usually, it cut only the end of my snippets ; I looked at the bottom and it was all right .. But this time, it cut the middle of my snippet

Edit>
Grrr, I posted again, and there's the same problem ... Here's an update :

+ Code Snippet
set display mode 800,600,32
sync on
sync rate 0

load bitmap "C:\Documents and Settings\Mathias_2\Mes documents\map.bmp",1
make memblock from bitmap 1,1
make image from memblock 1,1

set current bitmap 0
type t_coll
   coordx as float
   coordy as float
   sizer as float
   centrex as float
   centrey as float
   nbr as float
   hit as boolean
   angle as float
endtype
coll as t_coll


x as float = 350.0
y as float = 350.0
r as float = 10.00

do
   paste image 1,0,0
   set cursor 0,0
   print screen fps()

   circle x,y,r
   if upkey()=1 then dec y,2
   if downkey()=1 then inc y,2
   if leftkey()=1 then dec x,2
   if rightkey()=1 then inc x,2
   
   rem dans coll. mets les coordonnées et le rayon du point auquel tu veux
   rem faire subir une collision
   coll.coordx = x
   coll.coordy = y
   coll.sizer = r
   rem ensuite, mets le gosub
   gosub coll
   rem finalement, récupères tes variables
   x = coll.coordx
   y = coll.coordy
   r = coll.sizer
sync
loop






rem une fonction qui renvoie la couleur d'un pixel d'un memblock
function mem_point(x as integer,y as integer)
	m = 1
   sizex = memblock byte(m,0)+256*memblock byte(m,1)
   sizey = memblock byte(m,4)+256*memblock byte(m,5)
   if x>-1 and x<sizex
      if y>-1 and y<sizey
         n as double integer
         c as dword
         n = (4*((y*sizex)+x))+12
         c = rgb(memblock byte(m,n+2),memblock byte(m,n+1),memblock byte(m,n))
      endif
   endif
endfunction c

rem une fonction qui arrondit un nombre
function arrondit(n as float)
   if n-int(n)>=0.5 then n = int(n)+1 else n=int(n)
endfunction n

rem fonction qui dit s'il y a collision
function colliz(x,y,r)
x = arrondit(x)
y = arrondit(y)
res = 0
for cy=int(y-r) to int(y+r)
         cx = int(x-sqrt(r^2-abs(cy-y)^2))
         if cx>0 and cx<800
            if cy>0 and cy<600
               if rgbr(mem_point(cx,cy))+rgbg(mem_point(cx,cy))+rgbb(mem_point(cx,cy))>0
                  res = 1
                  exit
               endif
            endif
         endif
         cx = int(x+sqrt(r^2-abs(cy-y)^2))
         if cx>0 and cx<800
            if cy>0 and cy<600
               if rgbr(mem_point(cx,cy))+rgbg(mem_point(cx,cy))+rgbb(mem_point(cx,cy))>0
                  res = 1
                  exit
               endif
            endif
         endif
   next cy
endfunction res

rem le gosub qui fait collision
coll:
	coll.centrex = 0
	coll.centrey = 0
	coll.nbr = 0
	coll.coordx = x
	coll.coordy = y
	coll.sizer = r
	coll.hit = 0

   for cy=int(coll.coordy-coll.sizer) to int(coll.coordy+coll.sizer)
         cx = int(coll.coordx-sqrt(coll.sizer^2-abs(cy-coll.coordy)^2))
         if cx>0 and cx<800
            if cy>0 and cy<600
               if rgbr(mem_point(cx,cy))+rgbg(mem_point(cx,cy))+rgbb(mem_point(cx,cy))>0
                  inc coll.centrex,cx
                  inc coll.centrey,cy
                  inc coll.nbr
                  coll.hit=1
               endif
            endif
         endif
         cx = int(coll.coordx+sqrt(coll.sizer^2-abs(cy-coll.coordy)^2))
         if cx>0 and cx<800
            if cy>0 and cy<600
               if rgbr(mem_point(cx,cy))+rgbg(mem_point(cx,cy))+rgbb(mem_point(cx,cy))>0
                  inc coll.centrex,cx
                  inc coll.centrey,cy
                  inc coll.nbr
                  coll.hit = 1
               endif
            endif
         endif
   next cy

   rem traitement des données
   if coll.hit=1
	   coll.centrex = arrondit(coll.centrex / coll.nbr)
	   coll.centrey = arrondit(coll.centrey / coll.nbr)
	   coll.angle = atanfull(coll.centrex-coll.coordx,coll.centrey-coll.coordy)
      repeat
         coll.coordx = coll.coordx - sin(coll.angle)*0.5
         coll.coordy = coll.coordy - cos(coll.angle)*0.5
      until colliz(int(coll.coordx),int(coll.coordy),coll.sizer)=0
   endif
return
Posted: 13th Apr 2004 2:13
Why do you speak French Astreides? I make a mistake in my message!
Posted: 13th Apr 2004 15:58
no, but under your name, it's written that you live in France, and usually, French speak French
Posted: 14th Apr 2004 0:13