Making the Blocks and Ball
Bull in a china shop » Devlog
Goal
The basic block in BICS causes a deduction of 20 from the player scores, flashes red, makes a sound, before it is Destroyed( ).
The ball used in BICS makes sounds upon the start of the level, pauses every-time it spawns for 3 seconds before it starts moving, and makes sounds when it hits anything. It also has only 3 lives (3 chances for respawn before a fail-state).
Code
Blue-block code:
using UnityEngine; using System.Collections; public class Block : MonoBehaviour { public AudioSource crashSource; public AudioSource punishment; private bool crashed; //this bool is used for starting timer for punishment sounds/animations public double duration = .3; //timer duration public int timeRemaining; public bool blockfinishCount; //to detect when the timer finish //timer components public GameObject penalty; //penalty text UI gameObject void Start() { crashSource = GetComponent<audiosource>(); penalty.GetComponent<spriterenderer>().enabled = false; //text is disabled crashed = false; //has not collided with ball blockfinishCount = false; } void OnCollisionEnter2D(Collision2D collisionInfo) { crashSource.Play(); punishment.Play(); Debug.Log("play sound"); crashed = true; //has collided Invoke("Begin", .3f); // ScoreCounter.scoreValue -= 20; TOTALscore.TotalscoreValue -= 20; TOTALscore.changeinscore += 20; // penalty.GetComponent<spriterenderer>().enabled = true; //text appears //The block turns red GetComponent<spriterenderer>().color = new Color(225f, 0f, 0f, 225f); //the ball cannot collide with the block again GetComponent<boxcollider2d>().enabled = false; } public void Begin() { if (timeRemaining == 0) { Debug.Log("block timer end"); blockfinishCount = true; GetComponent<spriterenderer>().enabled = false;//the block is not rendered, but script continue } } void Update() { if (crashed) { if (!crashSource.isPlaying)//if the sound finished playing after ball has collided { Debug.Log("finished playing sound!"); // Destroy the whole Block once the sound has finished Destroy(gameObject); } else { //animation of the text upwards until block is Destroyed penalty.transform.position += transform.up * 1f * 10 * Time.deltaTime; } } } }
The Ball script contains a timer for the pause after the spawn and connects to the text displaying the ball's 3 lives:
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; public class Ball_28feb : MonoBehaviour { // Movement Speed public float speed; //Timer components public int duration; public int timeRemaining; public bool isCountingDown; public bool finishCount; //spawn timer indication in level public GameObject SpawnText; Text spawn; //hitting feedback: this sound plays whoever it collider with anything public AudioSource mooSource; //display for Life number public GameObject LifeText; //"LifeCounter" is another script. I am fetching the bool from that script public LifeCounter thebool; float hitFactor(Vector2 ballPos, Vector2 racketPos, float racketWidth) { // ascii art: // // 1 -0.5 0 0.5 1 <- x value // =================== <- racket //this is from the code in the Arkanoid tutorial return (ballPos.x - racketPos.x) / racketWidth; } // Use this for initialization void Start() { GetComponent<rigidbody2d>().velocity = Vector3.zero; //ball is stationary at start mooSource = GetComponent<audiosource>(); thebool = LifeText.GetComponent<lifecounter>();//access the script called "lifecounter" in the "lifeText" gameObject isCountingDown = false; finishCount = false; spawn = SpawnText.GetComponent<text>();//text that only appears during spawn pause Invoke("Begin", 1f);//timer start once level start } void OnCollisionEnter2D(Collision2D col) { // Hit the Racket? if (col.gameObject.name == "racket") { // Calculate hit Factor float x = hitFactor(transform.position, col.transform.position, col.collider.bounds.size.x); // Calculate direction, set length to 1 Vector2 dir = new Vector2(x, 1).normalized; // Set Velocity with dir * speed GetComponent<rigidbody2d>().velocity = dir * speed; //play sound mooSource.Play(); Debug.Log("play moo"); } //Hit DespawnZone (a 2d collision area) if (col.gameObject.name == "DespawnZone") { Debug.Log("restart ball position"); transform.position = new Vector3(0, -240, 0);//teleport ball to spawn location GetComponent<rigidbody2d>().velocity = Vector3.zero;//ball stop moving Invoke("Begin", 1f);//timer start again for the length of spawn pause LifeCounter.lifeValue -= 1; thebool.haveplayedforthislife = false;//fetch bool to set it in this script //the bool controls whether or not sound can play when a life is deducted //being put here makes sure that the bool is on false so the sound will play once } } private void Update() { if (finishCount)//currently timer has finished and isn't counting down { GetComponent<rigidbody2d>().velocity = Vector2.down * speed; Debug.Log("Carry On"); finishCount = false; //reset the bool this.GetComponent<spriterenderer>().material.color = new Color(1.0f, 1.0f, 1.0f, 1.0f);//the ball is no longer semi-transparent SpawnText.GetComponent<text>().enabled = false; } if (isCountingDown) { GetComponent<rigidbody2d>().velocity = Vector3.zero;//ball still stop moving Debug.Log("pause"); } spawn.text = "Spawning in " + timeRemaining; } public void Begin()//called when timer is supposed to start { if (!isCountingDown) { isCountingDown = true; this.GetComponent<spriterenderer>().material.color = new Color(1.0f, 1.0f, 1.0f, 0.5f);//ball slightly transparent SpawnText.GetComponent<text>().enabled = true; timeRemaining = duration; Invoke("Cont", 1f); } } private void Cont() { timeRemaining--; if (timeRemaining > 0) { Invoke("Cont", 1f); } else { isCountingDown = false; finishCount = true; } } }
The ball's life counter is contained in another script:
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; using UnityEngine.SceneManagement; public class LifeCounter : MonoBehaviour { public static int lifeValue = 3; public float playerscore = 3; Text score; public GameObject Life1; public GameObject Life2; public GameObject Life3; //these are the sprites that each display a logo for one life public AudioSource nopeSource; private bool play;//this triggers the sound to play public bool haveplayedforthislife;//check if the sound has already been triggered for this particular life deduction void Start() { score = GetComponent<text>(); play = false; haveplayedforthislife = false; } // printed in ui void Update() { score.text = "Life " + lifeValue; playerscore = lifeValue; //now get it to game over if (lifeValue == 0) { if (!haveplayedforthislife)//not yet play sound { if (!nopeSource.isPlaying)//if sound is not playing { play = true;//sound is allowed to play haveplayedforthislife = true;//bool set to true } if (nopeSource.isPlaying)//currently playing sound { play = false;//sound not allowed to start again } } else { play = false;//no sound should play } Destroy(Life3); SceneManager.LoadScene("Death"); Debug.Log("YouDied"); } if (lifeValue == 2) { if (!haveplayedforthislife) { if (!nopeSource.isPlaying) { play = true; haveplayedforthislife = true; } if (nopeSource.isPlaying) { play = false; } } else { play = false; } Destroy(Life1); } if (lifeValue == 1) { if (!haveplayedforthislife) { if (!nopeSource.isPlaying) { play = true; haveplayedforthislife = true; } if (nopeSource.isPlaying) { play = false; } } else { play = false; } Destroy(Life2); } if (play)//if sound is supposed to play { nopeSource.Play(); Debug.Log("play nope"); if (nopeSource.isPlaying) { play = false;//reset bool } else //finished playing sound { haveplayedforthislife = true; Debug.Log("finish playing"); } } } private void OnLevelWasLoaded(int level) { lifeValue = 3;//reset life to 3 } }
That's all for this post! In the next and last post about BICS code, I'll share with you how popups work :)
Get Bull in a china shop
Bull in a china shop
A bull breaks into your China Shop!
More posts
- First time doing PopupsMar 14, 2020
- Score system, saving high-scores and reactive endingMar 14, 2020
- BICS postmortemMar 11, 2020
- BICS ver.1.3 OverviewMar 05, 2020
Leave a comment
Log in with itch.io to leave a comment.