Search Unity

Bug In a 2D Animation prefab, on instantiation, scripts have references to different prefab

Discussion in '2D Experimental Preview' started by AcademyOfFetishes, Mar 2, 2019.

  1. AcademyOfFetishes

    AcademyOfFetishes

    Joined:
    Nov 16, 2018
    Posts:
    219
    Sorry, I cannot think of a succinct title to this post. I have no idea if this is related to 2D Animation or Prefabs or neither. Maybe I'm doing something wrong.

    Here's what I'm trying to do: I've got a 2D animation character with multiple faces. The player takes actions and then I enable/disable certain faces to make the character's expression change. In my hierarchy you can see the faces here:



    I have a scriptable object which has a reference to a prefab of my animation. This prefab has a script with references to the face GameObjects like so:



    Notice how the icon of Idle Face is different from the other two? That's because, after the prefab was instantiated, I manually dragged the face3 from the hierarchy (pictured above) to the script while in play mode. When I did that to with all the faces, it started working as expected, but before I did that, the actions had no effect on the screen.

    Here's how I'm instantiating the prefab:

    Code (CSharp):
    1.             if (characterData.humanAnimation != null)
    2.             {
    3.                 spriteRenderer.sprite = null;
    4.                 var animation = Instantiate(characterData.humanAnimation, sprite.transform);
    5.                 animation.name = "Animation";
    6.  
    7.                 var faceReferences = animation.GetComponent<FaceReferences>();
    8.                 faceReferences.BeIdle();
    9.             }
    characterData is the scriptable object. humanAnimation is the 2D Animation Package prefab.

    Here's the really weird thing (at least to me): After I stopped the game and started it again, the instantiated Face References script STILL had the right face3 and the wrong face1 and 2, even though I didn't do anything to save this prefab after I dragged the things over manually. Weirder still, after dragging face 1 and 2 over manually, after I restarted, it looked just like the image above: The instantiated Face References script STILL had the right face3 and the wrong face1 and 2.

    Anyway, the workaround I came up with is this, and it seems to fix the issue:

    Code (CSharp):
    1.             if (characterData.humanAnimation != null)
    2.             {
    3.                 spriteRenderer.sprite = null;
    4.                 var animation = Instantiate(characterData.humanAnimation, sprite.transform);
    5.                 animation.name = "Animation";
    6.  
    7.                 var faceReferences = animation.GetComponent<FaceReferences>();
    8.                 faceReferences.idleFace = animation.transform.Find(faceReferences.idleFace.name).gameObject;
    9.                 faceReferences.happyFace = animation.transform.Find(faceReferences.happyFace.name).gameObject;
    10.                 faceReferences.upsetFace = animation.transform.Find(faceReferences.upsetFace.name).gameObject;
    11.                 faceReferences.BeIdle();
    12.             }
    But, it feels like a bug that I have to do this at all. I would expect this to work with no manual intervention: Shouldn't the script get references to the instantiated prefab instead of what it's getting?

    Here's my FaceReferences script if that helps:

    Code (CSharp):
    1. using System;
    2. using System.Collections;
    3. using System.Collections.Generic;
    4. using UnityEngine;
    5.  
    6. public class FaceReferences : MonoBehaviour
    7. {
    8.     public GameObject idleFace;
    9.     public GameObject happyFace;
    10.     public GameObject upsetFace;
    11.  
    12.     public void BeHappy()
    13.     {
    14.         idleFace.SetActive(false);
    15.         happyFace.SetActive(true);
    16.         upsetFace.SetActive(false);
    17.     }
    18.  
    19.     public void BeIdle()
    20.     {
    21.         idleFace.SetActive(true);
    22.         happyFace.SetActive(false);
    23.         upsetFace.SetActive(false);
    24.     }
    25.  
    26.     public void BeUpset()
    27.     {
    28.         idleFace.SetActive(false);
    29.         happyFace.SetActive(false);
    30.         upsetFace.SetActive(true);
    31.     }
    32. }
    33.  
     
  2. Sergi_Valls

    Sergi_Valls

    Unity Technologies

    Joined:
    Dec 2, 2016
    Posts:
    204
    Hi, please report a bug to us so we can take a look. Thanks
     
  3. AcademyOfFetishes

    AcademyOfFetishes

    Joined:
    Nov 16, 2018
    Posts:
    219
    I tried to reproduce it and figured out it was my fault. I have a prefab of the original, then a variant. I put a script on the variant that has references to gameObjects and I accidentally dragged references from the original into the variant's script. I meant to drag references from the variant into the variant script. I'm sorry to waste your time, but thank you for offering to help.
     
    Last edited: Mar 5, 2019
  4. Sergi_Valls

    Sergi_Valls

    Unity Technologies

    Joined:
    Dec 2, 2016
    Posts:
    204
    Glad to hear you sorted it out!
     
    AcademyOfFetishes likes this.
unityunity