首页 > 解决方案 > Unity2d:dontDestroyOnLoad 只工作一次吗?

问题描述

public class ShopManager : MonoBehaviour
{
    // Start is called before the first frame update

    public Button itemBuyButton; //Almak istediğim itemin butonu.
    public Button moneyBar; //Para kutucuğu
    int price; //İslem yapabilmek için para kutucuğumdaki text i double a çeviricem. Bu değişken onu tutmak için.
    public Transform floatingText; //item aldığımda aldığım itemin fiyatının ekranda çıkmasını temsil eden object
    public Transform infoAboutShop; // item aldığımda itemden kaç tane aldığımı ekrana yazdıran object.
    public Canvas canvas;

  
    int n = 0;

    public void Awake()
    {
        DontDestroyOnLoad(canvas);
    }
    void Start()
    {
      //price = PlayerPrefs.GetInt("money");
        moneyBar = GameObject.Find("MoneyBar").GetComponent<Button>();
      
    } 

    // Update is called once per frame
    void Update()
    {
        //Butonların interaktifliği sürekli kontrol edilsin istediğimden ilgili methodu update metodumda çağırıyorum.
        
        buttonInteractable();
        PlayerPrefs.SetInt("money", price);
    }

    public void buy()
    {
        //floatingText objemin TextMesh componentine ilgili itemin fiyatını atıyorum.
        floatingText.GetComponent<TextMesh>().text = itemBuyButton.GetComponentInChildren<Text>().text;
        /*
        *Instantiate metodu clone yaratmaya yarıyor. floatingText objemden clone yaratıcam. Clonenun yaratılmasını istediğim yeri tıkladığım yer olarak belirttim.
        *Quaternion identity ise rotation olmadan ilgili objenin clonelamasını sağlıyor. Bu cloneun TextMesh componentine de aynı şekilde ilgili itemin fiyatını atıyorum.
        * Bu işlemleri buy metodunun içinde yapmamın nedeni de floatingText lerin item satın alındığında oluşacak olması.
        */
        Instantiate(floatingText, new Vector3(Input.mousePosition.x, Input.mousePosition.y, Input.mousePosition.z), Quaternion.identity).GetComponent<TextMesh>().text = itemBuyButton.GetComponentInChildren<Text>().text;


        //Para kutucuk butonumun text componentini double a çevirip yukarıda oluşturduğum moneyBarPrice değişkenine atıyorum. İşlemleri bu değişken üzerinden yapacağım.
        price = Convert.ToInt32(moneyBar.GetComponentInChildren<Text>().text);

        //Butonun text componentine ulaşıp aynı şekilde o text i de kıyaslama yapabilmek için double a çeviriyorum.
        if (price >= (Convert.ToDouble(itemBuyButton.GetComponentInChildren<Text>().text)))

        {
            // item aldıktan sonra itemin fiyatını total fiyatımdan düşüyorum.  
            price -= (Convert.ToInt32(itemBuyButton.GetComponentInChildren<Text>().text));
            // kalan fiyatımı string e çevirip para kutucuğuma yazıyorum.
            moneyBar.GetComponentInChildren<Text>().text = Convert.ToString(price);


            //infoAboutShop objemin TextMesh componentine ilgili itemin adını ve sayısını atıyorum.
            infoAboutShop.GetComponent<TextMesh>().text = Convert.ToString(n + 1) + " " + itemBuyButton.name;
            //floatingText teki mantıkla infoAboutShop objelerimi (200,200) konumunda clonelayıp ilgili nesnenin adı ve sayısını atıyorum.
            Instantiate(infoAboutShop, new Vector2(200, 200), Quaternion.identity).GetComponent<TextMesh>().text = infoAboutShop.GetComponent<TextMesh>().text;
            //her çağırıldığında ilgili objenin sayısını 1 artırıyorum.
            n += 1;

        }
        else
        {
            // eğer iteme tıkladıktan sonra param tıkladığım itemi almaya yetmiyorsa itemin aktifliği engelleniyor.
            itemBuyButton.interactable = false;
        }

    }

    void buttonInteractable()
    {
        price= Convert.ToInt32(moneyBar.GetComponentInChildren<Text>().text);
        Debug.Log(price);
        //Butonun text componentine ulaşıp aynı şekilde o text i de kıyaslama yapabilmek için double a çeviriyorum.
        if (price >= (Convert.ToDouble(itemBuyButton.GetComponentInChildren<Text>().text)))

        {
            itemBuyButton.interactable = true; // Eğer  start butonu aktif eğilse ve param almak istediğim itemden fazlaysa butonun aktifliği devam eder.
        }
        else
        {
            itemBuyButton.interactable = false; //  param tıkladığım itemi almaya yetmiyorsa itemin aktifliği engelleniyor.
        }
    }


   
}
public class DragandDrop : MonoBehaviour
{
    public GameObject box;
    public GameObject table;
    public Text scoreText;
   public Button moneyBarButton;
    public Canvas canvas;
    public int money;

    private bool isFit;
    private bool isMoving;

    private float startPosX;
    private float startPosY;
    private GameObject [] boxCountArray;
    private GameObject[] moneyCountArray;
    private Vector3 startPosition;

     void Awake()
    {
       
        DontDestroyOnLoad(canvas);
    }
    // Start is called before the first frame update
    void Start()
    {
       
        startPosition = this.transform.localPosition;
      moneyBarButton= GameObject.Find("MoneyBar").GetComponent<Button>();
        


    }

    // Update is called once per frame
    void Update()
    {
        // moneyBarButton = GameObject.Find("MoneyBar").GetComponent<Button>();
        SceneManager.SetActiveScene(SceneManager.GetSceneByName("Maingame"));
        PlayerPrefs.GetInt("money");
        moneyBarButton.GetComponentInChildren<Text>().text = Convert.ToString(money);
        scoreText.text = "Score: " + money / 10;
        boxCountArray = GameObject.FindGameObjectsWithTag("Box");
        control();
        scoreText.text = "Score: " + (boxCountArray.Length-1);//score artışı
        money = (boxCountArray.Length - 1) * 10;

        
        //moneyBarButton = GameObject.Find("MoneyBar").GetComponent<Button>();

    }
    public bool control() {
        if (!isFit)
        {
            if (isMoving)
            {
                
                Vector3 mousePos = Input.mousePosition;
                mousePos = Camera.main.ScreenToWorldPoint(mousePos);
                
                this.gameObject.transform.localPosition = new Vector3(mousePos.x - startPosX, mousePos.y - startPosY, this.gameObject.transform.localPosition.z);
                return true;
            }
            return false;
        }
        return false;
    }
     void moneyIncrease() {
        
        while (control() == true)
        {
            
            money += 10;
            moneyBarButton.GetComponentInChildren<Text>().text = money.ToString();//para artışı
            PlayerPrefs.SetInt("money", money);
            break;
        }
    
    
    
    }

    private void OnMouseDown()
    {
        if (Input.GetMouseButtonDown(0))
        {
            Vector3 mousePos = Input.mousePosition;
            mousePos = Camera.main.ScreenToWorldPoint(mousePos);

            startPosX = mousePos.x - this.transform.localPosition.x;
            startPosY = mousePos.y - this.transform.localPosition.y;

            isMoving = true;
        }
    }

    private void OnMouseUp()
    {
        isMoving = false;

        if (Mathf.Abs(this.transform.localPosition.x - table.transform.localPosition.x) <= 0.5f &&
            Mathf.Abs(this.transform.localPosition.y - table.transform.localPosition.y) <= 0.5f)
        {
            Vector3 position = new Vector3(UnityEngine.Random.Range(-11,1 ), UnityEngine.Random.Range(-3, 4), transform.position.z);//Yeni oluşacak boxun pozisyonunu random belirler.
            this.transform.position = new Vector3(box.transform.position.x, box.transform.position.y, box.transform.position.z);
            Instantiate(box,position ,Quaternion.identity);//Her kutu masaya yerleştiğinde yeni bir kutu oluşturur
            
            isFit = true;
        }
        else
        {
            this.transform.localPosition = new Vector3(startPosition.x, startPosition.y, startPosition.z);
        }
    }


}
public class closedButton : MonoBehaviour
{
    Scene scene;
  public Button moneyBar;
   
    

    // Start is called before the first frame update
    void Start()
    {

        
    }

    // Update is called once per frame
    void Update()
    {
        
    }
    public void ExitShop()
    {
        SceneManager.GetActiveScene();

        SceneManager.LoadScene(0);




    }
}
public class DragandDrop : MonoBehaviour
{
   private static DragandDrop instance;
    public GameObject box;
    public GameObject table;
    public Text scoreText;
   public Button moneyBarButton;
    public GameObject canvas;
    public int money;

    private bool isFit;
    private bool isMoving;

    private float startPosX;
    private float startPosY;
    private GameObject [] boxCountArray;
    private GameObject[] moneyCountArray;
    private Vector3 startPosition;

     void Awake()
    {
        canvas = (GameObject.Find("DontDestroyCanvas"));
        DontDestroyOnLoad(canvas);
        if (instance == null)
        {
            instance = this; 
            DontDestroyOnLoad(canvas);
        }
        else if (instance != this)
            Destroy(canvas);

    }

我正在做一个项目。认为有两个不同的场景。一个是 ShopScene,另一个是 Maingame 场景。Maingame 场景中有一个按钮显示我的钱。同样在这个场景中,我在这个按钮上赚钱和增加金钱。然后我换个场景。在 ShopScene 中,我可以看到我赚到的钱,我可以买东西。当然,我的钱减少了。但是,当我再次切换场景时,当我打开 Maingame 场景时,我的钱变成了 0。

如何使 ShopScene 和 Maingame 场景之间的金额相同?

Maingame 的拖放脚本,ShopScene 的商店经理。Alsı 关闭按钮关闭商店并打开主游戏。在代码的末尾,我添加了不起作用的单例代码

标签: c#unity3d

解决方案


看来你有两个画布。一个在您的主游戏场景中,一个在商店场景中。如果您的游戏在您的商店场景之前首先在 Maingame 上开始。我建议您在 awake 方法中找到该对象,而不是使用GameObject.Find(). 这将确保选择并放入正确的画布,DontDestroyOnLoad因为您似乎在主屏幕上以 0 的钱保存主屏幕画布,这是您不想要的。唤醒方法应该看起来像这样:

public void Awake()
{
    canvas = GameObect.Find('Canvas');//Canvas would be replaced by the gameobjects name
    DontDestroyOnLoad(canvas);
}

推荐阅读