Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

Trying to program bones that "drag" (jiggle bone but simpler).

Discussion in 'Scripting' started by Kyrieru, Jan 13, 2021.

  1. Kyrieru

    Kyrieru

    Joined:
    Mar 2, 2015
    Posts:
    42
    I'm a noob when it comes to unity and I'm trying to program limb drag. (basically dynamic bone or jiggle, but simpler)

    However it's more or less not working at all (bone stays at a weird angle and doesn't move), and there's probably something blatantly wrong with the concept. Any idea what I'm doing wrong (or horribly misunderstanding.)

    Code (CSharp):
    1. public class limb_drag : MonoBehaviour
    2. {
    3.     Vector3 prev_child_position;
    4.     Vector3 target_position;
    5.     Quaternion delay_rot;
    6.     Quaternion prev_rotation;
    7.     public float delay_amount;
    8.     public Transform child;
    9.     // Start is called before the first frame update
    10.     void Start()
    11.     {
    12.        
    13.         child = transform.GetChild(0);
    14.         prev_child_position = child.transform.position;
    15.         delay_rot = Quaternion.identity;
    16.         prev_rotation = transform.rotation;
    17.     }
    18.  
    19.     // Update is called once per frame
    20.     void Update()
    21.     {
    22.         //undo delay from last step
    23.         transform.rotation = transform.rotation * Quaternion.Inverse(delay_rot);
    24.        
    25.         ///save position of the end of this bone
    26.         prev_child_position = child.transform.position;
    27.  
    28.         ///save current rotation of bone
    29.         prev_rotation = transform.rotation;
    30.  
    31.         ///look at the saved position of the child bone from the last step
    32.         transform.LookAt(prev_child_position);
    33.  
    34.         //lerp between the orriginal rotation and the look rotation by 0.1 or so
    35.         delay_rot = Quaternion.Lerp(prev_rotation, transform.rotation, delay_amount);
    36.        
    37.         ///set rotation back to before look
    38.         transform.rotation = prev_rotation;
    39.  
    40.         ///rotate using lerped value
    41.         transform.rotation = transform.rotation * delay_rot;
    42.  
    43.     }
    44. }
    45.  
     
  2. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    36,756
    To help gain more insight into your problem, I recommend liberally sprinkling Debug.Log() statements through your code to display information in realtime.

    Doing this should help you answer these types of questions:

    - is this code even running? which parts are running? how often does it run?
    - what are the values of the variables involved? Are they initialized?

    Knowing this information will help you reason about the behavior you are seeing.
     
  3. Kyrieru

    Kyrieru

    Joined:
    Mar 2, 2015
    Posts:
    42
    It's not that it doesn't run, it's just that I know I probably have some very specific lack of understanding about the things I'm using there. Likely a difference between global and local rotation.
     
  4. Kurt-Dekker

    Kurt-Dekker

    Joined:
    Mar 16, 2013
    Posts:
    36,756
    Does not sound very specific.

    "weird angle" and "doesn't move" cannot be fixed.

    That was why I suggested the approach above, to help you narrow it down, get some hard numbers.

    I assure you nobody here has any numbers they can tell you.
     
  5. Kyrieru

    Kyrieru

    Joined:
    Mar 2, 2015
    Posts:
    42
    Well, to narrow it down, is there a reason why this code makes the bone flip around like crazy?
    It should rotate, and then rotate back, so I'm assuming what I'm misunderstanding here is playing a part in my overall problem.
    Code (CSharp):
    1.  
    2.         drag_undo = Quaternion.identity;
    3.     }
    4.  
    5.     // Update is called once per frame
    6.     void Update()
    7.     {
    8.         transform.rotation = transform.rotation * Quaternion.Inverse(drag_undo);
    9.  
    10.         prev_rotation = transform.rotation;
    11.         transform.Rotate(drag_x_offset, drag_y_offset, drag_z_offset);
    12.         drag_undo = Quaternion.Lerp(prev_rotation,transform.rotation, 1f);
    13. }
    14.