Hi!
I have an object that is randomly scaled through the game. Right now I'm calculating all the vertices with the scale applied, and using new ConvexHullShape (vertexList) to create it. This is of course a waste of time, because I'm calculating the convex hull every time (it's not fast and I do it a lot)
How do I...
1) create a new convex hull with a scale applied from an initial convex hull?
2) extract the data of the already calculated convex hull so that I can store it in disk, and reload it on runtime without applying the convex hull shape calculation algorithm?
thanks!
[v1]"Scaled" convex hull
Re: [v1]"Scaled" convex hull
One option would be to create a TransformableShape that wraps the original ConvexHullShape. The transformable shape allows arbitrary affine transforms, but it does cost a bit more in collision detection. There is still some overhead associated with inertia, though.1) create a new convex hull with a scale applied from an initial convex hull?
There are some more effortful options too- for some kinds of shapes and transforms, the inertia tensor can be directly updated without reintegration. For those, you could simply scale the vertices and directly update the inertia tensor without going through the convex hull+inertia calculation phases. In cases where you don't want to figure out how to properly scale the inertia tensor directly, you could still often avoid the need for the expensive retriangulation by caching the surface triangles computed by the ConvexHullHelper and feeding the scaled triangles into the InertiaHelper.ComputeShapeDistribution.
And, of course, there's the option of shrugging and approximating inertia. The inertia computed from a box approximation of a shape is often perceptually indistinguishable from the 'correct' analytic inertia.
To load and construct a convex hull efficiently, you'll want to use the ConvexHullShape constructor which directly takes cached information without doing any processing on it. Something like:2) extract the data of the already calculated convex hull so that I can store it in disk, and reload it on runtime without applying the convex hull shape calculation algorithm?
Code: Select all
SomeFunctionThatLoadsConvexHullShapes(out Vector3[] loadedVertices, out ConvexShapeDescription loadedDescription);
var loadedShape = new ConvexHullShape(loadedVertices, loadedDescription);
Code: Select all
var verticesToSave = new Vector3[convexHullShape.Vertices.Count];
convexHullShape.Vertices.CopyTo(verticesToSave, 0);
var descriptionToSave = new ConvexShapeDescription
{
CollisionMargin = convexHullShape.CollisionMargin,
EntityShapeVolume = new EntityShapeVolumeDescription { Volume = convexHullShape.Volume, VolumeDistribution = convexHullShape.VolumeDistribution },
MinimumRadius = convexHullShape.MinimumRadius,
MaximumRadius = convexHullShape.MaximumRadius
};
SomeFunctionThatSavesConvexHullShapes(verticesToSave, descriptionToSave);
Re: [v1]"Scaled" convex hull
hi Norbo, thanks a lot for your answer!
I've got number 2) working, now I'm working on 1) and I've decided to go the ComputeShapeDistribution way you described.
My idea is mixing 2) and 1) , please tell me if I'm wrong:
I get the hull vertices from question 2 and I scale them. Then I want to create a "scaled" ConvexShapeDescription. As I'll be only be doing uniform scales, I'm supposing that CollisionMargin, Minimum and Maximum radius can be the original values (also saved in 2) now) just multiplied by the scale value.
Finally the EntityShapeVolume values are the ones that must be calculated with InertiaHelper.ComputeShapeDistribution. Once I have the correct values from this function, I can just create a Description and use the same path I use to load the precalculated convex hulls to create a scaled hull.
My problem is with the parameter "indexList" of the ComputeShapeDistribution function. Where do I get that index list from? I've tried the ConvexHullShape constructor which allows to output an indexList, but those indexes seem to be refering the original object vertex list, not the convex hull vertex list.
Thanks!
I've got number 2) working, now I'm working on 1) and I've decided to go the ComputeShapeDistribution way you described.
My idea is mixing 2) and 1) , please tell me if I'm wrong:
I get the hull vertices from question 2 and I scale them. Then I want to create a "scaled" ConvexShapeDescription. As I'll be only be doing uniform scales, I'm supposing that CollisionMargin, Minimum and Maximum radius can be the original values (also saved in 2) now) just multiplied by the scale value.
Finally the EntityShapeVolume values are the ones that must be calculated with InertiaHelper.ComputeShapeDistribution. Once I have the correct values from this function, I can just create a Description and use the same path I use to load the precalculated convex hulls to create a scaled hull.
My problem is with the parameter "indexList" of the ComputeShapeDistribution function. Where do I get that index list from? I've tried the ConvexHullShape constructor which allows to output an indexList, but those indexes seem to be refering the original object vertex list, not the convex hull vertex list.
Thanks!
Re: [v1]"Scaled" convex hull
The surface vertices are created from the set of unique output indices, so if all you have is the reduced surface vertices you can remap the original indices by taking into account how the final surface points were ordered. From a ConvexHullHelper.GetConvexHull overload:My problem is with the parameter "indexList" of the ComputeShapeDistribution function. Where do I get that index list from? I've tried the ConvexHullShape constructor which allows to output an indexList, but those indexes seem to be refering the original object vertex list, not the convex hull vertex list.
Code: Select all
for (int i = outputTriangleIndices.Count - 1; i >= 0; i--)
{
int index = outputTriangleIndices[i];
if (alreadyContainedIndices.Add(index))
{
outputSurfacePoints.Add(points[index]);
}
}
I don't see any issues with the rest; should work.
Re: [v1]"Scaled" convex hull
thanks for the answer! I have a little problem with the center but I think it's an error in my code. Other than that it's working well!
Happy holidays!
Happy holidays!