Skip to content

Conversation

@RabiyaF
Copy link
Member

@RabiyaF RabiyaF commented Dec 2, 2025

Description of work

Closes #40299 .

To test:


Reviewer

Your comments will be used as part of the gatekeeper process. Comment clearly on what you have checked and tested during your review. Provide an audit trail for any changes requested.

As per the review guidelines:

  • Is the code of an acceptable quality? (Code standards/GUI standards)
  • Has a thorough functional test been performed? Do the changes handle unexpected input/situations?
  • Are appropriately scoped unit and/or system tests provided?
  • Do the release notes conform to the guidelines and describe the changes appropriately?
  • Has the relevant (user and developer) documentation been added/updated?
  • If the PR author isn’t in the mantid-developers or mantid-contributors teams, add a review comment rerun ci to authorize/rerun the CI

Gatekeeper

As per the gatekeeping guidelines:

  • Has a thorough first line review been conducted, including functional testing?
  • At a high-level, is the code quality sufficient?
  • Are the base, milestone and labels correct?

@RabiyaF RabiyaF added this to the Release 6.15 milestone Dec 2, 2025
@RabiyaF RabiyaF force-pushed the 40299-create-flatcell-algorithm branch from b679e70 to c596faa Compare December 8, 2025 22:34
@RabiyaF RabiyaF force-pushed the 40299-create-flatcell-algorithm branch from 24c3b5d to 3893c22 Compare January 5, 2026 22:43
@RabiyaF RabiyaF marked this pull request as ready for review January 6, 2026 11:39
@RabiyaF
Copy link
Member Author

RabiyaF commented Jan 6, 2026

The logic for the flatcell algorithm should now work with event workspaces and produce an xml file with the detector ids that need to be masked. Like I mentioned in the meeting, I think the excel sheet had a mistake in indexing the High Angle Banks (HAB). So, I have tried to correct those in the algorithm. The rest of the steps should be the same. Because of this change the results are not exactly equivalent to the ones provided in the reference file (113953). I think this PR will benefit from a review at this stage. I have also updated the system tests to output the X values as detector IDs (as was requested in the meeting). If there is a need to add more unit tests then let me know (I looked into it but because of the private methods - I could not).

@RabiyaF RabiyaF requested a review from MialLewis January 6, 2026 12:14
Copy link
Contributor

@MialLewis MialLewis left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for this, looks like we're not too far off.

First round of comments.

/// Execution code
void exec() override;
void execEvent();
double mean(const std::vector<double> &values);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Mark methods that's don't mutate class member variables const


// Validate the number of histograms in the Input WS
const size_t nHist = inputWS->getNumberHistograms();
if (nHist == 0) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can probably combine these two nHost checks into one.

Would also be good to give some context around the 17776 number too.


// The output is expected to have 17784 values (nHist+nMonitorOffset)
const int nMonitorOffset{8};
const int totalDetectorIDs{17784};
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's a lot of variables defined and numbers hardcoded related to LOQ pixel numbers.

Could we abstract these into a helper class that can be shared between algorithms if necessary?

/** Computes the mean of the input vector
*/
double FlatCell::mean(const std::vector<double> &values) {
return std::accumulate(values.begin(), values.end(), 0.0) / static_cast<double>(values.size());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we're not mutating the item's in values, we can use the constant iterators cbegin, cend etc.

WorkspaceFactory::Instance().create("Workspace2D", 1, totalDetectorIDs, totalDetectorIDs);
setProperty("OutputWorkspace", outputWS);

// Clone input before rebinning
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why clone before rebin, rather than just specifying a different output name?

std::vector<double> unmaskedLAB(outY.begin() + LABStart, outY.begin() + LABStop);
std::vector<double> unmaskedHAB(outY.begin() + HABStart, outY.begin() + HABStop);

// Calculate the thresholds
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we allow users to specify the threshold multipliers as an input property?

const double maskingThresholdLAB = 1 + normStdLAB;
const double maskingThresholdHAB = 1 + (0.5 * normStdHAB);

// Mask the LAB and HAB
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suspect a user might want to play around with the thresholds to see what is appropriate for a given run.

Could you allow the user a checkbox option to either apply the mask directly to to generate a separate mask workspace?

FlatCell::maskByThreshold(unmaskedLAB, maskingThresholdLAB);
FlatCell::maskByThreshold(unmaskedHAB, maskingThresholdHAB);

// Copy each of the vectors to outY
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Again, can we avoid the copy?

std::copy(unmaskedLAB.begin(), unmaskedLAB.end(), maskedOutY.begin() + LABStart);
std::copy(unmaskedHAB.begin(), unmaskedHAB.end(), maskedOutY.begin() + HABStart);

// Determine which detector IDs need to be masked
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This section of code relates to generating the mask file.

Currently SANS generate mask files using the instrument view, which I believe uses the SaveMask algorithm to save a mask workspace as an XML:

file. This algorithm has previously been renamed from SaveDetectorMasks.

I suggest the workflow be:

  1. Use MaskDetectorsIf algorithm to produce a workspace with applied mask. You can mask here conditionally based upon
  2. Extract mask workspace from workspace using ExtractMask. Output mask workspace to ads if user specifies.
  3. Use SaveMask on the mask workspace to save file as XML
  4. Output either the masked or unmasked workspace, depending on user input.

using namespace Mantid::DataObjects;

void FlatCell::init() {
declareProperty(std::make_unique<WorkspaceProperty<EventWorkspace>>("InputWorkspace", "", Direction::Input),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think your implementation would allow for the inputing of old non-event workspaces quite easily? It would be quite nice to be able to generate old mask workspaces to prove the logic.

If you make this a MatrixWorkspace property we could take both event and histo workspaces.

Perhaps come back to this at the end as a lower priority.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Create Mantid Algorithm to generate a FlatCell workspace

2 participants