如何降低SpriteKit场景中的UIView元素

时间:2014-11-23 05:48:42

标签: objective-c uiview uiimageview sprite-kit skview

我有一个常规的SpriteKit场景。事实上,它是从“Sprite Kit”创建的默认场景,它绘制了太空船。

我想在背景上画画。

我已经成功添加了一个UIImageView作为主skView的子视图。我可以用线条等来画这个。

但我似乎无法成功地将UIImageView放在主要的skview之后。

我该怎么做?这是我的示例代码。

(在UIImageView中,我每0.1秒只绘制一条随机行。)

@implementation GameViewController

- (void)viewDidLoad
{
    [super viewDidLoad];

    // Configure the view.
    SKView * skView = (SKView *)self.view;
//    skView.showsFPS = YES;
//    skView.showsNodeCount = YES;
    /* Sprite Kit applies additional optimizations to improve rendering performance */
    //skView.ignoresSiblingOrder = YES;

    // Create and configure the scene.
    GameScene *scene = [GameScene unarchiveFromFile:@"GameScene"];
    scene.scaleMode = SKSceneScaleModeAspectFill;

    [skView presentScene:scene];
}

-(void)viewWillLayoutSubviews{

    self.imageView = [UIImageView new];
    self.imageView.frame = self.view.frame;
    [self.view addSubview:self.imageView];
    [self startRepeatingTimer];
}

-(void)viewDidLayoutSubviews{

    // this doesn't work. was just trying it out.
    int i = [[self.view subviews] count];
    [self.view exchangeSubviewAtIndex:0 withSubviewAtIndex:i-1];

}

///// DRAW RANDOM LINES EVERY 0.1 SECONDS ON THE UIIMAGEVIEW SUBVIEW
- (IBAction)startRepeatingTimer {

    [self.repeatingTimer invalidate];
    self.repeatingTimer = [NSTimer scheduledTimerWithTimeInterval:0.1 target:self selector:@selector(drawOnImage:) userInfo:nil repeats:YES];
}

- (void)drawOnImage:(NSTimer*)theTimer {

    //setup
    float w = self.view.frame.size.width;
    float h = self.view.frame.size.height;

    UIGraphicsBeginImageContextWithOptions(self.view.frame.size,NO,0.0);
    [self.imageView.image drawInRect:CGRectMake(0, 0, w, h)];
    CGContextRef c = UIGraphicsGetCurrentContext();

    //draw
    CGContextMoveToPoint(c, drand48()*w,drand48()*h);
    CGContextAddLineToPoint(c, drand48()*w,drand48()*h);
    CGContextSetLineCap(c, kCGLineCapRound);
    CGContextSetLineWidth(c, 1.0f );
    CGContextSetRGBStrokeColor(c, drand48(), drand48(), drand48(), 1.0);
    CGContextStrokePath(c);

    // set the image
    self.imageView.image = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
}

1 个答案:

答案 0 :(得分:2)

这是一种SpriteKit友好的方式,可以在背景图像上绘制随机线条。基本步骤是

  1. 创建空白图片
  2. 将图像转换为SKTexture
  3. 使用纹理
  4. 创建一个精灵
  5. 在图像上绘制一条随机线
  6. 使用图像
  7. 更新精灵的纹理
  8. 等待0.1秒
  9. 迭代步骤4-6
  10. 在GameScene.m中,添加以下内容

    -(void)didMoveToView:(SKView *)view {
    
        self.scaleMode = SKSceneScaleModeResizeFill;
    
        // 1. Create an empty UIImage
        self.image = [self blankImageWithSize:view.frame.size];
        // 2. Convert the image to a texture
        SKTexture *texture = [SKTexture textureWithImage:_image];
        // 3. Create a sprite from the texture
        SKSpriteNode *sprite = [SKSpriteNode spriteNodeWithTexture:texture];
    
        // Center the sprite in the view
        sprite.position = CGPointMake(CGRectGetMidX(view.frame), CGRectGetMidY(view..frame));
        // Set zPosition such that the sprite is underneath other nodes
        sprite.zPosition = -1000;
        [self addChild:sprite];
    
        self.sprite = sprite;
    
        // 4. and 5. Create an SKAction that draw lines on the image and then update the
        // sprite's texture
        SKAction *drawAction = [SKAction runBlock:^{
            [self drawOnImage];
            _sprite.texture = [SKTexture textureWithImage:_image];
        }];
        // 6. create a 0.1 second delay
        SKAction *wait = [SKAction waitForDuration:0.1];
        SKAction *action = [SKAction sequence:@[drawAction,wait]];
    
        // 7. Iterate
        [self runAction:[SKAction repeatActionForever:action]];
    
        // Create a label and add it to the scene to show the image is
        // in the background
        SKLabelNode *myLabel = [SKLabelNode labelNodeWithFontNamed:@"Chalkduster"];
    
        myLabel.text = @"Hello, World!";
        myLabel.fontSize = 65;
        myLabel.position = CGPointMake(CGRectGetMidX(view.frame), CGRectGetMidY(view..frame));
    
        [self addChild:myLabel];
    
    }
    

    此方法会创建一个空白图像

    - (UIImage*) blankImageWithSize:(CGSize)size
    {
        UIGraphicsBeginImageContext(size);
        UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();
        return image;
    }
    

    此方法在图像上绘制线条

    - (void)drawOnImage {
    
        //setup
        float w = _image.size.width;
        float h = _image.size.height;
    
        UIGraphicsBeginImageContextWithOptions(_image.size,NO,0.0);
        [_image drawInRect:CGRectMake(0, 0, w, h)];
        CGContextRef c = UIGraphicsGetCurrentContext();
    
        //draw
        CGContextMoveToPoint(c, drand48()*w,drand48()*h);
        CGContextAddLineToPoint(c, drand48()*w,drand48()*h);
        CGContextSetLineCap(c, kCGLineCapRound);
        CGContextSetLineWidth(c, 1.0f );
        CGContextSetRGBStrokeColor(c, drand48(), drand48(), drand48(), 1.0);
        CGContextStrokePath(c);
    
        // set the image
        _image = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();
    }