Hey,
I’m creating a 2D vertical endless runner as my first game. I’ve wrote a script to place 5 wall prefabs at each side of the screen and 3 background prefabs. The camera follows the player vertically (with some dampening) and so when a prefab enters and then leaves the screen, it’s moved above the highest prefab:
public class SceneBuilder : MonoBehaviour
{
public Transform lWall;
public Transform rWall;
public Transform bg;
private IList<Entry> lWalls = new List<Entry>();
private IList<Entry> rWalls = new List<Entry>();
private IList<Entry> bgs = new List<Entry>();
private float wallDistance = 3.75f;
void Awake()
{
for (int y = -2; y <= 2; y++)
{
lWalls.Add(new Entry { Prefab = (Transform)Instantiate(lWall, new Vector3(-wallDistance, y * lWall.localScale.y, 0.5f), Quaternion.identity) });
rWalls.Add(new Entry { Prefab = (Transform)Instantiate(rWall, new Vector3(wallDistance, y * rWall.localScale.y, 0.5f), Quaternion.identity) });
if (y > -2 && y < 2)
{
bgs.Add(new Entry { Prefab = (Transform)Instantiate(bg, new Vector3(0, y * bg.localScale.y, 3f), Quaternion.identity) });
}
}
}
void Update()
{
new List<IList<Entry>>() { lWalls, rWalls, bgs }.ForEach(CheckVisibility);
}
private void CheckVisibility(IList<Entry> entries)
{
foreach (var entry in entries)
{
if (!entry.BeenVisible && entry.Prefab.renderer.isVisible)
{
entry.BeenVisible = true;
}
if (!entry.WentInvisible && entry.BeenVisible && !entry.Prefab.renderer.isVisible)
{
entry.WentInvisible = true;
}
}
if (entries.Any(p => p.WentInvisible))
{
var entry = entries.Where(p => p.WentInvisible).OrderBy(p => p.Prefab.transform.position.y).First();
entry.BeenVisible = false;
entry.WentInvisible = false;
MovePrefab(entry.Prefab, entries.OrderByDescending(p => p.Prefab.transform.position.y).First().Prefab.transform.position.y);
}
}
private void MovePrefab(Transform prefab, float maxPos)
{
var height = prefab.transform.localScale.y;
if (height == 3)
{
prefab.transform.position = new Vector3(prefab.transform.position.x, maxPos + 3, prefab.transform.position.z);
}
else
{
prefab.transform.position = new Vector3(prefab.transform.position.x, maxPos + 8, prefab.transform.position.z);
}
}
private class Entry
{
public Transform Prefab { get; set; }
public bool BeenVisible { get; set; }
public bool WentInvisible { get; set; }
}
}
I want to know if there’s a better way to achieve the same results that I’m not aware of. I’m experienced with C# but I’m learning Unity’s API as I go so I could have missed something that would make things easier/optimal.