Unity, keep playing music on different scenes - unity3d

So I've been looking around and no solution seems to work to me...
I want to play some background music in all the scenes without resetting the audio.
I've a prefab with an audio source and a scritp.
the script does:
private void Awake()
{
GameObject[] objs = GameObject.FindGameObjectsWithTag("BGAudio");
if (objs.Length > 1)
Destroy(this.gameObject);
DontDestroyOnLoad(this.gameObject);
}
So I also tagged the prefab with BGAudio but when i change the scene it stops the music. If i add the prefab to both scenes it starts from 0..
I tried also doing a singleton but that doesn't work either.
I'm using unity 2019
I'm using an android build which i doesn't think it changes anything but just in case.

Just found out that DontDestroyOnLoad only works for objects on the root. While my Bgsound was inside a bg empty object.

You can also create a brand new scene that only includes your BGAudio object. Load both your BGAudio scene and play scene as additive.
For example: create a BGSound scene. Then create an empty gameobject called BGSoundManager. Also create your BGSound object. Then add a BGSoundManager script to your BGSoundManager gameobject and edit it like that :
private IEnumerator Start()
{
yield return SceneManager.LoadSceneAsync("BGSound", LoadSceneMode.Additive);
yield return SceneManager.LoadSceneAsync("Level1", LoadSceneMode.Additive);
Destroy(gameObject);
}

Related

Loading a scene in Unity twice causes some game objects to lose some components

When I hit play the game scene behaves as normal, even if I come from a different scene.
But when I am on the game scene and go to other scene and back again to the game scene some components from some game objects.
I am using SceneManager.LoadScene("SceneName"); to move around scenes, and every component was added in the editor and saved in the scene.
And as an example here is the Game Manager inspector at first load of game scene:
And second load of game scene:
Windows Controls is a script much like the others missing.
Am I doing something wrong?
Thanks in advance.
Without knowing what's going on inside the GameManager and the FoodManager scripts, I think you use the DontDestroyOnLoad similar what is showed on the bottom of the page, and your code destroys the scripts.
Simply put, I was short-sighted, I used a singleton pattern to access the managers and the way I did, at least, doesn't work in this context.
Any manager that I needed access I created a static instance, but since I checked for its existence elsewhere, the second time the component was destroyed.
public GameManager Instance {get; private set;}
void Awake()
{
if(Instance is not Null && Instance != this)
{
Destroy(Instance);
return;
}
Instance = this;
}
I realize that every time the scene loads the components are new objects, but I am still to understand why there is still copies of the old components.
I fixed it by using the [SerializeField] on any manager reference that I could and and manually adding them on the inspector, for some game objects that were instantiated at run time I pass the manager in a method.
GameManager gameManager;
public void Manager(GameManager _gameManager)
{
gameManager = _gameMananger;
}
GameObject gameObject = Instantiate(prefab);
gameObject.GetComponent<Script>().Manager(this);

Attaching prefab's script to another prefab as a component

I have Player prefab with script Player
Also I have GameController prefab with script TouchMove.
This is TouchMove code:
public class TouchMove{
[SerializeField] Player player;
.....
}
So TouchMove has player object as a component, which I attach through unity inspector.
TouchMove script is responsible for player movement. That is why it neads the player object.
Also I have a lot of scenes and each one contains GameController and Player objects.
When I modify the GameController or Player components I wanted the all game objects at the all scenes to be updated. That is why I decided to create prefabs: GameController prefab and Player prefab.
In inspector I added Player prefab to GameController prefab because TouchMove of GameController requares player object.
But after it when I run the game the player script gets not active. I mean that I get unable to move player in the game. (the player script gets not working)
This problem solves if I attach Player to GameController as just game objects (not the prefabs or without prefabs)
So, my questions:
why player scripts gets not working if I attach it with prefabs and it works if I attach just as game objects (without prefabs)
Is it possible to link two prefabs in the way I described?
The reason you are getting this problem is that player prefab and specific instance of the player prefab - are not the same object. They are both GameObject-s, and can both be referenced.
In your case GameController references a player prefab, but the player in the scene is a new object, which was created on scene start by CLONING the player prefab. Since it was created only on scene start - another prefab can never reference it.
To solve this, you can take couple approaches.
First, parent both player and game controller under 1 new object, call it GameManager for example. Then you will have only one prefab - game manager, that contains both player and controller.
Second option, the one I usually use, is to find the player object at load time. Instead of passing player s a public argument, find it on awake, for example like this:
private Player player;
void Awake() {
player = FindObjectOfType<Player>();
Assert.IsNotNull(player);
}
Prefabs need to exist (be instantiated) in scenes to function, what you're attempting to do is a workflow of scriptable objects.
Instead of attaching a source prefab from your project directories through the inspector, try looking for an existing instance of the prefab in the scene (at runtime).
private void Awake()
{
player = FindObjectOfType<Player>();
}

Unity3D - How can I detect collison between my car object and terrain?

I am working on a driving game for a project. My issue is that I'm unable to detect collision (I want to place the car to a checkpoint whenever it goes off the road) between the wheels of my car and the terrain. I tried to use this simple script but it does not seem to work:
using UnityEngine;
public class CarCollision: MonoBehaviour
{
private void OnCollisionEnter(Collision other)
{
if (other.collider.name == "Terrain")
{
Debug.Log("We got off the road!");
}
}
}
Is it a 2d game? If yes, use OnCollisionEnter2D instead of OnCollisionEnter.
Is the script attached to the gameobject?
Are you sure that the terrain has a collider which is not marked as trigger?
Try copying and pasting this same thing in the main controller.
I hope it worked. Don't forget to mark my answer as accepted if it worked!

playing particle system in Unity

I am using Unity3D to develop for the HTV Vive using SteamVR. I have downloaded an asset from the asset store with explosion effect created using a particle system. I want to play the particle animation when an object is destroyed. Here is the code I am, unsuccessfully, using.
private void OnDestroy() {
explosion.GetComponent<ParticleSystem>().Play();
}
Explosion is a public variable of type GameObject set from the inspector. I drop the particle system object there.
Why is it not working? anyone a good recommendation on a short tutorial to learn to use (not to create) particle effects?
Thanks
view of the hierarchy
I have tried this with the PS as a child of the target and as an independent object.
view of the inspector (Target)
view of the inspector (particle system)
edit: for some reason, the particle effect is destroyed right after the scene starts.
Try making the explosion effect into a prefab and instantiate it when destroyed.
GameObject explosion; // Prefab asset
private void OnDestroy() {
Instantiate(explosion, transform.position, Quaternion.identity);
}
Also, don't forget the stop action to Destroy.

Unity Game Stops On Load Same Scene Again

I have 7 scenes in my game. one of the scenes is "Playing" scene witch is my game play scene. in this game, one match includes 3 round. i save some of match data in "MatchManager" script that attached to MatchManager game object that have a singleton and don't destroy on load. other info are in a script(PSceneManager) that attached to a gameObject(PSceneManager) belong to "Playing" scene.
In the end of each round i change some data and then I Have To Load "Playing" scene again.
HERE IS MY PROBLEM: when it loads again it stops at very beginning and even don't enter "start" function (method).
(I have a singleton in PSceneManager scrip. I delete that and even check and looking for any other static value.(there were no more static variables))
I HAVE NO IDEA WHAT IS MY PROBLEM??!(any idea can be helpful)
HEEELP PLEASE...I'M STUCKS HERE...
I don't know exactly what the problem is. Some more information would be helpful.
If I would have had this problem I would look for the first and last moment the script still works.
Unity has already build this in for us. Just like Start() and Update() we have OnEnable() and OnDisable(). So if you add a Debug.Log() statement in those MonoBehaviour functions you know if the script and object are still active.
void OnEnable() { Debug.Log( gameobject.name + " is enabled" ); }
void OnDisable() { Debug.Log( gameobject.name + " is disabled" ); }
https://docs.unity3d.com/Manual/ExecutionOrder.html
I have faced the same problem, and I found that before the loading of the other scene again I changed the Time.timeScale to zero.
I solved the problem by reassigning its value in the start of any game object of the scene that stops.