Загрузка данных
using UnityEngine;
using TMPro;
public class CubeController : MonoBehaviour
{
[SerializeField] float jumpForce = 8f;
[SerializeField] float rotationSpeed = 100f;
[SerializeField] float raycastDistance = 0.8f;
[SerializeField] LayerMask groundLayer;
[SerializeField] int step = 5;
[SerializeField] int maxCubes = 300;
[SerializeField] float wallMargin = 0f; // отступ стенок от края камеры
Rigidbody2D rb;
SpriteRenderer sr;
TextMeshPro txt;
int number;
int birthFrame;
static int cubeCount;
static bool wallsCreated;
[RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.SubsystemRegistration)]
static void ResetStatics()
{
cubeCount = 0;
wallsCreated = false;
}
void Awake()
{
rb = GetComponent<Rigidbody2D>();
sr = GetComponentInChildren<SpriteRenderer>();
txt = GetComponentInChildren<TextMeshPro>();
if (rb == null || sr == null || txt == null)
{
Debug.LogError("На корневом Cube нужен Rigidbody2D, а внутри Visual (SpriteRenderer) и текст", this);
enabled = false;
return;
}
birthFrame = Time.frameCount;
cubeCount++;
if (!wallsCreated)
{
CreateWalls();
wallsCreated = true;
}
RandomizeColors();
UpdateText();
}
void OnDestroy() { cubeCount--; }
void Update()
{
// вращается только картинка, физика не меняется
sr.transform.Rotate(0, 0, rotationSpeed * Time.deltaTime);
if (Time.frameCount == birthFrame) return;
if (Input.GetKeyDown(KeyCode.Space) && IsGrounded())
Jump();
}
bool IsGrounded()
{
RaycastHit2D hit = Physics2D.Raycast(transform.position, Vector2.down, raycastDistance, groundLayer);
return hit.collider != null;
}
void Jump()
{
rb.linearVelocity = new Vector2(rb.linearVelocity.x, 0f);
rb.AddForce(Vector2.up * jumpForce, ForceMode2D.Impulse);
number += step;
RandomizeColors();
UpdateText();
SpawnClone();
}
void SpawnClone()
{
if (cubeCount >= maxCubes) return;
Camera cam = Camera.main;
if (cam == null) return;
Vector3 pos = cam.ViewportToWorldPoint(
new Vector3(Random.Range(0.1f, 0.9f), Random.Range(0.5f, 0.9f), 10f));
pos.z = 0f;
GameObject clone = Instantiate(gameObject, pos, Quaternion.identity);
clone.GetComponent<CubeController>().Init(number);
}
// невидимые стенки по левому и правому краю камеры
void CreateWalls()
{
Camera cam = Camera.main;
if (cam == null) return;
float halfH = cam.orthographicSize;
float halfW = halfH * cam.aspect;
float left = cam.transform.position.x - halfW + wallMargin;
float right = cam.transform.position.x + halfW - wallMargin;
float thickness = 1f;
float height = halfH * 6f;
MakeWall("WallLeft", new Vector2(left - thickness / 2f, 0f), new Vector2(thickness, height));
MakeWall("WallRight", new Vector2(right + thickness / 2f, 0f), new Vector2(thickness, height));
}
void MakeWall(string wallName, Vector2 pos, Vector2 size)
{
GameObject wall = new GameObject(wallName);
wall.transform.position = pos;
wall.AddComponent<BoxCollider2D>().size = size;
}
public void Init(int startNumber)
{
number = startNumber;
RandomizeColors();
UpdateText();
}
void RandomizeColors()
{
sr.color = Random.ColorHSV(0f, 1f, 0.7f, 1f, 0.8f, 1f);
txt.color = Random.ColorHSV(0f, 1f, 0.7f, 1f, 0.8f, 1f);
}
void UpdateText()
{
txt.text = number.ToString();
}
}