collision problems
BlitzPlus Forums/BlitzPlus Programming/collision problems
| ||
Hi, On one of my many projects I'm having difficulties with collision detection. I have made it work great for vertical check but just can't seem to get further with the horizontal. Following is the current code. It's a scrolling platformer that moves from right to left. Any suggestions are very welcome. [code] Graphics 800,600,32,2 tileImg = LoadAnimImage("gfx\tiles.png",32,32,0,15) playerImg = LoadImage("gfx\player.png") playerX# = 200 playerY# = 32 playerZ# = -1 playerU# = 0 gravity# = .1 friction# = .98 offset = 0 scroll = 0 Dim playfield(100,2500,16) Gosub loadlevel SetBuffer BackBuffer() While Not KeyHit(1) ;----------------------------------------------------------------------------- ; CHECK PLAYER CONTROLS ;----------------------------------------------------------------------------- If chkkeys + 25 <= MilliSecs() Then chkkeys = MilliSecs() If KeyDown(203) Or JoyXDir()=-1 Then playerU = playerU - .2 ;left Left = 1 Else Left = 0 End If If KeyDown(205) Or JoyXDir()=1 playerU = playerU + .2 ;right Right = 1 Else Right = 0 End If jy = Int(JoyY()) If jy = -1 Or KeyHit(57) Then playerZ = 5.5 End If If mvscreen + 5 <= MilliSecs() Then mvscreen = MilliSecs() If offset > 0 And offset < 2475 Then If Left = 1 Then scroll = scroll - 2 If Right = 1 Then scroll = scroll + 2 End If If offset = 0 Then If Right = 1 And scroll < 31 Then scroll = scroll + 2 End If If offset = 2475 Then If Left = 1 And scroll > 0 Then scroll = scroll - 2 End If If offset < 0 Then offset = 0 If offset > 2475 Then offset = 2475 If scroll > 31 Then scroll = scroll - 32 offset = offset + 1 End If If scroll < 0 Then scroll = scroll + 32 offset = offset - 1 End If End If playerU = playerU * friction playerZ = playerZ - gravity playerX = playerX + playerU playerY = playerY - playerZ ;----------------------------------------------------------------------------- ; DRAW SCREEN AND CHECK FOR PLAYER COLLISION ;----------------------------------------------------------------------------- nomove = 0 For x=0 To 25 For y=0 To 15 If playfield(level,offset+x,y) >0 Then DrawImage tileImg,x*32-scroll,y*32,playfield(level,offset+x,y) If ImagesCollide(tileImg,x*32-scroll,y*32,playfield(level,offset+x,y),playerImg,playerX,playerY,0) Then nomove = 1 End If Next Next If nomove = 1 Then ; playerX = playerX - playerU playerY = playerY + playerZ ; playerU = 0 playerZ = 0 End If If playerY < 0 Then playerY = 0 If playerY > 480 Then playerY = 480 If playerX > 768 Then playerX = 768 If playerX < 0 Then playerX = 0 DrawImage playerImg,playerX,playerY Flip Cls Wend FreeImage titleImg FreeImage playerImg End ;----------------------------------------------------------------------------- ; LOAD LEVEL INTO ARRAY ;----------------------------------------------------------------------------- .loadLevel filein = ReadFile("gianasisters.lvl") ;For lv = 0 To 99 For x = 0 To 2499 For y = 0 To 15 playfield(lv,x,y) = ReadInt(filein) Next Next ;Next CloseFile(filein) Return [\code] |
| ||
I still have problems with this, but the code has changed a little, but basically my problem consist of not being able to get it to check right for collision left and right but it works fine up and down. Does anyone know of any code somewhere that shows how to do a collision check for a sideways platform scroller that is set up with arrays? |
| ||
What behaviour is currently happening? Walking through solid blocks? Getting stuck? This would really help. |
| ||
filein = ReadFile("gianasisters.lvl") Does this mean I have some competition? I am working on a Gianasisters remake, you can download a preview version form the Blitzcoder website. As for your little problem, I would suggest you take a look at some of the platform aware code which you can also find on the Blitzcoder site. |
| ||
Yes the image is going solid blocks but only left and right not up and down. Well its not really Giana Sisters, but it basically the same concept. Its a horizontal scrolling platform game that are one screen high, which is just what Giana Sisters was. GS is just the "codename" for the project until I see where its going and I find a title for it. |
| ||
Try uncommenting the line ; playerX = playerX - playerU Not sure if this will make everything OK or not. I know it's a pain in the B/S, but if you modify your code so it can be run without external files, people will be more likely to run it and come up with some feedback. Cheers |
| ||
I've tried that and it doesn't work. I think that I'll start from scratch and rethink this whole thing. If anyone have any links to anything that would be of help as far as doing collision checks on a horizontal scroller with tiles as background let me know. For now I'm back in the thinking box. |
| ||
I don't know if this can be the problem, but you only reset player position when hiting a wall, what about scroll and offsets? they still counting. Good luck. Bye. |
| ||
Try this Main loop: (This is not the best way do fix the problem) I removed Gravity, the gravity pushes player down to the floor,and the floor trigger a collision.(Player stucks). You must check if its a wall or floor that triggers the collision. While Not KeyHit(1) ;----------------------------------------------------------------------------- ; CHECK PLAYER CONTROLS ;----------------------------------------------------------------------------- If chkkeys + 25 <= MilliSecs() Then chkkeys = MilliSecs() If KeyDown(203) Or JoyXDir()=-1 Then playerU = playerU - .2 ;left Left = 1 Else Left = 0 End If If KeyDown(205) Or JoyXDir()=1 playerU = playerU + .2 ;right Right = 1 Else Right = 0 End If jy = Int(JoyY()) If jy = -1 Or KeyHit(57) Then playerZ = 5.5 End If ;Save Scroll value Savescroll=Scroll; <----------------------Save old scroll SaveOffset=Offset If mvscreen + 5 <= MilliSecs() Then mvscreen = MilliSecs() If offset > 0 And offset < 2475 Then If Left = 1 Then scroll = scroll - 2 If Right = 1 Then scroll = scroll + 2 End If If offset = 0 Then If Right = 1 And scroll < 31 Then scroll = scroll + 2 End If If offset = 2475 Then If Left = 1 And scroll > 0 Then scroll = scroll - 2 End If If offset < 0 Then offset = 0 If offset > 2475 Then offset = 2475 If scroll > 31 Then scroll = scroll - 32 offset = offset + 1 End If If scroll < 0 Then scroll = scroll + 32 offset = offset - 1 End If End If playerU = playerU * friction ;playerZ = playerZ - gravity playerX = playerX + playerU playerY = playerY - playerZ ;----------------------------------------------------------------------------- ; DRAW SCREEN AND CHECK FOR PLAYER COLLISION ;----------------------------------------------------------------------------- nomove = 0 For x=0 To 25 For y=0 To 15 If playfield(level,offset+x,y) >0 Then ;DrawImage tileImg,x*32-scroll,y*32,playfield(level,offset+x,y) If ImagesCollide(tileImg,x*32-scroll,y*32,playfield(level,offset+x,y),playerImg,playerX,playerY,0) Then nomove = 1 End If Next Next If nomove = 1 playerX = playerX - playerU playerY = playerY + playerZ playerU = 0 playerZ = 0 scroll=Savescroll offset=Saveoffset End If For x=0 To 25 For y=0 To 15 If playfield(level,offset+x,y) >0 Then DrawImage tileImg,x*32-scroll,y*32,playfield(level,offset+x,y) End If Next Next If playerY < 0 Then playerY = 0 If playerY > 480 Then playerY = 480 If playerX > 768 Then playerX = 768 If playerX < 0 Then playerX = 0 DrawImage playerImg,playerX,playerY Flip Cls Wend FreeImage titleImg FreeImage playerImg End Bye. |
| ||
Hi try this great tileengine from the blitz2d samples folder(i donīt know who coded this). I have added a few lines of collisionscode Bye Henrik Const width=640,height=480 Const map_width=96,map_height=48 Global tiles Dim map(map_width,map_height) Graphics 640,480 SetBuffer BackBuffer() CreateTiles() CreateMap() ;stars=LoadImage( "graphics/stars.bmp" ) max_x=map_width*32-width max_y=map_height*32-height While Not KeyDown(1) If KeyDown( 203 ) scroll_x=scroll_x-8:If scroll_x<0 Then scroll_x=0 Else If KeyDown( 205 ) scroll_x=scroll_x+8:If scroll_x>max_x Then scroll_x=max_x EndIf If KeyDown( 200 ) scroll_y=scroll_y-8:If scroll_y<0 Then scroll_y=0 Else If KeyDown( 208 ) scroll_y=scroll_y+8:If scroll_y>max_y Then scroll_y=max_y EndIf Cls ;TileBlock stars,-scroll_x/2,-scroll_y/2 RenderMap( scroll_x,scroll_y ) Color 200,0,0 Text 220,200,"Move your mouse and scroll with arrows" Line MouseX(),MouseY()-10,MouseX(),MouseY()+10 Line MouseX()-10,MouseY(),MouseX()+10,MouseY() If map(((MouseX()+scroll_x)/32),((MouseY())+scroll_y)/32)=0 Text 320,240,"collision" Flip Wend End Function RenderMap( x_offset,y_offset ) ty=y_offset/32 sy=-(y_offset Mod 32) While sy<height ty=ty Mod map_height tx=x_offset/32 sx=-(x_offset Mod 32) While sx<width DrawImage tiles,sx,sy,map( tx Mod map_width,ty ) tx=tx+1:sx=sx+32 Wend ty=ty+1:sy=sy+32 Wend End Function Function CreateMap() Color 255,255,255 Rect 0,0,map_width,map_height Color 0,0,0 Rect 1,1,map_width-2,map_height-2 Color 255,255,255 Text map_width/2,map_height/4,"YEEEHHHAAA!",1,1 Text map_width/2,map_height/2,"ALLRIGHTY!",1,1 Text map_width/2,map_height*3/4,"TILEMAPDEMO",1,1 For x=0 To map_width-1 For y=0 To map_height-1 GetColor x,y If ColorRed()>0 Then map(x,y)=0 Else map(x,y)=1 Next Next End Function Function CreateTiles() tiles=CreateImage( 32,32,2 ) Color 128,128,128 Rect 0,0,32,32 Color 192,192,192 Rect 0,0,31,1:Rect 0,0,1,31 Color 32,32,32 Rect 31,1,1,31:Rect 1,31,31,1 GrabImage tiles,0,0,0 Color 0,0,0 Rect 0,0,32,32 For k=7 To 31 Step 16 Color 192,192,192 Rect k,0,1,32 Color 32,32,32 Rect k+1,0,1,32 Next For k=7 To 31 Step 16 Color 192,192,192 Rect 0,k,32,1 Color 32,32,32 Rect 0,k+1,32,1 Next GrabImage tiles,0,0,1 End Function |
| ||
Nice one, Henrik. Another couple of ideas for you, Zarwan.... Using something like the above code, you can just think of your player's position in terms of x and y on a big (larger than screen) play area. Makes things a lot less melon twisting. To keep your player centre, screen; map\x=player\x-screenwidth/2 mapy\y=player\y-screenheight/2 origin 0,0 render_map(map\x,map\y) origin -map\x,-map\y draw your player and all the baddies at their x,y positions. Now all the game objects scroll with the map for little effort. You could also write a function to test a graphic for a precise collision with the map. Function figures out which map blocks the graphic will overlap with (e.g: if graphic has same side length as map blocks, it will overlap max 4 blocks) then do the images collide bit. |