{% extends layout|default('base.html', true) %} {% block style %} {% endblock %} {% block content %} Plexora - New Project {# One form, three inputs. The format of the data file is detected server-side (/inspect_data), so there is no tab strip and no per-format duplicate of the name/image/mask fields. The two extra controls below are hidden until the file itself makes them necessary: a .zarr store with several tables, and a table spanning several images, cannot be read at all until the user picks one. Everything else the old import wizard asked for is either worked out from the file or asked for later, by whichever feature actually needs it. #}
New Project

Import Data

An image is all that is required. Add a segmentation mask and single-cell data now, or later from the project's Edit page.

{% if data.error %} {% endif %}
{# One button. An OME-Zarr image is a directory and an OME-TIFF is a file, but which one you have is a fact about the format rather than a question worth asking -- mode "any" takes either (see native_dialog.py), and what lands in the box is sniffed the moment it arrives. #}
{# The formats, not a description of them. The File/Folder halves already name the common ones; this is the rest of the list for somebody whose format is not among them. #} .ome.tiff · .tiff · .qptiff · .svs · .ndpi · .scn · .mrxs · .png · .jpg · .zarr · .dcm
Please provide a valid path to the image file.
{# Images a registered data node is serving. Shown only when there are some, so an ordinary install never sees a control for a thing it does not use. Clicking one fills the field with `node:///`, which the field accepts as readily as a path. #} {% set node_images = (node_resources or [])|selectattr("kind", "equalto", "image")|list %} {% if node_images %}
or an image on a data node: {% for choice in node_images %} {% endfor %}
{% endif %} {# The project's name. Not asked for at the top of the form any more: the answer was always sitting in the field above it -- the image's filename -- so this shows what that came to and offers the pencil for the times it is not what the project should be called. One , readonly until the pencil is clicked, rather than a caption plus a hidden field: two elements would mean two copies of the name to keep in step, and the one that posts is not the one anybody can see. Hidden until there is a name, and `required` is carried on and off with it by showProjectName() -- a hidden required control refuses to submit with nothing on screen to explain why. #} {# The image type is not asked for. It is read from the file the moment one is named (/detect_image_type) and shown above as a fact, with the same pencil the name carries -- because for all but a handful of images the answer was never in doubt, and "Automatic" was a question whose answer the form already had. The select is still the control that POSTS, and still carries "Automatic" as its empty value: unfolding it and leaving it alone has to mean the same as never having opened it. It is only hidden, never removed -- a form that dropped the field would silently post nothing and the override would stop working. The other two options exist for the file that says nothing: a three-plane TIFF with no metadata is genuinely ambiguous, and only the person who ran the scan knows. Changeable afterwards on the project's edit page too, and it never rewrites the image. #}
{# A .zarr mask is a directory too -- the server has read one since LocalSegmentationProvider was written. #}
{% set node_masks = (node_resources or [])|selectattr("kind", "equalto", "segmentation")|list %} {% if node_masks %}
or a mask on a data node: {% for choice in node_masks %} {% endfor %}
{% endif %}
{# A .zarr store is a directory and a .csv/.h5ad is a file, and one input takes both -- so one button takes both. #}
.csv · .tsv · .txt · .h5ad · .zarr
{# The laptop-share layout: the viewer runs beside the images and the cell table never left the user's own machine, served by a data node over the same connection. Without this block that table is invisible here, and the form quietly demands a file this machine does not have. #} {% set node_tables = (node_resources or [])|selectattr("kind", "equalto", "table")|list %} {% if node_tables %}
or a table on a data node: {% for choice in node_tables %} {% endfor %}
{% endif %}
{# Shown only when the store holds more than one table. #} {# Which expression matrix to read is deliberately NOT asked here. It matters only to a plugin that reads marker intensities, so it is that plugin's requirement (Requires(features=True)) and the modal asks it -- along with whether to log-transform -- the first time such a tool opens. Importing an image is not the moment to answer a question about thresholding, and this form only asks what registering the project cannot proceed without. The layer names are still recorded from the inspection above, which is what lets the modal offer them without reopening the file. #} {# Shown only when the table spans several images. Loading them all would silently mix cells from different slides onto one image. #}
{% endblock %}