Reputation: 223
I've created an app where images fall from the sky and I have to "catch" them on the bottom with a user-moveable basket. I put the falling images and the basket image in CGRectMake frames and used CGRectIntersectsRect to detect for collisions. However, it's not detecting every collision. For example, I'll have visually "caught" 10 objects, the two frames definitely intersected, but it will only say I caught 2. What am I doing wrong?
Here is the code for the bucket:
(void)viewDidLoad { [super viewDidLoad];
basketView = [[UIImageView alloc]
initWithImage:[UIImage imageNamed:@"bucket.png"]];
basketView.frame = CGRectMake(130.0, 412.0, 30.0, 30.0);
[self.view addSubview:basketView];
}
Here is the falling object and collision code:
- (void)onTimer
{
UIImageView* appleView = [[UIImageView alloc] initWithImage:appleImage];
int applePosition = round(random() % 320); //random starting x coord
double scale = 1 / round(random() % 100) + 1.0; //random apple size
double speed = 1 / round(random() % 100) + 1.0; //random apple speed
appleView.frame = CGRectMake(applePosition, -100.0, 25.0 * scale, 25.0 * scale);
[self.view addSubview:appleView];
[UIView beginAnimations:nil context:(__bridge void *)(appleView)];
[UIView setAnimationDuration:3 * speed];
appleView.frame = CGRectMake(applePosition, 500.0, 25.0 * scale, 25.0 * scale);
// Test for landing in bucket
if (CGRectIntersectsRect(basketView.frame, appleView.frame)) {
collision++;
printf("%i\n", collision);
[appleView removeFromSuperview];
}
}
EDIT: I made the basket huge, and now I'm getting spammed numbers and no apples are showing up. So I'm assuming that it's only checking for intersection with the apple at its starting point, not during the actual animation. How can I make it check for intersection DURING the animation?
Upvotes: 0
Views: 300
Reputation: 9231
Obviously if your timer function spawns new objects, the test will be done exactly after the creation of the object, so if the object is not actually created in the basket, your hit test will always be negative.
Now, you need another timer which will test for collisions every 10th of a sec or so (depending on how fast you move your objects, this could be more or less). An even better option (form the performance point of view) is to use CADisplayLink
which works pretty much like a timer only it allows you to synchronise your tests to the refresh rate of the display.
Upvotes: 1