use of uk.ac.sussex.gdsc.smlm.results.filter.MultiPathFilter in project GDSC-SMLM by aherbert.
the class BenchmarkSpotFit method showDialog.
private boolean showDialog() {
ExtendedGenericDialog gd = new ExtendedGenericDialog(TITLE);
gd.addHelp(HelpUrls.getUrl("fit-spot-data"));
ImageJUtils.addMessage(gd, "Fit candidate spots in the benchmark image created by " + CreateData.TITLE + " plugin\nand identified by the " + BenchmarkSpotFilter.TITLE + " plugin.\nPSF width = %s nm (Square pixel adjustment = %s nm)\n \n" + "Configure the fitting:", MathUtils.rounded(simulationParameters.sd), MathUtils.rounded(getSa()));
gd.addSlider("Fraction_positives", 50, 100, settings.fractionPositives);
gd.addSlider("Fraction_negatives_after_positives", 0, 100, settings.fractionNegativesAfterAllPositives);
gd.addSlider("Min_negatives_after_positives", 0, 30, settings.negativesAfterAllPositives);
gd.addSlider("Match_distance", 0.5, 3.5, settings.distance);
gd.addSlider("Lower_distance", 0, 3.5, settings.lowerDistance);
gd.addSlider("Match_signal", 0, 3.5, settings.signalFactor);
gd.addSlider("Lower_signal", 0, 3.5, settings.lowerSignalFactor);
final FitEngineConfigurationProvider fitEngineConfigurationProvider = new PeakFit.SimpleFitEngineConfigurationProvider(config);
// Collect options for fitting
final double sa = getSa();
final FitConfiguration fitConfig = config.getFitConfiguration();
fitConfig.setInitialPeakStdDev(MathUtils.round(sa / simulationParameters.pixelPitch));
PeakFit.addPsfOptions(gd, fitConfig);
PeakFit.addFittingOptions(gd, fitEngineConfigurationProvider);
gd.addChoice("Fit_solver", SettingsManager.getFitSolverNames(), FitProtosHelper.getName(fitConfig.getFitSolver()));
gd.addMessage("Multi-path filter (used to pick optimum results during fitting)");
// Allow loading the best filter for these results
final boolean benchmarkSettingsCheckbox = BenchmarkSpotFitResult.fitResultsId.get() == BenchmarkFilterAnalysis.getLastFittingId();
Checkbox cbBenchmark = null;
if (benchmarkSettingsCheckbox) {
// This should always be an opt-in decision. Otherwise the user cannot use the previous
// settings.
cbBenchmark = gd.addAndGetCheckbox("Benchmark_settings", false);
}
gd.addTextAreas(XmlUtils.convertQuotes(multiFilter.toXml()), null, 6, 60);
textFailLimit = gd.addAndGetNumericField("Fail_limit", config.getFailuresLimit(), 0);
cbIncludeNeighbours = gd.addAndGetCheckbox("Include_neighbours", config.isIncludeNeighbours());
gd.addAndGetSlider("Neighbour_height", 0.01, 1, config.getNeighbourHeightThreshold());
textNeighbourHeight = gd.getLastTextField();
cbComputeDoublets = gd.addAndGetCheckbox("Compute_doublets", settings.computeDoublets);
PeakFit.addDuplicateDistanceOptions(gd, fitEngineConfigurationProvider);
gd.addCheckbox("Show_score_histograms", settings.showFilterScoreHistograms);
gd.addCheckbox("Show_correlation", settings.showCorrelation);
gd.addCheckbox("Plot_rank_by_intensity", settings.rankByIntensity);
gd.addCheckbox("Save_filter_range", settings.saveFilterRange);
if (extraOptions) {
// No extra options
}
// Add a mouse listener to the config file field
if (cbBenchmark != null && ImageJUtils.isShowGenericDialog()) {
taFilterXml = gd.getTextArea1();
cbBenchmark.addItemListener(this);
}
gd.showDialog();
if (gd.wasCanceled()) {
return false;
}
settings.fractionPositives = Math.abs(gd.getNextNumber());
settings.fractionNegativesAfterAllPositives = Math.abs(gd.getNextNumber());
settings.negativesAfterAllPositives = (int) Math.abs(gd.getNextNumber());
settings.distance = Math.abs(gd.getNextNumber());
settings.lowerDistance = Math.abs(gd.getNextNumber());
settings.signalFactor = Math.abs(gd.getNextNumber());
settings.lowerSignalFactor = Math.abs(gd.getNextNumber());
fitConfig.setPsfType(PeakFit.getPsfTypeValues()[gd.getNextChoiceIndex()]);
config.setFitting(gd.getNextNumber());
// Some enum values are not supported
fitConfig.setFitSolver(SettingsManager.getFitSolverValues()[gd.getNextChoiceIndex()]);
boolean myUseBenchmarkSettings = false;
if (benchmarkSettingsCheckbox) {
// useBenchmarkSettings =
myUseBenchmarkSettings = gd.getNextBoolean();
}
// Read dialog settings
final String xml = gd.getNextText();
final int failLimit = (int) gd.getNextNumber();
final boolean includeNeighbours = gd.getNextBoolean();
final double neighbourHeightThreshold = gd.getNextNumber();
final boolean myComputeDoublets = gd.getNextBoolean();
final double myDuplicateDistance = gd.getNextNumber();
gd.collectOptions();
MultiPathFilter myMultiFilter = null;
if (myUseBenchmarkSettings && !ImageJUtils.isShowGenericDialog()) {
// Only copy the benchmark settings if not interactive
final FitEngineConfiguration tmp = new FitEngineConfiguration();
final FitConfiguration tmpFitConfig = tmp.getFitConfiguration();
// Collect the residuals threshold
tmpFitConfig.setComputeResiduals(true);
if (BenchmarkFilterAnalysis.updateConfiguration(tmp, false)) {
config.setFailuresLimit(tmp.getFailuresLimit());
config.setIncludeNeighbours(tmp.isIncludeNeighbours());
config.setNeighbourHeightThreshold(tmp.getNeighbourHeightThreshold());
settings.computeDoublets = (tmp.getResidualsThreshold() < 1);
config.setDuplicateDistance(tmp.getDuplicateDistance());
config.setDuplicateDistanceAbsolute(tmp.getDuplicateDistanceAbsolute());
final DirectFilter primaryFilter = tmpFitConfig.getSmartFilter();
final double residualsThreshold = tmp.getResidualsThreshold();
myMultiFilter = new MultiPathFilter(primaryFilter, FitWorker.createMinimalFilter(tmpFitConfig.getFilterPrecisionMethod()), residualsThreshold);
}
} else {
myMultiFilter = MultiPathFilter.fromXml(xml);
config.setFailuresLimit(failLimit);
config.setIncludeNeighbours(includeNeighbours);
config.setNeighbourHeightThreshold(neighbourHeightThreshold);
settings.computeDoublets = myComputeDoublets;
config.setDuplicateDistance(myDuplicateDistance);
}
if (myMultiFilter == null) {
gd = new ExtendedGenericDialog(TITLE);
gd.addMessage("The multi-path filter was invalid.\n \nContinue with a default filter?");
gd.enableYesNoCancel();
gd.hideCancelButton();
gd.showDialog();
if (!gd.wasOKed()) {
return false;
}
} else {
multiFilter = myMultiFilter;
}
if (settings.computeDoublets) {
config.setResidualsThreshold(0);
fitConfig.setComputeResiduals(true);
} else {
config.setResidualsThreshold(1);
fitConfig.setComputeResiduals(false);
}
settings.showFilterScoreHistograms = gd.getNextBoolean();
settings.showCorrelation = gd.getNextBoolean();
settings.rankByIntensity = gd.getNextBoolean();
settings.saveFilterRange = gd.getNextBoolean();
// Avoid stupidness, i.e. things that move outside the fit window and are bad widths
// TODO - Fix this for simple or smart filter...
fitConfig.setDisableSimpleFilter(false);
// Realistically we cannot fit lower than this
fitConfig.setMinPhotons(15);
// Disable shift as candidates may be re-mapped to alternative candidates so the initial
// position is wrong.
fitConfig.setCoordinateShiftFactor(0);
fitConfig.setMinWidthFactor(1.0 / 5);
fitConfig.setMaxWidthFactor(5);
// Disable the direct filter
fitConfig.setDirectFilter(null);
if (extraOptions) {
// No extra options
}
if (gd.invalidNumber()) {
return false;
}
if (settings.lowerDistance > settings.distance) {
settings.lowerDistance = settings.distance;
}
if (settings.lowerSignalFactor > settings.signalFactor) {
settings.lowerSignalFactor = settings.signalFactor;
}
// Distances relative to sa (not s) as this is the same as the BenchmarkSpotFilter plugin
distanceInPixels = settings.distance * sa / simulationParameters.pixelPitch;
lowerDistanceInPixels = settings.lowerDistance * sa / simulationParameters.pixelPitch;
// Copy simulation defaults if a new simulation.
// if (lastSimulationId.get() != simulationParameters.id) {
// This is needed to configure the fit solver.
fitConfig.setNmPerPixel(simulationParameters.pixelPitch);
fitConfig.setGain(simulationParameters.gain);
fitConfig.setQuantumEfficiency(simulationParameters.qe);
fitConfig.setReadNoise(simulationParameters.readNoise);
fitConfig.setBias(simulationParameters.bias);
fitConfig.setCameraType(simulationParameters.cameraType);
fitConfig.setCameraModel(CreateData.getCameraModel(simulationParameters));
// }
if (!PeakFit.configurePsfModel(config)) {
return false;
}
return PeakFit.configureFitSolver(config, IJImageSource.getBounds(imp), null, (extraOptions) ? PeakFit.FLAG_EXTRA_OPTIONS : 0);
}
use of uk.ac.sussex.gdsc.smlm.results.filter.MultiPathFilter in project GDSC-SMLM by aherbert.
the class BenchmarkSpotFit method itemStateChanged.
@Override
public void itemStateChanged(ItemEvent event) {
if (event.getSource() instanceof Checkbox) {
final Checkbox checkbox = (Checkbox) event.getSource();
int failLimit;
boolean includeNeighbours;
double neighbourHeightThrehsold;
boolean computeDoublets;
MultiPathFilter myMultiFilter;
if (checkbox.getState()) {
final FitEngineConfiguration tmp = new FitEngineConfiguration();
final FitConfiguration tmpFitConfig = tmp.getFitConfiguration();
// Collect residuals threshold
tmpFitConfig.setComputeResiduals(true);
if (BenchmarkFilterAnalysis.updateConfiguration(tmp, false)) {
failLimit = tmp.getFailuresLimit();
includeNeighbours = tmp.isIncludeNeighbours();
neighbourHeightThrehsold = tmp.getNeighbourHeightThreshold();
computeDoublets = tmp.getResidualsThreshold() < 1;
final DirectFilter primaryFilter = tmpFitConfig.getSmartFilter();
final double residualsThreshold = tmp.getResidualsThreshold();
myMultiFilter = new MultiPathFilter(primaryFilter, FitWorker.createMinimalFilter(tmpFitConfig.getFilterPrecisionMethod()), residualsThreshold);
} else {
IJ.log("Failed to update settings using the filter analysis");
checkbox.setState(false);
return;
}
} else {
failLimit = config.getFailuresLimit();
includeNeighbours = config.isIncludeNeighbours();
neighbourHeightThrehsold = config.getNeighbourHeightThreshold();
computeDoublets = BenchmarkSpotFit.this.settings.computeDoublets;
myMultiFilter = multiFilter;
}
// Update the dialog
taFilterXml.setText(myMultiFilter.toXml());
textFailLimit.setText("" + failLimit);
cbIncludeNeighbours.setState(includeNeighbours);
textNeighbourHeight.setText(MathUtils.rounded(neighbourHeightThrehsold));
cbComputeDoublets.setState(computeDoublets);
}
}
use of uk.ac.sussex.gdsc.smlm.results.filter.MultiPathFilter in project GDSC-SMLM by aherbert.
the class BenchmarkSpotFit method run.
/**
* Run the analysis non-interactively using the given filter settings.
*
* @param filter the filter
* @param residualsThreshold the residuals threshold
* @param failuresLimit the failures limit
* @param duplicateDistance the duplicate distance
* @param duplicateDistanceAbsolute the duplicate distance absolute
*/
void run(DirectFilter filter, double residualsThreshold, int failuresLimit, double duplicateDistance, boolean duplicateDistanceAbsolute) {
clearFitResults();
silent = true;
finished = false;
if (!initialise()) {
return;
}
// Reset the filter
multiFilter = new MultiPathFilter(filter, FitWorker.createMinimalFilter(getPrecisionMethod(filter)), residualsThreshold);
// Update the appropriate fitting settings
config.setFailuresLimit(failuresLimit);
config.setDuplicateDistance(duplicateDistance);
config.setDuplicateDistanceAbsolute(duplicateDistanceAbsolute);
runFitting();
finished = true;
}
use of uk.ac.sussex.gdsc.smlm.results.filter.MultiPathFilter in project GDSC-SMLM by aherbert.
the class BenchmarkFilterAnalysis method readFilterSets.
@Nullable
@SuppressWarnings("unchecked")
private List<FilterSet> readFilterSets() {
if (extraOptions) {
final MultiPathFilter multiFilter = BenchmarkSpotFit.getMultiFilter();
if (multiFilter != null) {
final IDirectFilter f = multiFilter.getFilter();
if (f instanceof DirectFilter) {
final GenericDialog gd = new GenericDialog(TITLE);
gd.addMessage("Use an identical filter to " + BenchmarkSpotFit.TITLE);
gd.enableYesNoCancel();
gd.hideCancelButton();
gd.showDialog();
if (gd.wasOKed()) {
final List<FilterSet> filterSets = new ArrayList<>(1);
final List<Filter> filters = new ArrayList<>(1);
filters.add((DirectFilter) f);
final FilterSet filterSet = new FilterSet(filters);
filterSets.add(filterSet);
resetParametersFromFitting();
createResultsPrefix2();
return filterSets;
}
}
}
}
GUIFilterSettings filterSettings = SettingsManager.readGuiFilterSettings(0);
final String filename = ImageJUtils.getFilename("Filter_File", filterSettings.getFilterSetFilename());
if (filename != null) {
IJ.showStatus("Reading filters ...");
filterSettings = filterSettings.toBuilder().setFilterSetFilename(filename).build();
// Allow the filters to be cached
final Triple<String, Long, List<FilterSet>> filterCache = lastFilterList.get();
if (isSameFile(filename, filterCache)) {
final GenericDialog gd = new GenericDialog(TITLE);
gd.hideCancelButton();
gd.addMessage("The same filter file was selected.");
gd.addCheckbox("Re-use_filters", settings.reUseFilters);
gd.showDialog();
if (!gd.wasCanceled()) {
settings.reUseFilters = gd.getNextBoolean();
if (settings.reUseFilters) {
SettingsManager.writeSettings(filterSettings);
return filterCache.getRight();
}
}
}
final File file = new File(filename);
try (BufferedReader input = new BufferedReader(new UnicodeReader(new FileInputStream(file), null))) {
// Use the instance so we can catch the exception
final Object o = FilterXStreamUtils.getXStreamInstance().fromXML(input);
if (!(o instanceof List<?>)) {
IJ.log("No filter sets defined in the specified file: " + filename);
return null;
}
SettingsManager.writeSettings(filterSettings);
List<FilterSet> filterSets = (List<FilterSet>) o;
if (containsStandardFilters(filterSets)) {
IJ.log("Filter sets must contain 'Direct' filters");
return null;
}
// Check they are not empty lists
final List<FilterSet> filterSets2 = new LinkedList<>();
for (final FilterSet filterSet : filterSets) {
if (filterSet.size() != 0) {
filterSets2.add(filterSet);
} else {
IJ.log("Filter set empty: " + filterSet.getName());
}
}
if (filterSets2.isEmpty()) {
IJ.log("All Filter sets are empty");
return null;
}
// Maintain the same list type
filterSets.clear();
filterSets.addAll(filterSets2);
// Option to enumerate filters
filterSets = expandFilters(filterSets);
// Save for re-use
lastFilterList.set(Triple.of(filename, getLastModified(file), filterSets));
return filterSets;
} catch (final Exception ex) {
IJ.log("Unable to load the filter sets from file: " + ex.getMessage());
} finally {
IJ.showStatus("");
}
}
return null;
}
use of uk.ac.sussex.gdsc.smlm.results.filter.MultiPathFilter in project GDSC-SMLM by aherbert.
the class BenchmarkFilterAnalysis method scoreFilter.
private ParameterScoreResult scoreFilter(DirectFilter filter, DirectFilter minFilter, int failCount, double residualsThreshold, double duplicateDistance, CoordinateStore coordinateStore, boolean createTextResult) {
final MultiPathFilter multiPathFilter = new MultiPathFilter(filter, minFilter, residualsThreshold);
final FractionClassificationResult r = multiPathFilter.fractionScoreSubset(gaResultsListToScore, createFailCounter(failCount), fitResultData.countActual, null, null, coordinateStore);
final double score = getScore(r);
final double criteria = getCriteria(r);
// Create the score output
final String text = (createTextResult && criteria >= minCriteria) ? createResult(filter, r, buildResultsPrefix2(failCount, residualsThreshold, duplicateDistance)).toString() : null;
final double[] parameters = new double[] { failCount, residualsThreshold, duplicateDistance };
return new ParameterScoreResult(score, criteria, parameters, text);
}
Aggregations