RoiManager?

classic Classic list List threaded Threaded
6 messages Options
Reply | Threaded
Open this post in threaded view
|

RoiManager?

Kenneth R Sloan-2
I write Java plugins - mostly interactive data gathering applications.  My Java skills are good, but my knowledge of ImageJ utilities is weak.  I now have an application which looks like it is a direct application of ImageJ utilities about which I know nothing - in particular, the RoiManager.

Given an (extension of a) StackWindow displaying an ImageStack (plus overlays which I prefer to not disturb), I would like to allow the observer to:

        a) draw Polygon ROIs (0, 1, or (if easy) many) in each slice
        b) freely browse through the stack, using the normal stack controls (plus other
            controls implemented in my extension) - with ONLY the Roi(s) associated with a
            particular slice displayed at each step

So...can some kind soul please point me at the appropriate documentation, or sample Java code, that does something similar?

The only user interaction with the top level program will be to say "done", or possibly to say "add this Roi".

I was about to implement all of this "from scratch", but it occurs to me that (in the abstract) this is a common process.

It *may* be desirable to compute (and display in another window) some information on the current slice (for example, the area of the Rois in that slice) - but this is optional.

At the end, the plugin will analyze the collection of Rois and write a report file - which is why I need the "done" indication.  If the "add/edit Rois while browsing the stack" can be isolated in a separate thread - a WaitForUserDialog() may be all I need at the top level.

All clues gratefully rented.
 
--
Kenneth Sloan
[hidden email]
Vision is the art of seeing what is invisible to others.

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: RoiManager?

Michael Schmid
Hi Kenneth,

sounds to me like this could be best done with adding the rois to the
overlay.
You can have a special name for the rois added, to later remove them all
from the overlay and leave the rest of the overlay untouched:

overlay.add(Roi roi, String name)
   https://github.com/imagej/imagej1/blob/master/ij/gui/Overlay.java#L42
overlay.remove(String name)
   https://github.com/imagej/imagej1/blob/master/ij/gui/Overlay.java#L73

Before adding the roi, set the stack position:

roi.setPosition(int n)
   https://github.com/imagej/imagej1/blob/master/ij/gui/Roi.java#L2092

or if it is a multi-dimentional stack
roi.setPosition(int channel, int slice, int frame)
   https://github.com/imagej/imagej1/blob/master/ij/gui/Roi.java#L2112

For the gui part, the easiest would probably be a WaitForUserDialog
telling the user what to do and pressing 'ok' when done. For adding
single Rois, I'd add a KeyListener for the image canvas, and ask the
user to press some otherwise unused key for adding the ROIs.

 
https://github.com/imagej/imagej1/blob/master/ij/gui/WaitForUserDialog.java

Michael
________________________________________________________________
On 24.07.20 20:36, Kenneth Sloan wrote:

> I write Java plugins - mostly interactive data gathering applications.  My Java skills are good, but my knowledge of ImageJ utilities is weak.  I now have an application which looks like it is a direct application of ImageJ utilities about which I know nothing - in particular, the RoiManager.
>
> Given an (extension of a) StackWindow displaying an ImageStack (plus overlays which I prefer to not disturb), I would like to allow the observer to:
>
> a) draw Polygon ROIs (0, 1, or (if easy) many) in each slice
> b) freely browse through the stack, using the normal stack controls (plus other
>              controls implemented in my extension) - with ONLY the Roi(s) associated with a
>              particular slice displayed at each step
>
> So...can some kind soul please point me at the appropriate documentation, or sample Java code, that does something similar?
>
> The only user interaction with the top level program will be to say "done", or possibly to say "add this Roi".
>
> I was about to implement all of this "from scratch", but it occurs to me that (in the abstract) this is a common process.
>
> It *may* be desirable to compute (and display in another window) some information on the current slice (for example, the area of the Rois in that slice) - but this is optional.
>
> At the end, the plugin will analyze the collection of Rois and write a report file - which is why I need the "done" indication.  If the "add/edit Rois while browsing the stack" can be isolated in a separate thread - a WaitForUserDialog() may be all I need at the top level.
>
> All clues gratefully rented.
>  
> --
> Kenneth Sloan
> [hidden email]
> Vision is the art of seeing what is invisible to others.
>
> --
> ImageJ mailing list: http://imagej.nih.gov/ij/list.html
>

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: RoiManager?

Kenneth R Sloan-2
Thanks for the reply.

Ordinarily, I would use the Overlay (and have done that it in similar plugins - but it this case I am trapped by my own ineptitude.  The StackWindow involved is part of a code base that supports many plugins (briefly, two StackWindows which are different extensions of StackWindow and which talk to each other and separately manage their own Overlays).  It uses the Overlay for different purposes, and when I originally wrote it I had some confusion about how to handle Overlays.  As a result, I am loathe to go back to that code to modify it.  If memory serves, I first tried to implement the Overlay processing to allow for sharing of the Overlay (using names) - but during debugging I gave up and made that code "greedy" so that it has total control over the Overlay - which it re-establishes on every interaction with the StackWindow.  That's on my list of things to fix the next time I do a major re-structuring (which I need to do soon...just not this week!)

I may, indeed, use a KeyListener to add a new Roi - I'm still at the "on paper design stage".  The simplest scheme is to have the user click on "OK" (in a wfud box) and then fetch the current Roi.  But, I will experiment with using roi.setPosition().  I assume that if I do this for every Roi, then *only* the Roi attached to a particular slice will be displayed?  That's what I want, but I was prepared to use an ImageListener to notice when the slice changes, and change the current Roi on the fly.

I already need to keep a separate stack of Roi's (one per slice) for later processing - so this is not all that much extra work.  But, if roi.setPositition() works as advertised, perhaps I can eliminate this stack and simply process the Rois at the end by fetching them from the StackWindow.

Using KeyListener would allow multiple Roi editing functions (add, delete, clear all, ...) and I just finished debugging a KeyListener for another plugin.  There, I had trouble maintaining "focus".  Perhaps this new plugin is a chance to see if I have internalized the lessons learned there.

If it matters, the immediate application is to compute the volume of an object from cross-sections traced by the user, using the Calalieri principle with care taken to handle the "lost cap" issues on either end.

Now...for extra credit...using roi.setPosition(), can I have multiple Roi's in each slice?  I don't really need this (now...) and can't quite see how to control which Roi is the "current" Roi while allowing multiple Roi's to be displayed (I just haven't tried this before).  But - if this is possible, it makes it more likely that I would use a KeyListener to control this feature.

--
Kenneth Sloan
[hidden email]
Vision is the art of seeing what is invisible to others.

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: RoiManager?

Michael Schmid
Hi Kenneth,

concerning:
 > Ordinarily, I would use the Overlay ... It uses the Overlay for
different purposes

I think you can still use the overlay and use names to separate the
different rois in the overlay. Unless you have hundreds of thousands of
overlays, where performance becomes an issue, you can use a single call
to delete all overlays with a given name.

 > I already need to keep a separate stack of Roi's (one per slice) for
later processing

Unless you have a huge number of rois (see above), you could also use
the roi names in the overlay to determine which rois serve which
purpose. Then you can iterate over the rois in the overlay and only use
these with the desired name. So you don't need to keep a separate list
(unless that list has some structure that you won't have with roi names,
e.g. a linked list, tree, etc.)

 > I may, indeed, use a KeyListener to add a new Roi

Of course, you can also use a nonblocking dialog, e.g. a
NonBlockingGenericDialog where you can add a panel with buttons, or a
PlugInFrame. From the user's point of view, it is usually nicer to use
the keyboard if one has to add lots of rois; but I'd prefer a dialog
with buttons if it is only few clicks (The buttons avoid the need for a
help text telling the user to use a keystroke).

 > Using KeyListener would allow multiple Roi editing functions (add,
delete, clear all, ...)
Yes, but you could do the same using a dialog with several buttons.

 >...using roi.setPosition(), can I have multiple Roi's in each slice?
Yes. I have done it with hundreds of rois per slice.


Michael
________________________________________________________________
On 27.07.20 20:25, Kenneth Sloan wrote:

> Thanks for the reply.
>
> Ordinarily, I would use the Overlay (and have done that it in similar plugins - but it this case I am trapped by my own ineptitude.  The StackWindow involved is part of a code base that supports many plugins (briefly, two StackWindows which are different extensions of StackWindow and which talk to each other and separately manage their own Overlays).  It uses the Overlay for different purposes, and when I originally wrote it I had some confusion about how to handle Overlays.  As a result, I am loathe to go back to that code to modify it.  If memory serves, I first tried to implement the Overlay processing to allow for sharing of the Overlay (using names) - but during debugging I gave up and made that code "greedy" so that it has total control over the Overlay - which it re-establishes on every interaction with the StackWindow.  That's on my list of things to fix the next time I do a major re-structuring (which I need to do soon...just not this week!)
>
> I may, indeed, use a KeyListener to add a new Roi - I'm still at the "on paper design stage".  The simplest scheme is to have the user click on "OK" (in a wfud box) and then fetch the current Roi.  But, I will experiment with using roi.setPosition().  I assume that if I do this for every Roi, then *only* the Roi attached to a particular slice will be displayed?  That's what I want, but I was prepared to use an ImageListener to notice when the slice changes, and change the current Roi on the fly.
>
> I already need to keep a separate stack of Roi's (one per slice) for later processing - so this is not all that much extra work.  But, if roi.setPositition() works as advertised, perhaps I can eliminate this stack and simply process the Rois at the end by fetching them from the StackWindow.
>
> Using KeyListener would allow multiple Roi editing functions (add, delete, clear all, ...) and I just finished debugging a KeyListener for another plugin.  There, I had trouble maintaining "focus".  Perhaps this new plugin is a chance to see if I have internalized the lessons learned there.
>
> If it matters, the immediate application is to compute the volume of an object from cross-sections traced by the user, using the Calalieri principle with care taken to handle the "lost cap" issues on either end.
>
> Now...for extra credit...using roi.setPosition(), can I have multiple Roi's in each slice?  I don't really need this (now...) and can't quite see how to control which Roi is the "current" Roi while allowing multiple Roi's to be displayed (I just haven't tried this before).  But - if this is possible, it makes it more likely that I would use a KeyListener to control this feature.
>
> --
> Kenneth Sloan
> [hidden email]
> Vision is the art of seeing what is invisible to others.
>
> --
> ImageJ mailing list: http://imagej.nih.gov/ij/list.html
>

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: RoiManager?

Kenneth R Sloan-2
Following advice here, I'm trying to associate a user-drawn Roi with a specific slice in a StackWindow.

I do (in a Java plugin):

        int slice = ip.getCurrentSlice();
        Roi roi = ip.getRoi();
        roi.setPosition(slice);
        ip.setRoi(roi);

But, the Roi is displayed on every slice.  If I edit (or re-draw) the Roi while positioned at a different slice - it changes (and is displayed) everywhere.

What am I doing wrong, please?

I suppose I can work around this by storing the Rois in my own stack, and using an ImageListener to notice when the slice changes (on a slice change - re-instate the correct Roi from my saved stack).

But, I was optimistic that this would not be necessary, and that ImageJ would handle this all for me.
Is there some method I'm missing in the documentation?  Should I be using the StackWindow instead of the ImagePlus used to create the StackWindow? (I don't see any relevant methods in the StackWindow api).


--
Kenneth Sloan
[hidden email]
Vision is the art of seeing what is invisible to others.

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: RoiManager?

Kenneth R Sloan-2
Ah...I think I see the issue.  The Roi is NOT part of the Overlay set for the StackWindow.

As previously noted, it's not (easily) possible for me to use this Overlay (it's being used - incompetently - in another piece of code managing this StackWindow).

So...off to implement the ImageListener solution.

I'm getting closer and closer to biting the bullet and fixing the offending Overlay code...

--
Kenneth Sloan
[hidden email]
Vision is the art of seeing what is invisible to others.

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html