【问题标题】:How to remove or get the position of a certain node in SpriteKit?如何删除或获取 SpriteKit 中某个节点的位置?
【发布时间】:2014-01-16 20:49:39
【问题描述】:

我有一个用于 Mac 的精灵套件游戏,其中有多个精灵节点在屏幕上移动。我怎样才能做到removeFromParent某个节点? 例如,我有一个循环,每秒定期添加一个新节点:

-(void)spawnNew {
xPos = 100;
yPos = 1000;
CGPoint location = CGPointMake(xPos, yPos);
orb = [SKSpriteNode spriteNodeWithImageNamed:@"orb"];
orb.position = location;
orb.scale = 0.3;
orb.name = @"orbSprite";
CGFloat dirX = 0;
CGFloat dirY = -30;
CGVector vector1 = CGVectorMake(dirX, dirY);
SKAction *action = [SKAction moveBy:vector1 duration:0.1];
[orb runAction:[SKAction repeatAction:action count:100000]];
[self addChild:orb];

}

我将如何做到这一点,以便我能够获得位置或移除某些球体,而不是整个团队?例如,如果一个精灵的位置等于x=100, y=200,那么我会将它从父级中删除。目前,如果我尝试执行此操作并检查球体的位置,它只会检查要添加的最新球体的位置,而不是我想要的所有球体。

谢谢,我们将不胜感激。

【问题讨论】:

    标签: objective-c macos sprite-kit


    【解决方案1】:

    这可能不是最有效的答案,但它确实显示了您可以如何做到这一点。请记住,通常使用 Sprite Kit,您最终会得到很多节点,因此将它们分组在父级 SKNode 下是个好主意,它还可以指定树中的一个点,这样您就可以轻松地获得下面的子级它。 NSLog 语句仅用于测试/调试,我留下了,因为如果您尝试代码,它们可能会有所帮助。

    - (void)addOrbs {
        SKNode *orbRoot = [SKNode node];
        [orbRoot setName:@"ORB_ROOT"];
        [self addChild:orbRoot];
    
        for(int counter = 0; counter<5; counter++) {
            SKSpriteNode *newOrb = [SKSpriteNode spriteNodeWithColor:[SKColor redColor] size:CGSizeMake(20, 20)];
            [newOrb setPosition:CGPointMake(100, 100 + (100*counter))];
            NSLog(@"ORB POS: %@", NSStringFromCGPoint([newOrb position]));
            [newOrb setName:@"orbSprite"];
            [orbRoot addChild:newOrb];
        }
    }
    

    .

    - (void)removeOrbAtPoint:(CGPoint)point {
        SKNode *orbRoot = [self childNodeWithName:@"//ORB_ROOT"];
        NSArray *allOrbs = [orbRoot children];
        NSLog(@"ORBS: %@", allOrbs);
        for(SKNode *eachOrb in allOrbs) {
            if([eachOrb position].x == 100 && [eachOrb position].y == 200) {
                NSLog(@"REMOVING: %@ WITH POSITION: %@", [eachOrb name], NSStringFromCGPoint([eachOrb position]));
                [eachOrb removeFromParent];
            }
        }
    }
    

    使用快速块枚举删除的替代版本:

    - (void)removeOrbAtPoint_v2:(CGPoint)point {
        SKNode *orbRoot = [self childNodeWithName:@"//ORB_ROOT"];
        NSArray *allOrbs = [orbRoot children];
        NSLog(@"ORBS: %@", allOrbs);
        [orbRoot enumerateChildNodesWithName:@"orbSprite" usingBlock:^(SKNode *node, BOOL *stop) {
            if([node position].x == 100 && [node position].y == 200) {
                NSLog(@"REMOVING: %@ WITH POSITION: %@", [node name], NSStringFromCGPoint([node position]));
                [node removeFromParent];
            }
        }];
    }
    

    【讨论】:

      【解决方案2】:

      另一种方法 - 您可以将 removeFromParent 添加到操作序列中。这将在到达定义点时自动将其删除,无需额外代码。

      将您的moveBy: 操作更改为moveTo: 工作吗?

      SKAction *moveToFinish  = [SKAction moveTo:finishPoint duration:5.0];
      SKAction *removeMe = [SKAction removeFromParent];
      SKAction *actionSeq = [SKAction sequence:@[moveToFinish,removeMe]];
      [sprite runAction:actionSeq];
      

      我的 finishPoint 是由随机语句生成的,以赋予它一些变化。

      【讨论】:

        【解决方案3】:

        循环遍历要添加球体的节点或场景中的所有节点。

        for(SKNode * child in self.children) {
         ...
        }
        

        看看他们是否在这个盒子里。

        for(SKNode * child in self.children) {
           if(CGRectIntersectsRect(child.calculateAccumulatedFrame, CGRectMake(10, 50, 100, 200))) {
              ...        
           }
        }
        

        移除子元素(CGRectMake 以 x,y,width,height 为参数)

        for(SKNode * child in self.children) {
           if(CGRectIntersectsRect(child.calculateAccumulatedFrame, CGRectMake(10, 50, 100, 200))) {
              [child removeFromParent];       
           }
        }
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2012-03-10
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多