use of maspack.geometry.Vertex3d in project artisynth_core by artisynth.
the class SkinMeshBody method smoothWeights.
/**
* Smooths weights according to a weighting function of distance. At
* present, this <i>only</i> smooths the weights associated with Frame
* connections. Results when the SkinMeshBody contains other types of
* attachment connections are undefined.
*
* @param weightFunction single-input single-output function of distance
* to use as weights
* @param networkDist number of paths to traverse to collect vertices
*/
public void smoothWeights(SISOFunction weightFunction, int networkDist) {
ArrayList<Vertex3d> vtxs = getMesh().getVertices();
ArrayList<Vertex3d> vtxList = new ArrayList<Vertex3d>();
int numf = numFrames();
// double[] newWeights = new double[nBodies*vtxs.size()];
double[] w = new double[numf];
for (int i = 0; i < vtxs.size(); i++) {
Vertex3d vtx = vtxs.get(i);
vtxList.clear();
collectVertices(vtx, networkDist, vtxList);
Arrays.fill(w, 0);
double wTotal = 0;
for (Vertex3d vtxl : vtxList) {
double d = vtxl.getPosition().distance(vtx.getPosition());
double wd = weightFunction.eval(d);
wTotal += wd;
int idx = vtxs.indexOf(vtxl);
PointSkinAttachment attacher = myVertexAttachments.getByNumber(idx);
if (attacher != null) {
for (int j = 0; j < attacher.numConnections(); j++) {
Connection c = attacher.getConnection(j);
if (c instanceof FrameConnection) {
int fidx = ((FrameConnection) c).getFrameIndex();
w[fidx] += wd * attacher.getWeight(j);
}
}
}
}
PointSkinAttachment attacher = myVertexAttachments.getByNumber(i);
if (attacher != null) {
for (int j = 0; j < attacher.numConnections(); j++) {
Connection c = attacher.getConnection(j);
if (c instanceof FrameConnection) {
int fidx = ((FrameConnection) c).getFrameIndex();
attacher.setWeight(j, w[fidx] / wTotal);
}
}
}
}
}
use of maspack.geometry.Vertex3d in project artisynth_core by artisynth.
the class SkinMeshBody method createPointAttachment.
public PointSkinAttachment createPointAttachment(Point pnt) {
if (!(getMesh() instanceof PolygonalMesh)) {
return null;
}
PolygonalMesh mesh = (PolygonalMesh) getMesh();
if (!mesh.isTriangular()) {
return null;
}
// Find nearest face to the point; we'll need this to
// estimate a basePosition for the attachments from the
// start by find
BVFeatureQuery query = new BVFeatureQuery();
Point3d near = new Point3d();
Vector2d uv = new Vector2d();
Face face = query.nearestFaceToPoint(near, uv, mesh, pnt.getPosition());
// Create a new PointSkinAttachment
MeshDistCalc dcalc = new MeshDistCalc();
dcalc.computeDistancesAndWeights(pnt.getPosition(), myLastSigma);
PointSkinAttachment a = dcalc.computeDisplacementAttachment();
a.setSkinMesh(this);
// Now estimate the basePosition from the face vertices
Point3d basePos = new Point3d();
Vertex3d[] vtxs = face.getTriVertices();
double[] wgts = new double[] { 1 - uv.x - uv.y, uv.x, uv.y };
for (int i = 0; i < vtxs.length; i++) {
PointSkinAttachment va = (PointSkinAttachment) myVertexAttachments.get(vtxs[i].getIndex());
basePos.scaledAdd(wgts[i], va.getBasePosition());
}
a.setBasePosition(basePos);
a.setPoint(pnt);
return a;
}
use of maspack.geometry.Vertex3d in project artisynth_core by artisynth.
the class TetGenReader method readFaces.
public static PolygonalMesh readFaces(Vector3d scale, Reader nodeReader, Reader faceReader) throws IOException {
PolygonalMesh mesh = new PolygonalMesh();
ReaderTokenizer nodeFile = new ReaderTokenizer(new BufferedReader(nodeReader));
nodeFile.nextToken();
nodeFile.nextToken();
nodeFile.nextToken();
nodeFile.nextToken();
while (nodeFile.nextToken() != ReaderTokenizer.TT_EOF) {
Point3d coords = new Point3d();
for (int i = 0; i < 3; i++) {
coords.set(i, nodeFile.scanNumber());
}
if (scale != null) {
coords.x *= scale.x;
coords.y *= scale.y;
coords.z *= scale.z;
}
mesh.addVertex(coords.x, coords.y, coords.z);
}
ReaderTokenizer faceFile = new ReaderTokenizer(new BufferedReader(faceReader));
faceFile.nextToken();
faceFile.nextToken();
while (faceFile.nextToken() != ReaderTokenizer.TT_EOF) {
Vertex3d[] vtxs = new Vertex3d[3];
for (int i = 0; i < vtxs.length; i++) {
vtxs[i] = mesh.getVertices().get(faceFile.scanInteger());
}
// discard
faceFile.scanInteger();
mesh.addFace(vtxs);
}
return mesh;
}
use of maspack.geometry.Vertex3d in project artisynth_core by artisynth.
the class FemMeshComp method createPointAttachment.
public PointFem3dAttachment createPointAttachment(Point pnt) {
if (!(getMesh() instanceof PolygonalMesh)) {
return null;
}
PolygonalMesh mesh = (PolygonalMesh) getMesh();
if (!mesh.isTriangular()) {
return null;
}
// Find nearest face to the point. The vertices of this face will be used
// to find the nodes and weight for the attachment.
BVFeatureQuery query = new BVFeatureQuery();
Point3d near = new Point3d();
Vector2d uv = new Vector2d();
Face face = query.nearestFaceToPoint(near, uv, mesh, pnt.getPosition());
Vertex3d[] vtxs = face.getTriVertices();
double[] wgts = new double[] { 1 - uv.x - uv.y, uv.x, uv.y };
HashMap<FemNode, Double> nodeWeights = new HashMap<FemNode, Double>();
for (int i = 0; i < vtxs.length; i++) {
PointAttachment va = myVertexAttachments.get(vtxs[i].getIndex());
if (va instanceof PointParticleAttachment) {
PointParticleAttachment ppa = (PointParticleAttachment) va;
FemNode node = (FemNode) ppa.getParticle();
accumulateNodeWeights(node, wgts[i], nodeWeights);
} else if (va instanceof PointFem3dAttachment) {
PointFem3dAttachment pfa = (PointFem3dAttachment) va;
for (int k = 0; k < pfa.numMasters(); k++) {
FemNode node = pfa.getNodes()[k];
double w = pfa.getCoordinate(k);
accumulateNodeWeights(node, w * wgts[i], nodeWeights);
}
}
}
// Create a new PointFem3dAttachment
PointFem3dAttachment ax = new PointFem3dAttachment(pnt);
VectorNd weightVec = new VectorNd();
for (Double d : nodeWeights.values()) {
weightVec.append(d);
}
ax.setFromNodes(nodeWeights.keySet(), weightVec);
return ax;
}
use of maspack.geometry.Vertex3d in project artisynth_core by artisynth.
the class FemMeshComp method createVertex.
private Vertex3d createVertex(double s0, double s1, double s2, FemElement3d elem, FemNode3d n0, FemNode3d n1, FemNode3d n2) {
Vector3d coords = new Vector3d();
addNodeCoords(coords, s0, s1, s2, elem, n0, n1, n2);
addNodeCoords(coords, s1, s0, s2, elem, n1, n0, n2);
if (n2 != null) {
addNodeCoords(coords, s2, s1, s0, elem, n2, n1, n0);
}
ArrayList<FemNode> nodes = new ArrayList<FemNode>();
VectorNd weights = new VectorNd();
Point3d pos = new Point3d();
for (int i = 0; i < elem.numNodes(); i++) {
double w = elem.getN(i, coords);
if (Math.abs(w) > EPS) {
FemNode3d n = elem.getNodes()[i];
nodes.add(n);
weights.append(w);
pos.scaledAdd(w, n.getPosition());
}
}
Vertex3d vtx = new Vertex3d(pos);
PointFem3dAttachment attacher = new PointFem3dAttachment();
attacher.setFromNodes(nodes, weights);
myVertexAttachments.add(attacher);
getMesh().addVertex(vtx);
return vtx;
}
Aggregations