IntpAkimaUniform1<Real>::IntpAkimaUniform1 (int quantity, Real xMin, Real xSpacing, Real* F) : IntpAkima1<Real>(quantity, F) { assertion(xSpacing > (Real)0, "Spacing must be positive\n"); mXMin = xMin; mXMax = xMin + xSpacing*(quantity - 1); mXSpacing = xSpacing; // Compute slopes. Real invDX = ((Real)1)/xSpacing; Real* slope = new1<Real>(quantity + 3); int i, ip1, ip2; for (i = 0, ip1 = 1, ip2 = 2; i < quantity - 1; ++i, ++ip1, ++ip2) { slope[ip2] = (F[ip1] - F[i])*invDX; } slope[1] = ((Real)2)*slope[2] - slope[3]; slope[0] = ((Real)2)*slope[1] - slope[2]; slope[quantity + 1] = ((Real)2)*slope[quantity] - slope[quantity - 1]; slope[quantity + 2] = ((Real)2)*slope[quantity + 1] - slope[quantity]; // Construct derivatives. Real* FDer = new1<Real>(quantity); for (i = 0; i < quantity; ++i) { FDer[i] = ComputeDerivative(slope + i); } // Construct polynomials. Real invDX2 = ((Real)1)/(xSpacing*xSpacing); Real invDX3 = invDX2/xSpacing; for (i = 0, ip1 = 1; i < quantity - 1; ++i, ++ip1) { typename IntpAkima1<Real>::Polynomial& poly = mPoly[i]; Real F0 = F[i]; Real F1 = F[ip1]; Real df = F1 - F0; Real FDer0 = FDer[i]; Real FDer1 = FDer[ip1]; poly[0] = F0; poly[1] = FDer0; poly[2] = (((Real)3)*df - xSpacing*(FDer1 + ((Real)2)*FDer0))*invDX2; poly[3] = (xSpacing*(FDer0 + FDer1) - ((Real)2)*df)*invDX3; } delete1(slope); delete1(FDer); }
IntpAkimaNonuniform1<Real>::IntpAkimaNonuniform1 ( int quantity, Real* X, Real* F ) : IntpAkima1<Real>( quantity, F ), mX( X ) { // Compute slopes. Real* slope = new1<Real>( quantity + 3 ); int i, ip1, ip2; for ( i = 0, ip1 = 1, ip2 = 2; i < quantity - 1; ++i, ++ip1, ++ip2 ) { Real dx = X[ip1] - X[i]; Real df = F[ip1] - F[i]; slope[ip2] = df / dx; } slope[1] = ( ( Real )2 ) * slope[2] - slope[3]; slope[0] = ( ( Real )2 ) * slope[1] - slope[2]; slope[quantity + 1] = ( ( Real )2 ) * slope[quantity] - slope[quantity - 1]; slope[quantity + 2] = ( ( Real )2 ) * slope[quantity + 1] - slope[quantity]; // Construct derivatives. Real* FDer = new1<Real>( quantity ); for ( i = 0; i < quantity; ++i ) { FDer[i] = ComputeDerivative( slope + i ); } // Construct polynomials. for ( i = 0, ip1 = 1; i < quantity - 1; ++i, ++ip1 ) { typename IntpAkima1<Real>::Polynomial& poly = mPoly[i]; Real F0 = F[i]; Real F1 = F[ip1]; Real FDer0 = FDer[i]; Real FDer1 = FDer[ip1]; Real df = F1 - F0; Real dx = X[ip1] - X[i]; Real dx2 = dx * dx; Real dx3 = dx2 * dx; poly[0] = F0; poly[1] = FDer0; poly[2] = ( ( ( Real )3 ) * df - dx * ( FDer1 + ( ( Real )2 ) * FDer0 ) ) / dx2; poly[3] = ( dx * ( FDer0 + FDer1 ) - ( ( Real )2 ) * df ) / dx3; } delete1( slope ); delete1( FDer ); }
IntpAkimaNonuniform1<Real>::IntpAkimaNonuniform1 (int iQuantity, Real* afX, Real* afF) : IntpAkima1<Real>(iQuantity,afF) { m_afX = afX; // compute slopes Real* afSlope = WM4_NEW Real[iQuantity+3]; int i, iP1, iP2; for (i = 0, iP1 = 1, iP2 = 2; i < iQuantity-1; i++, iP1++, iP2++) { Real fDX = afX[iP1] - afX[i]; Real fDF = afF[iP1] - afF[i]; afSlope[iP2] = fDF/fDX; } afSlope[1] = ((Real)2.0)*afSlope[2] - afSlope[3]; afSlope[0] = ((Real)2.0)*afSlope[1] - afSlope[2]; afSlope[iQuantity+1] = ((Real)2.0)*afSlope[iQuantity] - afSlope[iQuantity-1]; afSlope[iQuantity+2] = ((Real)2.0)*afSlope[iQuantity+1] - afSlope[iQuantity]; // construct derivatives Real* afFDer = WM4_NEW Real[iQuantity]; for (i = 0; i < iQuantity; i++) { afFDer[i] = ComputeDerivative(afSlope+i); } // construct polynomials for (i = 0, iP1 = 1; i < iQuantity-1; i++, iP1++) { typename IntpAkima1<Real>::Polynomial& rkPoly = m_akPoly[i]; Real fF0 = afF[i], fF1 = afF[iP1]; Real fFDer0 = afFDer[i], fFDer1 = afFDer[iP1]; Real fDF = fF1 - fF0; Real fDX = afX[iP1] - afX[i]; Real fDX2 = fDX*fDX, fDX3 = fDX2*fDX; rkPoly[0] = fF0; rkPoly[1] = fFDer0; rkPoly[2] = (((Real)3.0)*fDF-fDX*(fFDer1+((Real)2.0)*fFDer0))/fDX2; rkPoly[3] = (fDX*(fFDer0 + fFDer1)-((Real)2.0)*fDF)/fDX3; } WM4_DELETE[] afSlope; WM4_DELETE[] afFDer; }
void SpringSys::UpdateParticleState(TimeValue t, Tab<Matrix3> tmArray, int index, TimeValue Delta) { Point3 t_pos, t_vel, orig_pos, orig_vel; Matrix3 tm; for (int b=0;b<parts[index].GetSprings()->length();b++) { if (parts[index].GetSpring(b)->GetPointConstraint()->GetIndex() < tmArray.Count()) { tm = tmArray[parts[index].GetSpring(b)->GetPointConstraint()->index]; ComputeControlledParticleForce(tm, index, b); /* compute bone deriv used by ApplySpring */ } } Clear_Forces(index); /* zero the force accumulators */ Compute_Forces(t, index); /* magic force function */ ComputeDerivative(index, t_pos, t_vel); /* get deriv */ //ComputeDerivative(pIndex, t_pos, t_vel, Delta); /* get deriv */ ScaleVectors(t_pos, t_vel, Delta); /* scale it */ GetParticleState(index, orig_pos, orig_vel); /* get state */ AddVectors(orig_pos, orig_vel, t_pos, t_vel); /* add -> temp2 */ SetParticleState(index, t_pos, t_vel); /* update state */ }