public void calculateTransformedVertex(int vertexIndex) { if (!FSkinWeights.ContainsKey(vertexIndex)) { return; } IDictionaryEnumerator influenceEnum = FSkinWeights[vertexIndex].GetEnumerator(); Matrix4x4 jointTransform; while (influenceEnum.MoveNext()) { FJointTransformsInput.GetMatrix((int)influenceEnum.Key, out jointTransform); FVertTransformed[vertexIndex] = (Vector3D)FVertTransformed[vertexIndex] + (double)influenceEnum.Value * (jointTransform * (Vector3D)FVertices[vertexIndex]); } }
//here we go, thats the method called by vvvv each frame //all data handling should be in here public void Evaluate(int SpreadMax) { //if any of the inputs has changed //recompute the outputs if (FTransformInput.PinIsChanged || FP1Input.PinIsChanged || FP2Input.PinIsChanged || FP3Input.PinIsChanged || FP4Input.PinIsChanged) { //first set slicecounts for all outputs //the incoming int SpreadMax is the maximum slicecount of all input pins, which is a good default FTransformOutput.SliceCount = SpreadMax; //the variables to fill with the input data Matrix4x4 matrixSlice; Vector4D p1Slice; Vector4D p2Slice; Vector4D p3Slice; Vector4D p4Slice; //loop for all slices for (int i = 0; i < SpreadMax; i++) { //read data from inputs FTransformInput.GetMatrix(i, out matrixSlice); FP1Input.GetValue4D(i, out p1Slice.x, out p1Slice.y, out p1Slice.z, out p1Slice.w); FP2Input.GetValue4D(i, out p2Slice.x, out p2Slice.y, out p2Slice.z, out p2Slice.w); FP3Input.GetValue4D(i, out p3Slice.x, out p3Slice.y, out p3Slice.z, out p3Slice.w); FP4Input.GetValue4D(i, out p4Slice.x, out p4Slice.y, out p4Slice.z, out p4Slice.w); //function per slice matrixSlice = VMath.BilerpMatrix(p1Slice, p2Slice, p4Slice, p3Slice) * matrixSlice; //write data to outputs FTransformOutput.SetMatrix(i, matrixSlice); } } }
//here we go, thats the method called by vvvv each frame //all data handling should be in here public void Evaluate(int SpreadMax) { //if any of the inputs has changed //recompute the outputs if (FJointNameInput.PinIsChanged) { string name; FJointNameInput.GetString(0, out name); if (!string.IsNullOrEmpty(name)) { FRootJoint.Name = name; FSkeleton.BuildJointTable(); FSkeletonOutput.MarkPinAsChanged(); } } if (FChildPins.Any(c => c.PinIsChanged)) { FSkeleton.ClearAll(); FSkeleton.Root = FRootJoint; FSkeleton.BuildJointTable(); for (int i = 0; i < FChildPins.Count; i++) { if (true) //childPinsList[i].PinIsChanged) { FSkeletonOutput.MarkPinAsChanged(); if (FChildPins[i].IsConnected) { object currInterface; FChildPins[i].GetUpstreamInterface(out currInterface); ISkeleton subSkeleton = (ISkeleton)currInterface; IJoint child = subSkeleton.Root.DeepCopy(); FSkeleton.InsertJoint(FSkeleton.Root.Name, child); FSkeleton.BuildJointTable(); } } } // re-calculate the IDs ... int currId = 0; foreach (KeyValuePair <string, IJoint> pair in FSkeleton.JointTable) { pair.Value.Id = currId; currId++; } } if (FBaseTransformInput.PinIsChanged) { Matrix4x4 baseTransform; FBaseTransformInput.GetMatrix(0, out baseTransform); FRootJoint.BaseTransform = baseTransform; FSkeletonOutput.MarkPinAsChanged(); } if (FRotationConstraintsInput.PinIsChanged) { FRootJoint.Constraints.Clear(); for (int i = 0; i < 3; i++) { double from, to; FRotationConstraintsInput.GetValue2D(i, out from, out to); FRootJoint.Constraints.Add(new Vector2D(from, to)); } FSkeletonOutput.MarkPinAsChanged(); } FSkeletonOutput.SetInterface(FSkeleton); }
//here we go, thats the method called by vvvv each frame //all data handling should be in here public void Evaluate(int SpreadMax) { //if any of the inputs has changed //recompute the outputs bool recalculate = false; if (FJointNameInput.PinIsChanged) { jointNames = new List <string>(); string jointName; for (int i = 0; i < FJointNameInput.SliceCount; i++) { FJointNameInput.GetString(i, out jointName); jointNames.Add(jointName); } recalculate = true; } if (FSkeletonInput.PinIsChanged || recalculate) { if (FSkeletonInput.IsConnected) { object currInterface; FSkeletonInput.GetUpstreamInterface(out currInterface); s = (Skeleton)currInterface; if (inputSkeleton == null || !s.Uid.Equals(inputSkeleton.Uid)) { inputSkeleton = (Skeleton)s.DeepCopy(); } else { foreach (KeyValuePair <string, IJoint> pair in s.JointTable) { if (!jointNames.Exists(delegate(string name) { return(name == pair.Key); })) { inputSkeleton.JointTable[pair.Key].BaseTransform = pair.Value.BaseTransform; inputSkeleton.JointTable[pair.Key].AnimationTransform = pair.Value.AnimationTransform; } inputSkeleton.JointTable[pair.Key].Constraints = pair.Value.Constraints; } } } else { inputSkeleton = null; } } if (FSkeletonInput.PinIsChanged || FAnimationTransformInput.PinIsChanged || FBaseTransformInput.PinIsChanged || FParentNameInput.PinIsChanged || FConstraintsInput.PinIsChanged || recalculate) { if (inputSkeleton != null) { IJoint currJoint; for (int i = 0; i < jointNames.Count; i++) { currJoint = inputSkeleton.JointTable[jointNames[i]]; Matrix4x4 currAnimationT; Matrix4x4 currBaseT; string currParentName; if (currJoint != null) { if (FAnimationTransformInput.IsConnected) { FAnimationTransformInput.GetMatrix(i, out currAnimationT); currJoint.AnimationTransform = currAnimationT; } else { currJoint.AnimationTransform = s.JointTable[currJoint.Name].AnimationTransform; } if (FBaseTransformInput.IsConnected) { FBaseTransformInput.GetMatrix(i, out currBaseT); currJoint.BaseTransform = currBaseT; } else { currJoint.BaseTransform = s.JointTable[currJoint.Name].BaseTransform; } /*if (FRotationInput.IsConnected) * { * currRotation = new Vector3D(0); * FRotationInput.GetValue3D(i, out currRotation.x, out currRotation.y, out currRotation.z); * //currJoint.Rotation = currRotation; * * } */ /*if (FConstraintsInput.IsConnected) * { * currConstraints = new List<Vector2D>(); * Vector2D currConstraint; * for (int j=0; j<3; j++) * { * currConstraint = new Vector2D(0); * FConstraintsInput.GetValue2D(i*3, out currConstraint.x, out currConstraint.y); * currConstraints.Add(currConstraint); * } * currJoint.Constraints = currConstraints; * } */ FParentNameInput.GetString(i, out currParentName); if (currParentName != null && (FParentNameInput.SliceCount > 1 || !string.IsNullOrEmpty(currParentName))) { IJoint parent = inputSkeleton.JointTable[currParentName]; if (parent != null) { currJoint.Parent = parent; } } } } } FSkeletonOutput.MarkPinAsChanged(); } FSkeletonOutput.SetInterface(inputSkeleton); }
//here we go, thats the method called by vvvv each frame //all data handling should be in here public void Evaluate(int SpreadMax) { //if any of the inputs has changed //recompute the outputs bool recalculate = false; if (FJointNameInput.PinIsChanged || FBaseTransformInput.PinIsChanged || FOffsetModeInput.PinIsChanged || FParentNameInput.PinIsChanged || FConstraintsInput.PinIsChanged || recalculate) { skeleton = new Skeleton(); int currId = 0; for (int i = 0; i < FJointNameInput.SliceCount; i++) { string jointName; string parentName; FJointNameInput.GetString(i % FJointNameInput.SliceCount, out jointName); FParentNameInput.GetString(i % FParentNameInput.SliceCount, out parentName); IJoint currJoint = new JointInfo(jointName); Matrix4x4 baseTransform; FBaseTransformInput.GetMatrix(i % FBaseTransformInput.SliceCount, out baseTransform); currJoint.BaseTransform = baseTransform; //VMath.Translate(basePositionX, basePositionY, basePositionZ); currJoint.Constraints.Clear(); for (int j = i * 3; j < i * 3 + 3; j++) { double constraintMin, constraintMax; FConstraintsInput.GetValue2D(j % FConstraintsInput.SliceCount, out constraintMin, out constraintMax); currJoint.Constraints.Add(new Vector2D(constraintMin, constraintMax)); } if (string.IsNullOrEmpty(parentName)) { if (skeleton.Root == null) { skeleton.Root = currJoint; currJoint.Id = currId; currId++; skeleton.BuildJointTable(); } } else { if (skeleton.JointTable.ContainsKey(parentName)) { currJoint.Parent = skeleton.JointTable[parentName]; currJoint.Id = currId; currId++; } skeleton.BuildJointTable(); } } int positionInWorldSpace = 0; FOffsetModeInput.GetOrd(0, out positionInWorldSpace); if (positionInWorldSpace > 0) { List <Vector3D> offsetList = new List <Vector3D>(); foreach (KeyValuePair <string, IJoint> pair in skeleton.JointTable) { Vector3D worldPos = pair.Value.BaseTransform * (new Vector3D(0)); Vector3D parentWorldPos; if (pair.Value.Parent != null) { parentWorldPos = pair.Value.Parent.BaseTransform * (new Vector3D(0)); } else { parentWorldPos = new Vector3D(0); } Vector3D offset = worldPos - parentWorldPos; offsetList.Add(offset); } int i = 0; foreach (KeyValuePair <string, IJoint> pair in skeleton.JointTable) { pair.Value.BaseTransform = VMath.Translate(offsetList[i]); i++; } } FSkeletonOutput.MarkPinAsChanged(); } FSkeletonOutput.SetInterface(skeleton); }
//here we go, thats the method called by vvvv each frame //all data handling should be in here public void Evaluate(int SpreadMax) { //if any of the inputs has changed //recompute the outputs bool recalculate = false; if (FJointNameInput.PinIsChanged) { jointNames = new List <string>(); string jointName; for (int i = 0; i < FJointNameInput.SliceCount; i++) { FJointNameInput.GetString(i, out jointName); jointNames.Add(jointName); } recalculate = true; if (jointNames.Count == 1 && string.IsNullOrEmpty(jointNames[0])) { jointsSelected = false; } else { jointsSelected = true; } } if (FSkeletonInput.PinIsChanged) { if (FSkeletonInput.IsConnected) { object currInterface; FSkeletonInput.GetUpstreamInterface(out currInterface); inputSkeleton = (Skeleton)currInterface; // if there are no specific joints selected via input pin, collect them all if (jointNames == null || !jointsSelected) { jointNames = new List <string>(); foreach (KeyValuePair <string, IJoint> pair in inputSkeleton.JointTable) { // Only add those with a valid array index. // It's not a must that all bones are used as skinning matrices. if (pair.Value.Id >= 0) { jointNames.Add(pair.Key); } } } } else { inputSkeleton = null; } recalculate = true; } if (FInverseBindPoseInput.PinIsChanged) { recalculate = true; } if (FOutputModeInput.PinIsChanged) { FOutputModeInput.GetOrd(0, out outputMode); recalculate = true; } if (recalculate && inputSkeleton != null) { inputSkeleton.CalculateCombinedTransforms(); int jointCount; if (outputMode == OUTPUT_MODE_DYNAMIC) { jointCount = jointNames.Count; } else { jointCount = 60; } FTransformOutput.SliceCount = jointCount; IJoint currJoint; Matrix4x4 currIBPMatrix; int i = 0; for (i = 0; i < jointNames.Count; i++) { currJoint = inputSkeleton.JointTable[jointNames[i]]; if (currJoint != null) { int sliceIndex; if (outputMode == OUTPUT_MODE_STATIC) { sliceIndex = currJoint.Id; } else { sliceIndex = i; } FInverseBindPoseInput.GetMatrix(sliceIndex, out currIBPMatrix); FTransformOutput.SetMatrix(sliceIndex, currIBPMatrix * currJoint.CombinedTransform); } } // Pad remaining slices with Identity Matrices for (int j = i; j < jointCount; j++) { FTransformOutput.SetMatrix(j, VMath.IdentityMatrix); } } }