Hello all,
does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: ... Roi roi = im.getRoi(); for (Point p : roi.getContainedPoints()) { ... // process p } Any help appreciated! --Wilhelm -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
I posted a similar solution in Jython here:
http://forum.imagej.net/t/pointroi-input-different-from-output-point-positions/1038 So you can get, e.g., points, etc., in Java with: Roi roi = im.getRoi(); int [] xArr = roi.getPolygon().xpoints int [] yArr = roi.getPolygon().ypoints See: http://javadoc.imagej.net/ImageJ1/ij/gui/PolygonRoi.html#getNCoordinates%28%29 |
In reply to this post by Burger Wilhelm
> On Apr 10, 2016, at 11:08 AM, Burger Wilhelm <[hidden email]> wrote:
> > Hello all, > > does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: > > ... > Roi roi = im.getRoi(); > for (Point p : roi.getContainedPoints()) { > ... // process p > } Get the ROI mask and use it to determine which pixels are contained in the ROI. The following JavaScript/BeanShell code calculates the mean value of the pixels contained in the current ROI or the mean of the entire image if there is no ROI. -wayne img = IJ.getImage(); ip = img.getProcessor(); bounds = ip.getRoi(); mask = img.getMask(); sum = 0; count = 0; for (y=0; y<bounds.height; y++) { for (x=0; x<bounds.width; x++) { if (mask==null||mask.getPixel(x,y)!=0) { count++; sum += ip.getf(x+bounds.x, y+bounds.y); } } } IJ.log("mean,count: "+IJ.d2s(sum/count,4)+" "+count); -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
In reply to this post by Burger Wilhelm
Following up on this, does anyone have a plugin or algo to do the opposite, namely, collect a group of contiguous points into an ImageJ ROi?
Eric Sent from [ProtonMail](https://protonmail.ch), encrypted email based in Switzerland. ---------------------------------------------------------------------- Date: Sun, 10 Apr 2016 15:08:40 +0000 From: Burger Wilhelm <[hidden email]> Subject: Iterator over Roi points anywhere? Hello all, does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: ... Roi roi = im.getRoi(); for (Point p : roi.getContainedPoints()) { ... // process p } Any help appreciated! --Wilhelm -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html ------------------------------ Date: Sun, 10 Apr 2016 09:21:57 -0700 From: Bio7 <[hidden email]> Subject: Re: Iterator over Roi points anywhere? I posted a similar solution in Jython here: http://forum.imagej.net/t/pointroi-input-different-from-output-point-positions/1038 So you can get, e.g., points, etc., in Java with: Roi roi = im.getRoi(); int [] xArr = roi.getPolygon().xpoints int [] yArr = roi.getPolygon().ypoints See: http://javadoc.imagej.net/ImageJ1/ij/gui/PolygonRoi.html#getNCoordinates%28%29 -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
In reply to this post by Rasband, Wayne (NIH/NIMH) [E]
Thanks Wayne,
this works nicely for some types of ROIs (polygon, ellipse, freehand). However, ROIs of sub-type rectangle, line, point and multi-point do not seem to define a mask. --Wilhelm -----Original Message----- From: ImageJ Interest Group [mailto:[hidden email]] On Behalf Of Rasband, Wayne (NIH/NIMH) [E] Sent: Montag, 11. April 2016 04:48 To: [hidden email] Subject: Re: Iterator over Roi points anywhere? > On Apr 10, 2016, at 11:08 AM, Burger Wilhelm <[hidden email]> wrote: > > Hello all, > > does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: > > ... > Roi roi = im.getRoi(); > for (Point p : roi.getContainedPoints()) { > ... // process p > } Get the ROI mask and use it to determine which pixels are contained in the ROI. The following JavaScript/BeanShell code calculates the mean value of the pixels contained in the current ROI or the mean of the entire image if there is no ROI. -wayne img = IJ.getImage(); ip = img.getProcessor(); bounds = ip.getRoi(); mask = img.getMask(); sum = 0; count = 0; for (y=0; y<bounds.height; y++) { for (x=0; x<bounds.width; x++) { if (mask==null||mask.getPixel(x,y)!=0) { count++; sum += ip.getf(x+bounds.x, y+bounds.y); } } } IJ.log("mean,count: "+IJ.d2s(sum/count,4)+" "+count); -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Hi Wilhelm,
Wayne's code should work for rectangles. They do not have a masks - the if (mask==null...) clause is meant for that case. For non-area rois, I fear that it is not so easy to get all points. For lines, you can use the 'Line to Area' command first. For Multi-Point Rois, you can use Roi.contains, or take the detour via 'Create Mask' and 'Create Selection'. The 'Roi.contains' method seems to be meant for this purpose, but unfortunately it does not work with lines. An implementation to make it work for lines would be nice (anyone out there who could do this?) A nasty problem with Roi.contains: For polygons, the pixels reported by 'Roi.contains' and those affected by 'Fill' and are not the same. It seems that there is a half-pixel offset in x and y between them. The reason is that PolygonRoi.contains uses FloatPolygon.contains instead of the mask. (The mask, which uses the ImageJ PolygonFiller, better fits the ImageJ conventions, i.e., it better fits what you see at high magnification). Another small inconsistency, if someone should find time to look at this: Both 'Fill' and 'Roi.contains' for rectangular rois with non-integer position do not round coordinates to the nearest integer but truncate them. For rectangles with positions like 9.99, this will cause an operation to be almost 1 pixel off from what you see at the screen. This seems to be a remainder from the days when ImageJ Rois could only have integer coordinates. Nothing is perfect... Michael ________________________________________________________________ On 2016-04-11 13:36, Burger Wilhelm wrote: > Thanks Wayne, > > this works nicely for some types of ROIs (polygon, ellipse, freehand). However, ROIs of sub-type rectangle, line, point and multi-point do not seem to define a mask. > > --Wilhelm > > > -----Original Message----- > From: ImageJ Interest Group [mailto:[hidden email]] On Behalf Of Rasband, Wayne (NIH/NIMH) [E] > Sent: Montag, 11. April 2016 04:48 > To: [hidden email] > Subject: Re: Iterator over Roi points anywhere? > >> On Apr 10, 2016, at 11:08 AM, Burger Wilhelm <[hidden email]> wrote: >> >> Hello all, >> >> does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: >> >> ... >> Roi roi = im.getRoi(); >> for (Point p : roi.getContainedPoints()) { >> ... // process p >> } > > Get the ROI mask and use it to determine which pixels are contained in the ROI. The following JavaScript/BeanShell code calculates the mean value of the pixels contained in the current ROI or the mean of the entire image if there is no ROI. > > -wayne > > img = IJ.getImage(); > ip = img.getProcessor(); > bounds = ip.getRoi(); > mask = img.getMask(); > sum = 0; > count = 0; > for (y=0; y<bounds.height; y++) { > for (x=0; x<bounds.width; x++) { > if (mask==null||mask.getPixel(x,y)!=0) { > count++; > sum += ip.getf(x+bounds.x, y+bounds.y); > } > } > } > IJ.log("mean,count: "+IJ.d2s(sum/count,4)+" "+count); > > -- > ImageJ mailing list: http://imagej.nih.gov/ij/list.html > > -- > ImageJ mailing list: http://imagej.nih.gov/ij/list.html > -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
You are certainly right. Then again, multi-rectangle ROIS *do* have a mask ...
Guess to make this generic I could revert to my original plan of merging the result of painting the ROI with its mask (if provided). I also noticed that Roi.contains() may be quite slow. Of course this will not eliminate the fill/contains discrepancies you mentioned. Thanks, Wilhelm -----Original Message----- From: ImageJ Interest Group [mailto:[hidden email]] On Behalf Of Michael Schmid Sent: Montag, 11. April 2016 14:57 To: [hidden email] Subject: Re: Iterator over Roi points anywhere? Hi Wilhelm, Wayne's code should work for rectangles. They do not have a masks - the if (mask==null...) clause is meant for that case. For non-area rois, I fear that it is not so easy to get all points. For lines, you can use the 'Line to Area' command first. For Multi-Point Rois, you can use Roi.contains, or take the detour via 'Create Mask' and 'Create Selection'. The 'Roi.contains' method seems to be meant for this purpose, but unfortunately it does not work with lines. An implementation to make it work for lines would be nice (anyone out there who could do this?) A nasty problem with Roi.contains: For polygons, the pixels reported by 'Roi.contains' and those affected by 'Fill' and are not the same. It seems that there is a half-pixel offset in x and y between them. The reason is that PolygonRoi.contains uses FloatPolygon.contains instead of the mask. (The mask, which uses the ImageJ PolygonFiller, better fits the ImageJ conventions, i.e., it better fits what you see at high magnification). Another small inconsistency, if someone should find time to look at this: Both 'Fill' and 'Roi.contains' for rectangular rois with non-integer position do not round coordinates to the nearest integer but truncate them. For rectangles with positions like 9.99, this will cause an operation to be almost 1 pixel off from what you see at the screen. This seems to be a remainder from the days when ImageJ Rois could only have integer coordinates. Nothing is perfect... Michael ________________________________________________________________ On 2016-04-11 13:36, Burger Wilhelm wrote: > Thanks Wayne, > > this works nicely for some types of ROIs (polygon, ellipse, freehand). However, ROIs of sub-type rectangle, line, point and multi-point do not seem to define a mask. > > --Wilhelm > > > -----Original Message----- > From: ImageJ Interest Group [mailto:[hidden email]] On Behalf Of > Rasband, Wayne (NIH/NIMH) [E] > Sent: Montag, 11. April 2016 04:48 > To: [hidden email] > Subject: Re: Iterator over Roi points anywhere? > >> On Apr 10, 2016, at 11:08 AM, Burger Wilhelm <[hidden email]> wrote: >> >> Hello all, >> >> does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: >> >> ... >> Roi roi = im.getRoi(); >> for (Point p : roi.getContainedPoints()) { >> ... // process p >> } > > Get the ROI mask and use it to determine which pixels are contained in the ROI. The following JavaScript/BeanShell code calculates the mean value of the pixels contained in the current ROI or the mean of the entire image if there is no ROI. > > -wayne > > img = IJ.getImage(); > ip = img.getProcessor(); > bounds = ip.getRoi(); > mask = img.getMask(); > sum = 0; > count = 0; > for (y=0; y<bounds.height; y++) { > for (x=0; x<bounds.width; x++) { > if (mask==null||mask.getPixel(x,y)!=0) { > count++; > sum += ip.getf(x+bounds.x, y+bounds.y); > } > } > } > IJ.log("mean,count: "+IJ.d2s(sum/count,4)+" "+count); > > -- > ImageJ mailing list: http://imagej.nih.gov/ij/list.html > > -- > ImageJ mailing list: http://imagej.nih.gov/ij/list.html > -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
In reply to this post by Burger Wilhelm
> On Apr 10, 2016, at 11:08 AM, Burger Wilhelm <[hidden email]> wrote:
> > Hello all, > > does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: > > ... > Roi roi = im.getRoi(); > for (Point p : roi.getContainedPoints()) { > ... // process p > } The latest ImageJ daily build (1.51a5) adds an Roi.getContainedPoints() method which works with arbitrary ROIs, including point and line selections. Here is example Java code that calculates the mean pixel value of the current ROI: ImagePlus img = IJ.getImage(); ImageProcessor ip = img.getProcessor(); Roi roi = img.getRoi(); double sum=0; int count=0; for (Point p : roi.getContainedPoints()) { count++; sum += ip.getf(p.x, p.y); } IJ.log("mean,count: "+IJ.d2s(sum/count,4)+" "+count); -wayne -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Hi,
Great question. Is there any chance there is an equally nice solution on macro writing level? Currently I use a (time consuming) workaround by making all pixels outside the ROI black and subtracting 1 from all pixels in the image. Then I iterate through the bounding box of the ROI and use an if statement to check if the value of the pixel. If -1, then we must be outside the ROI... A nice solution like the getcontainedpoints method would be great (and much faster, I assume). Kind greetings, Dimitri Vanhecke -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
In reply to this post by Rasband, Wayne (NIH/NIMH) [E]
Awesome, works great -- thanks much, Wayne!
--Wilhelm -----Original Message----- From: ImageJ Interest Group [mailto:[hidden email]] On Behalf Of Rasband, Wayne (NIH/NIMH) [E] Sent: Dienstag, 12. April 2016 03:19 To: [hidden email] Subject: Re: Iterator over Roi points anywhere? > On Apr 10, 2016, at 11:08 AM, Burger Wilhelm <[hidden email]> wrote: > > Hello all, > > does anyone know of a straight way to enumerate/iterate over all points contained in an (arbitrary) Roi? That is (in Java terms), something like this: > > ... > Roi roi = im.getRoi(); > for (Point p : roi.getContainedPoints()) { ... // process p } The latest ImageJ daily build (1.51a5) adds an Roi.getContainedPoints() method which works with arbitrary ROIs, including point and line selections. Here is example Java code that calculates the mean pixel value of the current ROI: ImagePlus img = IJ.getImage(); ImageProcessor ip = img.getProcessor(); Roi roi = img.getRoi(); double sum=0; int count=0; for (Point p : roi.getContainedPoints()) { count++; sum += ip.getf(p.x, p.y); } IJ.log("mean,count: "+IJ.d2s(sum/count,4)+" "+count); -wayne -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
In reply to this post by Dimitri Vanhecke
On Apr 12, 2016, at 2:17 AM, Dimitri Vanhecke <[hidden email]> wrote:
> > Hi, > Great question. Is there any chance there is an equally nice solution on macro writing level? Currently I use a (time consuming) workaround by making all pixels outside the ROI black and subtracting 1 from all pixels in the image. Then I iterate through the bounding box of the ROI and use an if statement to check if the value of the pixel. If -1, then we must be outside the ROI... > A nice solution like the getcontainedpoints method would be great (and much faster, I assume). The latest ImageJ daily build (1.51a9) adds the Roi.getContainedPoints() macro function. Here is an example macro that uses this function to calculate the mean pixel value of the current selection: sum=0; count=0; Roi.getContainedPoints(x,y); for (i=0; i<x.length; i++) { count++; sum += getPixel(x[i], y[i]); } print("mean,count: "+d2s(sum/count,4)+" "+count); -wayne -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Free forum by Nabble | Edit this page |