一定の時間間隔の後に画面に入る UIImageView が 1 つと UIImageView の数があります。その 1 つの ImageView が他の ImageView と衝突しているかどうかを確認したいと思います。
私を助けてください。
長方形のビュー間の衝突を検出する一般的なプロセスはCGRectIntersectsRect()
、2 つのビューのフレームが交差するかどうかを確認するために使用します。したがって、オブジェクトがある場合は、NSMutableArray
それらUIImageView
を高速に列挙して衝突を探すことができます。たとえば、次のようになります。
for (UIView* view in self.imageViewsArray)
{
if (CGRectIntersectsRect(view.frame, viewToDetectCollisionWith.frame))
{
// do whatever you want when you detect the collision
}
}
または、enumerateObjectsUsingBlock
高速な列挙を使用する を使用できますが、1 つのステートメントで数値インデックスidx
と配列内の個々のUIView
オブジェクトの両方を取得できます。
[self.imageViewsArray enumerateObjectsUsingBlock:^(UIView *view, NSUInteger idx, BOOL *stop) {
if (CGRectIntersectsRect(view.frame, viewToDetectCollisionWith.frame))
{
// do whatever you want when you detect the collision
}
}];
元の答え:
UIImageView
さまざまな自動アニメーション技術を使用してオブジェクトをアニメーション化する場合は、iOS がアニメーションを処理しており、アニメーションの途中でさまざまなビューについてCADisplayLink
通知されないため、衝突をチェックするようなものを使用する必要があります。 frame
. はCADisplayLink
アニメーションが進行するたびにアプリに通知するため、アニメーションの進行に応じてビューの位置に関する情報を取得できます。組み込みのアニメーション技術を利用していないように聞こえますが、NSTimer
フレームを手動で調整するために a を使用しているため、以下のコードは必要ないかもしれません。ただし、より自動化されたアニメーションを追求する場合は、次の手法を使用できます。
できることはCADisplayLink
、アニメーションの進行中に a を使用して画面に関する情報を取得することです。
#import <QuartzCore/QuartzCore.h>
CADisplayLink *displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(displayLinkHandler)];
[displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSDefaultRunLoopMode];
ビューが表示されたり消えたりするときに追加および削除できるように、それをクラス プロパティに保存することもできます。
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
self.displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(displayLinkHandler)];
[self.displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSDefaultRunLoopMode];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
[self.displayLink removeFromRunLoop:[NSRunLoop mainRunLoop] forMode:NSDefaultRunLoopMode];
self.displayLink = nil;
}
その後、アニメーションを開始できます。ここでは、標準のブロック ベースのアニメーションを使用して、2 つの画像ビュー フレームの変化を継続的にアニメーション化していますが、アプリに適した操作を行うことは明らかです。
[UIView animateWithDuration:4.0
delay:0.5
options:UIViewAnimationOptionAutoreverse | UIViewAnimationOptionRepeat
animations:^{
self.imageView1.frame = ... // I set the frame here
self.imageView2.frame = ... // I set the frame here
}
completion:nil];
これで、これら 2 つのフレームがいつ衝突するか (つまり、それらのフレームが交差するかどうか) を、関連するプロパティを取得して「進行中」のフレーム座標を取得するこのCADisplayLink
ハンドラーで検出できます。presentationLayer
- (void)displayLinkHandler
{
id presentationLayer1 = self.imageView1.layer.presentationLayer;
id presentationLayer2 = self.imageView2.layer.presentationLayer;
BOOL nowIntersecting = CGRectIntersectsRect([presentationLayer1 frame], [presentationLayer2 frame]);
// I'll keep track of whether the two views were intersected in a class property,
// and therefore only display a message if the intersected state changes.
if (nowIntersecting != self.wasIntersected)
{
if (nowIntersecting)
NSLog(@"imageviews now intersecting");
else
NSLog(@"imageviews no longer intersecting");
self.wasIntersected = nowIntersecting;
}
}
ところで、Quartz 2D をQuartzCore.framework
プロジェクトに追加する必要がある場合があります。プロジェクト エディタのヘルプ を参照してください。