LoginLogin

How do i do AABB collision on this program?

Root / Programming Questions / [.]

furcutieCreated:
Hi i am new to this site! And i have been following some tutorials online about this. I already know how a character moves, That's easy for me but I've been having trouble on the way of creating collision on this program. Can someone plz show me a short example on here? <3

There are several ways to do collision in SB. You can make your own custom collision with just regular code (like Separating Axis) or you can use some of the builtin SmileBASIC functions like SPHIT / SPHITRC I'm going to make a full collision detection tutorial using the builtin commands later today if you want to wait. Edit: oh sorry I just noticed you wanted axis-aligned bounding box. You can use math to do it manually if you want, but SPHIT and SPHITRC use AABB (I'm pretty sure) to detect collisions between sprites.

I would really appreciate it if you could do that for me. And don't worry it's alright maybe i should have been more clearer in my post. Also wouldn't you mind doing the tutorial and after you finish it, could you post here a example on how to make a aabb collision?<3

I would really appreciate it if you could do that for me. And don't worry it's alright maybe i should have been more clearer in my post. Also wouldn't you mind doing the tutorial and after you finish it, could you post here a example on how to make a aabb collision?<3
Do you want specifically AABB done manually or are you just trying to get a sprite to collide with tiles from a map? The tutorial will cover map collision (hopefully in a way that's easy to understand). Doing any collision detection manually is going to be much slower; SB isn't very fast, so you want to use the built-in functions as much as possible.

I just want to make sprites collide manually at the moment, with the aabb collision method. specifically 2 moving sprites, even tho i am open to new methods of doing things in this program. <3

I just want to make sprites collide manually at the moment, with the aabb collision method. specifically 2 moving sprites, even tho i am open to new methods of doing things in this program. <3
Oh two sprites? That's not bad:
'Setup two sprites
SPSET 0,856
SPSET 1,900

'Give them both a collision box. It's ID,Start,End,Width,Height,ScaleWithSprite,Mask.
'Collision is only detected if at least one bit is set in the same place in both masks.
SPCOL 0,0,0,16,16,TRUE,&HFFFFFFFF
SPCOL 1,0,0,16,16,TRUE,&HFFFFFFFF

'And this is all you need to check if those two are colliding
IF SPHITSP(0,1) THEN PRINT "HITTING";

'You can also check against a range
VAR HITTER=SPHITSP(0,1,100) 'Anything from 1 to 100 hitting 0?
IF HITTER>=0 THEN PRINT "HITTING ";HITTER

Thankyou! It actually works! But, not to be unappreciative of you taking your precious time here, but can you explain me how can i make a collision doing something that is similar to this kind of code for sprite collision?
IF X2<X+W AND X2+W2>X AND Y2<Y+H AND Y2+H2>Y THEN BEEP 

Thankyou! It actually works! But, not to be unappreciative of you taking your precious time here, but can you explain me how can i make a collision doing something that is similar to this kind of code for sprite collision?
IF X2<X+W AND X2+W2>X AND Y2<Y+H AND Y2+H2>Y THEN BEEP 
That IS what this is doing though. Like I said before, it's much slower to do it manually (and it's a waste of time) because SmileBASIC has this check built in. I'm sorry, I really suggest against doing this manually. This collision check is exactly what that is. If you need collision with an arbitrary rectangle rather than two sprites, SB provides that too:
IF SPHITRC(0,X,Y,W,H) THEN 'hitting rectangle at X,Y with width W,H
This is precisely what your kind of code collision is doing; you just don't have to do the check yourself. If you're absolutely dead-set on doing it manually, the code is long and slow:
SPOFS 0 OUT X,Y 'Get sprite X and Y
SPOFS 1 OUT X2,Y2 'The other sprite's position
SPCHR 0 OUT U,V,W,H 'Get sprite width and height (U,V is mandatory)
SPOFS 1 OUT U,V,W2,H2 'Other sprite's width/height
XM=X+W
YM=Y+H
X2M=X2+W2
Y2M=Y2+H2
IF XM>X2 && YM>Y2 && X<X2M && Y<Y2M THEN PRINT "HITTING"

(Don't forget SPHOME)

(Don't forget SPHOME)
Doesn't it default to the top-left corner? If so, it's fine right?

Doing SPHOME messes up the collision box. Also, i've been having a problem. The program doesn't read the hight and width of the sprites.( /,\) it still collides tho.. Here is the code:
ACLS

SPSET 0, 702

SPSET 1, 34
SPHOME 1, -100, -100

WHILE 1
H=500
W=500
W2=100
H2=100

SPOFS 0, X, Y
SPOFS 1, X2,Y2

SPOFS 0 OUT X,Y
SPOFS 1 OUT X2,Y2

SPCHR 0 OUT U,V,W,H
SPCHR 1 OUT U,V,W2,H2

BTN=BUTTON( )

IF BTN AND #RIGHT THEN X=X+1
IF BTN AND #LEFT THEN X=X-1
IF BTN AND #UP THEN Y=Y-1
IF BTN AND #DOWN THEN Y=Y+1

IF BTN AND #A THEN X2=X2+2
IF BTN AND #Y THEN X2=X2-2
IF BTN AND #X THEN Y2=Y2-2
IF BTN AND #B THEN Y2=Y2+2

IF X+W>X2 AND Y+H>Y2 AND X<X2+W2 AND Y<Y2+H2 THEN HIT=HIT+1
LOCATE 10, 10: PRINT HIT
VSYNC
WEND

Why do you have sphome -100 -100? Are you trying to move the sprite? If so, you use SPOFS instead (just without the OUT).
SPOFS 1,100,100 'Move sprite to 100 across, 100 down

Idk i though it was necessary. ( / b\) i found something weird that happend using SPHOME tho. The collision box of the second sprite, ( SPSET 1, 34) stayed at the corner of the screen but that's only when SPHOME is set, unless I've done a mistake. Also, this might sound dumb, but what's the difference between the out option? I understand it stands for output but doesn't SPOFS does the same thing without the out being written there? Also, I have another problem, what's wrong with my variables? when i change the variables that stand for the width and the height of the sprite, the collision box doesn't get bigger. When it's supposed to get bigger..sorry if i ask to much questions. <3

SPHOME sets the origin of the sprite's internal coordinate system, NOT its home position relative to the screen. By default, the origin is the top left corner of the sprite: This has implications for rotation and (maybe?) collision: if we rotate the sprite, it rotates around that corner point. Usually if we redefine the home, it's to the center or maybe in a platformer it can be useful to set it to the "feet" of a sprite. If you want to normalize everything to a screen coordinate, you'll have to account for it in SPOFS (perhaps with a CENTERX/Y constant)

A summary, as source code, of the suggestions in this thread
VAR W=16,H=16, W2=16,H2=16

SPSET 0,304,176,W,H
SPSET 1,32,16,W2,H2

SPCOL 0,0,0,W,H,TRUE,&HFFFFFFFF
SPCOL 1,0,0,W2,H2,TRUE,&HFFFFFFFF

VAR X,Y, X2,Y2
VAR HIT = 0
WHILE 1
  SPOFS 0 OUT X,Y
  SPOFS 1 OUT X2,Y2

  SPCHR 0 OUT ,,W,H
  SPCHR 1 OUT ,,W2,H2

  BTN=BUTTON( )
  IF BTN AND #RIGHT THEN SPOFS 0,X+1,Y
  IF BTN AND #LEFT THEN SPOFS 0,X-1,Y
  IF BTN AND #UP THEN SPOFS 0,X,Y-1
  IF BTN AND #DOWN THEN SPOFS 0,X,Y+1

  IF BTN AND #A THEN SPOFS 1,X2+1,Y2
  IF BTN AND #Y THEN SPOFS 1,X2-1,Y2
  IF BTN AND #X THEN SPOFS 1,X2,Y2-1
  IF BTN AND #B THEN SPOFS 1,X2,Y2+1


  'ignoring custom AABB for now
  IF SPHITSP(0,1) THEN INC HIT
  LOCATE 10,10:PRINT HIT
  VSYNC
WEND
SPHITSP should still work even if you change the SPHOME; I think not accounting for the origin offset may have broken your attempt.

SmileBASIC has an in-game manual that tells what each command does and how to use it. For instance, type SPOFS and click the little ? button above the right side of the keyboard and it'll tell you how to use it. Use the circle pad to scroll through the text and see new ways of using it. SPOFS moves a sprite to a location on the screen, as I'm sure you've seen. It can also give the position: this is the OUT version. For instance:
SPOFS 0,50,75 'Put sprite 0 at 50,75
SPOFS 0 OUT X,Y 'Get sprite 0 position and put in X,Y
PRINT X,Y 'Prints 50     75
This is true of most of the other sprite commands. For instance, as Lumage said, SPHOME sets the origin of the sprite. 12me21 was suggesting that we retrieve the origin as part of the collision check. You can set SPHOME just like SPOFS, and you can also get the values.
SPHOME 0,8,8 'Set the origin to the middle of a 16x16 sprite
SPHOME 0 OUT X,Y 'Get the origin of the sprite and put it in X,Y
PRINT X,Y 'Prints 8     8
I'm not sure what to say about the variables though.