- Home /
How do I make make objects stick to a ball and affect (but not stop) its movement (like Katamari Damacy)
I'm pretty new to Unity. I've done a few tutorials now and I'm pretty familiar with the editor and have a very basic understanding of scripting.
I've done two different tutorials now that have involved rolling balls and I have not been able to get Katamari Damacy off of my mind.
Thanks to some helpful advice from Nesis and some experimenting, the pickup objects (cubes) now stick to the ball. However, as soon as a cube sticks to the ball, I lose pretty much all control over the ball. Sometimes I can still move it a bit but I have very little control over which way it goes. What I want to happen is that I can continue to roll the ball but the cubes throw off the rolling with their shape causing it to wobble. If you're having trouble understanding what I mean by this, just go watch a gameplay video of Katamari Damacy on youtube and you'll see what I mean.
Currently, I am achieving this "sticking" effect with a script attached to the pickup object (cubes). Both the cubes and the player objects (the ball) have two colliders, a non-trigger which is the same size as the object (to make the objects solid), and a trigger collider that is .1 units larger than the object mesh.
I've tried several different things so far, such toggling gravity, kinemetics, and isTrigger on collision but none of that helped.
Edit: I just noticed that if I roll the ball into so that it gets stuck to an outer edge of the ball (from the player's perspective behind the ball) then the ball will keep rolling normally, but the cube just clips through the floor, it doesn't affect the rolling in any way. However, if you roll over a cube, you roll over it (not through it) and it sticks just as it should, but when the ball rolls around to where the cube is on top the ball stops rolling and sometimes spins like a top. :-/
Here is the script for objects that can be picked up:
using UnityEngine;
using System.Collections;
public class Sticky : MonoBehaviour
{
public bool isSticky;
private bool isStuck;
void OnTriggerEnter(Collider other)
{
if ((other.gameObject.CompareTag("Player")) && (isSticky == true) && (isStuck == false))
{
transform.parent = other.transform;
isStuck = true;
}
}
}
Here is the player control script (including this in case there is some change needed to player control in order for this to work properly):
using UnityEngine;
using System.Collections;
public class PlayerController : MonoBehaviour
{
public float speed;
void FixedUpdate ()
{
float moveHorizontal = Input.GetAxis ("Horizontal");
float moveVertical = Input.GetAxis ("Vertical");
Vector3 movement = new Vector3 (moveHorizontal, 0.0f, moveVertical);
rigidbody.AddForce(movement * speed * Time.deltaTime);
}
}
Answer by nesis · Feb 08, 2014 at 02:31 PM
In the OnTriggerEnter(Collider other)
method, get the cube's transform and set its parent to your player controller's transform (`other.transform = transform;`). Unity's physics engine will then treat the cube and its transform's parent as one physical object when colliding and moving. I'm not sure whether you'll need to remove the cube's rigidbody component before adding it, but I suspect you will. You can do this in the OnTriggerEnter(Collider other)
method by using other.rigidbody = null;
.
Thank you!! I had to use 'other.transform.parent = transform;'to make it work without an error but I probably wouldn't have even got that far without your help.
'other.rigidbody = null;' also creates an error as it's read-only. I tried to use 'Destroy (other.rigidbody);' but that causes all of the objects fly in different directions as soon as I collide with one of the pickup objects.
I'm pretty sure I need the pickup objects to keep their rigid bodies though. I need their physics to affect the way that the ball rolls. So if I have a cube stuck to my ball, whenever I roll the ball onto the side with the cube, the cube should affect the roll, making it uneven/wobbly.
As it is right now, the cubes stick to the ball and stay on in exactly the way that I want them to, but they clip right through the ground and everything else. I have the cubes set to $$anonymous$$inematic because their colliders are triggers. I tried setting is$$anonymous$$inematic to false when I collide with the cubes but when I do that they fall off the ball and through the ground.
Thanks again for the help so far!
P.S. - I would upvote you but I don't have enough rep. :-(
If your colliders are triggers, things will pass through them and because they have rigidbodies, gravity and any other forces will push them through the floor, and other objects because of the lack of a "solid" collider. You can use OnCollisionEnter ins$$anonymous$$d to detect and "trigger" other code.
Also, have you adjusted the mass of the rigidbodies? If you have a large sphere and it picks up a small cube but the mass it the same for each object, you'll get all kinds of weird stuff happening. lol. So your smaller "collectible" items should have much lower mass than the sphere. Also, try rigidbody.active = false.
Both the player object and the collectibles have non-trigger colliders that are the same size as the objects to make them solid, and slightly larger trigger colliders. At this point I'm not having trouble getting them to stick to the ball, it just totally screws up the control of the ball once they do stick.
I did have both objects' mass set to 1 so I set the collectibles to .1 but it didn't make a difference. The ball still stops rolling once the cube is at top. Then it just spins or doesn't move at all. :-(
Once the cube is at the top? Not sure... seems odd... like some sort of physics conflict. Are you able to disable the rigidbodies of the collectibles with rigidbody.active = false? From memory, that's what I used in the past. Actually, scrap that, it turns off the whole game object.