Schema for multi-dimensional microscopy experiments
Project description
useq-schema
An implementation agnostic schema for describing a sequence of events during a multi-dimensional imaging acquisition.
Documentation: https://pymmcore-plus.github.io/useq-schema/
The goal of this repo is to provide a specification (and some python utilities) for generating event objects that can be consumed by microscope acquisition engines. The hope is that this will encourage inter-operability between various efforts to drive automated image acquisition.
The schema tries to remain agnostic to the specific acquisition engine, though it was designed based on the Micro-Manager acquisition engine. One hope is to solicit feedback from interested parties regarding limitations and/or potential extensions to the schema. Similarly, while the "ideal" schema will support arbitrary dimensions (i.e. more than the conventional position, time, channel, z, ...), it also hard to avoid hard-coding some assumptions about dimensionality in certain places. Any and all feedback (even minor stuff, such as parameter naming, etc...) is welcome!
MDAEvent
The primary "event" object is useq.MDAEvent
. This captures a single event
that a microscope should perform, including preparation of the hardware, and
execution of the event (such as an image acquisition).
- For micro-manager, this
object is most similar (though not that similar) to the events generated by
generate-acq-sequence
in the clojure acquisition engine. - For pycro-manager, this
object is similar to an individual acquisition event
dict
generated bymulti_d_acquisition_events
, (and,useq.MDAEvent
provides ato_pycromanager()
method that returns a single pycro-manager event dict) - your object here?...
# simplified, and possibly outdated. See useq.MDAEvent in codebase
# where `None` generally means "make no change"
class MDAEvent:
metadata: Dict[str, Any] = {} # user-specific data
index: Dict[str, int] = {} # {'axis'->index} for this event
channel: Optional[Channel] # optical config
exposure: Optional[PositiveFloat] # will likely expand for camera
min_start_time: Optional[int] # min time delta for beginning event
x_pos: Optional[float] # stage x
y_pos: Optional[float] # stage y
z_pos: Optional[float] # stage z
properties: Optional[Sequence[PropertyTuple]] # set arbitrary device props
# TBD
# action: Action ... such as "acquire", etc...
class Channel:
config: str
group: str = "Channel"
class PropertyTuple(NamedTuple):
device_name: str
property_name: str
property_value: Any
useq-schema
usespydantic
to define models, so you can retrieve the json schema for theMDAEvent
object withMDAEvent.schema_json()
MDASequence
useq.MDASequence
represents a sequence of events (as might be generated by the
multidimensional acquisition GUI in most microscope software). A
useq.MDASequence
object is itself iterable, and yields MDAEvent
objects.
- For micro-manager, this
object is most similar to
org.micromanager.acquisition.SequenceSettings
, (generated by clicking the "Acquire!" button in the Multi-D Acquisition GUI) - For pycro-manager, this
object is similar to the
multi_d_acquisition_events
convenience function, (anduseq.MDASequence
provides ato_pycromanager()
method that returns a list of pycro-manager events) - your object here?...
# simplified, and possibly outdated. See useq.MDASequence in codebase
class MDASequence(BaseModel):
metadata: Dict[str, Any] = {} # user-specific data
axis_order: str # e.g. 'tpcz'
stage_positions: Tuple[Position]
channels: Tuple[Channel, ...]
time_plan: AnyTimePlan # see details below
z_plan: AnyZPlan # see details below
class Position(BaseModel):
# if None, implies 'do not move this axis'
x: Optional[float]
y: Optional[float]
z: Optional[float]
name: Optional[str]
z_plan: Optional[AnyZPlan]
class Channel(BaseModel):
config: str
group: str
exposure: Optional[PositiveFloat]
do_stack: bool = True
z_offset: float = 0.0
acquire_every: PositiveInt = 1 # acquire every n frames
camera: Optional[str]
useq-schema
usespydantic
to define models, so you can retrieve the json schema for theMDASequence
object withMDASequence.schema_json()
TimePlan
and ZPlan
are each iterable objects that allow for various ways to
describe time and Z series. These are each rather configurable and will be documented more later.
TimePlans
:
TIntervalDuration
- specify interval and durationTIntervalLoops
- specify interval and number of timepointsTDurationLoops
- specify duration and number of timepoints
ZPlans
:
ZTopBottom
- specify absolute top, bottom, and stepZRangeAround
- specify symmetric range and stepZAboveBelow
- specify asymmetric range above and below reference, with stepZRelativePositions
- directly specify a sequence of relative z positionsZAbsolutePositions
- directly specify a sequence of absolute z positions
example MDASequence
usage:
from useq import MDASequence
mda = MDASequence(
stage_positions=[(100, 100, 30), (200, 150, 35)],
channels=["DAPI", "FITC"],
time_plan={'interval': 1, 'loops': 20},
z_plan={"range": 4, "step": 0.5},
axis_order='tpcz',
)
len(mda)
# 720
list(mda)
# [
# MDAEvent(index={'t': 0, 'p': 0, 'c': 0, 'z': 0}, ... z_pos=28.0),
# MDAEvent(index={'t': 0, 'p': 0, 'c': 0, 'z': 1}, ... z_pos=28.5),
# ...
# ]
mda.to_pycromanager()
# [
# {'axes': {'position': 0, 'time': 0, 'z': 0},
# 'z': 28.0,
# 'x': 100.0,
# 'y': 100.0,
# 'min_start_time': 0,
# 'channel': {'config': 'DAPI', 'group': 'Channel'}},
# {'axes': {'position': 0, 'time': 0, 'z': 1},
# 'z': 28.5,
# 'x': 100.0,
# 'y': 100.0,
# 'min_start_time': 0,
# 'channel': {'config': 'DAPI', 'group': 'Channel'}},
# ...
# ]
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Hashes for useq_schema-0.2.1-py3-none-any.whl
Algorithm | Hash digest | |
---|---|---|
SHA256 | 70814496867fede09555c25655e9b326f638956177b33ba585f6e4de4510bc4f |
|
MD5 | daea6a334517942a4741ecd9f0d6e5c2 |
|
BLAKE2b-256 | 3a53c368cd5f40d34d3d6338d9ca7d478860435449aece3e6d6573cef3f04b7f |