How to turn off user interaction of child node whe

2019-07-15 02:43发布

I have an SKNode that has user interaction enabled and I am adding an SKEmitterNode to that and I want the user interaction to be disabled for just the child. This code does not work.

SKNode* parentNode = [[SKNode alloc] init];
parentNode.userInteractionEnabled = YES;
NSString* path = [[NSBundle mainBundle] pathForResource:@"ABCDEFG" ofType:@"xyz"];
SKEmitterNode* childNode = [NSKeyedUnarchiver unarchiveObjectWithFile:path];
childNode.userInteractionEnabled = NO;
[parentNode addChild:childNode];

I also tried setting user interaction to NO after adding to the parent. Is this possible or do I need to add the emitter to the parent's parent somehow?

2条回答
够拽才男人
2楼-- · 2019-07-15 03:06

I achieved this by sending a notification from the parent, to its parent with the location of the tap. The function in the parent-parent spawns the emitter with user interaction disabled and the target of the emissions set to the parent. Perhaps some code is in order.

In the parent:

UITouch *touch = [touches anyObject];
// to get the location in the scene
CGPoint location = [touch locationInNode:[self parent]];
NSDictionary* locationDic = [NSDictionary dictionaryWithObjects:[NSArray arrayWithObjects: [NSNumber numberWithFloat:location.x],                                                                                          
                                                                                           [NSNumber numberWithFloat:location.y],
                                                                                           nil]
                                                        forKeys:[NSArray arrayWithObjects:@"loc_x", @"loc_y", nil]];
[[NSNotificationCenter defaultCenter] postNotificationName:@"Ntf_SpawnParticles"
                                                    object:nil
                                                  userInfo:locationDic];

In the parent's parent (the scene), register for the event:

[[NSNotificationCenter defaultCenter] addObserver:self
                                         selector:@selector(spawnParticles:)
                                             name:@"Ntf_SpawnParticles"
                                           object:nil];

Still in the parent's parent (the scene), implement "spawnParticles":

- (void)spawnRockDebris:(NSNotification *)ntf
{
    float x = [[[ntf userInfo] valueForKey:@"loc_x"] floatValue];
    float y = [[[ntf userInfo] valueForKey:@"loc_y"] floatValue];
    CGPoint location = CGPointMake(x, y);

    NSString* particlePath = [[NSBundle mainBundle] pathForResource:@"CoolParticles" ofType:@"sks"];
    SKEmitterNode* particleEmitterNode = [NSKeyedUnarchiver unarchiveObjectWithFile:particlePath];
    // set up other particle properties here
    particleEmitterNode.position = location;
    particleEmitterNode.userInteractionEnabled = NO;
    particleEmitterNode.targetNode = [self childNodeWithName:@"particleTargetNode"];
    [self addChild:particleEmitterNode];
}
查看更多
我欲成王,谁敢阻挡
3楼-- · 2019-07-15 03:26

I'm sure there is a better way (and hope there is!!), but its a start.

Maybe this is how it should be done. Problem is if you have an emitter over a sprite, the touch doesn't pass through (well didn't in my testing).

  -(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {

    for (UITouch *touch in touches) {

        UITouch *touch = [touches anyObject];
        CGPoint positionInScene = [touch locationInNode:self];
        SKSpriteNode *touchedNode = (SKSpriteNode *)[self nodeAtPoint:positionInScene];

        if (touchedNode.userInteractionEnabled) {
            NSLog(@"Name of node touched %@", touchedNode.name);
        }
        else {
            NSLog(@"Can't touch this! %@", touchedNode.name);
        }
    }
}
查看更多
登录 后发表回答