私はこれを何時間も理解しようとしてきましたが、ここでは完全に途方に暮れています。ゲームにカスタムUIImageViewの一部を実装しようとしてUIPinchGestureRecognizer
いますが、機能しません。私が調査したすべてのことは、それが機能するはずだと言っていますが、そうではありません。ピンチをビューコントローラまたはカスタムUIViewに追加すると正常に機能しますが、UIImageViewsには追加できません。私はすべての一般的な修正と微調整を試しましたが、成功しませんでした。はいに設定しましたuserInteractionEnabled
。multipleTouchEnabled
デリゲートとセレクターを適切に設定しています。shouldRecognizeSimultaneouslyWithGestureRecognizer
YESを返すように設定しました。
ジェスチャレコグナイザーがUIImageViewに追加され、更新ループの後半でそのプロパティにアクセスできましたが、ピンチしようとしたときにセレクターのNSLogがUIImageViewに対して呼び出されることはありません。ビューのz位置を調整して、ビューが上にあるがサイコロがないことを確認しました。
私のUIImageViewsはNSMutableDictionaryに保存され、ゲームの各更新ループ中にループすることで更新されます。これは、UIPinchGestureRecognizerが呼び出されないことに影響を与える可能性がありますか?...他に何も考えられず、コードを投稿してもおそらく役に立たないでしょう-UIViewまたはViewControllerに使用した場合とまったく同じコードが機能するためです。
ビューコントローラのtouchesBeganイベントとtouchedMovedイベントにタッチ処理コードがあります...しかし、それをオフにしましたが、問題は解決せず、ピンチはとにかく他の要素で機能しました。
UIImageViewでジェスチャセレクターが起動するのを妨げる可能性のあるアイデアはありますか?辞書?ゲームループで絶えず更新されることと何か関係がありますか?どんなアイデアでも歓迎します、これは実装がとても簡単なようです...
編集:UIImageViewのコードとそれを使って何をしているのか...これが役立つかどうかはわかりません。
拡張UIImageViewクラスPaper.m(prpはstruct
、カスタム変数を初期化するために使用されるプロパティの1つです。
NSString *tName = [NSString stringWithUTF8String: prp.imagePath];
UIImage *tImage = [UIImage imageNamed:[NSString stringWithFormat:@"%@.png",tName]];
self = [self initWithImage: tImage];
self.userInteractionEnabled = YES;
self.multipleTouchEnabled = YES;
self.center = CGPointMake(prp.spawnX, prp.spawnY);
if (prp.zPos != 0) { self.layer.zPosition = prp.zPos; }
// other initialization excised
次に、NSMutableDictionaryを保持し、そのようにすべてのUIImageViewオブジェクトを初期化するObjManagerというカスタムクラスがあります。ここで、addObjは、各オブジェクトを追加するためにループで呼び出されます。
- (ObjManager*) initWithBlank {
// create an array for our objects
self = [super init];
if (self) {
objects = [[NSMutableDictionary alloc] init];
spawnID = 100; // start of counter for dynamically spawned object IDs
}
return self;
}
- (void) addObj:(Paper *)paperPiece wasSpawned:(BOOL)spawned {
// add each paper piece, assign spawnID if dynamically spawned
NSNumber *newID;
if (spawned) { newID = [NSNumber numberWithInt:spawnID]; spawnID++; }
else { newID = [NSNumber numberWithInt:paperPiece.objID]; }
[objects setObject:paperPiece forKey:newID];
}
ビューコントローラは、ObjManagerの初期化を呼び出します(VCでは_worldと呼ばれます)。次に、次のように_worldをループします。
// Populate additional object managers and add all subviews
for (NSNumber *key in _world.objects) {
_eachPiece = [_world.objects objectForKey:key];
// Populate collision object manager
if (_eachPiece.collision) {
[_world_collisions addObj:_eachPiece wasSpawned:NO];
}
// only add pinch gesture if the object flag is set
if (_eachPiece.pinch) {
UIPinchGestureRecognizer *pinchGesture = [[UIPinchGestureRecognizer alloc] initWithTarget:self action:@selector(pinchPaper:)];
pinchGesture.delegate = self;
[_eachPiece addGestureRecognizer:pinchGesture];
NSLog(@"Added pinch recognizer scale: %@", pinchGesture.view.description);
}
// Add each object as a subview
[self.view addSubview:_eachPiece];
}
_eachPieceは、ビューコントローラのオブジェクトであり、.hファイルで宣言されています(_worldと同様)。
@property (nonatomic, strong) ObjManager *world;
@property (nonatomic, strong) Paper *eachPiece;
次に、_world(ObjManager)内のすべての移動可能なPaperオブジェクト(UIImageViews)を次のようにフレームごとに更新するNSTimerオブジェクトがあります。
// loop through each piece and update
for (NSNumber *key in _world.objects) {
eachPiece = [_world.objects objectForKey:key];
// only update moveable pieces
if ((eachPiece.moveType == Move_Touch) || (eachPiece.moveType == Move_Auto)) {
CGPoint paperCenter;
paperCenter = eachPiece.center;
// a bunch of code to update paperCenter x & y for the object's new position based on velocity and user input
// determine image direction and transformation matrix
[_world updateDirection:eachPiece];
CGAffineTransform transformPiece = [_world imageTransform:eachPiece];
if (transformEnabled) {
eachPiece.transform = transformPiece;
}
// finally move it
[eachPiece setCenter:paperCenter];
}
}
そしてピンチセレクター:
- (void)pinchPaper:(UIPinchGestureRecognizer *)recognizer {
NSLog(@"Pinch scale: %f", recognizer.scale);
recognizer.view.transform = CGAffineTransformScale(recognizer.view.transform, recognizer.scale, recognizer.scale);
recognizer.scale = 1;
}
私の知る限り、ピンチは機能するはずです。同じピンチジェスチャコードをビューコントローラに追加するように設定すると、ビュー全体で機能します。また、境界線(ビューの周りに描かれた長方形)として機能するカスタムUIViewクラスがあり、ピンチジェスチャコードをそこに移動すると、境界線のみをピンチできます。