מסך פתיחה
שיעור 20 מתוך 21 בקורס משחק Unity: מסלולי שמיים של Coddy.
למשחק יש התחלה: הוא נפתח במסך כותרת עם השם, הניקוד הגבוה ביותר וההנחיה לקפוץ כדי להתחיל. הדרך נשארת ללא תנועה והמקשים לא עושים דבר עד שמקש קפיצה (Space או W) מתחיל את הריצה.
לשם כך דרוש מצב נוסף לצד over: running. הוא מתחיל כ-false, קפיצה משנה אותו ל-true, ו-GameOver משנה אותו שוב ל-false. \n בהודעה מתחיל שורה חדשה:
messageText.text = "My Game\nBest: " + PlayerPrefs.GetInt("BestScore", 0) + "\nPress to start";כל מה שב-Update שמניע את המשחק מופיע אחרי if (!running) return;, כך שבמסך הכותרת שום דבר לא זז.
אתגר
בינוניפתח את המשחק במסך פתיחה שממתין לקפיצה.
- ב־
GameManagerהוסףpublic bool running;. ב־Start הגדרspeed = 0fואתmessageText.text = "Sky Lanes\nBest: " + PlayerPrefs.GetInt("BestScore", 0) + "\nJump to run";. - ב־Update, לחיצה על Space או W כאשר
!running && !overמגדירה אתrunning = trueומציגה הודעה ריקה; לאחר מכןif (!running) return;. - התחל את GameOver עם
if (!running) return;ועםrunning = false;. - ב־
Runner, קרא את המקשים ובדוק את הטריגרים רק כאשרgame.running.
לחץ על "שחק": מסך הפתיחה ימתין עד שתקפוץ. לאחר מכן לחץ על "בדיקה".
נסו בעצמכם
using UnityEngine;
public class Runner : MonoBehaviour
{
public float laneWidth = 2.5f;
public float laneSpeed = 16f;
public float jumpHeight = 1.6f;
public float gravity = -40f;
public float slideTime = 0.7f;
public float magnetTime = 8f;
public int lane;
public float magnet;
public bool shield;
private CharacterController controller;
private GameManager game;
private Renderer body;
private float fallSpeed;
private float slide;
private Color color;
void Start()
{
controller = GetComponent<CharacterController>();
game = FindFirstObjectByType<GameManager>();
body = GetComponent<Renderer>();
color = body.material.color;
}
void Update()
{
if (!game.over)
{
if (Input.GetKeyDown(KeyCode.A) || Input.GetKeyDown(KeyCode.LeftArrow)) lane = Mathf.Max(-1, lane - 1);
if (Input.GetKeyDown(KeyCode.D) || Input.GetKeyDown(KeyCode.RightArrow)) lane = Mathf.Min(1, lane + 1);
bool jump = Input.GetKeyDown(KeyCode.W) || Input.GetKeyDown(KeyCode.UpArrow) || Input.GetKeyDown(KeyCode.Space);
if (jump && controller.isGrounded)
{
fallSpeed = Mathf.Sqrt(jumpHeight * -2f * gravity);
StopSlide();
}
if ((Input.GetKeyDown(KeyCode.S) || Input.GetKeyDown(KeyCode.DownArrow)) && controller.isGrounded)
{
slide = slideTime;
Resize(0.5f);
}
}
if (slide > 0f)
{
slide -= Time.deltaTime;
if (slide <= 0f) StopSlide();
}
if (magnet > 0f) magnet -= Time.deltaTime;
if (controller.isGrounded && fallSpeed < 0f) fallSpeed = -2f;
fallSpeed += gravity * Time.deltaTime;
float targetX = lane * laneWidth;
float x = Mathf.MoveTowards(transform.position.x, targetX, laneSpeed * Time.deltaTime);
Vector3 move = new Vector3(x - transform.position.x, fallSpeed * Time.deltaTime, 0f);
controller.Move(move);
body.material.color = shield ? new Color(0.3f, 0.9f, 1f) : color;
ShowPower();
}
void StopSlide()
{
if (transform.localScale.y < 1f) Resize(1f);
slide = 0f;
}
void Resize(float height)
{
controller.enabled = false;
transform.position += Vector3.up * (height - transform.localScale.y);
transform.localScale = new Vector3(1f, height, 1f);
controller.enabled = true;
}
void ShowPower()
{
string text = "";
if (magnet > 0f) text = "Magnet " + Mathf.CeilToInt(magnet);
if (shield) text += (text == "" ? "" : " ") + "Shield";
game.powerText.text = text == "" ? " " : text;
}
void OnTriggerEnter(Collider other)
{
if (game.over) return;
if (other.CompareTag("Obstacle"))
{
if (shield)
{
shield = false;
Destroy(other.gameObject);
return;
}
game.GameOver();
}
else if (other.CompareTag("Coin"))
{
game.AddCoin();
Destroy(other.gameObject);
}
else if (other.CompareTag("Magnet"))
{
magnet = magnetTime;
Destroy(other.gameObject);
}
else if (other.CompareTag("Shield"))
{
shield = true;
Destroy(other.gameObject);
}
}
}
כל השיעורים ביחידה משחק Unity: מסלולי שמיים
תרגלו בעצמכם: Unity אונליין