There are too many previous chapters. Switch to this chapter and jump to the previous chapter

Destroy player effects

  • Create a new empty gameobject
  • Added particle effect Paricle System
  • Open up Shape

Change the diffusion range to Circle and Radius to 0.3

  • Open up the Emission panel

人 民 : change the Rate over Time to 0, add count to the surrounding constant, the interval between 40 and 60 is 0.01 randomly, cancel loop, there is only one Time, (start speed) surge Time is 1.5, (Start lifetime) 2s,(start size) 0.1

  • Renderer specifies the (Material) Material
  • Modify hierarchy – display

The Renderer specifies the sorting layer as GUI

  • Change a color you like

Stored in preform

Instantiate the death effect

  • Open the object pool and create a list of objects to destroy

  • Open the ManagerVars script

Public GameObject deathEffect; Return object pool script, add

        for (int i = 0; i < initSpawnCount; i++)
        {
            InstantiateObject(vars.deathEffect, ref deathEffectList);
        }
Copy the code

Panel specifies the dead preformModify the position of the particle display

suspended

Scores increase

Next platform detected, score +1, broadcast an event code F12 with a score +Direct broadcast, direct does not applyPrivate GameObject lastHitGo = null;

The gameManager adds a listener

private int gameScore; Display game scoreGamePanelIn the script,awakeListening definition modifies the score event codeUpdateScoreTextAdd methods to update grades Remember to destroy, and then call broadcast every time the grade increases

  • Score increased by 2 at first run

(At the beginning of the platform, call method to judge, meet the platform is not equal condition, broadcast the event)

Add a judgment, the first time no result return out, specify the object assignment, otherwise always return out, no result add (hair~)

lastHitGo = hit.collider.gameObject;

Platform drop

PlatformSpawner script adds a method to update the spawner drop time

Private void the Update () {if (GameManager. Instance. IsGameStarted && GameManager. Instance. IsGameOver = = false) / /, No end {UpdateFallTime(); }}Copy the code

Defined in the UpdateFallTime method

// </summary> public int milestone =10; public float fallTime; public float minFallTime; Public float multple; / / coefficientCopy the code

methods

/// </summary> private void UpdateFallTime() {if (GameManager. Instance. GetGameScore () > milestoneCount) / / is greater than the milestone, update the falling time {milestoneCount * = 2; fallTime *= multple; if (fallTime<minFallTime) { fallTime = minFallTime; }}}Copy the code

returnplatformSpawnerScript resolves the error and adds fallTimeReturn PlatformSprite script, definition private Rigidbody2D my_body;Get the component in Awake. Set the initial drop time 2, minimum 0.5 and coefficient 0.9 in the panel Platforms fall off the page before the game even runs

Fixed the platform drop timing Bug

  • Increase the judgment

The scriptPlayControllerDefine the conditions for determining whether or not to moveprivate bool isMove=false; // Whether the player movesWhen a touch screen is detected, if the player does not move, set to True and broadcast the event code PlayerIsMove for the player movement.

  • Listen in the gameManagerpublic bool PlayerIsMove { get; set; }

EventCenter.AddListener(EventDefine.PlayerIsMove,PlayerMove); PlayerMove method PlayerIsMove = true destroyed EventCenter. RemoveListener (EventDefine PlayerIsMove, PlayerMove);

  • PlatformSprite

In the update method, make a judgment

if (GameManager.Instance.IsGameStarted == false|| GameManager.Instance.PlayerIsMove==false) return;
Copy the code

The third judgment is that the game is over

The platform is too far from the camera

Random generation of diamonds

First, take the Sprite renderer of the diamond, add layers, labels, colliders, and rigid body components to it and define the Z-axis so that the object doesn’t rotate, and set it up as a prefab Object poolingObjectPool, defineprivate List<GameObject> diamondList = new List<GameObject>(); / / diamond, go to the scriptManagerVarsAdd container: eat diamond field inpublic GameObject diamondPre;Initialize it into the object pool and add the method to get the diamond

for (int i = 0; i < initSpawnCount; i++)
        {
            InstantiateObject(vars.diamondPre, ref diamondList);
        }
Copy the code

Script PlatformSpawner, generates platform method in addition to diamond

Int ranSpawnDiamond = Random.Range(0,10); // spawndiamond int ranSpawnDiamond = Random. If (ranSpawnDiamond = = 6 & & GameManager. Instance. PlayerIsMove) {/ / is currently moving characters, Avoid the first step is to eat -- instantiate diamonds GameObject. Go = ObjectPool Instance. GetDiamond (); Go.transform. position = new Vector3(platformspawnPosition. x, platformspawnPosition. y+0.5f,0); go.SetActive(true); / / show}Copy the code

Test: preform given in panel

Eat a diamond

Add listeners to the PlayController script

// </summary> private void OnCollisionEnter2D(Collision2D Collision) // </summary> private void OnCollisionEnter2D(Collision2D collision) {if (collision. Starts. Tag = = "Picker") {/ / eat the diamond - hidden collision. GameObject. SetActive (false); Broadcast(EventDefine.AddDiamond); }}Copy the code

Add diamond to GameManager script Private int gameDiamond; AddListener(EventDefine.AddDiamond, AddGameDiamond); Destroyed,

// </summary> private void AddGameDiamond() {gameDiamond++; EventCenter.Broadcast(EventDefine.updateDiamondText,gameDiamond); // The number of diamonds broadcast out}Copy the code

Display in the UI panel, willgamePanelScript to listen to the diamond modification method Testing:

Create the finished interface

Create a script that ends the game PlayControllerIn the scriptTesting:

The bug directly shows that the effect is not good, I change the following 1.5 to 1s delay, the following modification is because.

  • Note that the third death (the one where the camera doesn’t follow the object) is slower

Ctrip delay time must be less than the platform drop time, otherwise cannot open end, into a loop state Can be!

  • In addition to the use of listening mode display, the previous use of instantiation mode

The panel display of this script was removed because it was already written in the GameOver script

Change the particle level to match the game level, and resolve the position of the end panel

To a game

The reload scene is introducedusing UnityEngine.SceneManagement; SceneManager.LoadScene(SceneManager.GetActiveScene().name); // Load the pageRecreate the script

Store panel

Empty objects serve as content, covered with parent objects, and are slippable areasI’m going to hide the parent object

The child object is the same width as the parent object so that the drag is complete, the anchor point is on the left, the Pivot x is 0, and the slide is on the left

Tip: Error (weird – the object has no skin), a change was made here in the video to clear the image component, do not clear the error (you need to clear the image on the empty object)

The formation of regular skin

Generate the ShopPanel script and get all the skins and preforms in the ManagerVars scriptpublic List<Sprite> skinSpriteList = new List<Sprite>(); public GameObject skinChooseItemPre; Test: drag preform on panel, skin

The width is set by default, if excess skin appears ~~

Parent. GetComponent < RectTransform > (.) sizeDelta = new Vector2 ((vars. SkinSpriteList. Count + 2) * 160302); // Set the width to 0 by default

Determine the size of the currently selected skin

Sliding size of skin

Using DoTween requires the introduction of the namespace using DG.Tweening;

Public List

skinNameList = new List

(); The skin’s name panel defines four names: Ang Gru, Ninja Hobbit and zombie

Add fields to the ShopPanel scriptprivate Text txt_Name; methods

/// </summary> private void RefreshUI(int selectIndex) {txt_name.text = vars.skinNameList[selectIndex]; }Copy the code

Back button

  • defineprivate Button btn_Back;
  • Initialize the awake,btn_Back = transform.Find("btn_Back").GetComponent<Button>();

btn_Back.onClick.AddListener(OnBackOnClick);Display MainPanel so, first go to MainPanel modify, add listening methodRemove the monitorRemove the monitor

Data classes

GameData script, set get

Data storage and reading, serialization and deserialization

Write in GameManagerInstantiated in the awake methoddata = new GameData();

Initialize game data

defineprivate ManagerVars vars;Initialize thevars = ManagerVars.GetManagerVars();

/// </summary> private void InitGameData() {// Read data (); // If (data! =null) {isFirstGame = data.getisFitstGame (); } else { isFirstGame = true; } if (isFirstGame) { isMusicOn = true; bestScoreArr = new int[3]; selectSkin = 0; / / the first skin skinUnlocked = new bool [vars. SkinSpriteList. Count]; // Array length skinUnlocked[0] = true; // Ununlocked first diamondCount = 10; / / diamond Save (); } else { isMusicOn = data.GetIsMusicOn(); bestScoreArr = data.GetBestScoreArr(); selectSkin = data.GetSelectSkin(); skinUnlocked = data.GetSkinUnlocked(); diamondcount = data.GetDiamondcount(); }}Copy the code

The store

Skin ununlocked set to grayMall determines whether the skin is unlockedMall page display, if locked, display the purchase button

Please note that there is no Button control in the previous creation.

Skin purchase

Diamond countAdd the Save() method to the ShopPanel and the script initializes the diamond counttxt_Diamond = transform.Find("Diamond/Text").GetComponent<Text>();The refresh method retrieves all diamonds and assigns valuestxt_Diamond.text = GameManager.Instance.getAllDiamond().ToString();You can define the price of the skin in the panel To set the current skin method, add a save method panel to add the purchased method

When judging the first game

Test: Disconnect run and start again

Player skin changes

At one point, the player is facing us, which is not correct. So skinSpriteList is all of the skins, redefine one// Player store-bought skins public List<Sprite> characterSkinSpriteList = new List<Sprite>();callspriteRenderer.sprite = vars.characterSkinSpriteList[skinIndex];To replace the skin, select the picture ending b from the skin collection in the panel

Disconnect and restart the game, need to re-select the skin, modify

Can no longer be called in the Awake method because the original game of the GameManage was played in the Awake method, creating a method receive that gets the skin

Open the mall to show the currently used skin

MainPanel scriptsThe shop panel shows that the currently selected skin should be -160Test: First run shows hermit skinLocates directly to the currently selected skin

Encountered a problem, the selection of skin is not determined, click the back button to re-enter the display is not the skin of the game, it is the skin I just slid without selection

That’s it, where the Start method can be dispensed with.

  • [Bug] The character jumps twice when clicking twice in a round

Prompt information
  • Prompt diamond insufficient, cannot purchase

Start from scratch, fade away Gray background use image, child text spread full screen, set color size, cancel Raycast Target not click on UI panelThe parent picture mount script (DoTween) implements animation effects using broadcast listeners to see if they can be purchasedPrompt script

using DG.Tweening; using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; public class hint : MonoBehaviour { private Image img_Bg; private Text txt_Hit; private void Awake() { img_Bg = GetComponent<Image>(); txt_Hit = GetComponentInChildren<Text>(); // Hide img_bg.color = new color (img_bg.color. r, img_bg.color. g, img_bg.color. b, 0); txt_Hit.color = new Color(txt_Hit.color.r, txt_Hit.color.g, txt_Hit .color.b, 0); AddListener<string>(EventDefine.Hint,Show); } private void OnDestroy () {/ / listen to radio - tooltip EventCenter. RemoveListener < string > (EventDefine. Hint, Show); } private void Show(string text) {private void Show(string text) { Transform. localPosition = new Vector3(0, -70,0); Transform.dolocalmovey (0,0.3f).oncomplete (()=> {// Start ctrip StartCoroutine("Dealy"); }); Img_Bg. DOColor (new Color (img_Bg. Color. R, img_Bg. Color. G, img_Bg. Color. B, 0.4 f), 0.1 f); Txt_hit.color (new Color(txt_hit.color. r, txt_hit.color. g, txt_hit.color. b, 1), 0.1f); } private IEnumerator Dealy() { yield return new WaitForSeconds(1f); The transform. DOLocalMoveY,0.3 (70 f); // Hide img_bg.docolor (new Color(img_bg.color. r, img_bg.color. g, img_bg.color. b, 0), 0.1f); Txt_hit.color (new Color(txt_hit.color. r, txt_hit.color. g, txt_hit.color. b,0), 0.1f); }}Copy the code

IEnumerable Dealy() used by Ctrip

Make a note of the problem

  • Using the previous method with the end method at that time is not effective

StartCoroutine(Dealy()); Ctrip StopCoroutine(Dealy()); It can’t be closed

Close it as a string

StartCoroutine(“Dealy”); StopCoroutine(“Dealy”); // Ctrip must be closed with quotation marks

Reset the game data screen

Home page adds reset button event

Hold down Alt+Shift on the side corner to zoom in

Reset game data

Making the Reset panel

  • Add the reset method to the gameManager script

  • ResetPanel script

using UnityEngine.SceneManagement; // Introduce naming

/ / / < summary > click on the button monitored YES / / / / / / < summary > private void OnYesButtonClick () {GameManager. Instance. ResetData (); / / to reload the current scenario SceneManager. LoadScene (SceneManager. GetActiveScene () buildIndex); </summary> private void OnNoButtonClick() {img_bg.docolor (new) Color(img_bg.color. r, img_bg.color. g, img_bg.color. b, 0), 0.3f); // Delegate - when the animation is finished, Transform.DOScale(Vector3. Zero, (0.3 f). The OnComplete () = > {/ / Broadcast event -- sound EventCenter. Broadcast (EventDefine. PlayClickAudio); gameObject.SetActive(false); }); }Copy the code

The preservation of the results, the highest score to obtain

// </param> public void SaveScore(int score) {// public void SaveScore(int score) {// public void SaveScore(int score) List<int> list = bestScoreArr.ToList(); / smallest to * * * * prompted for incoming comparison is (x, y) = > (x.Com pareTo (y)) * x, y comparison * * need from big to small, therefore a - number * / list. Sort ((x, y) => (-x.CompareTo(y))); bestScoreArr = list.ToArray(); //50 20 10 int index = -1; for (int i = 0; i < bestScoreArr.Length; i++) { if (score>bestScoreArr[i]) { index = i; If (index == -1) return; For (int I = bestScoreArr.Length-1; i>index ; I ++) {// Assign bestScoreArr[I] = bestScoreArr[I] -1; } bestScoreArr[index] = score; Save(); } /// <param name="score"></param> public int GetBestScore() {//Linq provides method return  bestScoreArr.Max(); }Copy the code

Modify the page

Results ranking interface

using DG.Tweening; using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; public class RankPanel : MonoBehaviour { private Button bg_btn; public Text[] txt_Scores; private GameObject go_RankList; private void Awake() { EventCenter.AddListener(EventDefine.ShowRankPanel,Show); bg_btn = transform.Find("bg_btn").GetComponent<Button>(); bg_btn.onClick.AddListener(OnImageButtonClose); go_RankList = transform.Find("RankList").gameObject; Bg_btn.getcomponent <Image>().color = new color (bg_btn.getComponent <Image>().color.r, bg_btn.GetComponent<Image>().color.g, bg_btn.GetComponent<Image>().color.b,0); go_RankList.transform.localScale = Vector3.zero; gameObject.SetActive(false); } public void Show() { gameObject.SetActive(true); Bg_btn.getcomponent <Image>().docolor (new Color(bg_btn.getComponent <Image>().color.r, Bg_btn. GetComponent < Image > () color. J g, bg_btn. GetComponent < Image > () color. B, f), 0.3 0.3 f); / / rotating go_RankList. Transform. DOScale (Vector3. One, 0.3 f); } private void OnDestroy() { EventCenter.RemoveListener(EventDefine.ShowRankPanel, Show); } private void OnImageButtonClose() {// hide bg_btn.getComponent <Image>().docolor (new Color) bg_btn.GetComponent<Image>().color.r, bg_btn.GetComponent<Image>().color.g, bg_btn.GetComponent<Image>().color.b,0), 0.3 f); Go_RankList. Transform. DOScale (Vector3. Zero, 0.3 f.) the OnComplete (() = > {gameObject. SetActive (false); }); }}Copy the code
  • Listening to the

EventCenter.AddListener(EventDefine.ShowRankPanel,Show); Add methods

public void Show() { gameObject.SetActive(true); Bg_btn.getcomponent <Image>().docolor (new Color(bg_btn.getComponent <Image>().color.r, Bg_btn. GetComponent < Image > () color. J g, bg_btn. GetComponent < Image > () color. B, f), 0.3 0.3 f); / / rotating go_ScoreList. Transform. DOScale (Vector3. One, 0.3 f); }Copy the code

Remove the monitor

 private void OnDestroy()
    {
       EventCenter.RemoveListener(EventDefine.ShowRankPanel, Show);
    }
Copy the code

Broadcast in the main panel

  • Update results

  • Performance display

Test game reset, leaderboard cleared

  • The game end panel displays the leaderboard

sound

Add the Audio Source component to the player’s prefab, and cancel open the script On Play On AwakePlayControllerTo defineprivate AudioSource m_AudioSource;Initialize them_AudioSource = GetComponent<AudioSource>();Play sound effects when you jump and fall Hit an obstacle, or better yetThe sound is specified in the panel

  • Creating a Sound Class

Add Audio Sound to GameManagerUnmount the initial play option

Sound class

using System.Collections; using System.Collections.Generic; using UnityEngine; // </summary> public class AudioSound: MonoBehaviour { private AudioSource m_AudioSource; private ManagerVars vars; private void Awake() { m_AudioSource = GetComponent<AudioSource>(); vars = ManagerVars.GetManagerVars(); EventCenter.AddListener(EventDefine.PlayClickAudio, PlayAudio); } private void OnDestroy() { EventCenter.RemoveListener(EventDefine.PlayClickAudio,PlayAudio); } private void PlayAudio() { m_AudioSource.PlayOneShot(vars.buttonClip); }}Copy the code

I’m going to click on the event to set up the broadcast,EventCenter.Broadcast(EventDefine.PlayClickAudio); // Broadcast event code -- sound

Turn sound off or on

Sets whether sound is enabled// Whether to enable sound effectspublic Sprite isMusicOn, isMusicOff;

  • The game change

Listen for button clicks to reset the sound

  • The game starts controller initialization listening

Pack and test it on your phone

Drag the icon up to adapt to other sizesGradle needs to be changed. No secret key signature

bug

During the game, the player backs away

Add back

That’s right, no return =-=

Write one yourself, application.quit (); Quit the game

Check the phone’s back button

At the end

Follow SKIN college teachers _Carson learning fun game creation xiexie (www.sikiedu.com/course/375)