我使用了来自此问题SpriteKit Objective-C: programming directional pad controls的解决方案以及来自此处Correct way to create button in Sprite Kit?的自定义类按钮的版本,省略了目标操作方法,以便为我的SpriteKit游戏创建虚拟控制按钮。所以这就是问题所在:我想要实现的是两组彼此无关的独立按钮(例如,左边的D-pad和右边的fire按钮)以及同时使用它们的能力在多点触控的帮助下,就像在硬件控制器上一样,右侧有动作按钮,左侧是dirs。让我们想象一下情况:
1)我首先按住方向按钮和开火按钮。然后我将左手指拖到方向按钮之外,这会触发if(node.name)的ELSE语句,该语句将所有按钮的“选定”bool设置为NO。这不是我想要的,因为仍然保持着火按钮,它应该保持它的“选定”状态,而方向按钮则不应该。
2)同样的情况,但是如果我将右手指拖到防火按钮外面,并继续按住方向按钮。当按钮不应该执行时,两个按钮都会被“取消选择”。
那么如何通过检测方式正确实现它,哪个按钮完全“取消选择”以“取消选择”该特定按钮组?请把我推向正确的方向。希望我所要求的是可能的。
当前代码(相当混乱,请原谅大猩猩风格的编码):
DirectionalButton.h
#import <SpriteKit/SpriteKit.h>
@interface DirectionalButton : SKSpriteNode
@property (nonatomic) BOOL isEnabled;
@property (nonatomic) BOOL isSelected;
@property (nonatomic, readonly, strong) SKLabelNode *title;
@property (nonatomic, readwrite, strong) SKTexture *normalTexture;
@property (nonatomic, readwrite, strong) SKTexture *selectedTexture;
@property (nonatomic, readwrite, strong) SKTexture *disabledTexture;
- (instancetype)initWithTextureNormal:(SKTexture *)normal selected:(SKTexture *)selected;
- (instancetype)initWithTextureNormal:(SKTexture *)normal selected:(SKTexture *)selected disabled:(SKTexture *)disabled;
- (instancetype)initWithImageNamedNormal:(NSString *)normal selected:(NSString *)selected;
- (instancetype)initWithImageNamedNormal:(NSString *)normal selected:(NSString *)selected disabled:(NSString *)disabled;
@end
DirectionalButton.m
#import "DirectionalButton.h"
@implementation DirectionalButton
#pragma mark Texture Initializer
- (instancetype)initWithTexture:(SKTexture *)texture color:(UIColor *)color size:(CGSize)size {
return [self initWithTextureNormal:texture selected:nil disabled:nil];
}
- (instancetype)initWithTextureNormal:(SKTexture *)normal selected:(SKTexture *)selected {
return [self initWithTextureNormal:normal selected:selected disabled:nil];
}
- (instancetype)initWithTextureNormal:(SKTexture *)normal selected:(SKTexture *)selected disabled:(SKTexture *)disabled {
self = [super initWithTexture:normal color:[UIColor whiteColor] size:normal.size];
if (self) {
[self setNormalTexture:normal];
[self setSelectedTexture:selected];
[self setDisabledTexture:disabled];
[self setIsEnabled:YES];
[self setIsSelected:NO];
_title = [SKLabelNode labelNodeWithFontNamed:@"Arial"];
[_title setVerticalAlignmentMode:SKLabelVerticalAlignmentModeCenter];
[_title setHorizontalAlignmentMode:SKLabelHorizontalAlignmentModeCenter];
[self addChild:_title];
[self setUserInteractionEnabled:YES];
}
return self;
}
#pragma mark Image Initializer
- (instancetype)initWithImageNamedNormal:(NSString *)normal selected:(NSString *)selected {
return [self initWithImageNamedNormal:normal selected:selected disabled:nil];
}
- (instancetype)initWithImageNamedNormal:(NSString *)normal selected:(NSString *)selected disabled:(NSString *)disabled {
SKTexture *textureNormal = nil;
if (normal) {
textureNormal = [SKTexture textureWithImageNamed:normal];
}
SKTexture *textureSelected = nil;
if (selected) {
textureSelected = [SKTexture textureWithImageNamed:selected];
}
SKTexture *textureDisabled = nil;
if (disabled) {
textureDisabled = [SKTexture textureWithImageNamed:disabled];
}
return [self initWithTextureNormal:textureNormal selected:textureSelected disabled:textureDisabled];
}
#pragma -
#pragma mark Setter overrides
- (void)setIsEnabled:(BOOL)isEnabled {
_isEnabled = isEnabled;
if ([self disabledTexture]) {
if (!_isEnabled) {
[self setTexture:_disabledTexture];
} else {
[self setTexture:self.normalTexture];
}
}
}
- (void)setIsSelected:(BOOL)isSelected {
_isSelected = isSelected;
if ([self selectedTexture] && [self isEnabled]) {
if (_isSelected) {
[self setTexture:_selectedTexture];
[self runAction:[SKAction fadeAlphaTo:0.55 duration:0.12f]];
} else {
[self setTexture:self.normalTexture];
[self runAction:[SKAction fadeAlphaTo:1 duration:0.12f]];
}
}
}
@end
GameScene.m
- (void)createHUD {
//Executed in didMoveToView
NSString *pathToImageForLeftButtonTexture = @"buttonDirectionalLeft";
NSString *pathToImageForRightButtonTexture = @"buttonDirectionalRight";
dirBtnLeft = [[DirectionalButton alloc]initWithImageNamedNormal:pathToImageForLeftButtonTexture selected:pathToImageForLeftButtonTexture];
/*
Set size and position for left
*/
dirBtnLeft.name = @"directionalLeft";
dirBtnRight = [[DirectionalButton alloc]initWithImageNamedNormal:pathToImageForRightButtonTexture selected:pathToImageForRightButtonTexture];
/*
Set size and position accordingly to left button for right
*/
dirBtnRight.name = @"directionalRight";
dirBtnLeftFrame = [SKSpriteNode spriteNodeWithColor:[SKColor clearColor] size:dirBtnLeft.size];
dirBtnLeftFrame.position = dirBtnLeft.position;
dirBtnRightFrame = [SKSpriteNode spriteNodeWithColor:[SKColor clearColor] size:dirBtnRight.size];
fireBtn = [[DirectionalButton alloc]initWithImageNamedNormal:@"default.jpg" selected:@"default.jpg"];
/*
Set position and size for fire
*/
fireBtnFrame = [SKSpriteNode spriteNodeWithColor:[SKColor clearColor] size:fireBtn.size];
fireBtnFrame.position = fireBtn.position;
dirBtnRightFrame.position = dirBtnRight.position;
dirBtnLeftFrame.zPosition = 100;
dirBtnRightFrame.zPosition = 100;
fireBtnFrame.zPosition = 100;
dirBtnRight.zPosition = 99;
dirBtnLeft.zPosition = 99;
fireBtn.zPosition = 99;
dirBtnLeftFrame.name = @"directionalLeftFrame";
dirBtnRightFrame.name = @"directionalRightFrame";
fireBtnFrame.name = @"primaryFire";
[self addChild:dirBtnLeft];
[self addChild:dirBtnRight];
[self addChild:dirBtnLeftFrame];
[self addChild:dirBtnRightFrame];
[self addChild:fireBtn];
[self addChild:fireBtnFrame];
}
-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
[self touchesMoved:touches withEvent:event];
}
-(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
{
for(UITouch *touch in [event allTouches]){
CGPoint touchLocation = [touch locationInNode:self];
SKNode *node = [self nodeAtPoint:touchLocation];
if (node.name)
{
if ([node.name isEqualToString:@"directionalRightFrame"])
{
if(!dirBtnRight.isSelected){
[dirBtnRight setIsSelected:YES];
[dirBtnLeft setIsSelected:NO];}
}
else if ([node.name isEqualToString:@"directionalLeftFrame"])
{
if(!dirBtnLeft.isSelected){
[dirBtnRight setIsSelected:NO];
[dirBtnLeft setIsSelected:YES];}
}
else if ([node.name isEqualToString:@"primaryFire"]) {
if (!fireBtn.isSelected) {
[fireBtn setIsSelected:YES];
}
}
}
else
{
[dirBtnRight setIsSelected:NO];
[dirBtnLeft setIsSelected:NO];
[fireBtn setIsSelected:NO];
}}
}
-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
{
for (UITouch *touch in [event allTouches]) {
CGPoint touchPoint = [touch locationInNode:self];
SKNode *node = [self nodeAtPoint:touchPoint];
if(node.name){
if ([node.name isEqualToString:@"directionalLeftFrame"]) {
dirBtnLeft.isSelected = NO;}
else if ([node.name isEqualToString:@"directionalRightFrame"])
{
dirBtnRight.isSelected = NO;
}
else if([node.name isEqualToString:@"primaryFire"]){
fireBtn.isSelected = NO;}
} else
{
dirBtnLeft.isSelected = NO;
dirBtnRight.isSelected = NO;
fireBtn.isSelected = NO;}}
}
-(void)update:(CFTimeInterval)currentTime {
if(dirBtnLeft.isSelected){
//Do something
}
else if(dirBtnRight.isSelected){
//Do something else
}
else
{
//Stop doing anything
}
}
答案 0 :(得分:0)
在touchesEnded
中,您正在循环浏览SKScene中的所有活动内容。
[event allTouches]
返回所有活动的触摸。
而不仅仅是使用touches NSSet
来循环实际结束的触摸。
请在touchesMoved
和touchesEnded
中使用以下代码。
-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
{
for (UITouch *touch in touches) {
// Your conditions
}
}