10 #include <itkSymmetricEigenAnalysis.h> 16 std::string sampleDirFileName)
18 std::vector <std::vector <double> > resVal;
20 if (sampleDirFileName ==
"")
22 if ((nbTheta == 0)&&(nbPhi == 0))
25 std::vector <double> tmpVector(2,0);
26 for (
unsigned int i = 0;i < nbTheta;++i)
29 tmpVector[0] = M_PI/(4*nbTheta) + i*M_PI/(2*nbTheta);
30 for (
unsigned int j = 0;j < nbPhi;++j)
33 tmpVector[1] = M_PI/nbPhi + 2*i*M_PI/nbPhi;
34 resVal.push_back(tmpVector);
40 std::ifstream inputDirectionsFile(sampleDirFileName.c_str());
41 std::string errorMsg =
"Could not open sample directions file (";
42 errorMsg += sampleDirFileName;
45 if (!inputDirectionsFile.is_open())
46 throw itk::ExceptionObject(__FILE__, __LINE__,errorMsg,ITK_LOCATION);
48 std::vector <double> gradTmp(3,0);
49 std::vector <double> sphericalGrad(2,0);
51 std::cout <<
"Using sample directions from file " << sampleDirFileName.c_str() <<
"..." << std::endl;
53 while (!inputDirectionsFile.eof())
56 inputDirectionsFile.getline(tmpStr,2048);
58 if (strcmp(tmpStr,
"") == 0)
61 std::stringstream tmpStrStream(tmpStr);
62 tmpStrStream >> gradTmp[0] >> gradTmp[1] >> gradTmp[2];
65 resVal.push_back(sphericalGrad);
68 inputDirectionsFile.close();
83 resVal[0] = std::atan2(R(1,2),R(0,2));
84 resVal[1] = std::acos(R(2,2));
85 resVal[2] = std::atan2(R(2,1),-R(2,0));
90 resVal[0] = - std::acos(R(0,0));
92 resVal[0] = std::acos(R(0,0));
99 double GetDValue(
unsigned int l,
int m,
int mp,
double angle)
102 if ((m - mp) % 2 == 1)
105 long double factor = std::sqrt(std::tgamma(l+m+1) * std::tgamma(l-m+1) *
106 std::tgamma(l+mp+1) * std::tgamma(l-mp+1));
109 if (lowBoundK < mp - m)
112 int supBoundK = l + mp;
113 if (supBoundK > (
int)l - m)
114 supBoundK = (int)l - m;
116 long double resVal = 0;
118 for (
int k = lowBoundK;k <= supBoundK;++k)
120 long double cosVal = 1, sinVal = 1;
122 long double factDenom = std::tgamma(k+1) * std::tgamma(l - m - k + 1) *
123 std::tgamma(l + mp - k + 1) * std::tgamma(m - mp + k + 1);
125 int powNum = 2*(l-k) - m + mp;
127 double cosValTmp = cos(angle/2);
128 for (
int i = 1;i <= abs(powNum);++i)
134 powNum = 2*k + m - mp;
136 long double sinValTmp = sin(angle/2);
137 for (
int i = 1;i <= abs(powNum);++i)
147 resVal += kSign*cosVal*sinVal/factDenom;
150 resVal *= factor*globalSign;
155 double alpha,
double beta,
double gamma)
157 unsigned int sizeMat = 2*l + 1;
158 resVal.set_size(sizeMat,sizeMat);
161 vnl_matrix <double> dValues(2*l+1,2*l+1);
164 for (
unsigned int m = 1;m <= l;++m)
167 for (
unsigned int mp = 1;mp <= l;++mp)
169 for (
unsigned int m = 1;m <= l;++m)
171 dValues(m+l,mp+l) =
GetDValue(l,m,mp,beta);
172 dValues(l-m,mp+l) =
GetDValue(l,-m,mp,beta);
176 for (
int m = -l;m < 0;++m)
178 unsigned int absm = abs(m);
184 for (
int mp = -l;mp < 0;++mp)
191 unsigned int absmp = abs(mp);
192 resVal(m+l,mp+l) = dValues(absmp+l,absm+l)*cos(m*alpha+mp*gamma) + signmp*dValues(m+l,absmp+l)*cos(m*alpha-mp*gamma);
195 for (
int mp = 1;mp <= (int)l;++mp)
198 resVal(m+l,mp+l) = dValues(m+l,mp+l)*sin(m*alpha+mp*gamma) - signm*dValues(l+absm,l+mp)*sin(m*alpha-mp*gamma);
202 for (
int m = 1;m <= (int)l;++m)
208 for (
int mp = -l;mp < 0;++mp)
219 resVal(m+l,mp+l) = - signall*dValues(l-m,l-mp)*sin(m*alpha+mp*gamma) + signmp1*dValues(l+m,l-mp)*sin(m*alpha-mp*gamma);
223 for (
int mp = 1;mp <= (int)l;++mp)
226 resVal(m+l,mp+l) = dValues(l+m,l+mp)*cos(m*alpha+mp*gamma) + signm1*dValues(l-m,l+mp)*cos(m*alpha-mp*gamma);
232 double sqrt2 = sqrt(2.0);
233 for (
int m = 1;m <= (int)l;++m)
235 double dValue = dValues(l+m,l);
236 double oppDValue = dValue;
240 resVal(l-m,l) = sqrt2*oppDValue*cos(m*alpha);
241 resVal(l,l-m) = sqrt2*dValue*cos(m*gamma);
243 resVal(m+l,l) = - sqrt2*dValue*sin(m*alpha);
244 resVal(l,m+l) = sqrt2*oppDValue*sin(m*gamma);
void GetEulerAnglesFromRotationMatrix(vnl_matrix< double > &R, std::vector< double > &resVal)
void EstimateLocalODFRotationMatrix(vnl_matrix< double > &resVal, unsigned int l, double alpha, double beta, double gamma)
double GetDValue(unsigned int l, int m, int mp, double angle)
std::vector< std::vector< double > > InitializeSampleDirections(unsigned int nbTheta, unsigned int nbPhi, std::string sampleDirFileName)
void TransformCartesianToSphericalCoordinates(const VectorType &v, VectorType &resVec)