@@ -69,12 +69,16 @@ def nd2_ome_metadata(
6969 (x for x in DimensionOrder if x .value .startswith (dims )), DimensionOrder .XYCZT
7070 )
7171
72+ # Exposure time and detectors come from raw metadata
73+ raw_meta = rdr ._cached_raw_metadata ()
74+ sample_settings = raw_meta .get ("sPicturePlanes" , {}).get ("sSampleSetting" , {})
75+
7276 # if sizes.get(AXIS.CHANNEL, 1) > 1 and sizes.get(AXIS.RGB, 1) > 1:
7377 # warn("multi-channel RGB images are not well supported in nd2 OME metadata.")
7478
7579 instrument = m .Instrument (
7680 id = "Instrument:0" ,
77- detectors = ome_detectors (rdr . _cached_raw_metadata () ),
81+ detectors = ome_detectors (raw_meta ),
7882 # TODO:
7983 # dichroics: List[Dichroic]
8084 # filter_sets: List[FilterSet]
@@ -84,6 +88,13 @@ def nd2_ome_metadata(
8488 )
8589
8690 ch0 = next (iter (meta .channels or ()), None )
91+ objective_settings = (
92+ None
93+ if ch0 is None
94+ else m .ObjectiveSettings (
95+ id = "Objective:0" , refractive_index = ch0 .microscope .immersionRefractiveIndex
96+ )
97+ )
8798 channels = []
8899 for c_idx , ch in enumerate (meta .channels or ()):
89100 channel = m .Channel (
@@ -143,13 +154,24 @@ def nd2_ome_metadata(
143154 # TODO: i think RGB might actually need to be 3 planes with 1 spp
144155 z_idx = loop_idx .get (AXIS .Z , 0 )
145156 t_idx = loop_idx .get (AXIS .TIME , 0 )
157+
158+ # sSampleSetting has one entry per acquisition (not per channel)
159+ # Laser-scanning confocals use a single entry governing all channels
160+ # Entry count is always either 1 or SizeC
161+ ch_setting = sample_settings .get (f"a{ c_idx } " )
162+ if ch_setting is None and len (sample_settings ) == 1 :
163+ ch_setting = next (iter (sample_settings .values ()))
164+
165+ # 0.0 is a placeholder value so set that as None
166+ exposure_time = (ch_setting or {}).get ("dExposureTime" ) or None
167+
146168 planes .append (
147169 m .Plane (
148170 the_z = z_idx ,
149171 the_t = t_idx ,
150172 the_c = c_idx ,
151- # exposure_time=... ,
152- # exposure_time_unit=... ,
173+ exposure_time = exposure_time ,
174+ exposure_time_unit = UnitsTime . MILLISECOND ,
153175 delta_t = round (fm_ch .time .relativeTimeMs , 6 ),
154176 delta_t_unit = UnitsTime .MILLISECOND , # default is "s"
155177 position_x = round (fm_ch .position .stagePositionUm .x , 6 ),
@@ -200,7 +222,7 @@ def nd2_ome_metadata(
200222 images .append (
201223 m .Image (
202224 instrument_ref = m .InstrumentRef (id = instrument .id ),
203- # objective_settings=...
225+ objective_settings = objective_settings ,
204226 id = f"Image:{ p } " ,
205227 name = name ,
206228 pixels = pixels ,
@@ -215,7 +237,7 @@ def nd2_ome_metadata(
215237 id = "Objective:0" ,
216238 nominal_magnification = scope .objectiveMagnification ,
217239 lens_na = scope .objectiveNumericalAperture ,
218- # model=... # something like "Plan Fluor 10x Ph1 DLL"
240+ model = scope . objectiveName ,
219241 # immersion=scope.ome_objective_immersion(),
220242 )
221243 )
0 commit comments