Login  Register

help with 3D segmentation

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
25 messages Options Options
Embed post
Permalink
12
Reply | Threaded
Open this post in threaded view
| More
Print post
Permalink

Re: java3D and java 1.8

chin
40 posts
Hi aryeh,

It seems that using higher graphic cards are nessary for running 3D viewer in Fiji with Java 1.8. Using the ngeforce 8800, I got the messages as followed,
3D [dev] 1.6.0-scijava-2-pre11-daily-experimental daily

org.scijava.java3d.IllegalRenderingStateException: Java 3D ERROR : OpenGL 1.2 or better is required (GL_VERSION=1.1)
        at org.scijava.java3d.JoglPipeline.setupCanvasProperties(JoglPipeline.java:8083)
        at org.scijava.java3d.JoglPipeline.createNewContext(JoglPipeline.java:6440)
        at org.scijava.java3d.Canvas3D.createNewContext(Canvas3D.java:4602)
        at org.scijava.java3d.Canvas3D.createNewContext(Canvas3D.java:2376)
        at org.scijava.java3d.Renderer.doWork(Renderer.java:881)
        at org.scijava.java3d.J3dThread.run(J3dThread.java:271)
Exception occurred in RenderingErrorListener:
java.lang.RuntimeException
        at ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
        at org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
        at org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
        at org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
nFrames = 1
-----------------------------------

However, when using the ngeforce 680x, I got the fewer meaasges,
Exception occurred in RenderingErrorListener:
java.lang.RuntimeException
        at ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
        at org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
        at org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
        at org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
nFrames = 1
---------------------------------
I have no idea why the 3D viewer downloaded from 3D site as Curtis mentioned could not work correctly.

Best regards,
chin

 
<quote author='Aryeh Weiss'>
Hi Curtis,

Thank you for your response.

On 24/11/2015 5:33 AM, Curtis Rueden wrote:
> Hi Aryeh,
>
> Apologies for the long delay in reply. I have been working to get Java
Reply | Threaded
Open this post in threaded view
| More
Print post
Permalink

Re: java3D and java 1.8

Aryeh Weiss
468 posts
Hi Chin

Thank you for your response. Sorry it has taken me so long to follow up.

On 24/11/2015 12:00 PM, chin wrote:

> Hi aryeh,
>
> It seems that using higher graphic cards are nessary for running 3D viewer
> in Fiji with Java 1.8. Using the ngeforce 8800, I got the messages as
> followed,
> 3D [dev] 1.6.0-scijava-2-pre11-daily-experimental daily
>
> org.scijava.java3d.IllegalRenderingStateException: Java 3D ERROR : OpenGL
> 1.2 or better is required (GL_VERSION=1.1)
> at
> org.scijava.java3d.JoglPipeline.setupCanvasProperties(JoglPipeline.java:8083)
> at org.scijava.java3d.JoglPipeline.createNewContext(JoglPipeline.java:6440)
> at org.scijava.java3d.Canvas3D.createNewContext(Canvas3D.java:4602)
> at org.scijava.java3d.Canvas3D.createNewContext(Canvas3D.java:2376)
> at org.scijava.java3d.Renderer.doWork(Renderer.java:881)
> at org.scijava.java3d.J3dThread.run(J3dThread.java:271)
> Exception occurred in RenderingErrorListener:
> java.lang.RuntimeException
> at ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
> at
> org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
> at
> org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
> at org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
> nFrames = 1
> -----------------------------------
>
> However, when using the ngeforce 680x, I got the fewer meaasges,
> Exception occurred in RenderingErrorListener:
> java.lang.RuntimeException
> at ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
> at
> org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
> at
> org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
> at org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
> nFrames = 1
> ---------------------------------
>
My Macbook Pro uses the NVidea GeForce GT 650M with 1GB VRAM.

This is the error I get when I try to resize the 3D Viewer window.

com.jogamp.opengl.GLException: detachAllImpl failed: FBO implementation
fault, FBO[name r/w 1/1, init true, bound true, size 529x524, samples
0/8, modified true/true, depth RenderAttachment[type DEPTH, format
0x81a5, samples 0, 529x524, name 0xffffffff, obj 0x478dcfc9], stencil
null, colorbuffer attachments: 1/8, with 1 textures:
[TextureAttachment[type COLOR_TEXTURE, target GL_TEXTURE_2D, level 0,
format 0x8051, 529x524, border 0, dataFormat 0x1907, dataType 0x1401;
min/mag 0x2600/0x2600, wrap S/T 0x812f/0x812f; name 0xffffffff, obj
0x589f76eb], null, null, null, null, null, null, null], msaa[null,
hasSink false, dirty true], state FBO implementation fault, obj 0x6486d1fd]
     at com.jogamp.opengl.FBObject.detachAllImpl(FBObject.java:2198)
     at com.jogamp.opengl.FBObject.reset(FBObject.java:1139)
     at
org.scijava.java3d.JoglPipeline.resizeOffscreenLayer(JoglPipeline.java:6290)
     at org.scijava.java3d.Canvas3D.setViewport(Canvas3D.java:4864)
     at org.scijava.java3d.Renderer.doWork(Renderer.java:993)
     at org.scijava.java3d.J3dThread.run(J3dThread.java:271)
Exception occurred in RenderingErrorListener:
java.lang.RuntimeException
     at
ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
     at
org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
     at
org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
     at
org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)

This is reproducible, but there is some variability. Sometimes it
happens on the second resize, instead of the first. Usually, it causes
FIji to ignore all subsequents mouse clinks (eg, to close windows or to
exit FIji), but the menus still appear when selected (they just do not
do anything).

Best regards,
--aryeh

>
> Hi Curtis,
>
> Thank you for your response.
>
> On 24/11/2015 5:33 AM, Curtis Rueden wrote:
>> Hi Aryeh,
>>
>> Apologies for the long delay in reply. I have been working to get Java
>
>
> --
> View this message in context: http://imagej.1557.x6.nabble.com/help-with-3D-segmentation-tp5014798p5015014.html
> Sent from the ImageJ mailing list archive at Nabble.com.
>
> --
> ImageJ mailing list: http://imagej.nih.gov/ij/list.html
>


--
Aryeh Weiss
Faculty of Engineering
Bar Ilan University
Ramat Gan 52900 Israel

Ph:  972-3-5317638
FAX: 972-3-7384051

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

Re: java3D and java 1.8

ctrueden
1670 posts
Hi Aryeh,

> This is reproducible

Thanks for testing, and sorry to hear there are problems. I am indeed able
to reproduce this behavior on my system as well. Unfortunately, it appears
to be a bug within Java 3D 1.6 and/or JOGL.

I filed an issue for it:
   https://github.com/fiji/3D_Viewer/issues/15

Regards,
Curtis

On Tue, Dec 1, 2015 at 2:22 AM, Aryeh Weiss <[hidden email]> wrote:

> Hi Chin
>
> Thank you for your response. Sorry it has taken me so long to follow up.
>
>
> On 24/11/2015 12:00 PM, chin wrote:
>
>> Hi aryeh,
>>
>> It seems that using higher graphic cards are nessary for running 3D viewer
>> in Fiji with Java 1.8. Using the ngeforce 8800, I got the messages as
>> followed,
>> 3D [dev] 1.6.0-scijava-2-pre11-daily-experimental daily
>>
>> org.scijava.java3d.IllegalRenderingStateException: Java 3D ERROR : OpenGL
>> 1.2 or better is required (GL_VERSION=1.1)
>>         at
>>
>> org.scijava.java3d.JoglPipeline.setupCanvasProperties(JoglPipeline.java:8083)
>>         at
>> org.scijava.java3d.JoglPipeline.createNewContext(JoglPipeline.java:6440)
>>         at
>> org.scijava.java3d.Canvas3D.createNewContext(Canvas3D.java:4602)
>>         at
>> org.scijava.java3d.Canvas3D.createNewContext(Canvas3D.java:2376)
>>         at org.scijava.java3d.Renderer.doWork(Renderer.java:881)
>>         at org.scijava.java3d.J3dThread.run(J3dThread.java:271)
>> Exception occurred in RenderingErrorListener:
>> java.lang.RuntimeException
>>         at
>> ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
>>         at
>>
>> org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
>>         at
>>
>> org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
>>         at
>> org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
>> nFrames = 1
>> -----------------------------------
>>
>> However, when using the ngeforce 680x, I got the fewer meaasges,
>> Exception occurred in RenderingErrorListener:
>> java.lang.RuntimeException
>>         at
>> ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
>>         at
>>
>> org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
>>         at
>>
>> org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
>>         at
>> org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
>> nFrames = 1
>> ---------------------------------
>>
>> My Macbook Pro uses the NVidea GeForce GT 650M with 1GB VRAM.
>
> This is the error I get when I try to resize the 3D Viewer window.
>
> com.jogamp.opengl.GLException: detachAllImpl failed: FBO implementation
> fault, FBO[name r/w 1/1, init true, bound true, size 529x524, samples 0/8,
> modified true/true, depth RenderAttachment[type DEPTH, format 0x81a5,
> samples 0, 529x524, name 0xffffffff, obj 0x478dcfc9], stencil null,
> colorbuffer attachments: 1/8, with 1 textures: [TextureAttachment[type
> COLOR_TEXTURE, target GL_TEXTURE_2D, level 0, format 0x8051, 529x524,
> border 0, dataFormat 0x1907, dataType 0x1401; min/mag 0x2600/0x2600, wrap
> S/T 0x812f/0x812f; name 0xffffffff, obj 0x589f76eb], null, null, null,
> null, null, null, null], msaa[null, hasSink false, dirty true], state FBO
> implementation fault, obj 0x6486d1fd]
>     at com.jogamp.opengl.FBObject.detachAllImpl(FBObject.java:2198)
>     at com.jogamp.opengl.FBObject.reset(FBObject.java:1139)
>     at
> org.scijava.java3d.JoglPipeline.resizeOffscreenLayer(JoglPipeline.java:6290)
>     at org.scijava.java3d.Canvas3D.setViewport(Canvas3D.java:4864)
>     at org.scijava.java3d.Renderer.doWork(Renderer.java:993)
>     at org.scijava.java3d.J3dThread.run(J3dThread.java:271)
> Exception occurred in RenderingErrorListener:
> java.lang.RuntimeException
>     at
> ij3d.ImageWindow3D$ErrorListener.errorOccurred(ImageWindow3D.java:295)
>     at
> org.scijava.java3d.VirtualUniverse.notifyRenderingErrorListeners(VirtualUniverse.java:1198)
>     at
> org.scijava.java3d.NotificationThread.processNotifications(NotificationThread.java:86)
>     at
> org.scijava.java3d.NotificationThread.run(NotificationThread.java:104)
>
> This is reproducible, but there is some variability. Sometimes it happens
> on the second resize, instead of the first. Usually, it causes FIji to
> ignore all subsequents mouse clinks (eg, to close windows or to exit FIji),
> but the menus still appear when selected (they just do not do anything).
>
> Best regards,
> --aryeh
>
>>
>> Hi Curtis,
>>
>> Thank you for your response.
>>
>> On 24/11/2015 5:33 AM, Curtis Rueden wrote:
>>
>>> Hi Aryeh,
>>>
>>> Apologies for the long delay in reply. I have been working to get Java
>>>
>>
>>
>> --
>> View this message in context:
>> http://imagej.1557.x6.nabble.com/help-with-3D-segmentation-tp5014798p5015014.html
>> Sent from the ImageJ mailing list archive at Nabble.com.
>>
>> --
>> ImageJ mailing list: http://imagej.nih.gov/ij/list.html
>>
>>
>
> --
> Aryeh Weiss
> Faculty of Engineering
> Bar Ilan University
> Ramat Gan 52900 Israel
>
> Ph:  972-3-5317638
> FAX: 972-3-7384051
>
> --
> 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
| More
Print post
Permalink

Re: help with 3D segmentation - update

TimFeinstein
48 posts
In reply to this post by Aryeh Weiss
Hello Aryeh and others,

Thank you!! The droplet finder plus Gaussian blur and background
subtraction works extremely well for nucleus detection in 3D tissue.  I
put together the script at the bottom based on yours to get the most
reliable results with our data.  The live preview was essential for
calibrating the variables correctly.

Some follow-up questions:

Fiji can do Gaussian blur and median filtering in 3D.  Is there any
advantage to doing it that way?  Does the extra time offset any precision
improvement?

Also, I am having trouble scripting the final quality control step.  Right
now I export the results, filter outliers in Excel and re-import the X and
Y positions via Import>XY CoordinatesŠ  That works pretty well when I
overlay it on a max intensity projection, although it misses nuclei
sitting on top of each other in the stack. It would be nice to preserve
the masks from the live preview window as a stack image.  Alternatively I
wonder whether it would be possible to draw a small sphere centered on
each XYZ centroid.  Say, make a stack with spheres and merge that with the
data stack using color merge, with spheres in red and data in green. You
could pretty quickly judge which nuclei are inappropriately detected.
This is just an idea; drawing a sphere in a stack centered on a designated
XYZ position is outside my current abilities.

My version of the nucleus detector (40x 1.2 water lens; 0.11 x 0.11 x 0.5
um pixels):

dupTitle=getTitle
BG = getNumber("Enter background:",80);
run("Subtract...", "value=BG stack");
run("Despeckle", "stack");
run("Median 3D...", "x=2 y=2 z=2");
run("Gaussian Blur...", "sigma=0.70 scaled stack");
run("32-bit");
run("Brightness/Contrast...");
run("Enhance Contrast", "saturated=0.35");
run("DF_Filterstacker", "maximal_feature_size=8 minimal_feature_size=3
z/x_aspect_ratio=5.000 radius_x=2 radius_y=2 radius_z=2 invert
image=[BP_"+dupTitle+"] mask=[WS_BP_"+dupTitle+"] area_threshold=0.150
maximum_threshold=0.30 connect_threshold=0.40 slice=1");

All the best,



Tim

Timothy Feinstein, Ph.D.
Research Scientist
University of Pittsburgh Department of Developmental Biology





On 11/13/15, 6:04 AM, "ImageJ Interest Group on behalf of Aryeh Weiss"
<[hidden email] on behalf of [hidden email]> wrote:

>This last week I focused mostly on the 3D-watershed approach.
>Updates are interleaved below.
>
>On 08/11/2015 9:10 AM, Aryeh Weiss wrote:
>> Further on my adventures using the DoG function:
>>
>> I mentioned that the DoGPeaks function appears to find minima as well as
>> maxima. I decided to go to the Difference of Gaussian function
>>
>>http://javadoc.imagej.net/Fiji/mpicbg/imglib/algorithm/scalespace/Differe
>>nceOfGaussian.html#DifferenceOfGaussian(mpicbg.imglib.image.Image,%20mpic
>>bg.imglib.image.ImageFactory,%20mpicbg.imglib.function.Converter,%20mpicb
>>g.imglib.outofbounds.OutOfBoundsStrategyFactory,%20double[],%20double[],%
>>20B,%20B)
>>
>> Here I see that it explicitly states that it extracts local minima and
>> maxima of a certain size. I wonder if I can get only the maxima fro this
>> function.
>>
>
>Jan Eglinger posted the answer to this. Here is what he wrote:
>-----
>You have to go one step further: the `DifferenceOfGaussian` class has a
>`findPeaks` method that gives you a list of `DifferenceOfGaussianPeak`s.
>
>In its Javadoc [1] you find the methods:
>     boolean isMin()
>     boolean isMax()
>that you can use to differentiate between minima and maxima.
>
>I modified your script to only get the maxima:
>https://gist.github.com/imagejan/7cc228b9a5e57cce44a0
>
>Here's what I changed:
>https://gist.github.com/imagejan/7cc228b9a5e57cce44a0/revisions
>-----
>
>This enables the threshold to be set lower, without picking up the minima.
>
>> Among its parameters are Converter, OutOfBoundsStrategy (among others).
>> I did not understand how to use these classes, so I wonder if someone on
>> this list can tell me how to use them, or even better, point me at the
>> documentation that might help (the class definitions in javadoc were not
>> enough for me).
>>
>
>Jan also added the following:
>-----
>Albert's excellent tutorials unfortunately make use of the
>now-deprecated ImgLib1 code that was superseded by ImgLib2 [2].
>
>Jean-Yves Tinevez's TrackMate plugin is a great example how to use
>ImgLib2. It's `LogDetector` [3] and `DogDetector` [4] classes show how
>to detect spots using ImgLib2 implementations of LoG and DoG.
>
>I added a script to the ImageJ wiki illustrating how to use
>`DogDetector` from a Python script:
>http://imagej.net/Jython_Scripting#Find_peaks_in_a_3D_image
>-----
>
>I did not have a chance to try this, because I focused on the watershed
>approach (see comments below).
>
>> Thank in advance.
>> --aryeh
>>
>>
>> On 05/11/2015 12:58 PM, Aryeh Weiss wrote:
>>> This is an update on the problem I posted.
>>>
>>> First, thanks to the people who replies with suggestions. From these, I
>>> am now following up on two of them.
>>>
>>> 1. Albert Cardona suggested trying the 3D (actually multi-D) difference
>>> of Gaussians (DoG) filter. This looks promising, plus it introduced me
>>> to imglib. It works great on isolated cells (actually, everything works
>>> great on isolated cells) and seems reasonable for my image, but still
>>> needs work. because I have such a dense collection of nuclei, it
>>> sometimes detects dark blobs, which are actually an approximately
>>> cell-sized island within a sea of nuclei.
>>> Albert's sample code  displays the result in 3D using the 3D viewer.
>>> Unfortunately, java3D does not work in java 1.8, and in Java 1.6, while
>>> the java3D test works, the code that generates the 3D view fails --
>>>that
>>> will go into a separate thread.
>>> The net result is that I can mark the centers of the nuclei (which is
>>> why it look promising) but I cannot visualize it in 3D to see if it
>>> really looks right.
>>>
>>> 2. Thomas Boudier suggest some 3D bandpass filtering followed by a
>>> seeded watershed. I will work more on finding the right parameters for
>>> this approach  after I finish with the DoG approach.   One problem is
>>> that the resolution in Z is much lower that in X-Y. As a result, the
>>> watershed does not separate the nuclei along Z. It is not clear to me
>>> why the DoG does.  However, I still need to learn to to use the output
>>> of the watershed -- I may not be interpreting the output correctly.
>>>
>
>I found that I got a very good segmentation (ie, marking of the nuclei)
>by using the watershed in the droplet finder plugins. Or more
>accurately, using the droplet finder workflow which is run by
>Plugins>Droplet Finder>DF_Filterstacker
>
>The macro recorder enabled me to script it.
>
>// The code to get the file and parse
>// the filename and image title has been left out.
>
>run("32-bit"); // DF-Bandpass wants 32 bit input
>
>// The median, rolling ball filter, and Gaussian blur
>// greatly improved the accuracy
>run("Median...", "radius=2 stack");
>run("Subtract Background...", "rolling=50 sliding stack");
>run("Gaussian Blur...", "sigma=1.5 scaled stack");
>
>// macro recorder created this. This is a long command, so if you
>// cut and paste, you may have to reassemble it
>run("DF_Filterstacker", "maximal_feature_size=15 minimal_feature_size=7
>z/x_aspect_ratio=5.000 radius_x=2 radius_y=2 radius_z=2 invert
>image=[BP_"+dupTitle+"] mask=[WS_BP_"+dupTitle+"] area_threshold=0.300
>maximum_threshold=0.3 connect_threshold=0.80 slice=5");
>IJ.renameResults("Results");
>IJ.renameResults("Particle Results");
>
>
>This script produces a table called "Particle Results", with (among
>other things) the X, Y, and Z coordinates of the objects.
>
>>> I recently got access to Imaris (basic) with a spot detector. It does a
>>> decent job, but since I don't have it on my computer, I plan to solve
>>> this with ImageJ.
>>>
>>> When I have something that works and that I can visualize, I will post
>>> it for the benefit of other who, like me, have to muddle their way from
>>> 2D to 3D.
>>>
>
>In order to visualize the results, I have a python script to read the
>Particle Results table and produce a set of point ROIs that can mark the
>original image.
>The i can flatten the image and display this with the 3D Viewer (Java
>1.6 only).
>
>"""
>This script converts the output of the droplet finder plugin (Paticle
>Results)
>to a set of point ROIs whcih can be used to mark the drops (in my case,
>nuclei)
>on the original image.
>
>Input: Particle Results table from Droplet Finder
>Output: An ROI Manager populated with point ROIs whose coordinates
>         correspond to the list in the table.
>
>Bugs to fix: If the ROI Manager is open when the program is run,
>rm.addRoi fails with a null pointer error.
>"""
>
># Does not require auto-import
>
>from ij import IJ, WindowManager
>from ij.plugin.frame import RoiManager
>from ij.measure import ResultsTable
>from ij.gui import PointRoi
>
>dfTitle = "Particle Results"
>IJ.renameResults(dfTitle , "Results")
>
>rt = ResultsTable.getResultsTable()
>
>pos = []
>
>for i in range(rt.size()):
> pos.append([rt.getValue("position_x",i), rt.getValue("position_y", i),
>rt.getValue("position_z", i)])
>
>for i in range(rt.size()):
> print pos[i];
>
>print len(pos)
>
>dfTitle = "Particle Results"
>IJ.renameResults( "Results" , dfTitle )
>
># I do not know why this does not prevent the null pointer error
># which I get if the ROI Manager is open when this script is run
>if "ROI Manager" in WindowManager.getImageTitles():
> WindowManager.getWindow("ROI Manager").close()
>
>rm = RoiManager()
>rm.show()
>
>for p in pos:
>   cellRoi = PointRoi(int(p[0]),int(p[1]))
>   cellRoi.setPosition(int(p[2]))
>   rm.addRoi(cellRoi)
>
>rm.runCommand("Show All without labels")
>
># end of script
>
>I actually created two images -- one is the original, and the second is
>a blank image with the point ROIs flattened into it. Then I overlay them
>with the 3D viewer and increase transparency of the data to see the
>marks. What I really want to do is make the nuclei into surfaces and
>then "peel" them away to reveal the marks. I have not yet figured that
>out, and the surface rendering takes a really long time.
>
>One problem I have is that sooner or later, the 3D Viewer menus get
>grayed out (though mouse clicks in the 3D Viewer window still work).
>The I have to close it and start again. I have not been able to
>associate this with a reproducible set of actions.
>
>
>I hope this is useful
>--aryeh
>
>--
>Aryeh Weiss
>Faculty of Engineering
>Bar Ilan University
>Ramat Gan 52900 Israel
>
>Ph:  972-3-5317638
>FAX: 972-3-7384051
>
>--
>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
| More
Print post
Permalink

Re: help with 3D segmentation - update

Aryeh Weiss
468 posts
In reply to this post by Aryeh Weiss
On 10/12/2015 10:00 PM, Feinstein, Timothy N wrote:

> Hello Aryeh and others,
>
> Thank you!! The droplet finder plus Gaussian blur and background
> subtraction works extremely well for nucleus detection in 3D tissue.  I
> put together the script at the bottom based on yours to get the most
> reliable results with our data.  The live preview was essential for
> calibrating the variables correctly.
>
> Some follow-up questions:
>
> Fiji can do Gaussian blur and median filtering in 3D.  Is there any
> advantage to doing it that way?  Does the extra time offset any precision
> improvement?
In my case, it did not matter. In X-Y, the resolution is high enough
that without blurring their would be many split nuclei,
because the nuclear staining is more donut like (with significant
variance).
In Z that is not the case, so I stayed with 2D blurring.

> Also, I am having trouble scripting the final quality control step.  Right
> now I export the results, filter outliers in Excel and re-import the X and
> Y positions via Import>XY CoordinatesŠ  That works pretty well when I
> overlay it on a max intensity projection, although it misses nuclei
> sitting on top of each other in the stack. It would be nice to preserve
> the masks from the live preview window as a stack image.  Alternatively I
> wonder whether it would be possible to draw a small sphere centered on
> each XYZ centroid.  Say, make a stack with spheres and merge that with the
> data stack using color merge, with spheres in red and data in green. You
> could pretty quickly judge which nuclei are inappropriately detected.
> This is just an idea; drawing a sphere in a stack centered on a designated
> XYZ position is outside my current abilities.

Below I appended an updated version of a python script which will prompt
for a file that contains a particle results table (as generated by
droplet finder) and produces a point ROIset which marks the center of
each particle (as listed in the particle results table). If you flatten
this onto the original 3D stack, you can use the 3D-viewer (in Java 1.6)
to get a reasonable idea of how well it is working. Even scrolling
though the stack gives you an idea of how well it is doing.

Another thing I did was to create a blank image stack, flatten the point
ROIs into that, threshold and dilate to get larger marks (like spheres)
at the centers. The the two stacks can be overlayed in the 3D viewer.

I still need to play more with the other approach (difference of
Gaussians), which  also shows promise.
However, the nice thing about the DF plugins is that they take care of
processing the 3D watershed results and producing the Particle Results
table.

The person for whom I did this just needed a count of the cells, and he
is currently running it on lots of images to see how it works.
> My version of the nucleus detector (40x 1.2 water lens; 0.11 x 0.11 x 0.5
> um pixels):
>
> dupTitle=getTitle
> BG = getNumber("Enter background:",80);

I wonder if you can use a broad Gaussian filter, or one of the various
BG subtraction/estimation tools,
to find the background for subtraction.
> run("Subtract...", "value=BG stack");
> run("Despeckle", "stack");
Is Despeckle needed given the 3D median that you run in the next line?

> run("Median 3D...", "x=2 y=2 z=2");
> run("Gaussian Blur...", "sigma=0.70 scaled stack");
> run("32-bit");
> run("Brightness/Contrast...");
> run("Enhance Contrast", "saturated=0.35");
> run("DF_Filterstacker", "maximal_feature_size=8 minimal_feature_size=3
> z/x_aspect_ratio=5.000 radius_x=2 radius_y=2 radius_z=2 invert
> image=[BP_"+dupTitle+"] mask=[WS_BP_"+dupTitle+"] area_threshold=0.150
> maximum_threshold=0.30 connect_threshold=0.40 slice=1");
>
>
> On 05/11/2015 12:58 PM, Aryeh Weiss wrote:
>> This script produces a table called "Particle Results", with (among
>> other things) the X, Y, and Z coordinates of the objects.
>>
>>

"""
This script converts the output of the droplet finder plugin (Paticle
Results)
to a set of point ROIs whcih can be used to mark the drops (in my case,
nuclei)
on the original image.

Input: A particle-results table which was generated by the Droplet
Finder plugin
http://imagejdocu.tudor.lu/doku.php?id=plugin:analysis:droplet_counter:start

Output: A ROI set (in an open ROI Manager window) which contains a
single PointRoi
         for each blob that is listed in the particle-results table.

Author: Aryeh Weiss
Last modified: 22 Nov 2015

"""

from ij import IJ, WindowManager
from ij.plugin.frame import RoiManager
from ij.measure import ResultsTable
from ij.gui import PointRoi
from ij.io import DirectoryChooser,  OpenDialog

DEBUG = False

# Prompt for the input particle-results table
op = OpenDialog("Choose input table...", "")
path = op.getDirectory()+ op.getFileName()
tableName = op.getFileName()
tableDir = op.getDirectory()
tablePath = tableDir + tableName
print tablePath

if tableName[-4] == ".":
     tablePrefix = tableName[:-4]    # assumes that a suffix exists
else:
     tablePrefix = inputName


# Open the table as a results table
rt = ResultsTable.open2(tablePath)
#IJ.renameResults("Results")
rt.show("Results")   # automatically names the table "Results"


# Create an empty list to hold the 3D blob positions
pos = []
# Populate the 3D position list
for i in range(rt.size()):
     pos.append([rt.getValue("position_x",i), rt.getValue("position_y",
i), rt.getValue("position_z", i)])

if (DEBUG):
     for i in range(rt.size()):
         print pos[i];

print len(pos)

# Some results-table methods require a table named "Results"
IJ.renameResults( "Results" , tableName )

# Close the ROI manager if it is open
# First Deselect and then Delete all ROIs so that the user will not be
prompted  to save as overlay
# when closing the ROI manager
if "ROI Manager" in WindowManager.getNonImageTitles():
     rm = RoiManager.getInstance()
     rm.runCommand("Deselect")
     rm.runCommand("Delete")
     rm.close()

# Create a new ROI Manager
rm = RoiManager()
rm.show()

# Populate the ROI set by adding the PointRoi objects one at a time to
the ROI manager
for p in pos:
# The PointRoi constructor sets the XY coordinate of the ROI
     cellRoi = PointRoi(int(p[0]),int(p[1]))
# setPosition sets the stack slice associated with the PointRoi
     cellRoi.setPosition(int(p[2]))
     rm.addRoi(cellRoi)

rm.runCommand("Show All without labels")
rm.runCommand("Save", tableDir + tablePrefix + "RoiSet.zip");



Hope you find this useful.
--aryeh

--
Aryeh Weiss
Faculty of Engineering
Bar Ilan University
Ramat Gan 52900 Israel

Ph:  972-3-5317638
FAX: 972-3-7384051

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