Calculations/Data-Analyzer/+Analyzer/extract2DAutocorrelation.m

88 lines
3.6 KiB
Matlab
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

function results = extract2DAutocorrelation(od_imgs, scan_parameter_values, options)
%% extract2DAutocorrelation
% Author: Karthik
% Date: 2025-09-14
% Version: 1.0
%
% Description:
% Computes 2D autocorrelation g² for a set of real-space images.
% Returns all g2 maps grouped by unique scan parameter, mean, error
%
% Inputs:
% od_imgs - 1xN cell array of 2D image matrices (i × j)
% scan_parameter_values - array or cell array of scan parameters (similar format as in extractAutocorrelation)
% options - options struct containing maximum pixel shift to compute g2 along x and y
%
% Outputs (struct):
% results.g2_curves - cell array of 3D autocorrelation matrices [2*max_shift+1 × 2*max_shift+1 × N_reps] per unique scan parameter
% results.g2_mean - mean autocorrelation per unique scan parameter
% results.g2_error - SEM per unique scan parameter
% results.scan_parameter_values - unique scan parameter values
%
% Notes:
% Optional notes, references.
if isfield(options, 'maximumShift') && ~isempty(options.maximumShift)
max_shift = options.maximumShift;
else
max_shift = 5; % [µm]
end
pixel_size = options.pixel_size;
magnification = options.magnification;
% ===== Convert images to 3D array =====
N_shots = numel(od_imgs);
[M, N] = size(od_imgs{1});
img_stack = zeros(M, N, N_shots);
for k = 1:N_shots
img_stack(:, :, k) = od_imgs{k};
end
% ===== Determine unique scan parameter values =====
if isnumeric(scan_parameter_values) && isvector(scan_parameter_values)
[unique_scan_parameter_values, ~, idx] = unique(scan_parameter_values(:), 'stable');
elseif iscell(scan_parameter_values)
params = cell2mat(scan_parameter_values);
[unique_scan_parameter_values, ~, idx] = unique(params, 'rows', 'stable');
else
error('Unsupported format for scan_parameter_values.');
end
N_unique = size(unique_scan_parameter_values, 1);
% ===== Preallocate outputs =====
g2_curves = cell(1, N_unique); % each cell: [2*max_shift+1 × 2*max_shift+1 × N_reps]
% ===== Compute 2D autocorrelation for each unique scan parameter =====
for i = 1:N_unique
group_idx = find(idx == i); % indices of repetitions for this unique value
group_data = img_stack(:, :, group_idx);
N_reps = length(group_idx);
g2_stack = zeros(2*max_shift+1, 2*max_shift+1, N_reps);
for j = 1:N_reps
img = group_data(:, :, j);
[g2_matrix, ~, ~] = Calculator.compute2DAutocorrelation(img, max_shift, pixel_size, magnification);
g2_stack(:, :, j) = g2_matrix;
end
% Store all repetitions for this unique scan parameter
g2_curves{i} = g2_stack;
end
% ===== Compute mean and SEM per unique value =====
g2_mean = cellfun(@(G) mean(G, 3, 'omitnan'), g2_curves, 'UniformOutput', false);
g2_error = cellfun(@(G) std(G, 0, 3, 'omitnan') ./ sqrt(size(G,3)), g2_curves, 'UniformOutput', false);
% ===== Package results =====
results = struct();
results.g2_curves = g2_curves; % raw [2*max_shift+1 × 2*max_shift+1 × N_reps] per unique group
results.g2_mean = g2_mean; % mean per unique group
results.g2_error = g2_error; % SEM per unique group
results.scan_parameter_values = unique_scan_parameter_values;
results.max_shift = max_shift;
end