how can I enable and disable script on enemy object when I pressed specific button in unity
void OnButtonClick()
{
StartCoroutine(Cooldown());
GetComponent<FollowEnemy>().enabled = !GetComponent<FollowEnemy>().enabled;
}
GetComponent(MyScript).enabled = false;
Might be a good place to start,
For the button a Input.GetKey(KeyCode.Space), would do the trick.
You might need to experiment a bit, you can find more information here:
https://answers.unity.com/questions/26844/enabledisable-specific-components.html
Official documentation:
https://docs.unity3d.com/ScriptReference/KeyCode.html
Related
I have tried for a while now and can not get this code to work:
// Update is called once per frame
void Update()
{
if (Input.GetKey(KeyCode.E))
{
Debug.Log("Testing");
}
}
I wanted to spawn in a GameObject (which I would have added later) when the player pressed the "E" key on their keyboard.
If you start the project from the template, the project might have enabled the new Input System. Or you might have enabled it yourself.
In any of the cases, follow these steps:
Open Preferences: Edit -> Project Settings.
Navigate to Player.
Scroll to Other Settings.
From the Dropdown Active Input Handling*, Choose Both.
According to the Information you have given, this seems to be the answer. If this doesn't solve your problem, please include some more information.
I have four GameObjects in the game I am making and when I click on each one a dialogue box opens.
My problem is that I am using OnMouseDown and the first one always need to be clicked twice. It happens just on the OnMouseDown, I have buttons on the game that work just fine.
public static GameObject selectedClient;
public bool isBuying;
private Manager manager;
private void Start()
{
manager = GameObject.FindObjectOfType(typeof(Manager)) as Manager;
}
private void OnMouseDown()
{
if (isBuying == true)
{
selectedClient = this.gameObject;
manager.Talk();
}
else if (isBuying == false)
{
manager.NotTalk();
}
}
The Talk() and NotTalk() are as follows:
public void Talk()
{
dialogueBox.SetActive(true);
Time.timeScale = 0f;
actualClient = Client.selectedClient;
}
public void NotTalk()
{
dialogueBox.SetActive(false);
Time.timeScale = 1f;
}
Someone knows why this happens?
Thanks in advance.
Assuming manager.Talk() opens the dialog, perhaps isBuying is false initially, and is toggled when you click once?
Edit: User updated question with Talk and NotTalk methods.
Since your say that initially, only the time stops, but the dialogueBox doesn't show, by any chance, is this because it isn't populated, or correctly initialized? Can you show is code of what your expect to show up?
It may just be that dialogueBox has nothing to display, and therefore, doesn't, however, by the second click, it somehow it's correctly populated and can display.
If I understand correctly, it seems that OnMouseDown() and Talk() is being called successfully on the first mouse click, but a second mouse click is required to get the dialogueBox to show.
If dialogueBox.SetActive(true) is being called successfully, you could take a look at the Unity Scene Hierarchy window to see if it became active like you expect after the first mouse click. If it did, then you can examine that object to see why it's not appearing on screen. (As another poster mentioned, it may be related to dialogueBox initialization.)
Also, these questions might help us debug and figure out the issue:
What error do you get when you "click on one object and then on other"?
What happens if you click the buttons in a different order? If there are 4 buttons, is it the first button that is always affected, or the first button that you click?
In general, as other posters have suggested, using Debug.Log and Debug.Assert should help you narrow down the issue. Similarly, you can set breakpoints in the code and step through to see if the code is running like you expect. And as I mentioned in this post, the Unity Scene Hierarchy window is useful for debugging as well.
Add a Debug.log(isBuying); above (isBuying == true).
Then you'll know if the OnMouseDown() is being called in the first place and if it proceeds like you expect it to. After that, you should probably be able to fix it yourself, otherwise, please let me know what you found.
In case of a Unity mobile app, would it be good (at all) for performance, to deactivate the navigation through canvas objects like TextFields and Buttons?
When selecting e.g. a Button or TextField in the sceneview, the inspector shows the option "Navigation", which can be set to different things and can also be visualized. This feature is usually used to tab through input fields, like you would expect it on a website. On my mobile game I don't need this "tabbing". Would there be any sort of performance increase if I deactivated it everywhere?
Would deactivating this rather be a waste of time, or even make
performance worse for some obscure reason?
Usually there are 3 ways to show and hide UI. I will list them from worst to best.
1.Instantiate (Show), Destroy (Hide).
public GameObject uiPanelPrefab;
void Start()
{
//Show
Instantiate(uiPanelPrefab);
//Hide
Destroy(uiPanelPrefab);
}
This creates and destroys Objects each time. (Not Recommended).
2.Activate (Show) or Deactivate (Hide) the GameObject of that UI.
public GameObject uiPanelPrefab;
void Start()
{
//Show
uiPanelPrefab.SetActive(true);
//Hide
uiPanelPrefab.SetActive(false);
}
This creates garbage each time it is set to active and also cause quick freezes. You will notice this a lot when making VR apps. Fine on Desktops. Not good or recommended on mobile devices.
3.Enable (Show) or Disable (Hide) the Component of that UI.
public GameObject uiPanelPrefab;
void Start()
{
//Show
uiPanelPrefab.GetComponent<Image>().enabled = true;
//Hide
uiPanelPrefab.GetComponent<Image>().enabled = false;
}
This simply enables and disables the components. This method requires a custom function for each UI Control such as Button, Text, InputField as each Control has different components attached to them. This is the recommended method especially on mobile devices.
After long experiment with these, I came to conclusion that #3 is the best and should be used.The downside is that you have to make a function that will disable every components of each UI Control.
For example, the Button Control has more than 1 components. Simply disabling the Button component will not do it. You have to write a simple function that will disable Button, Image and Text components. Something like below:
void showButton(GameObject button, bool show, bool includeInactive = false)
{
Button bt = button.GetComponentInChildren<Button>(includeInactive);
bt.enabled = show;
Text txt = button.GetComponentInChildren<Text>(includeInactive);
txt.enabled = show;
Image img = button.GetComponentInChildren<Image>(includeInactive);
img.enabled = show;
}
Usage:
//Show
showButton(uiPanelPrefab, true);
//Hide
showButton(uiPanelPrefab, false);
I can confirm, that deactivating the navigation of UI elements has no performance influence. Behind the scenes there's just a handler, that gets triggered, when you hit "tab" on pc, or analogeously on mobile.
In my unity game I have two toggle buttons that are both in a toggle group together. They are buttons that are labeled "On" and "Off" for turning the game music on and off.
The way I have it set up right now makes it behave very strange. If the music is on and I click the "Off" toggle, the music turns off. Then if I hit "On" again, I get a null object reference error and the check mark doesn't show up in the "On" toggle button until I hit "On" a second time and then the sound comes back on. The really weird part is that when it turns back on, a gameobject is created for the musicplayer, of course. When I try to turn it off again, the music stays on and a second musicplayer gameobject is created. I don't understand what is going on.
void Start ()
{
checkWhatsOn();
}
void checkWhatsOn()
{
bool sound = PlayerPrefs.GetInt("Sound Playing", 1) == 1;
//if (sound) soundToggle.isOn = true; //THESE TWO STATEMENTS
//else soundToggle.isOn = false; //ARE CAUSING THE ISSUE!!
}
public void switchSound()
{
print (string.Format("In switch method sound is {0}", PlayerPrefs.GetInt("Sound Playing", 6)));
bool sound = PlayerPrefs.GetInt("Sound Playing", 1) == 1;
if (sound)
{
if (GameObject.FindObjectOfType<MusicPlayer>() != null)
{
PlayerPrefs.SetInt("Sound Playing", 0);
PlayerPrefs.Save();
GameObject.FindObjectOfType<MusicPlayer>().GetComponent<MusicPlayer>().Disable();
}
else print ("Sound wasn't changed, MusicPlayer needs to be null.");
}
else if (!sound)
{
PlayerPrefs.SetInt("Sound Playing", 1);
PlayerPrefs.Save();
if (GameObject.FindObjectOfType<MusicPlayer>() == null)
{
musicPlayer = Instantiate (Resources.Load ("MusicPlayer")) as GameObject;
GameObject.DontDestroyOnLoad(musicPlayer);
}
else print ("Sound wasn't changed, MusicPlayer shouldn't be null.");
}
print (string.Format("After switch method sound is {0}", PlayerPrefs.GetInt("Sound Playing", 7)));
}
In the inspector I have the "On" button call the function above while passing in a 1. When "Off" pressed, it calls the same function with a 0.
9/2/14
I have updated my code using only one toggle button. The toggle button calls a method which checks the PlayerPrefs to see whether the sound should be on or not. I still end up with an issue when I move from one scene into the scene that has the toggle button in it. When I do that, the music stops. It is for some reason calling the method that should only be called when the toggle button is pressed. Any ideas?
9/4/15
After testing what Thaina had told me (code updated above), I narrowed my issue down to the fact that if I try to set my toggle button to on, it automatically calls the function that is attached to the toggle. I only want to have the function called if it is pressed, not when setting it's saved state. Is there a way to do this?
SOLUTION
I ended up just letting the toggle.isOn call the function that it was trying to access and used a static bool to only let it access certain code when I wanted it to. Thaina's answer is what got me far enough to get to that point so credit goes to Thaina.
I suggest you should use GameObject.FindObjectOfType<MusicPlayer>(). So you can be sure that it will get MusicPlayer in the scene
I suspect that your MusicPlayer object is actually named "MusicPlayer " not "MusicPlayer". Anyway get object by its name is bad idea in my opinion. It prone to error
I've been struggling with what appears to be a simple task for the past few hours. I have been successfully able to turn a GameObject's guiTexture on an off using GameObject.guiTexture.enabled as I have read in other similar questions. I do this in a script that is attached to the GameObject I wish to toggle.
The problem arises when I try to preform this same command from another script that is attached to an empty game object in my scene. When I interact with the button, simply nothing happens.
To give this some context, I am trying to create functionality to switch menus on the screen. When a user taps a certain UI button, I want to call unloadMenu() so I can wipe everything off the screen and draw the textures that belong to the appropriate menu.
//When the user lifts their finger
void OnTouchEnded ()
{
switch (this.gameObject.name)
{
//If they have selected the quiz button
case "QuizButton":
//this.guiTexture.enabled = false;
//Call the unloadMenu function which will clear the GUITextures
menuMgr.unloadMenu();
break;
The commented out section is what works fine. But now, I wish to perform this code in a function that is located in another script - menuMgr.unloadMenu()
This is what the MenuManager script looks like:
public GameObject quizButton;
void unloadMenu()
{
quizButton.guiTexture.enabled = false;
}
I have ensured to drag the quizButton gameobject from my scene into the inspector and connect it properly with the variable I have created yet nothing happens when this function is called. Does anyone have any idea why? Thanks in advanced.
How you declare MenuManager creates a new script while the reference to quizButton is in your MenuManager GameObject. That is why your menuMgr.UnloadMenu didn't do anything.
I have created something similar to yours and I found it worked fine :
Quizbutton Script:
public GameObject menuMgr; // reference to the empty game object (menu manager)
void OnMouseDown() // In your case, this is OnTouchEnded
{
// get the script of menu manager here
MenuMgrScript menuscript = menuMgr.GetComponent<MenuMgrScript>();
// and execute the function you want
menuscript.UnloadMenu();
}
Menu Manager Script:
// this script is exactly the same as yours, nothing's wrong here
// oh except add public to function UnloadMenu, so it can be called
// in the quizbutton script
public GameObject quizButton;
public void UnloadMenu() {
quizButton.guiTexture.enabled = false;
}