Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

The definitive answer to C# cross script communication

Discussion in 'Scripting' started by ericbenner91, Nov 21, 2013.

  1. ericbenner91

    ericbenner91

    Joined:
    Nov 13, 2013
    Posts:
    7
    Hello everyone,

    I will get straight to the point. After much searching and much head scratching, I cannot find one functioning method to call a method across scripts in C. Now, on the attempted list, we have:

    • Instantiating a new copy of the script through gameObject(<scriptName>)
    • Directly accessing the code through variable reference. ScriptName renameofScript or any combination of
    • Adding the public and static modifiers to the accessed function's name in the accessed script
    • Accessing the script via accessing the parent

    NONE OF THESE SEEM TO WORK!

    I am attempting to animate an object from a mouse down trigger on another object. As the new 2D functionality is accessible only through C as of now, a way to bridge the gap here would be a great move forward.

    Are there any answers on the table so far? Is there not a single definitive way of cross script communication? It would seem that such a simple question is left without a simple answer.
     
    unity_EMF_WQ1QgS9V3Q likes this.
  2. Eric5h5

    Eric5h5

    Volunteer Moderator Moderator

    Joined:
    Jul 19, 2006
    Posts:
    32,401
    The methods are covered in the docs, and work fine. If you have trouble, you could post specific code.

    What? Unity doesn't use C for scripting, but if you mean C#, that's certainly not the case and has never been implied anywhere. As always, the entire Unity API is usable with all languages. It wouldn't make any sense otherwise.

    --Eric
     
  3. ericbenner91

    ericbenner91

    Joined:
    Nov 13, 2013
    Posts:
    7
    Hello fellow Eric :D

    You knew what I meant the moment you posted your reply considering the sentence following your statement. Please do not sully a genuine concern with frivolity. Also, what you posted is java script, not C#.

    I thank you for your reply, though, as it seems to be in honesty and sincerity, but your reply does not answer the core concern. There is no established technique for cross class communication in C# unless you know of a good solution.

    Also, posting specific code would restrict the answers to follow or, in turn, bloat this forum in response. I have tried many combinations of code and still have no answer, and, as posted earlier, I have explained my attempts in required detail.

    The question remains the same. What is the combination required to access methods from a script attached to another object via C#?
     
    Last edited: Nov 21, 2013
    barrylachapelle likes this.
  4. angrypenguin

    angrypenguin

    Joined:
    Dec 29, 2011
    Posts:
    15,614
    The distinction between C and C# (and also between Java, JavaScript and UnityScript, all of which are different) is actually a pretty important one. Also, the link he posted has drop-down menus so you can set the language you need to see, it is not just JavaScript (which is actually UnityScript).
     
  5. ericbenner91

    ericbenner91

    Joined:
    Nov 13, 2013
    Posts:
    7
    Thank you Angry Penguin,

    I did not know about the drop downs in the docs. They seem to me to not be links except the down arrow which in forums annotates response.

    Further more, I have been developing for some time and assumed that people would understand the difference. As Unity3D's own website differentiates their support of C#, I falsely assumed that people would make the leap and I only wrote as such for the sake of shorthanding a conversation.

    Never the less. The answers found in this doc are ineffective. I have found a solution however found in the wise words of a fellow forum contributor. I will list the link below.

    http://forum.unity3d.com/threads/57072-Calling-function-from-other-scripts-c

    "Any deviation from GameObject.FindObjectOfType(typeof(scriptName) as scriptName; does now seem to work, and Garth's example above rings true."

    By the way, this is by and far the most responsive developing thread I have ever partaken in. Once again, thank all and more!
     
    Last edited: Nov 21, 2013
  6. hpjohn

    hpjohn

    Joined:
    Aug 14, 2012
    Posts:
    2,190
    Your posts reek of machine translation. It's pretty funny really.

    Using GameObject.Findxxxx is much less efficient than
    public ScriptA otherScript
    Infact if you have a reference to anything relative to where you know the other script is, it's better to get to it via references and getComponents than it is Find'ing

    No, you are just mis-understanding them.
     
  7. angrypenguin

    angrypenguin

    Joined:
    Dec 29, 2011
    Posts:
    15,614
    But there are plenty of alternatives, many of which are discussed in the docs that Eric linked to.

    FindObjectOfType only returns the first object of the specified type, so it's only suitable for a small number of use cases. I'd suggest looking into GetComponent(). You'll also want to get familiar with traversing and/or searching the scene hierarchy via Transform objects.
     
  8. Eric5h5

    Eric5h5

    Volunteer Moderator Moderator

    Joined:
    Jul 19, 2006
    Posts:
    32,401
    It's not "shorthand", it's a different language altogether. If you're going to program, you need to be exact and specific. Since your writing is somewhat unclear, I wasn't 100% sure that you weren't actually talking about C and were trying to do some communication with a C plugin.

    They are not. They work fine and I use them all the time. As I said, if you have trouble, post the exact code you're using, and it can be corrected.

    --Eric
     
  9. ericbenner91

    ericbenner91

    Joined:
    Nov 13, 2013
    Posts:
    7
    Very well
     

    Attached Files:

    Last edited: Nov 21, 2013
  10. hippocoder

    hippocoder

    Digital Ape

    Joined:
    Apr 11, 2010
    Posts:
    29,723
    Eric5h5, how dare you sully this thread with sensible and well thought out replies. Joking aside, ericbenner91 what is the meaning of the troll picture? It is normal in programming boards to ask for the source code to help fix your nonsense.
     
    NIOS and M3Ninja like this.
  11. Eric5h5

    Eric5h5

    Volunteer Moderator Moderator

    Joined:
    Jul 19, 2006
    Posts:
    32,401
    Well, it's pretty clear you don't actually want any help and would rather complain and blame your tools instead of learning. As I've said several times now, if you had posted code that you had trouble with I would have shown what you were doing wrong, but so be it.

    --Eric
     
    NIOS and kreaturian like this.
  12. paulwhowrites

    paulwhowrites

    Joined:
    May 20, 2018
    Posts:
    1
    This is still the number one search result on Google for anyone who searches this issue.
    For future users, the easiest way to get one script to call a method in another script is as follows:

    1. First, add the script as a public gameobject with 'public GameObject myScript;'
    2. Drag the gameobject the script is attached to into this slot in the inspector
    3. Add the code 'myScript.GetComponent<myScript>().myMethod();' where you want to call the script. myMethod is the relevant method you want to call in your other script.

    Here's an example:

    Code (CSharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4.  
    5. public class NextLevel : MonoBehaviour
    6. {
    7.     public GameObject ZombieScript1;
    8.  
    9.     // Start is called before the first frame update
    10.     void Start()
    11.     {
    12.        
    13.     }
    14.  
    15.     // Update is called once per frame
    16.     void Update()
    17.     {
    18.        
    19.     }
    20.    
    21.     public void MoveUpLevel()
    22.     {
    23.         ZombieScript1.GetComponent<ZombieScript1>().SetExperience();
    24.  
    25.  
    26.     }

    Hope this helps someone!

    Paul
     
    henriquepro, Topthink, Nezniw and 2 others like this.
  13. koirat

    koirat

    Joined:
    Jul 7, 2012
    Posts:
    2,068
    There is a better way.
    Code (CSharp):
    1.  
    2.  
    3.     using UnityEngine;
    4.  
    5.     public class NextLevel : MonoBehaviour
    6.     {
    7.         public ZombieScript zombieScript1;
    8.    
    9.         public void MoveUpLevel()
    10.         {
    11.                  zombieScript1?.SetExperience();
    12.  
    13.  
    14.         }
    15. }
    16.  
     
    CynderR_nAsh likes this.
  14. Owen-Reynolds

    Owen-Reynolds

    Joined:
    Feb 15, 2012
    Posts:
    1,992
    Declaring the Inspector variable as the script you want is better: it still requires you to drag in a gameObject, but now we have a hint, it rejects GO's without that script, and it can be used directly in code: zombieScript1.attack().

    But the ? seems questionable. It prevents the program from throwing an error (and crashing in a build) if zombieScript1 is null. That's great for add-on stuff you don't really care about -- if you mess up, it just won't do anything but at least won't crash. But zombieScript1 is probably vital. If it's not set, our game is broken -- we just stand around an empty area with no zombies, stuck. We don't even know why. Instead, we want the script to throw an error, that way we know where the problem is.

    If zombies have 3 different things they do when they explode, then maybe explode1?.activate(); explode2?.activate(); ... is nice; if you leave some null, no problem. But event then, you might want the error. Maybe you want to be sure to give all 3 to every zombie. Or maybe you want to hand check if(explode1==null) so you can play the default explosion for that slot.
     
  15. koirat

    koirat

    Joined:
    Jul 7, 2012
    Posts:
    2,068
    We use "?" because zombieScript1 might not be present at all, or destroyed.
    We might connect script to this variable later on.
    Also we can disable leveling for some characters by simply not using ZombieScript.
     
  16. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    8,773
    I think Owen's point is: there are times when you want an exception in response to an incorrect setup. An exception will point you to exactly where the problem is. If you attach this script and forget to set zombieScript1, the exception will immediately make it clear that that's the problem.

    If this script's functionality does not require zombieScript1 to be set, then yeah, use ?. However, if the script functionality doesn't make any sense without that field being set, then "?" will cause the script to fail silently, and you'll be sitting there wondering why your experience value isn't changing.

    Exceptions aren't bad. Exceptions are tools.
     
    ensiferum888 likes this.
  17. henriquepro

    henriquepro

    Joined:
    Nov 26, 2021
    Posts:
    2
    Simplest solution , Arigathanks




    Here's an example:

    Code (CSharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4.  
    5. public class NextLevel : MonoBehaviour
    6. {
    7.     public GameObject ZombieScript1;
    8.  
    9.     // Start is called before the first frame update
    10.     void Start()
    11.     {
    12.      
    13.     }
    14.  
    15.     // Update is called once per frame
    16.     void Update()
    17.     {
    18.      
    19.     }
    20.  
    21.     public void MoveUpLevel()
    22.     {
    23.         ZombieScript1.GetComponent<ZombieScript1>().SetExperience();
    24.  
    25.  
    26.     }

    Hope this helps someone!

    Paul[/QUOTE]
     
  18. tleylan

    tleylan

    Joined:
    Jun 17, 2020
    Posts:
    616
    I believe you can improve it slightly. I wouldn't declare a GameObject when my intention was to get the script. Declare it as public ZombieScript1, drag the GameObject to the inspector as you do now and the script will be available as the script.
     
    Bunny83 likes this.