I’m creating a 2D game and I have a problem - I don’t know how to make a looping animation of scrolling the background, that is, so that the background moves to the left all the time and does not end.
1 Answer
1One way this can be done is move the image until it has moved one full image width, then teleport it back so that it can keep scrolling. For the purposes of this example, I am scrolling the background to the left.
First, you need an image that can seamlessly repeat horizontally. Add this to the scene and set the Sprite Renderer Draw Mode to “Tiled”.

Set the Width to at least 2x the full width of the sprite. This will cause the image to repeat at least twice. In this example, the sprite I used was 56 units wide, so I set the width to 120.
Shift the image to the right so that the starting position is on the left side of the sprite.
This script will move the object every frame based on the speed parameter you set in the inspector. Once it detects that the image has moved one full sprite width, it resets the position. If you watch the game run while in Scene view (rather than Game view), you can see this behavior in action.
Attach this script to the Game Object that has the background sprite.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ContinuousBackgroundScroll : MonoBehaviour
{
[SerializeField] private float speed;
private float spriteWidth;
private float originX;
void Start()
{
originX = transform.position.x;
//This code gets the width of the sprite in world units.
//I'm assuming that there is no scaling done in the Transform.
SpriteRenderer sr = GetComponent<SpriteRenderer>();
Bounds spriteBounds = sr.sprite.bounds;
spriteWidth = spriteBounds.size.x;
}
void Update()
{
//Every frame, move the image too the left based on the speed and elapsed time
transform.Translate(-speed * Time.deltaTime, 0, 0);
//Once we have moved one full sprite width, jump back exactly one width.
//Since this is a tiled image, the pixels after the jump will be exactly
// the same as before the jump, so this jump is not noticable.
if(transform.position.x < (originX - spriteWidth))
{
transform.Translate(spriteWidth, 0, 0);
}
}
}
This can be modified to support vertical scrolling for a shmup instead of horizontal scrolling.
Hopefully this makes sense, please let me know if you have any questions.
