Mantid
Loading...
Searching...
No Matches
LeanElasticPeak.cpp
Go to the documentation of this file.
1// Mantid Repository : https://github.com/mantidproject/mantid
2//
3// Copyright © 2018 ISIS Rutherford Appleton Laboratory UKRI,
4// NScD Oak Ridge National Laboratory, European Spallation Source,
5// Institut Laue - Langevin & CSNS, Institute of High Energy Physics, CAS
6// SPDX - License - Identifier: GPL - 3.0 +
13
14#include "boost/make_shared.hpp"
15
16#include <algorithm>
17#include <cctype>
18#include <string>
19#include <utility>
20
21using namespace Mantid;
22using namespace Mantid::Kernel;
23using namespace Mantid::Geometry;
24
25namespace Mantid::DataObjects {
26
27//----------------------------------------------------------------------------------------------
29LeanElasticPeak::LeanElasticPeak() : BasePeak(), m_Qsample(V3D(0, 0, 0)), m_wavelength(0.) {}
30
31//----------------------------------------------------------------------------------------------
40 : BasePeak(), m_Qsample(QSampleFrame), m_wavelength(0.) {}
41
42//----------------------------------------------------------------------------------------------
51 const Mantid::Kernel::Matrix<double> &goniometer,
52 std::optional<std::shared_ptr<const Geometry::ReferenceFrame>> refFrame)
53 : BasePeak() {
54 if (refFrame.has_value())
55 setReferenceFrame(refFrame.value());
56 setQSampleFrame(QSampleFrame, goniometer);
57}
58
59//----------------------------------------------------------------------------------------------
68LeanElasticPeak::LeanElasticPeak(const Mantid::Kernel::V3D &QSampleFrame, double wavelength)
69 : BasePeak(), m_Qsample(QSampleFrame), m_wavelength(wavelength) {}
70
76
77//----------------------------------------------------------------------------------------------
83 : BasePeak(ipeak), m_Qsample(ipeak.getQSampleFrame()), m_wavelength(ipeak.getWavelength()) {}
84
85//----------------------------------------------------------------------------------------------
90void LeanElasticPeak::setWavelength(double wavelength) { m_wavelength = wavelength; }
91
93std::shared_ptr<const Geometry::ReferenceFrame> LeanElasticPeak::getReferenceFrame() const {
94 return (m_refFrame) ? m_refFrame : std::make_shared<const ReferenceFrame>();
95}
96
101void LeanElasticPeak::setReferenceFrame(std::shared_ptr<const ReferenceFrame> frame) { m_refFrame = std::move(frame); }
102
103// -------------------------------------------------------------------------------------
106
107// -------------------------------------------------------------------------------------
112 throw Exception::NotImplementedError("LeanElasticPeak::getTOF(): no detector infomation in LeanElasticPeak");
113}
114
115// returns the detectorID of the pixel, throws NotImplementedError for LeanElasticPeak
117 throw Exception::NotImplementedError("LeanElasticPeak::getDetectorID(): no detector infomation in LeanElasticPeak");
118}
119
122 throw Exception::NotImplementedError("LeanElasticPeak::getRow(): no detector infomation in LeanElasticPeak");
123}
124
127 throw Exception::NotImplementedError("LeanElasticPeak::getCol(): no detector infomation in LeanElasticPeak");
128}
129
130// -------------------------------------------------------------------------------------
132double LeanElasticPeak::getScattering() const { return asin(getWavelength() / (2 * getDSpacing())) * 2; }
133
134// -------------------------------------------------------------------------------------
137 const V3D qLab = getQLabFrame();
138 std::shared_ptr<const ReferenceFrame> refFrame = getReferenceFrame();
139 const double qSign = (m_convention != "Crystallography") ? 1.0 : -1.0;
140 const V3D detectorDir = -qLab * qSign;
141 if (refFrame)
142 return atan2(detectorDir[refFrame->pointingUp()], detectorDir[refFrame->pointingHorizontal()]);
143 else
144 return atan2(detectorDir[1], detectorDir[0]);
145}
146
147// -------------------------------------------------------------------------------------
150 const V3D qSample = getQSampleFrame();
151 const double qSign = (m_convention != "Crystallography") ? 1.0 : -1.0;
152 return getSourceDirectionSampleFrame() * -1.0 - qSample * qSign * getWavelength() / (2 * M_PI);
153}
154
155// -------------------------------------------------------------------------------------
158 std::shared_ptr<const ReferenceFrame> refFrame = getReferenceFrame();
159 if (refFrame)
160 return getInverseGoniometerMatrix() * refFrame->vecPointingAlongBeam() * -1.0;
161 else
162 return getInverseGoniometerMatrix() * V3D(0, 0, -1);
163}
164
165// -------------------------------------------------------------------------------------
167double LeanElasticPeak::getDSpacing() const { return 2 * M_PI / m_Qsample.norm(); }
168
169//----------------------------------------------------------------------------------------------
176
177//----------------------------------------------------------------------------------------------
181
182//----------------------------------------------------------------------------------------------
190void LeanElasticPeak::setQSampleFrame(const Mantid::Kernel::V3D &QSampleFrame, std::optional<double>) {
191 m_Qsample = QSampleFrame;
192}
193
195 const Mantid::Kernel::Matrix<double> &goniometer) {
196 m_Qsample = QSampleFrame;
197 setGoniometerMatrix(goniometer);
198
199 const V3D qLab = getQLabFrame();
200
201 try {
202 double wl = calculateWavelengthFromQLab(qLab);
203 setWavelength(wl);
204 } catch (std::exception &e) {
205 g_log.information() << "Unable to automatically determine wavelength from q-lab\n"
206 << e.what() << ", goniometer is likely not correct\n";
207 }
208}
209
210//----------------------------------------------------------------------------------------------
219void LeanElasticPeak::setQLabFrame(const Mantid::Kernel::V3D &qLab, std::optional<double>) {
221}
222
223//----------------------------------------------------------------------------------------------
226 // Velocity of the neutron (non-relativistic)
227 const double velocity = PhysicalConstants::h / (m_wavelength * 1e-10 * PhysicalConstants::NeutronMass);
228 // Energy in J of the neutron
229 const double energy = PhysicalConstants::NeutronMass * velocity * velocity / 2.0;
230 // Convert to meV
232}
233
236
239double LeanElasticPeak::getEnergyTransfer() const { return 0.; }
240
243 throw Exception::NotImplementedError("Use LeanElasticPeak::setWavelength");
244}
245
248 throw Exception::NotImplementedError("Use LeanElasticPeak::setWavelength");
249}
250
251// -------------------------------------------------------------------------------------
254 throw Exception::NotImplementedError("LeanElasticPeak has no detector information");
255}
256
257// -------------------------------------------------------------------------------------
260 throw Exception::NotImplementedError("LeanElasticPeak has no detector information");
261}
262
269 if (&other != this) {
270 BasePeak::operator=(other);
271 m_Qsample = other.m_Qsample;
272 m_wavelength = other.m_wavelength;
273 }
274 return *this;
275}
276
278
279} // namespace Mantid::DataObjects
double energy
Definition GetAllEi.cpp:157
Structure describing a single-crystal peak.
Definition BasePeak.h:33
Mantid::Kernel::Matrix< double > getInverseGoniometerMatrix() const
Get the goniometer rotation matrix at which this peak was measured.
Definition BasePeak.cpp:213
BasePeak & operator=(BasePeak &&) noexcept=default
double calculateWavelengthFromQLab(const Mantid::Kernel::V3D &qLab)
Definition BasePeak.cpp:349
Mantid::Kernel::Matrix< double > getGoniometerMatrix() const override
Get the goniometer rotation matrix at which this peak was measured.
Definition BasePeak.cpp:209
void setGoniometerMatrix(const Mantid::Kernel::Matrix< double > &goniometerMatrix) override
Set the goniometer rotation matrix at which this peak was measured.
Definition BasePeak.cpp:219
Structure describing a single-crystal peak.
void setQSampleFrame(const Mantid::Kernel::V3D &QSampleFrame, std::optional< double >=std::nullopt) override
Set the peak using the peak's position in reciprocal space, in the sample frame.
int getCol() const override
returns the column (x) of the pixel of the detector, throws NotImplementedError for LeanElasticPeak
std::shared_ptr< const Geometry::ReferenceFrame > getReferenceFrame() const override
Return a shared ptr to the reference frame for this peak.
Mantid::Kernel::V3D getDetectorDirectionSampleFrame() const override
Calculate the scattered beam direction in the sample frame
void setWavelength(double wavelength) override
Set the wavelength of the neutron.
void setFinalEnergy(double m_finalEnergy) override
Set the final energy.
double getWavelength() const override
Return the neutron wavelength (in angstroms)
std::shared_ptr< const Geometry::ReferenceFrame > m_refFrame
double getAzimuthal() const override
Calculate the azimuthal angle of the peak
double getEnergyTransfer() const override
Get the difference between the initial and final neutron energy in meV, elastic so always 0.
double getL1() const override
Return the L1 flight path length (source to sample), in meters.
static Mantid::Kernel::Logger g_log
Static logger.
double m_wavelength
Wavelength of neutrons at the peak.
Mantid::Kernel::V3D getQSampleFrame() const override
Return the Q change (of the lattice, k_i - k_f) for this peak.
void setInitialEnergy(double m_initialEnergy) override
Set the initial energy.
Mantid::Kernel::V3D m_Qsample
Q_sample vector.
Mantid::Kernel::V3D getSourceDirectionSampleFrame() const override
Calculate the reverse incident beam direction in the sample frame
double getFinalEnergy() const override
Get the final neutron energy in meV.
double getScattering() const override
Calculate the scattering angle of the peak
double getTOF() const override
Calculate the time of flight (in microseconds) of the neutrons for this peak, using the geometry of t...
double getDSpacing() const override
Calculate the d-spacing of the peak, in 1/Angstroms
int getRow() const override
returns the row (y) of the pixel of the detector, throws NotImplementedError for LeanElasticPeak
double getInitialEnergy() const override
Get the initial (incident) neutron energy in meV.
void setReferenceFrame(std::shared_ptr< const Geometry::ReferenceFrame > frame)
Setter for the reference frame.
double getL2() const override
Return the L2 flight path length (sample to detector), in meters.
Mantid::Kernel::V3D getQLabFrame() const final
Return the Q change (of the lattice, k_i - k_f) for this peak.
LeanElasticPeak & operator=(LeanElasticPeak &&) noexcept=default
void setQLabFrame(const Mantid::Kernel::V3D &qLab, std::optional< double >=std::nullopt) override
Set the peak using the peak's position in reciprocal space, in the lab frame.
Structure describing a single-crystal peak.
Definition IPeak.h:26
Marks code as not implemented yet.
Definition Exception.h:138
The Logger class is in charge of the publishing messages from the framework through various channels.
Definition Logger.h:51
void information(const std::string &msg)
Logs at information level.
Definition Logger.cpp:136
Numerical Matrix class.
Definition Matrix.h:42
Class for 3D vectors.
Definition V3D.h:34
double norm() const noexcept
Definition V3D.h:269
static constexpr double NeutronMass
Mass of the neutron in kg.
static constexpr double h
Planck constant in J*s.
static constexpr double meV
1 meV in Joules.
Helper class which provides the Collimation Length for SANS instruments.