HusseinB
HusseinB

Reputation: 1341

Sprite kit side scrolling

I started working with Sprite kit and I Was wondering how can I create an infinite side scrolling game? I read the Sprite kit documentation and I read through the pre-processing of the scene. It's stated that we can readjust the scene's position in case the content is larger then the scene. I tried it and it works however, when I scroll through out the entire background image, I start seeing the default background of the scene. How can I create the infinite background? Can anybody point me to the right documentation or articles that talk about his issue? Thank you.

Upvotes: 11

Views: 11703

Answers (4)

Alexander Bourlotos
Alexander Bourlotos

Reputation: 91

My code example for this exact reference using SpriteKit and Swift is seen below.

func background1() {
        let backgroundTexture = SKTexture(imageNamed: "bg")

        //move background right to left; replace
        let shiftBackground = SKAction.moveByX(-backgroundTexture.size().width, y: 0, duration: 15)
        let replaceBackground = SKAction.moveByX(backgroundTexture.size().width, y:0, duration: 0)
        let movingAndReplacingBackground = SKAction.repeatActionForever(SKAction.sequence([shiftBackground,replaceBackground]))

        for var i:CGFloat = 0; i<3; i++ {
            //defining background; giving it height and moving width
            let background = SKSpriteNode(texture:backgroundTexture)
            background.position = CGPoint(x: backgroundTexture.size().width/2 + (backgroundTexture.size().width * i), y: CGRectGetMidY(self.frame))
            background.size.height = self.frame.height
            background.zPosition = -20
            background.runAction(movingAndReplacingBackground)

            self.addChild(background)
  1. create constant backgroundTexture created as an SKTexture with your image.
  2. create constants for moving your background to the left (shiftBackground) and for adding another instance of your background to the right side of your currently displayed one (replaceBackground)
  3. create constant (movingAndReplacingBackground) as an SKAction that repeats forever, setting the parameter of function repeatActionForever to a SKAction.sequence with your shiftBackground and replaceBackground constants referenced.
  4. create a loop that defines the definitions for your background. (for variable i, if amount of i is less than 3, increment i by one.
  5. in the loop, defend the texture, position, size, and zPosition (if sibling order is turned off) and then call your movingAndReplacingBackground as your action, which then iterates your sequence.
  6. finally, the last part of the loop is adding your background. It will perform this action any time there is less than 3 iterations of it. and as soon as your first background reaches far left of screen, it will remove the nodes to 2, therefore running the action in the loop over again.

I wrapped this in a function because for a parallax background, I was able to copy this function 4 times, rename the variables, change the "duration" for the shiftBackground constant, and get different speeds based on their distance.

I hope this helps! When Swift goes to Swift 3 this "C-Style" for loop will be deprecated, so I'm not sure how to fix that yet for the long term.

Upvotes: 1

JP Illanes
JP Illanes

Reputation: 3675

I've been working on a library for an infinite tile scroller, hopefully could be the starting point for a side scroller:

RPTileScroller

It's using a tableView-like delegate, so I hope is really easy to provide tiles, or any kind of node, to the scroller. I don't have any collision logic implemented yet, but I am planning on adding that also.

Upvotes: 0

Alexis C.
Alexis C.

Reputation: 4918

I did a generic composant called SKScrollingNode for this purpose as I usually add multiple scrolling backgrounds to achieve a parallax effect. Using it is pretty straightforward :

Declare it in your scene class

@property(strong,nonatomic) SKScrollingNode * clouds;

Create it and add it to the scene instance

self.clouds = [SKScrollingNode spriteNodeWithImageNamed:@"clouds"];
self.clouds.scrollingSpeed = .5; // Speed at which the clouds will scroll
[self addChild:clouds];

And in you scene 'update' method, just call

[self.clouds update:currentTime]

Done !

You can find the full code for the 'SKScrollinNode' composant here :

https://github.com/kirualex/SprityBird/blob/master/spritybird/Classes/Scenes/

Upvotes: 3

DogCoffee
DogCoffee

Reputation: 19966

Something like this should get you started:

Add the background images...

for (int i = 0; i < 2; i++) {
    SKSpriteNode * bg = [SKSpriteNode spriteNodeWithImageNamed:@"background"];
    bg.anchorPoint = CGPointZero;
    bg.position = CGPointMake(i * bg.size.width, 0);
    bg.name = @"background";
    [self addChild:bg];
}

In your update method.

[self enumerateChildNodesWithName:@"background" usingBlock: ^(SKNode *node, BOOL *stop) {
    SKSpriteNode *bg = (SKSpriteNode *) node;
    bg.position = CGPointMake(bg.position.x - 5, bg.position.y);

    if (bg.position.x <= -bg.size.width) {
        bg.position = CGPointMake(bg.position.x + bg.size.width * 2, bg.position.y);
    }
}];

This is from an example in RW his example used background image size of 1136 px.

Upvotes: 12

Related Questions