use of uk.ac.sussex.gdsc.smlm.data.config.CalibrationReader in project GDSC-SMLM by aherbert.
the class TrackPopulationAnalysis method showInputDialog.
private boolean showInputDialog(List<MemoryPeakResults> combinedResults) {
// Show a list box containing all the clustered results.
// This should remember the last set of chosen items.
final MultiDialog md = ResultsManager.createMultiDialog(TITLE, MemoryPeakResults::hasId);
md.setSelected(settings.input);
md.setHelpUrl(HelpUrls.getUrl("track-population-analysis"));
md.showDialog();
if (md.wasCancelled()) {
return false;
}
final List<String> selected = md.getSelectedResults();
if (selected.isEmpty()) {
IJ.error(TITLE, "No results were selected");
return false;
}
settings.input = selected;
for (final String name : selected) {
final MemoryPeakResults r = MemoryPeakResults.getResults(name);
if (r != null) {
combinedResults.add(r);
}
}
// Check calibration exists for the first set of results
if (combinedResults.isEmpty() || !checkCalibration(combinedResults.get(0))) {
return false;
}
// Check the calibration is the same for the rest
final CalibrationReader cal = combinedResults.get(0).getCalibrationReader();
final double nmPerPixel = cal.getNmPerPixel();
final double exposureTime = cal.getExposureTime();
final DistanceUnit distanceUnit = cal.getDistanceUnit();
for (int i = 1; i < combinedResults.size(); i++) {
final MemoryPeakResults results = combinedResults.get(i);
if (!results.hasCalibration() || results.getCalibrationReader().getExposureTime() != exposureTime || results.getNmPerPixel() != nmPerPixel || results.getDistanceUnit() != distanceUnit) {
IJ.error(TITLE, "The exposure time, pixel pitch and distance unit must match across all the results");
return false;
}
}
return true;
}
use of uk.ac.sussex.gdsc.smlm.data.config.CalibrationReader in project GDSC-SMLM by aherbert.
the class TrackPopulationAnalysis method getTracks.
/**
* Gets the tracks. Each track has contiguous frames and the length is enough to fit
* {@code minTrackLength} overlapping windows of the specified size:
*
* <pre>
* length >= window + minTrackLength - 1
* </pre>
*
* @param combinedResults the combined results
* @param window the window size
* @param minTrackLength the minimum track length (assumed to be {@code >= 1})
* @return the tracks
*/
private static List<Trace> getTracks(List<MemoryPeakResults> combinedResults, int window, int minTrackLength) {
final LocalList<Trace> tracks = new LocalList<>();
final Statistics stats = new Statistics();
final int minSize = window + Math.max(minTrackLength, 1) - 1;
combinedResults.forEach(results -> {
final int start = tracks.size();
// Sort by id then frame
results = results.copy();
results.sort(IdFramePeakResultComparator.INSTANCE);
final int size = results.size();
// Skip IDs not associated with clustering
int index = 0;
while (index < size && results.get(index).getId() < 1) {
index++;
}
// Initialise current id and frame
int id = results.get(index).getId() - 1;
int frame = results.get(index).getFrame();
Trace track = new Trace();
for (; index < size; index++) {
final PeakResult result = results.get(index);
// Same ID and contiguous frames
if (result.getId() != id || result.getFrame() != frame + 1) {
addTrack(minSize, tracks, track);
track = new Trace();
}
id = result.getId();
frame = result.getFrame();
track.add(result);
}
addTrack(minSize, tracks, track);
stats.reset();
for (int i = start; i < tracks.size(); i++) {
stats.add(tracks.unsafeGet(i).size());
}
final StringBuilder sb = new StringBuilder(256);
TextUtils.formatTo(sb, "%s tracks=%d, length=%s +/- %s", results.getName(), stats.getN(), MathUtils.rounded(stats.getMean(), 3), MathUtils.rounded(stats.getStandardDeviation(), 3));
// Limit of diffusion coefficient from the localisation precision.
// Just use the entire dataset for simplicity (i.e. not the tracks of min length).
final PrecisionResultProcedure pp = new PrecisionResultProcedure(results);
try {
pp.getPrecision();
final Mean mean = new Mean();
for (final double p : pp.precisions) {
mean.add(p);
}
// 2nDt = MSD (n = number of dimensions)
// D = MSD / 2nt
final CalibrationReader reader = results.getCalibrationReader();
final double t = reader.getExposureTime() / 1000.0;
// Assume computed in nm. Convert to um.
final double x = mean.getMean() / 1000;
final double d = x * x / (2 * t);
TextUtils.formatTo(sb, ", precision=%s nm, D limit=%s um^2/s", MathUtils.rounded(x * 1000, 4), MathUtils.rounded(d, 4));
} catch (final DataException ex) {
// No precision
}
IJ.log(sb.toString());
});
return tracks;
}
use of uk.ac.sussex.gdsc.smlm.data.config.CalibrationReader in project GDSC-SMLM by aherbert.
the class BenchmarkFit method summariseResults.
private void summariseResults(Statistics[] stats, CameraModel cameraModel) {
createTable();
final StringBuilder sb = new StringBuilder();
// Create the benchmark settings and the fitting settings
sb.append(benchmarkParameters.getMolecules()).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.getSignal())).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.sd)).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.pixelPitch)).append('\t');
sb.append(MathUtils.rounded(getSa() * benchmarkParameters.pixelPitch)).append('\t');
// Report XY in nm from the pixel centre
sb.append(MathUtils.rounded(distanceFromCentre(benchmarkParameters.x))).append('\t');
sb.append(MathUtils.rounded(distanceFromCentre(benchmarkParameters.y))).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.pixelPitch * benchmarkParameters.z)).append('\t');
final CameraType cameraType = benchmarkParameters.cameraType;
if (cameraType == CameraType.SCMOS) {
sb.append("sCMOS (").append(benchmarkParameters.cameraModelName).append(") ");
final Rectangle bounds = benchmarkParameters.cameraBounds;
final Rectangle cropBounds = cameraModel.getBounds();
sb.append(" ").append(bounds.x + cropBounds.x).append(",").append(bounds.y + cropBounds.y);
sb.append(" ").append(region.width).append("x").append(region.width);
} else {
sb.append(CalibrationProtosHelper.getName(cameraType));
sb.append(" Gain=").append(benchmarkParameters.gain);
sb.append(" B=").append(benchmarkParameters.bias);
}
sb.append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.getBackground())).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.noise)).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.getSignal() / benchmarkParameters.noise)).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.precisionN)).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.precisionX)).append('\t');
sb.append(MathUtils.rounded(benchmarkParameters.precisionXml)).append('\t');
sb.append(region.width).append("x");
sb.append(region.height).append('\t');
sb.append(MathUtils.rounded(fitConfig.getInitialPeakStdDev() * benchmarkParameters.pixelPitch)).append('\t');
sb.append(PsfProtosHelper.getName(fitConfig.getPsf().getPsfType()));
// Only fixed fitting can ignore the signal
if (fitConfig.isFixedPsf() && !signalFitting) {
sb.append("NS");
}
if (!backgroundFitting) {
sb.append("NB");
}
sb.append(":").append(PeakFit.getSolverName(fitConfig));
if (fitConfig.isModelCameraMle()) {
sb.append(":Camera\t");
// Add details of the noise model for the MLE
final CalibrationReader r = new CalibrationReader(fitConfig.getCalibration());
sb.append("EM=").append(r.isEmCcd());
sb.append(":G=").append(r.getCountPerPhoton());
sb.append(":N=").append(r.getReadNoise());
} else {
sb.append('\t');
}
// Convert to units of the image (ADUs and pixels)
final double[] convert = getConversionFactors();
// Store the results for fitting on this benchmark dataset
final BenchmarkResult benchmarkResult = new BenchmarkResult(benchmarkParameters, answer, sb.toString(), convert, this.results, this.resultsTime);
if (!benchmarkResults.isEmpty()) {
// Clear the results if the benchmark has changed
if (benchmarkResults.getFirst().benchmarkParameters.id != benchmarkParameters.id) {
benchmarkResults.clear();
}
}
benchmarkResults.add(benchmarkResult);
// Now output the actual results ...
sb.append('\t');
final double recall = (stats[0].getN() / (double) startPoints.length) / benchmarkParameters.getMolecules();
sb.append(MathUtils.rounded(recall));
for (int i = 0; i < stats.length; i++) {
if (convert[i] != 0) {
sb.append('\t').append(MathUtils.rounded(stats[i].getMean() * convert[i], 6)).append('\t').append(MathUtils.rounded(stats[i].getStandardDeviation() * convert[i]));
} else {
sb.append("\t0\t0");
}
}
summaryTable.append(sb.toString());
}
use of uk.ac.sussex.gdsc.smlm.data.config.CalibrationReader in project GDSC-SMLM by aherbert.
the class HysteresisFilter method setup.
@Override
public void setup(MemoryPeakResults peakResults) {
ok = new HashSet<>();
// Create a set of candidates and valid peaks
final MemoryPeakResults traceResults = new MemoryPeakResults();
// Initialise peaks to check
final LinkedList<PeakResult> candidates = new LinkedList<>();
peakResults.forEach((PeakResultProcedure) result -> {
switch(getStatus(result)) {
case OK:
ok.add(result);
traceResults.add(result);
break;
case CANDIDATE:
candidates.add(result);
traceResults.add(result);
break;
default:
break;
}
});
if (candidates.isEmpty()) {
// No candidates for tracing so just return
return;
}
double distanceThreshold;
switch(searchDistanceMode) {
case 1:
distanceThreshold = searchDistance / peakResults.getNmPerPixel();
break;
case 0:
default:
distanceThreshold = getSearchDistanceUsingCandidates(peakResults, candidates);
}
if (distanceThreshold <= 0) {
return;
}
// This must be in frames
int myTimeThreshold;
if (timeThresholdMode == 1) {
// time threshold is in Seconds.
// Default to 1 frame if not calibrated.
myTimeThreshold = 1;
if (peakResults.hasCalibration()) {
// Convert time threshold in seconds to frames
final CalibrationReader cr = peakResults.getCalibrationReader();
final double et = cr.getExposureTime();
if (et > 0) {
myTimeThreshold = (int) Math.round((this.timeThreshold / et));
}
}
} else {
// frames
myTimeThreshold = (int) this.timeThreshold;
}
if (myTimeThreshold <= 0) {
return;
}
// Trace through candidates
final TraceManager tm = new TraceManager(traceResults);
tm.setTraceMode(TraceMode.LATEST_FORERUNNER);
tm.traceMolecules(distanceThreshold, myTimeThreshold);
final Trace[] traces = tm.getTraces();
for (final Trace trace : traces) {
if (trace.size() > 1) {
// Check if the trace touches a valid point
boolean isOk = false;
for (int i = 0; i < trace.size(); i++) {
if (ok.contains(trace.get(i))) {
isOk = true;
break;
}
}
// Add the entire trace to the OK points
if (isOk) {
for (int i = 0; i < trace.size(); i++) {
ok.add(trace.get(i));
}
}
}
}
}
use of uk.ac.sussex.gdsc.smlm.data.config.CalibrationReader in project GDSC-SMLM by aherbert.
the class TraceDiffusion method showMultiDialog.
private boolean showMultiDialog(ArrayList<MemoryPeakResults> allResults) {
multiMode = true;
// Show a list box containing all the results. This should remember the last set of chosen
// items.
final MultiDialog md = ResultsManager.createMultiDialog(TITLE);
md.setSelected(selectedRef.get());
md.setHelpUrl(HelpUrls.getUrl("trace-diffusion-multi"));
md.showDialog();
if (md.wasCancelled()) {
return false;
}
final List<String> selected = md.getSelectedResults();
if (selected.isEmpty()) {
IJ.error(TITLE, "No results were selected");
return false;
}
selectedRef.set(selected);
for (final String name : selected) {
final MemoryPeakResults r = MemoryPeakResults.getResults(name);
if (r != null) {
allResults.add(r);
}
}
if (allResults.isEmpty()) {
return false;
}
// Check calibration exists for the first set of results
if (!checkCalibration(allResults.get(0))) {
return false;
}
// Check the calibration is the same for the rest
final CalibrationReader cal = allResults.get(0).getCalibrationReader();
final double nmPerPixel = cal.getNmPerPixel();
final double exposureTime = cal.getExposureTime();
final DistanceUnit distanceUnit = cal.getDistanceUnit();
for (int i = 1; i < allResults.size(); i++) {
final MemoryPeakResults results = allResults.get(i);
if (!results.hasCalibration() || results.getCalibrationReader().getExposureTime() != exposureTime || results.getNmPerPixel() != nmPerPixel || results.getDistanceUnit() != distanceUnit) {
IJ.error(TITLE, "The exposure time, pixel pitch and distance unit must match across all the results");
return false;
}
}
return true;
}
Aggregations