-
Notifications
You must be signed in to change notification settings - Fork 311
Add support for OME XML shapes #1848
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
You can use Fiji to get some view of the OME-XML. I see the ROIs are There is some information at https://forum.image.sc/t/prepping-and-including-roi-masks/48750 but I'm struggling to understand how this information is supposed to be parsed. Still, I hacked together this as an alternative to the current private static ROI convertMask(Mask mask) {
logger.debug("Converting mask {} to QuPath rectangle ROI", mask);
// I don't know why width and height are doubles...
// since we don't have the scale info here, I assume square pixels & try to figure out
// the required transform
var binData = mask.getBinData();
long nPixels = binData.getLength().getValue();
int width = (int)Math.sqrt(Math.round(nPixels * (mask.getWidth() / mask.getHeight())));
int height = (int)(nPixels / width);
if (((long)width * height) != nPixels) {
logger.warn("Couldn't figure out dimensions: {}x{} != {} pixels", width, height, nPixels);
return null;
}
// Create an image we can pass to ContourTracing
var array = binData.getBase64Binary();
var simpleImage = SimpleImages.createFloatImage(width, height);
for (int i = 0; i < nPixels; i++) {
if (array[i] != 0) {
simpleImage.setValue(i % width, i / width, 1.0f);
}
}
// Create a request we can use to calibrate the ROI
// We're assuming x and y are integers and that there is no other transform!
var request = RegionRequest.createInstance("", 1.0,
mask.getX().intValue(),
mask.getY().intValue(),
simpleImage.getWidth(),
simpleImage.getHeight(),
ImagePlane.getPlane(mask.getTheZ().getValue(), mask.getTheT().getValue()));
return ContourTracing.createTracedROI(simpleImage, 1, 1, request);
} It gives much more plausible ROIs for the sample image: There's also an interesting script that shows conversion in the opposite direction at https://github.com/glencoesoftware/ome-omero-roitool/blob/7b3896f6f6f3c168f3610a4a416ccf46df1aa278/src/dist/QuPath.scripts/OME_XML_export.groovy#L243 And a potentially-useful sample that shows more contortions are likely to be needed to figure out how to ensure that we only get annotations for the current I've converted this to a draft PR as we probably shouldn't merge it currently.
|
Indeed, the ROIs you get are more plausible. There's a script that shows a similar conversion here (it's in the same repo than the script you mentionned). I tried to implement it but it wasn't working, as it seems to expect I'll start from your code and check that the correct |
I integrated your code, handled transforms, and added unit tests for the converter from OME shape to QuPath ROI. I could create a sample image by opening Fiji, opening any sample image, adding ROIs to the ROIs manager, and then About |
Implement #1749.
This lacks proper testing, but I haven't be able to find another image than https://zenodo.org/records/14685515 (and even on this image I don't know what the expected annotations are).