DOI: 10.5281/zenodo.11428244
title: Revealing real-time 3D in vivo pathogen dynamics in plants by label-free optical coherence tomography

description: This repository contains all data and code underlying the publication: J. de Wit et al. "Revealing real-time 3D in vivo pathogen dynamics in plants by label-free optical coherence tomography" in Nature Communications (2024) (https://doi.org/10.1038/s41467-024-52594-x)

--------------Code description------------------

The set of scripts is largely organized around the figures. For each (sub)figure, also from supplementary materials, that involves data and plotting, there is a script that generates the plot from data that can be found in the different zip files that are present in the Zenodo repository under https://doi.org/10.5281/zenodo.11428245.

The scripts use the data that is contained in the ZIP folders. The ZIP folders are organized by experiment (Experiment 1, including contrast optimization; Experiment 2), one for the other data (OtherData, the validation for with Trypan blue, and the Arabidopsis, Radish and nematode) and one as a smaller dataset to explain the method on a single B-scan (Example_Bscan_dynamicOCT).

IMPORTANT: The folder where the ZIP files are unzipped should be put in the file 'basepath.txt', such that the data can be automatically loaded.

Besides the figures that mention 'MakeFig...' there are a few more scripts:



pointcloud_generation_experiment1.py: this file makes the point clouds from the dynamic OCT images as described in Fig 2b. The resulting data is saved as maximum intensity projections and axial sums(forming the basis for Fig S4, S6 and S7) and as voxel counts (forming the basis of Fig.2c and Fig S5)

pointcloud_generation_timelapses.py: this file does the segmentation for experiment 2 and saves the maximum intensity projections and axial sums of the different stages in the segmentation (forming the basis of Fig3a,d,e and FigS9a,b), and saves the point clouds of the data. These point clouds were refined manually in CloudCompare as described in methods. These segmented point clouds are contained in the data zip folder of experiment 2.

StatisticalTests.R: This R file calculates the statistical tests for Fig.2cd and Fig.S5d. Here the path is not automatically updated, and should be manually set. The input file is contained in "Experiment1/SegmentationData/segmentationdata_samples.csv" and the output of the file is "D:/DataZenodo/Experiment1/SegmentationData/data_combined_Rstats_output.csv"

example_dynamic_Bscan.py: This script gives an example of the dynamic OCT processing as proposed in this paper. First it shows the process from an OCT interference spectrum to a B-scan. Then it loads 100 B-scans and applies dynamic OCT, including normalization with histograms. Finally it gives a dynamic B-scan and plots this against the average normal OCT image. This script can be used with only the zip folder "Example_Bscan_dynamicOCT", which reduces the amount of data needed to download/unzip.


The list of other script files to load the data and generate the figures (guiding to the path of uncropped figures) is:



MakeFig1bce_Fig2e.py

MakeFig1d.py

MakeFig1agraphs_FigureS1.py

MakeFig3acde_S9ab.py

MakeFigS2_determine_dynamic_range_experiment1.py

MakeFigS8.py

MakeFigureS4-S6-S7.py

MakeFigureS5.py

MakeHistFig2b_makeFigS3b-e.py

MakePlotsFig2ab.py

MakePlotsFig2cd.py


Code was all run in Python 3 using Anaconda Spyder.

Moreover, the zip file with the code contains the folder 'figures' with all subfigures. Some of them are automatically saved from the scripts, others (like photos, icons, but also the Trypan blue microscopy figure) are added in the respective folder. The are logically organized by figure number.

--------------Dataset Description-----------------

As mentioned above, the data is organized in four zip folders for both experiments, the other data (validation with Trypan blue, other plant-pathogens) and one for the dynamic OCT B-scan example. The data contain the following:

Experiment 1: 



DynamicOCTimages whose subfolders (organized by date) contain a folder per volume dataset in experiment 1 with a z-stack of .tif files that form the imaged volume. The lateral sampling is 3 um and the axial sampling is 1.37 um. 

ContrastOptimization: This folder contains 



Bscans_with_segmentation: segmented B-scans for contrast optimization (Fig S3)

Bscan_figS1_fig1: The B-scans and segementation for Figure S1.

histogramdata_dynamicrange: The histograms, bins and deducted reference data for determining the dynamic range per color channel for experiment 1 (Fig S2)

logcompressed_3value_dOCT_example: An example data stack for obtaining histograms (see script MakeFigS2_determine_dynamic_range_experiment1.py)

overlaps_threshold-100-98-95-92-90-85-80-75-70-65-60-55-50-45perc_red-1_2_blue_-3_0_green1_filt.npy: A file with intermediate data for the contrast optimization, which can also be generated with the script "MakeHistFig2b_makeFigS3b-e.py"



SegmentationData: This folder contains 



MIP_segmentation_stages: maximum intensityp projections and axial sums for all images at different stages in the segmentation (basis for Fig S4,6,7)

processed_masks and StackMasks: the manually obtained masks (segmented in StackMasks, made into masks in the folder 'processed_masks') for filtering out stomata, veins and artefacts.

Unmasked_axialsum_th34_formanualsegmentation: This folder contains the images of Fig.S4 and were used for the segmentation (we addes a small offset, such that the in segmentation we could set it to 0 and have a unique mask). 

overview_samples_bremiayn.csv: A dataframe with the data for all the samples in experiment 1 that is used as input for the segmentation. It also contains the result of the manual check whether it has infection (Fig2c, left).

segmentationdata_samples.csv: This supplements the file of overview_samples_bremiayn.csv with the results from the segmentation and is output to script "pointcloud_generation_experiment1.py". It forms the basis of Fig.2a-c, and FigS5, as well as for the R-script to do the statistical testing.

qPCR_dOCT.csv: This script contains the qPCR data and is input to Fig2d. 




Experiment 2:



DynamicOCTimages: This contains the z-stacks of .tif files of the volumes for experiment 2 (and one extra, where a z-slice is used in Fig.1b, bottom). Sampling step size is here again 3 um in lateral direction and 1.37 um in axial direction.

.npy files with the histograms (with same bins as Experiment 1), maxvalues and reference values for the dynamic range calculation.

segmentation_data: this folder contains:



quantification_volume_disc160_33_10.csv and quantification_volume_disc160_33_10.xlsx: data from the manually segmented point clouds that form the basis of Fig.3c.

timelapse_sampleoverview.csv: overview of the samples that is used as input in the file "pointcloud_generation_timelapses.py"

pointclouds: Folder with segmented point clouds for the three leaf discs. These files could  be loaded in CloudCompare.

overviewMIPs: folder with overview maximum intensity projections for the different steps in segmentation, which also forms the input of Fig.3a, FigS9ab.

rawpointclouds: folder with the automatically generated point clouds from file pointcloud_generation_timelapses.py which were imported into CloudCompare as the basis for the segmented point clouds.




OtherData:

This folder contains the z-stacks of dynamic OCT tif images for Arabidopsis (here both a normal contrast and one that has been increased to only contain the original 0-180 range); nematodes, radish (called radijs_test_PP_py_0002), spores for Fig1c (SporesImaging) and the dynamic OCT image of Fig1d. 

example_Bscan_dynamicOCT:

This folder contains data to run the script example_dynamic_Bscan.py to show the dynamic OCT imaging process from raw OCT spectra.



raw_spectra_exampleframe: contains interference spectra, a reference spectrum and interpolation grid to show how to get from a raw OCT spectrum to a normal single B-scan.

abs_images: contains 100 subsequent B-scans that can be used to generate a dynamic OCT image as done in example_dynamic_Bscan.py