[a7684e5] | 1 | # This is how a model would look if we were to stick it all into one file. |
---|
| 2 | r""" |
---|
| 3 | CylinderModel |
---|
| 4 | ============= |
---|
| 5 | |
---|
| 6 | This model provides the form factor for a right circular cylinder with uniform |
---|
| 7 | scattering length density. The form factor is normalized by the particle volume. |
---|
| 8 | |
---|
| 9 | For information about polarised and magnetic scattering, click here_. |
---|
| 10 | |
---|
| 11 | Definition |
---|
| 12 | ---------- |
---|
| 13 | |
---|
| 14 | The output of the 2D scattering intensity function for oriented cylinders is |
---|
| 15 | given by (Guinier, 1955) |
---|
| 16 | |
---|
| 17 | .. math:: |
---|
| 18 | |
---|
| 19 | P(q,\alpha) = \frac{\text{scale}}{V}f^2(q) + \text{bkg} |
---|
| 20 | |
---|
| 21 | where |
---|
| 22 | |
---|
| 23 | .. math:: |
---|
| 24 | |
---|
| 25 | f(q) = 2 (\Delta \rho) V |
---|
| 26 | \frac{\sin (q L/2 \cos \alpha)}{q L/2 \cos \alpha} |
---|
| 27 | \frac{J_1 (q r \sin \alpha)}{q r \sin \alpha} |
---|
| 28 | |
---|
| 29 | and $\alpha$ is the angle between the axis of the cylinder and $\vec q$, $V$ |
---|
| 30 | is the volume of the cylinder, $L$ is the length of the cylinder, $r$ is the |
---|
| 31 | radius of the cylinder, and $d\rho$ (contrast) is the scattering length density |
---|
| 32 | difference between the scatterer and the solvent. $J_1$ is the first order |
---|
| 33 | Bessel function. |
---|
| 34 | |
---|
| 35 | To provide easy access to the orientation of the cylinder, we define the |
---|
| 36 | axis of the cylinder using two angles $\theta$ and $\phi$. Those angles |
---|
| 37 | are defined in Figure :num:`figure #CylinderModel-orientation`. |
---|
| 38 | |
---|
| 39 | .. _CylinderModel-orientation: |
---|
| 40 | |
---|
| 41 | .. figure:: img/image061.JPG |
---|
| 42 | |
---|
| 43 | Definition of the angles for oriented cylinders. |
---|
| 44 | |
---|
| 45 | .. figure:: img/image062.JPG |
---|
| 46 | |
---|
| 47 | Examples of the angles for oriented pp against the detector plane. |
---|
| 48 | |
---|
| 49 | NB: The 2nd virial coefficient of the cylinder is calculated based on the |
---|
| 50 | radius and length values, and used as the effective radius for $S(Q)$ |
---|
| 51 | when $P(Q) \cdot S(Q)$ is applied. |
---|
| 52 | |
---|
| 53 | The returned value is scaled to units of |cm^-1| and the parameters of |
---|
| 54 | the CylinderModel are the following: |
---|
| 55 | |
---|
| 56 | %(parameters)s |
---|
| 57 | |
---|
| 58 | The output of the 1D scattering intensity function for randomly oriented |
---|
| 59 | cylinders is then given by |
---|
| 60 | |
---|
| 61 | .. math:: |
---|
| 62 | |
---|
| 63 | P(q) = \frac{\text{scale}}{V} |
---|
| 64 | \int_0^{\pi/2} f^2(q,\alpha) \sin \alpha d\alpha + \text{background} |
---|
| 65 | |
---|
| 66 | The *theta* and *phi* parameters are not used for the 1D output. Our |
---|
| 67 | implementation of the scattering kernel and the 1D scattering intensity |
---|
| 68 | use the c-library from NIST. |
---|
| 69 | |
---|
| 70 | Validation of the CylinderModel |
---|
| 71 | ------------------------------- |
---|
| 72 | |
---|
| 73 | Validation of our code was done by comparing the output of the 1D model |
---|
| 74 | to the output of the software provided by the NIST (Kline, 2006). |
---|
| 75 | Figure :num:`figure #CylinderModel-compare` shows a comparison of |
---|
| 76 | the 1D output of our model and the output of the NIST software. |
---|
| 77 | |
---|
| 78 | .. _CylinderModel-compare: |
---|
| 79 | |
---|
| 80 | .. figure:: img/image065.JPG |
---|
| 81 | |
---|
| 82 | Comparison of the SasView scattering intensity for a cylinder with the |
---|
| 83 | output of the NIST SANS analysis software. |
---|
| 84 | The parameters were set to: *Scale* = 1.0, *Radius* = 20 |Ang|, |
---|
| 85 | *Length* = 400 |Ang|, *Contrast* = 3e-6 |Ang^-2|, and |
---|
| 86 | *Background* = 0.01 |cm^-1|. |
---|
| 87 | |
---|
| 88 | In general, averaging over a distribution of orientations is done by |
---|
| 89 | evaluating the following |
---|
| 90 | |
---|
| 91 | .. math:: |
---|
| 92 | |
---|
| 93 | P(q) = \int_0^{\pi/2} d\phi |
---|
| 94 | \int_0^\pi p(\theta, \phi) P_0(q,\alpha) \sin \theta d\theta |
---|
| 95 | |
---|
| 96 | |
---|
| 97 | where $p(\theta,\phi)$ is the probability distribution for the orientation |
---|
| 98 | and $P_0(q,\alpha)$ is the scattering intensity for the fully oriented |
---|
| 99 | system. Since we have no other software to compare the implementation of |
---|
| 100 | the intensity for fully oriented cylinders, we can compare the result of |
---|
| 101 | averaging our 2D output using a uniform distribution $p(\theta, \phi) = 1.0$. |
---|
| 102 | Figure :num:`figure #CylinderModel-crosscheck` shows the result of |
---|
| 103 | such a cross-check. |
---|
| 104 | |
---|
| 105 | .. _CylinderModel-crosscheck: |
---|
| 106 | |
---|
| 107 | .. figure:: img/image066.JPG |
---|
| 108 | |
---|
| 109 | Comparison of the intensity for uniformly distributed cylinders |
---|
| 110 | calculated from our 2D model and the intensity from the NIST SANS |
---|
| 111 | analysis software. |
---|
| 112 | The parameters used were: *Scale* = 1.0, *Radius* = 20 |Ang|, |
---|
| 113 | *Length* = 400 |Ang|, *Contrast* = 3e-6 |Ang^-2|, and |
---|
| 114 | *Background* = 0.0 |cm^-1|. |
---|
| 115 | """ |
---|
| 116 | |
---|
| 117 | from numpy import pi, inf |
---|
| 118 | |
---|
| 119 | name = "cylinder" |
---|
| 120 | title = "Cylinder with uniform scattering length density" |
---|
| 121 | description = """ |
---|
| 122 | f(q)= 2*(sldCyl - sldSolv)*V*sin(qLcos(alpha/2)) |
---|
| 123 | /[qLcos(alpha/2)]*J1(qRsin(alpha/2))/[qRsin(alpha)] |
---|
| 124 | |
---|
| 125 | P(q,alpha)= scale/V*f(q)^(2)+background |
---|
| 126 | V: Volume of the cylinder |
---|
| 127 | R: Radius of the cylinder |
---|
| 128 | L: Length of the cylinder |
---|
| 129 | J1: The bessel function |
---|
| 130 | alpha: angle betweenthe axis of the |
---|
| 131 | cylinder and the q-vector for 1D |
---|
| 132 | :the ouput is P(q)=scale/V*integral |
---|
| 133 | from pi/2 to zero of... |
---|
| 134 | f(q)^(2)*sin(alpha)*dalpha+ bkg |
---|
| 135 | """ |
---|
| 136 | |
---|
| 137 | parameters = [ |
---|
| 138 | # [ "name", "units", default, [lower, upper], "type", |
---|
| 139 | # "description" ], |
---|
| 140 | [ "sld", "1e-6/Ang^2", 4, [-inf,inf], "", |
---|
| 141 | "Cylinder scattering length density" ], |
---|
| 142 | [ "solvent_sld", "1e-6/Ang^2", 1, [-inf,inf], "", |
---|
| 143 | "Solvent scattering length density" ], |
---|
| 144 | [ "radius", "Ang", 20, [0, inf], "volume", |
---|
| 145 | "Cylinder radius" ], |
---|
| 146 | [ "length", "Ang", 400, [0, inf], "volume", |
---|
| 147 | "Cylinder length" ], |
---|
| 148 | [ "theta", "degrees", 60, [-inf, inf], "orientation", |
---|
| 149 | "In plane angle" ], |
---|
| 150 | [ "phi", "degrees", 60, [-inf, inf], "orientation", |
---|
| 151 | "Out of plane angle" ], |
---|
| 152 | ] |
---|
| 153 | |
---|
| 154 | source = [ "lib/J1.c", "lib/gauss76.c", "lib/cylkernel.c" ] |
---|
| 155 | |
---|
[5d4777d] | 156 | form_volume = """ |
---|
[a7684e5] | 157 | return M_PI*radius*radius*length; |
---|
[5d4777d] | 158 | """ |
---|
[a7684e5] | 159 | |
---|
[5d4777d] | 160 | Iq = """ |
---|
[a7684e5] | 161 | const real h = REAL(0.5)*length; |
---|
| 162 | real summ = REAL(0.0); |
---|
| 163 | for (int i=0; i<76 ;i++) { |
---|
| 164 | //const real zi = ( Gauss76Z[i]*(uplim-lolim) + uplim + lolim )/2.0; |
---|
| 165 | const real zi = REAL(0.5)*(Gauss76Z[i]*M_PI_2 + M_PI_2); |
---|
| 166 | summ += Gauss76Wt[i] * CylKernel(q, radius, h, zi); |
---|
| 167 | } |
---|
| 168 | //const real form = (uplim-lolim)/2.0*summ; |
---|
| 169 | const real form = summ * M_PI_4; |
---|
| 170 | |
---|
| 171 | // Multiply by contrast^2, normalize by cylinder volume and convert to cm-1 |
---|
| 172 | // NOTE that for this (Fournet) definition of the integral, one must MULTIPLY by Vcyl |
---|
| 173 | // The additional volume factor is for polydisperse volume normalization. |
---|
| 174 | const real s = (sld - solvent_sld) * form_volume(radius, length); |
---|
| 175 | return REAL(1.0e-4) * form * s * s; |
---|
[5d4777d] | 176 | """ |
---|
[a7684e5] | 177 | |
---|
[5d4777d] | 178 | Iqxy = """ |
---|
[a7684e5] | 179 | real sn, cn; // slots to hold sincos function output |
---|
| 180 | |
---|
| 181 | // Compute angle alpha between q and the cylinder axis |
---|
| 182 | SINCOS(theta*M_PI_180, sn, cn); |
---|
| 183 | // # The following correction factor exists in sasview, but it can't be |
---|
| 184 | // # right, so we are leaving it out for now. |
---|
| 185 | // const real correction = fabs(cn)*M_PI_2; |
---|
| 186 | const real q = sqrt(qx*qx+qy*qy); |
---|
| 187 | const real cos_val = cn*cos(phi*M_PI_180)*(qx/q) + sn*(qy/q); |
---|
| 188 | const real alpha = acos(cos_val); |
---|
| 189 | |
---|
| 190 | // The following is CylKernel() / sin(alpha), but we are doing it in place |
---|
| 191 | // to avoid sin(alpha)/sin(alpha) for alpha = 0. It is also a teensy bit |
---|
| 192 | // faster since we don't mulitply and divide sin(alpha). |
---|
| 193 | SINCOS(alpha, sn, cn); |
---|
| 194 | const real besarg = q*radius*sn; |
---|
| 195 | const real siarg = REAL(0.5)*q*length*cn; |
---|
| 196 | // lim_{x->0} J1(x)/x = 1/2, lim_{x->0} sin(x)/x = 1 |
---|
| 197 | const real bj = (besarg == REAL(0.0) ? REAL(0.5) : J1(besarg)/besarg); |
---|
| 198 | const real si = (siarg == REAL(0.0) ? REAL(1.0) : sin(siarg)/siarg); |
---|
| 199 | const real form = REAL(4.0)*bj*bj*si*si; |
---|
| 200 | |
---|
| 201 | // Multiply by contrast^2, normalize by cylinder volume and convert to cm-1 |
---|
| 202 | // NOTE that for this (Fournet) definition of the integral, one must MULTIPLY by Vcyl |
---|
| 203 | // The additional volume factor is for polydisperse volume normalization. |
---|
| 204 | const real s = (sld - solvent_sld) * form_volume(radius, length); |
---|
| 205 | return REAL(1.0e-4) * form * s * s; // * correction; |
---|
[5d4777d] | 206 | """ |
---|
[a7684e5] | 207 | |
---|
| 208 | def ER(radius, length): |
---|
| 209 | ddd = 0.75*radius*(2*radius*length + (length+radius)*(length+pi*radius)) |
---|
| 210 | return 0.5 * (ddd)**(1./3.) |
---|
| 211 | |
---|