21#include "boost/make_shared.hpp"
43template <
typename Func>
bool withRayTracer(
Instrument const &inst, Func
const &func) {
55Peak::Peak() :
BasePeak(), m_row(-1), m_col(-1), m_detectorID(-1), m_initialEnergy(0.), m_finalEnergy(0.) {}
68 std::optional<double> detectorDistance)
163 :
BasePeak(), m_row(-1), m_col(-1) {
170 const auto detectorDir =
V3D(sin(scattering), 0.0, cos(scattering));
187 :
BasePeak(ipeak), m_initialEnergy(ipeak.getInitialEnergy()), m_finalEnergy(ipeak.getFinalEnergy()) {
188 const auto *peak =
dynamic_cast<const Peak *
>(&ipeak);
190 throw std::invalid_argument(
"Cannot construct a Peak from this non-Peak object");
192 detid_t id = peak->getDetectorID();
200 std::optional<double> detectorDistance)
232 throw std::runtime_error(
"Peak::setInstrument(): No instrument is set!");
235 throw std::runtime_error(
"Peak::setInstrument(): No detector was found!");
261 parent = parent->getParent();
274 parent = parent->getParent();
282 std::pair<int, int> xy = retDet->getXYForDetectorID(
m_detectorID);
321 throw std::runtime_error(
"Peak::setInstrument(): No instrument is set!");
325 if (sourceObj ==
nullptr)
327 "to get source component from "
330 if (sampleObj ==
nullptr)
332 "to get sample component from "
390 return wavelength * 1e10;
399 double L1 = this->
getL1();
400 double L2 = this->
getL2();
408 double tof = L1 / vi + L2 / vf;
420 return detDir.
angle(beamDir);
429 return atan2(detDir.
Y(), detDir.
X());
436 detDir /= detDir.
norm();
444 beamDir /= beamDir.
norm();
457 two_theta = detDir.
angle(beamDir);
458 }
catch (std::runtime_error &) {
478 beamDir /= beamDir.
norm();
481 detDir /= detDir.
norm();
492 double wvi = 1.0 / wi;
500 return (beamDir * wvi - detDir * wvf) * qSign;
549 throw std::invalid_argument(
"Setting QLab without an instrument would lead "
550 "to an inconsistent state for the Peak");
569 const double norm_q = qLab.
norm();
571 throw std::invalid_argument(
"Peak::setQLabFrame(): Q cannot be 0,0,0.");
573 std::shared_ptr<const ReferenceFrame> refFrame = this->
m_inst->getReferenceFrame();
574 const V3D refBeamDir = refFrame->vecPointingAlongBeam();
576 const double qSign = (
m_convention !=
"Crystallography") ? 1.0 : -1.0;
577 const double qBeam = qLab.
scalar_prod(refBeamDir) * qSign;
580 throw std::invalid_argument(
"Peak::setQLabFrame(): Q cannot be 0 in the beam direction.");
582 const double one_over_wl = (norm_q * norm_q) / (2.0 * qBeam);
583 const double wl = (2.0 * M_PI) / one_over_wl;
585 std::ostringstream mess;
586 mess <<
"Peak::setQLabFrame(): Wavelength found was negative (" << wl <<
" Ang)! This Q is not physical.";
587 throw std::invalid_argument(mess.str());
593 V3D detectorDir = -qLab * qSign;
594 detectorDir[refFrame->pointingAlongBeam()] = one_over_wl - qBeam;
598 if (detectorDistance.has_value()) {
604 const bool found = withRayTracer(
608 g_log.
debug(
"Could not find detector after setting qLab via setQLab with "
618 const auto component =
getInstrument()->getComponentByName(
"extended-detector-space");
622 const auto object = std::dynamic_pointer_cast<const ObjComponent>(component);
624 return detectorDir * distance;
628 std::transform(
name.begin(),
name.end(),
name.begin(), ::tolower);
629 std::map<std::string, double> colVals = {
631 auto it = colVals.find(
name);
632 if (it != colVals.end())
684 detPos = detInfo.position(detIndex);
689 else if (
m_inst->hasParameter(
"tube-gap")) {
690 std::vector<double> gaps =
m_inst->getNumberParameter(
"tube-gap",
true);
692 const auto gap =
static_cast<double>(gaps.front());
695 for (
int i = 0; i < 3; i++) {
698 V3D beam1 = beam + gapDir;
701 V3D beam2 = beam - gapDir;
709 detPos = detInfo.position(detIndex1);
713 detPos = detInfo.position(detIndex2);
760 if (&other !=
this) {
789 if (det ==
nullptr) {
Structure describing a single-crystal peak.
Mantid::Kernel::Matrix< double > getInverseGoniometerMatrix() const
Get the goniometer rotation matrix at which this peak was measured.
BasePeak & operator=(BasePeak &&) noexcept=default
Mantid::Kernel::V3D m_samplePos
Cached sample position.
void setHKL(double H, double K, double L) override
Set all three H,K,L indices of the peak.
Mantid::Kernel::Matrix< double > getGoniometerMatrix() const override
Get the goniometer rotation matrix at which this peak was measured.
virtual double getValueByColName(std::string colName) const
Helper function for displaying/sorting peaks.
Structure describing a single-crystal peak.
Mantid::Kernel::V3D getQLabFrame() const final
Return the Q change (of the lattice, k_i - k_f) for this peak.
Structure describing a single-crystal peak.
int getCol() const override
For RectangularDetectors only, returns the column (x) of the pixel of the detector or -1 if not found...
void setQSampleFrame(const Mantid::Kernel::V3D &QSampleFrame, std::optional< double > detectorDistance=std::nullopt) override
Set the peak using the peak's position in reciprocal space, in the sample frame.
Mantid::Kernel::V3D getSourceDirectionSampleFrame() const override
Calculate the reverse incident beam direction in the sample frame
Geometry::Instrument_const_sptr getInstrument() const
Return a shared ptr to the instrument for this peak.
Geometry::IDetector_const_sptr m_det
Detector pointed to.
Peak()
Default constructor.
double getDSpacing() const override
Calculate the d-spacing of the peak, in 1/Angstroms
int m_row
Cached row in the detector.
const std::set< int > & getContributingDetIDs() const
Return the set of detector IDs that contribute to this peak.
void addContributingDetID(const int id)
Add a detector ID that contributed to this peak.
static Mantid::Kernel::Logger g_log
Static logger.
Mantid::Kernel::V3D getDetectorPosition() const
Forwarding function.
int getRow() const override
For RectangularDetectors only, returns the row (y) of the pixel of the detector or -1 if not found.
std::set< int > m_detIDs
List of contributing detectors IDs.
void setWavelength(double wavelength) override
Set the incident wavelength of the neutron.
std::string m_bankName
Name of the parent bank.
double getL1() const override
Return the L1 flight path length (source to sample), in meters.
void removeContributingDetector(const int id)
Removes an ID from the list of contributing detectors.
Mantid::Kernel::V3D detPos
Cached detector position.
Peak & operator=(Peak &&) noexcept=default
double getInitialEnergy() const override
Get the initial (incident) neutron energy in meV.
Mantid::Kernel::V3D getQLabFrame() const override
Return the Q change (of the lattice, k_i - k_f) for this peak.
void setRow(int row)
For RectangularDetectors only, sets the row (y) of the pixel of the detector.
void setQLabFrame(const Mantid::Kernel::V3D &qLab, std::optional< double > detectorDistance=std::nullopt) final
Set the peak using the peak's position in reciprocal space, in the lab frame.
void setDetectorID(int id)
Set the detector ID of the pixel at the centre of the peak and look up and cache values related to it...
double m_initialEnergy
Initial energy of neutrons at the peak.
void setBankName(std::string bankName)
Set the BankName of this peak.
Geometry::Instrument_const_sptr m_inst
Shared pointer to the instrument (for calculating some values )
double getEnergyTransfer() const override
Get the difference between the initial and final neutron energy in meV.
int getDetectorID() const override
Get the ID of the detector at the center of the peak
Mantid::Kernel::V3D sourcePos
Cached source position.
double getAzimuthal() const override
Calculate the azimuthal angle of the peak
int m_col
Cached column in the detector.
bool findDetector()
After creating a peak using the Q in the lab frame, the detPos is set to the direction of the detecto...
Geometry::IDetector_const_sptr getDetector() const
Return a shared ptr to the detector at center of peak.
Mantid::Kernel::V3D getDetectorDirectionSampleFrame() const override
Calculate the scattered beam direction in the sample frame
void setInitialEnergy(double m_initialEnergy) override
Set the initial energy.
double getFinalEnergy() const override
Get the final neutron energy in meV.
Kernel::V3D getVirtualDetectorPosition(const Kernel::V3D &detectorDir) const
Get the approximate position of a peak that falls off the detectors.
double getWavelength() const override
Calculate the neutron wavelength (in angstroms) at the peak (Note for inelastic scattering - it is th...
void setCol(int col)
For RectangularDetectors only, sets the column (x) of the pixel of the detector.
double getTOF() const override
Calculate the time of flight (in microseconds) of the neutrons for this peak, using the geometry of t...
std::shared_ptr< const Geometry::ReferenceFrame > getReferenceFrame() const override
Return a shared ptr to the reference frame from the instrument for this peak.
virtual Mantid::Kernel::V3D getDetPos() const
Return the detector position vector.
Mantid::Kernel::V3D getQSampleFrame() const override
Return the Q change (of the lattice, k_i - k_f) for this peak.
double getL2() const override
Return the L2 flight path length (sample to detector), in meters.
const std::string & getBankName() const
Find the name of the bank that is the parent of the detector.
void setInstrument(const Geometry::Instrument_const_sptr &inst)
Set the instrument (and save the source/sample pos).
void setFinalEnergy(double m_finalEnergy) override
Set the final energy.
double getScattering() const override
Calculate the scattering angle of the peak
double getValueByColName(std::string colName) const override
Helper function for displaying/sorting peaks.
Mantid::Kernel::V3D getDetectorPositionNoCheck() const
Forwarding function.
double m_finalEnergy
Final energy of the neutrons at peak (normally same as m_InitialEnergy)
int m_detectorID
ID of the detector.
static constexpr size_t invalidIndex
Returned by indexOfOrInvalid() for a component ID that is not part of this instrument.
bool isParametrized() const override
Return true if the Component is, in fact, parametrized (that is - it has a valid parameter map)
Structure describing a single-crystal peak.
This class is responsible for tracking rays and accumulating a list of objects that are intersected a...
const DetectorInfo & detectorInfo() const
void traceFromSample(const Kernel::V3D &dir) const
Trace a given track from the sample position in the given direction.
size_t getDetectorResult() const
Get the index of the first non-monitor detector intersected since the previous call to trace,...
std::pair< std::unique_ptr< ComponentInfo >, std::unique_ptr< DetectorInfo > > makeWrappers() const
Make the wrappers from the data collected by walkInstrument(), which must be called first.
std::shared_ptr< ParameterMap > getParameterMap() const
Pointer to the NOT const ParameterMap holding the parameters of the modified instrument components.
Defines a track as a start point and a direction.
Exception for errors associated with the instrument definition.
Exception thrown when an attempt is made to dereference a null pointer.
The Logger class is in charge of the publishing messages from the framework through various channels.
void debug(const std::string &msg)
Logs at debug level.
constexpr double scalar_prod(const V3D &v) const noexcept
Calculates the cross product.
constexpr double X() const noexcept
Get x.
double normalize()
Make a normalized vector (return norm value)
constexpr double Y() const noexcept
Get y.
std::string toString() const
double angle(const V3D &) const
Angle between this and another vector.
double norm() const noexcept
double cosAngle(const V3D &) const
cos(Angle) between this and another vector
std::shared_ptr< const IComponent > IComponent_const_sptr
Typdef of a shared pointer to a const IComponent.
std::shared_ptr< const RectangularDetector > RectangularDetector_const_sptr
std::shared_ptr< const Mantid::Geometry::IDetector > IDetector_const_sptr
Shared pointer to IDetector (const version)
std::shared_ptr< const Instrument > Instrument_const_sptr
Shared pointer to an const instrument object.
std::shared_ptr< Mantid::Geometry::IDetector > IDetector_sptr
Shared pointer to IDetector.
MANTID_KERNEL_DLL int endsWithInt(const std::string &word)
Get an int from the end of a word.
MANTID_KERNEL_DLL V3D normalize(V3D v)
Normalizes a V3D.
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.
static constexpr double h_bar
Planck constant in J*s, divided by 2 PI.
Helper class which provides the Collimation Length for SANS instruments.
int32_t detid_t
Typedef for a detector ID.
Generate a tableworkspace to store the calibration results.