Closed nathanvogel closed 5 years ago
I'm not sure if I know exactly what you're trying to do, but if you want an effect to follow the camera perfectly you could just make the deformer object a child of the camera. Feel free to explain your goal further if I'm misunderstanding :+1:
Sorry I'll try to be clearer 👍 I want to do something like this:
black = before red = after deform
The line is the deformed mesh and the camera is another independant object.
I gotcha. So the camera needs to be deformed as if it's a vertice on the mesh. There isn't currently a way to do this with deform, but I'll look into parenting objects to vertices as I think that's a useful feature. When I get the time I'll try and make a hacky temporary script you can use in the meantime.
Awesome! Thanks for the help :)
@nathanvogel Sorry for the delay. I threw together a quick and dirty script (emphasis on dirty). It's not super easy to use but, just drop it on an object, give it a reference to a Deformable component, and increase the triangle index
property until the triangle you want is selected. (sorry I know that's lame) The object will be pinned to that triangle. Do note: I didn't add control for changing rotation/position offsets. They shouldn't be hard to add, but I figured it'd be easier to attach an empty object to the triangle and then add the camera as a child. Then you can change the offsets via the scene transform handles rather than fiddling with offsets in the inspector.
I needed to expose the mesh data to be able to access the triangles (without copying the vertex array every frame). Those changes are currently only on the develop branch but will probably make their way into the next release. You can apply the changes to your installation of Deform manually or work off of the linked commit.
Here's the script:
using UnityEngine;
using Deform;
[ExecuteAlways]
public class AttachToTriangle : MonoBehaviour
{
public struct Triangle
{
public Vector3 a, b, c;
public void Multiply(Matrix4x4 m)
{
a = m.MultiplyPoint3x4(a);
b = m.MultiplyPoint3x4(b);
c = m.MultiplyPoint3x4(c);
}
public Vector3 GetPosition() => (a + b + c) / 3f;
public Quaternion GetRotation() => Quaternion.LookRotation((c - b).normalized, (b - a).normalized);
}
public Deformable target;
public int triangleIndex;
#if UNITY_EDITOR
[SerializeField] private bool drawTriangle = true;
#endif
private void Update()
{
if (target == null)
return;
var data = target.GetDynamicManagedMeshData();
if (data == null)
return;
triangleIndex = Mathf.Clamp(triangleIndex, 0, data.Triangles.Length / 3);
var triangle = GetTriangle(data, triangleIndex);
triangle.Multiply(target.transform.localToWorldMatrix);
#if UNITY_EDITOR
if (drawTriangle)
DrawTriangle(triangle);
#endif
var newPosition = triangle.GetPosition();
var newRotation = triangle.GetRotation();
transform.SetPositionAndRotation(newPosition, newRotation);
}
public Triangle GetTriangle(ManagedMeshData data, int triangleIndex)
{
var vertexIndex = triangleIndex * 3;
var triangles = data.Triangles;
var vertices = data.Vertices;
return new Triangle
{
a = vertices[triangles[vertexIndex + 0]],
b = vertices[triangles[vertexIndex + 1]],
c = vertices[triangles[vertexIndex + 2]]
};
}
private void DrawTriangle(Triangle triangle)
{
Debug.DrawLine(triangle.a, triangle.b);
Debug.DrawLine(triangle.b, triangle.c);
Debug.DrawLine(triangle.c, triangle.a);
}
}
Super cool! Thanks a lot, I really appreciate and I'll try it this week :)
Hey! I'm working on another part of the project these days, but I tried your script and just wanted to give you some feedback:
Thanks again!
That's great to hear! 👍
Hi, I would like to transform the position + rotation of a GameObject (a camera) along with the deformation of a mesh. Is there a way to do that?
Thank you for this ++ asset!