Player interaction between scripts and teleportation

Hey guys!

I have a couple of questions and i’m pretty new to coding, so bear with me.

In my game, the player moves around and collects “coins” and ultimately tries to reach an end point to advance onto the next level. I also want to add in some sort of teleporter which requires the player to have a certain score value in order to use.

Currently I have a script which contains my movement and score collection code, and I also have a teleporter script which identifies when then player enters and returns “Teleport!” in Console.

Question 1: Is it a better idea to have my movement, coin collection, teleporter, and most/all other player interactions on one script? I feel like that would make my game assets cleaner and would probably be easier to code?

Question 2: How do I go about coding the teleporter to translate the player to a specific location, and vise versa from the other side of the teleporter? Ultimately i’d love to be able to have multiple teleporters in a single level (each linked to a single “receiver”, so not like an interconnecting web) so how should I go about specifying which locations to translate too? (This is what makes me think individual scripts for each transporter would be better)

Question 3: (If I do individual scripts) Once I have the actual translation code done, how do I check the score value of the player to make sure its high enough? I was thinking I would do something along the lines on declaring the score as an independent variable (I think my terminology is off) so that I can access it from any script.

Well let me know what you guys think, any and all help is definitely appreciated!

Note The “Respawn” tag check is where my end point is going to advance to the next level.

Player

public class Player : MonoBehaviour {

    public float MoveSpeed = 4;
    public float RotateSpeed = 90;
   


    private int Score;
    private float gravity = 20.0F;

    // Use this for initialization
    void Start () {
        Score = 0;
    Debug.Log("You're current score is: " + Score);
   
    }
   
    // Update is called once per frame
    void Update () {
        transform.Translate(Vector3.forward * Time.deltaTime * (Input.GetAxis("Vertical") * MoveSpeed));
        transform.Rotate(Vector3.up  * Input.GetAxis("Horizontal") * RotateSpeed);
       


    }

    void OnTriggerEnter(Collider other)
    {
        if (other.gameObject.CompareTag("coin"))
        {
            other.gameObject.SetActive(false);
            Score += 1;
            Debug.Log ("You're score is now " + Score);
        }

        if (other.gameObject.CompareTag("Respawn"))
        {
            Debug.Log("Poof!");
           
        }
    }
}

Teleporter

public class TransporterScript : MonoBehaviour {


    // Use this for initialization
    void Start () {
   
    }
   
    // Update is called once per frame
    void OnTriggerEnter (Collider other) {
        if (other.gameObject.CompareTag("Player")) {
            Debug.Log("Teleport!");
        }
   
    }
}
  1. Use OOP, don’t put everything in 1 script; Unity is designed to allow for easy communication between scripts, makes things much more manageable.

  2. If you are talking about moving the existing player to a new scene, there are a few ways of doing this. I wrote an asset last year for this: Here. This bit really depends on what you are looking to do.

  3. To check the score, you would use an If statement to check if the value was equal to or greater than a value:

if(score=>200)
{
//Do some stuff
}

1/3) If I call Score >=200 on the teleporter script, will it read the value from the player script (where its being tracked)? wouldn’t I need to declare the variable within the teleporter script?

  1. I dont wanna move to a new scene, just a new location within the scene. for loading to a new scene id use application.LoadLevel right?

1/3) Yes, you will need a reference to the script (If it only exists once, I would recommend finding it in the scene programmatically).

  1. If you just need to move to a new area in the scene, you can do something like this:
public GameObject player;
public GameObject finalPosition;

void MyFunction()
{
player.position = finalPosition.position;
}

Or you can use a Vector3 for the position if you don’t want to represent it with a GO:

public GameObject player;
public Vector3 finalPosition;

void MyFunction()
{
player.position = finalPosition;
}

Again, if you want to find the player programmatically, I would recommend (if there is only 1), tagging it with the built-in tag of Player, and using:

private GameObject player;

void Start()
{
player.FindGameObjectsWithTag("Player");
}

Im having a hard time getting the FindGameObjectsWithTag function to work properly, but I was able to get a functioning teleporter up and running! thanks for the help!

public class TransporterScript : MonoBehaviour {

    public GameObject player;
    public GameObject finalPosition;

    private Vector3 offset;

    // Use this for initialization
    void Start () {
        offset = player.transform.position;

    }
   
    // Update is called once per frame
    void OnTriggerEnter (Collider other) {
        if (player) {
            player.transform.position = finalPosition.transform.position + offset;
            Debug.Log("Teleport");
            Debug.Log(finalPosition.transform.position);
        }
   
    }
}

That if-statement will be true as long as player is not null, so every object that collides with the teleporter will be moved. Swap line 17 with

if(other.gameObject == player){

should work better.

Ah! Thank you for the correction!

Hypothetically speaking, if I wanted to make it so that certain objects can go through the teleporter, would I create a variable containing a list of tags?

You can do that… making simple collider checks using tags is easy and fast…

…but when it gets complicated I typically test by the object’s composition (as in does it have component X?) not by the tag. I’ve almost completely stopped using tags in my game.

so I’d make a Teleportable script (specifically as an interface, but its not essential plus lets try and keep this simple) attach it to any game object that I want the teleporter to be able to teleport without having to worry if the gameobject has the right tag (in case it was set to something else for some other code). Then when the teleporter gets an OnTriggerEnter is simple check if the the other.GetComponent() is not null, if so the teleporter can teleport it.

now just add that Teleportable script onto any gameobject with a collider and the teleporter can teleport it. then remove it (for example in a use case where an npc doesn’t have security clearance) and the teleporter will stop teleporting them.

This way I don’t have to change any code to include a new tag. and the Teleporter can be more dynamic at runtime

Thats actually a good idea, then i could make it so that I can take away the ability to teleport during game play. thanks for the input!