PointLocatorData

Object Hierarchy | 関連する C++クラス:PointLocatorData

導入

v5.0

詳細

PointLocatorData オブジェクトは、ポイントロケータのコレクションを示します。ポイントロケータはジオメトリックサーフェイス座標で、ジオメトリ上の正確な位置を示します。ポイントロケータは、位相的に定義されるため、位置またはジオメトリのデフォーメーションに依存しません(サーフェイスに固定されます)。ポイントロケータの実際のデータは、抽出されジオメトリタイプに依存します。

ポイント ロケータは Point を一般化したものです。ポイントとして、ポイント ロケータはジオメトリ タイプとは別個に処理できます。ポイントインデックスのように、ポイントロケータは特定のジオメトリインスタンスには関連していません。同じPointLocatorDataと同じトポロジを持つジオメトリを問い合わせることができます。インスタンスのために、ポイントロケータを使用して異なる時間にアニメーションのジオメトリの位置を検証することができます。

ポイントロケータは特定のジオメトリインスタンスに適用できないため、PointLocatorData オブジェクトにはそれ自体の機能がありません。PointLocatorDataに関連するほとんどのメソッドは、GeometryPolygonMesh、およびNurbsSurfaceMeshで定義されます。PointLocatorData は、Geometry.GetClosestLocationsGeometry.GetClosestLocationsWithinRadiusGeometry.GetRaycastIntersectionsGeometry.GetSurfacePointLocatorsFromPointsNurbsSurfaceMesh.ConstructPointLocators、およびPolygonMesh.ConstructPointLocatorsメソッドを使用して作成できます。

PointLocatorData の使用方法のその他の例は、PointLocatorData.CountPolygonMesh.ConstructPointLocatorsなど、関連するさまざまなメソッドに記載されています。

ポイントロケータは現在、PolygonMeshおよびNurbsSurfaceMeshオブジェクトのみでサポートされています。

プロパティ

Countオペレータ      
       

1. Python の例

#
#       This example uses PointLocatorData to shrink-wrap a sphere to a cube,
#       and then pushes the sphere along cube's normals.
#
app = Application
app.NewScene( "", 0 )
root = app.ActiveSceneRoot
CubeGeom = root.AddGeometry("Cube", "MeshSurface").ActivePrimitive.Geometry
SphereObj = root.AddGeometry("Sphere", "MeshSurface")
SphereObj.subdivv = 24
SphereObj.subdivu = 24
# Freeze it, otherwise its position array cannot be set:
app.FreezeObj(SphereObj)
SphereGeom = SphereObj.ActivePrimitive.Geometry
SphereOnCubePointLocators = CubeGeom.GetClosestLocations(SphereGeom.Points.PositionArray)
SphereOnCubePositions = CubeGeom.EvaluatePositions(SphereOnCubePointLocators)
SphereOnCubeNormals = CubeGeom.EvaluateNormals(SphereOnCubePointLocators)
SphereNewPositions = []
i = 0
while i < len(SphereOnCubePositions) :
        j = 0
        tmplist = []
        while j < len(SphereOnCubePositions[i]) :
                tmplist.append( SphereOnCubeNormals[i][j]*3 )
                j = j + 1
        SphereNewPositions.append(tmplist)
        i = i + 1
SphereGeom.Points.PositionArray = SphereNewPositions;

2. JScript の例

/*
        This example uses PointLocatorData to deform a polygon mesh based on
        the closest weight map value of a NURBS surface mesh.
*/
// Scene creation:
//     Polygon mesh grid and a NURBS surface grid.
//     On the NURBS grid, a weight map having a radial gradient
NewScene( null, false );
var root = Application.ActiveSceneRoot;
var MeshGridObj = root.AddGeometry("Grid", "MeshSurface");
MeshGridObj.subdivu = 24;
MeshGridObj.subdivv = 24;
// We must freeze it, otherwise setting its position array will be forbidden:
FreezeObj(MeshGridObj);
var MeshGridGeom = MeshGridObj.ActivePrimitive.Geometry;
var NURBSGridObj = root.AddGeometry("Grid", "NurbsSurface");
NURBSGridObj.subdivu = 2;
NURBSGridObj.subdivv = 2;
var NURBSGridGeom = NURBSGridObj.ActivePrimitive.Geometry;
var NURBSWeightMap = CreateWeightMap(null, NURBSGridObj, "Weight_Map").item(0);
SetValue(NURBSWeightMap + ".weightmapop.type", 5);
SetValue(NURBSWeightMap + ".weightmapop.weight", 1);
SetValue(NURBSWeightMap + ".weightmapop.invert", true);
NURBSWeightMap = GetValue(NURBSWeightMap);      // Get the weight map again to have an updated copy
// Applying the deformation
var MeshGridPos = MeshGridGeom.Points.PositionArray.toArray();
var MeshGridOnNURBSGridPointLocators = NURBSGridGeom.GetClosestLocations(MeshGridPos);
var WeightMapValuesForMesh = NURBSGridGeom.EvaluateClusterProperty(     MeshGridOnNURBSGridPointLocators,
                                                                        NURBSWeightMap.Parent,
                                                                        NURBSWeightMap ).toArray();
// Push mesh vertices along Y, modulated by NURBS grid's closest surface's weight map value
for(i = 0; i < MeshGridPos.length; i+=3)
        MeshGridPos[i+1] += WeightMapValuesForMesh[i/3]*5;
MeshGridGeom.Points.PositionArray = MeshGridPos;

3. JScript の例

// The following example is more complex but shows the PointLocatorData 
// at work in the context of a relatively complex scripted operator.
//
// This example creates a "skinning" custom operator, which a kind
// of shrink wrap-based cage deform operator. This operator
// wraps a deformed "body" object with a "skin" object having a different
// topology. In order to create the surface correspondance between
// the skin and the body, it uses a static copy of the "body", which
// is not animated and stands as a reference. The operator supports,
// too, arbitrary poses on each object.
//
// Since the skin and the reference body are not animated, the
// custom operator can create the point locators only once,
// at the first evaluation, and then only need to evaluate
// them on the deformed body at each frame. This improves a lot
// the performance since creating point locators from spatial
// proximity is much more costly than simply evaluating their
// positions or normals.
//
// Additionally, in order to improve the skinning result, the
// operator pushes the sking along the normals of the body,
// and the amplitude of this push can be controlled by a parameter.
NewScene( null, false );
var root = Application.ActiveSceneRoot;
Translate("Camera", 0, 0, 50.0, siRelative, siView, siObj, siXYZ);
// Create the reference body object, non-animated object (a cube),
// and move it to a non-trivial pose
var ReferenceCubeObj = root.AddGeometry("Cube", "MeshSurface");
Translate(ReferenceCubeObj, -25.0, 0, 0, siRelative, siView, siObj, siXYZ);
// Create the skin object (a sphere with more resolution),
// and move it to a non-trivial pose
var ShrinkWrappedSphereObj = root.AddGeometry("Sphere", "MeshSurface");
ShrinkWrappedSphereObj.subdivu = 25;
ShrinkWrappedSphereObj.subdivv = 25;
Rotate(ShrinkWrappedSphereObj, 0, 0, -60.0, siRelative, siLocal, siObj, siXYZ);
Scale(ShrinkWrappedSphereObj, 1.5, 1.5, 1.5, siRelative, siLocal, siObj, siXYZ);
Translate(ShrinkWrappedSphereObj, -25.0, 0, 0, siRelative, siView, siObj, siXYZ);
// Create the animated target body object.
// In order to show the scripted op at work, add kinematic and
// shape animation.
var TargetCubeObj = root.AddGeometry("Cube", "MeshSurface");
Translate(TargetCubeObj, 10.0, 10.0, 0, siRelative, siView, siObj, siXYZ);
SetValue("Context.constructionmode", 1);
Scale("cube1.pnt[2,3,6,LAST]", 0.3, 0.3, 0.3, siRelative, siLocal, siObj, siXYZ);
SaveShapeKey("cube1.pnt[2,3,6,LAST]", null, null, 1);
Scale("cube1.pnt[2,3,6,LAST]", 10.0, 10.0, 10.0, siRelative, siLocal, siObj, siXYZ);
SaveShapeKey("cube1.polymsh.cls.Shape", null, null, 100);
SaveKey("cube1.kine.local.posx,cube1.kine.local.posy,cube1.kine.local.posz");
SaveKey("cube1.kine.local.rotx,cube1.kine.local.roty,cube1.kine.local.rotz");
Rotate(TargetCubeObj, 50.0, 0, 50.0, siRelative, siLocal, siObj, siXYZ);
SetValue("PlayControl.Current", 100);
SaveKey("cube1.kine.local.rotx,cube1.kine.local.roty,cube1.kine.local.rotz", 100);
Translate(TargetCubeObj, -15.0, -15.0, 0.0, siRelative, siView, siObj, siXYZ);
SaveKey("cube1.kine.local.posx,cube1.kine.local.posy,cube1.kine.local.posz", 100);
SetValue("PlayControl.Current", 1);
// Apply the scripted op to the skin.
var SkinOp = ApplySkinOp( ShrinkWrappedSphereObj, ReferenceCubeObj, TargetCubeObj );
SetValue("PlayControl.Loop", true);
PlayForwardsFromStart();
InspectObj(SkinOp);
function ApplySkinOp( inSkinObj, inReferenceBody, inTargetBody )
{
        var op = XSIFactory.CreateScriptedOp( "MySkinOp", MySkinOp_Update.toString(), "JScript" );
        // Define connections
        var skin_group = op.AddPortGroup( "SkinGroup" );
        op.AddIOPort( inSkinObj.ActivePrimitive, "Geom", skin_group.Index );
        op.AddInputPort( inSkinObj.Kinematics.Global, "Pose", skin_group.Index );
        var ref_group = op.AddPortGroup( "ReferenceBodyGroup" );
        op.AddInputPort( inReferenceBody.ActivePrimitive, "Geom", ref_group.Index );
        op.AddInputPort( inReferenceBody.Kinematics.Global, "Pose", ref_group.Index );
        var tgt_group = op.AddPortGroup( "TargetBodyGroup" );
        op.AddInputPort( inTargetBody.ActivePrimitive, "Geom", tgt_group.Index );
        op.AddInputPort( inTargetBody.Kinematics.Global, "Pose", tgt_group.Index );
        // Define a parameter for the push amplitude
        var pdef = XSIFactory.CreateParamDef2( "PushAmplitude", siDouble, 2, -1, 5 );
        op.AddParameter(pdef);
        // Connect operator
        op.Connect(inSkinObj + ";" + inReferenceBody + ";" + inTargetBody);
        return op;
}
// This function contains the implementation of the scripted operator.
function MySkinOp_Update( ctx, out, InSkinGeom, InSkinPose, InReferenceBodyGeom, InReferenceBodyPose, InTargetBodyGeom, InTargetBodyPose )
{
        // TransformPositionArray: transforms in place an array of packed XYZ vectors
        function TransformPositionArray( array, transfo )
        {
                for (i = 0; i < array.length; i+=3)
                {
                        var TempVector3 = XSIMath.CreateVector3()
                        TempVector3.Set(array[i], array[i+1], array[i+2]);
                        TempVector3.MulByTransformationInPlace(transfo);
                        var XYZArray = TempVector3.Get2().toArray();
                        array[i] = XYZArray[0];
                        array[i+1] = XYZArray[1];
                        array[i+2] = XYZArray[2];
                }
        }
        var SkinGeom = InSkinGeom.Value.Geometry;
        var ReferenceBodyGeom = InReferenceBodyGeom.Value.Geometry;
        /////////////////////////////////////////////////////////
        //1) Create skin point locators relatively to the surface 
        //   proximity to the reference body. We intentionally keep
        //   a snapshot of the point locators to speed up the 
        //   next evaluations; we assume that InSkinGeom, InSkinPose, 
        //   InReferenceBodyGeom and InReferenceBodyPose are not
        //   animated.
        var SkinPointLocators = ctx.UserData;
        if(SkinPointLocators == null)   // No user data means that this is the first evaluation of the operator
        {
                // The skin object and the reference may have different poses, so we
                // will compute the surface proximity computation in global space.
                // We will use the closest smoothed surface method (2==siClosestSmoothedSurface).
                ReferenceBodyGeom.SetupPointLocatorQueries(2, InReferenceBodyPose.Value.Transform); 
                // Transform the skin positions in global space
                var SkinGeomPosArray = SkinGeom.Points.PositionArray.toArray();
                // TransformPositionArray: transforms in place an array of packed XYZ vectors
                TransformPositionArray( SkinGeomPosArray, InSkinPose.Value.Transform );
                SkinPointLocators = ReferenceBodyGeom.GetClosestLocations(SkinGeomPosArray);
                ctx.UserData = SkinPointLocators;
        }
        /////////////////////////////////////////////////////////
        //2) Evaluate the point locators on the target body, and
        //   displace them along target body's normals, with the
        //   amplitude given by the scirted op parameter.
        var TargetBodyGeom = InTargetBodyGeom.Value.Geometry;
        var SkinOnTargetBodyPositions = TargetBodyGeom.EvaluatePositions(SkinPointLocators).toArray();
        var SkinOnTargetBodyNormals = TargetBodyGeom.EvaluateNormals(SkinPointLocators).toArray();
        var SkinToTargetTransform = XSIMath.MapWorldPoseToObjectSpace(InSkinPose.Value.Transform, InTargetBodyPose.Value.Transform);
        var dPushAmplitude = ctx.Parameters("PushAmplitude").Value
        for (i = 0; i < SkinOnTargetBodyPositions.length; i++)
                SkinOnTargetBodyPositions[i] += SkinOnTargetBodyNormals[i]*dPushAmplitude;
        // TransformPositionArray: transforms in place an array of packed XYZ vectors
        TransformPositionArray( SkinOnTargetBodyPositions, SkinToTargetTransform );
        SkinGeom.Points.PositionArray = SkinOnTargetBodyPositions;
}

関連項目

Geometry Geometry.GetClosestLocations Geometry.GetClosestLocationsWithinRadius Geometry.GetRaycastIntersections Geometry.SetupPointLocatorQueries Geometry.GetSurfacePointLocatorsFromPoints Geometry.EvaluatePositions Geometry.EvaluateNormals Geometry.EvaluateClusterProperty PolygonMesh.GetPolygonIndexArray PolygonMesh.GetTriangleVertexIndexArray PolygonMesh.GetTriangleNodeIndexArray PolygonMesh.GetTriangleWeightArray PolygonMesh.ConstructPointLocators NurbsSurfaceMesh.GetSubSurfaceIndexArray NurbsSurfaceMesh.GetNormalizedUVArray NurbsSurfaceMesh.ConstructPointLocators