Welcome, Guest. Please login or register.
Did you miss your activation email?

Login with username, password and session length

 
Advanced search

878378 Posts in 32918 Topics- by 24332 Members - Latest Member: IrritumGame

May 21, 2013, 06:40:57 PM
TIGSource ForumsDeveloperTechnical (Moderators: Glaiel-Gamer, ThemsAllTook)What cells on a HashMap does my Rectangle occupy
Pages: [1]
Print
Author Topic: What cells on a HashMap does my Rectangle occupy  (Read 1069 times)
st33d
Guest
« on: September 21, 2010, 01:35:50 PM »

I've gone with (pos + extent - 1) in the past because a rectangle's area is somewhat like an array.

if an object is at x + width of your rectangle it does not intersect. It is in fact, sitting snugly next to it - but not intersecting.

So that means anything from x and up to x + width but not including x + width is an intersection.

If you're not buying this - consider arrays. An array of 3 width is [0,1,2], if you try to access the third slot you get an error. It's width only contains the contents. It's like the lid on a jar of jam (or jelly to you americans). You don't eat the lid do you? What? Stop eating the lid!

Anyway - that forms my problem.

I want to find out what cells I'm going to fit this rectangle into on my hashmap. The hashmap has regular size units in a grid larger than the rect and if I round down the top left hand corner of the rectangle I can find the first cell I'm going to populate. Obviously, because of intersections, a rectangle may be in more than one cell.

But what about the extent of the rectangle? How do I find out what cell is at less that x + width but not equal to or over? I'm sure there's simple logic for it but I can't think of it.

(first person to suggest subtracting 0.0001 off the width gets a slap)
Logged
Will Vale
Level 4
****


will@secondintention.com
View Profile WWW Email
« Reply #1 on: September 21, 2010, 03:04:24 PM »

If I understand it right, the problem is that you can't round down the other corner, because if the edge is spot on a cell boundary you want it in the lower cell, not the upper?

In which case, can you round up the lower right corner and then subtract one cell?

i.e. if N is a cell boundary, and x is in [0, 1), you get:

(N + x) -> (N + 1) ->   N     
(N + 0) ->    N    -> (N-1)

HTH,

Will
Logged
zacaj
Level 3
***


void main()


View Profile WWW Email
« Reply #2 on: September 21, 2010, 10:09:03 PM »

Wouldnt you just divide the topo left and bottom right by the width of the cells(if theyre square), and then round the resulting decimal up and down, respectively to get the cells?
Logged

My twitter: @zacaj_

Quote from: mcc
Well let's just take a look at this "getting started" page and see--
Quote
Download and install cmake
Noooooooo
bateleur
Level 10
*****



View Profile
« Reply #3 on: September 22, 2010, 12:55:56 AM »

Wouldnt you just divide the topo left and bottom right by the width of the cells(if theyre square), and then round the resulting decimal up and down, respectively to get the cells?

If I'm understanding you correctly, this doesn't work for the same reason that the naive approach doesn't work...

The "bottom right" is (x_position + width, y_position + height), but the object is the half open interval in each case. The endpoint is not included.

Now obviously st33d could just write some explicit conditional along the lines of "if my right and/or bottom edges are exactly on a cell boundary then subtract one", but what he's asking is whether there's an elegant expression he can use which avoids the need to do this.

(I think Will Vale's Math.ceil(x_position % cell_width)-1 does indeed achieve this.)
Logged

st33d
Guest
« Reply #4 on: September 22, 2010, 01:03:15 AM »

Thanks Will, Math.ceil() is indeed the answer.
Logged
Will Vale
Level 4
****


will@secondintention.com
View Profile WWW Email
« Reply #5 on: September 22, 2010, 02:07:46 PM »

Sweet, glad it helped!
Logged
BorisTheBrave
Level 10
*****


View Profile WWW
« Reply #6 on: September 22, 2010, 02:41:47 PM »

Steed, you look like a man in need of some mathematical formalism - you are explaining in over a sentence what should be a word.

0 <= x < 5 is the sort of space you are thinking your rectangle is occupying (in one dimension). This is a half open interval, because the bottom end of the interval is closed (i.e. contains its end point) and the top end is open. Half open intervals are the most common in programming.

Notationally, one uses square brackets for closed intervals, and parentheses for open, so youd write the same range as [0,5).

It's just a bit of notation, but it is useful. You can see several of the posters are using it, so I thought I'd point it out.
Logged
st33d
Guest
« Reply #7 on: September 22, 2010, 03:19:50 PM »

Point me to a paper please Boris, I'm having trouble grounding the word interval. I'm interesting in reading up on it though.
Logged
Zaphos
Guest
« Reply #8 on: September 22, 2010, 03:38:07 PM »

It's on wiki -- http://en.wikipedia.org/wiki/Interval_(mathematics)
Logged
BorisTheBrave
Level 10
*****


View Profile WWW
« Reply #9 on: September 24, 2010, 01:31:49 PM »

Wiki is correct, but hard to read, as usual.

An interval is just a range, i.e. the values of x such that  a <= x <= b, where a and b are two numbers, and those comparisons could be strict or not (which is the open/closed aspect i was talking about). It's very useful to consider AABBs in terms of a pair of half open intervals, i.e. a rectangle is a collection of points x,y s.t. a <=x < b and c<=y<d.
Two rectangles intersect if they have a point in common. It's clear from this treatment why adjacent rectangles are not considered to overlap.

You in particular will find it useful, as you are so far using off-by-one methods, and, judging from the other thread, are having difficulties adapting it to real numbers from integers.
Using the treatment I've described, I hope way becomes more clear. Rather than consider the range [a,b-1], you talk about the range [a,b). Rewrite all your integer algorithms in that form (you should find it is possible without ever adding or subtracting a unit, by being careful with <= vs <), and then it will work for reals, too.

E.g. your intersection algorith probably looks like this:

bool intersect(r1, r2)
{
  // Is the max of the r1 less than the min of r2 in the x axis?
  if(r1.x + r1.width - 1 < r2.x)
    return false;
  // etc...
}

Instead do

bool intersect(r1,r2)
{
  if(r1.x + r1.width <= r2.x)
    return false;
  // etc
}

It's clear in the above example that they are substantially the same, but try to keep in mind the underlying intervals [r1.x, r1.x+r1.width) and [r2.x, r2.x+r2.width), and how in the case r1.x+r1.width = r2.x they both go up to the same point, but only the second interval includes that point, so they are considered not to overlap.
Logged
st33d
Guest
« Reply #10 on: September 24, 2010, 02:46:33 PM »

Cheers Boris - I've got a foothold in understanding this now. I'm going to put this work up open source when I'm done and try to get some nit-picking in on it.

I'm very interested in rectangular collision - it forms a basis for a lot of platform games and it's a bit of a pet project of mine.
Logged
Pages: [1]
Print
Jump to:  

Theme orange-lt created by panic