Loading... |
Reply to author |
Edit post |
Move post |
Delete this post |
Delete this post and replies |
Change post date |
Print post |
Permalink |
Raw mail |
36 posts
|
Hello,
I wrote a simple plugin that puts all pixel values of a selected ROI into a 1D table. What I can't figure out is how to pass the resulting 1D array to a macro calling the plugin? i.e., similarly to getStatistics, which makes a histogram array available in the macro calling the function for example. Many thanks for your help, All the best, Emmanuel ~~~~~~~~~~~~~ Run function of the (very simple) plugin: In the end, the float array myT contains the pixel values of the currently selected ROI --> how to make myT available in a macro? public float[] myT; public void run(ImageProcessor ip) { Rectangle r = ip.getRoi(); ImageProcessor mask = ip.getMask(); if (mask==null) { mask = new ByteProcessor(r.width, r.height); mask.invert(); } int total = 0; for (int x= 0; x < r.width; x++) { for (int y=0; y < r.height; y++) { if(mask.getf(x,y) > 0){ total++; } } } myT = new float[total]; total=0; for (int x= 0; x < r.width; x++) { for (int y=0; y < r.height; y++) { if(mask.getf(x,y) > 0){ myT[total++]=ip.getf(x, y); } //IJ.log("Pixel: Y="+y+" ; X="+x+" ; value=" + ip.getf(x, y) + "Mask = "+ mask.getf(x,y) ); } } } -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Loading... |
Reply to author |
Edit post |
Move post |
Delete this post |
Delete this post and replies |
Change post date |
Print post |
Permalink |
Raw mail |
1631 posts
|
Hi Emmanuel,
On Mon, 1 Apr 2013, Emmanuel Levy wrote: > I wrote a simple plugin that puts all pixel values of a selected ROI > into a 1D table. What I can't figure out is how to pass the resulting 1D > array to a macro calling the plugin? i.e., similarly to getStatistics, > which makes a histogram array available in the macro calling the > function for example. I fear that you are trying to do something with the macro language that it was not designed for. Remember, the macro language is meant to be very simple so it is easy to learn, it is not meant to be fast (and it is indeed not fast) nor a fully-fledged scripting language. Javascript is. Sure, you may get Wayne to extend the macro language, but everytime the syntax gets extended, the macro interpreter becomes more brittle since the original design was not intended to be extended in that way. In your case, the easiest may be a work-around: you *can* set the ROI thusly: dummy = new float[myT.length]; image.setRoi(new PointRoi(myT, dummy, dummy.length)); Ciao, Johannes -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Loading... |
Reply to author |
Edit post |
Move post |
Delete this post |
Delete this post and replies |
Change post date |
Print post |
Permalink |
Raw mail |
36 posts
|
Hi Johannes,
Thanks, I understand that this does sound a bit strange but the reason is that i started working on a macro a long time ago and it would require a significant amount of work to port the whole thing to Javascript. I was thinking that there should already be a way to do this as the getSttatistics function gives access to an array of values (hist) that (i suppose) is calculated from java code. I'm not sure I explained my question clearly, all I want is to pass an array of values back to the macro language to process it, not set or modify a ROI. E.g., just like one has access to the value of "hist" after calling getStatistics, id like to have access to myT. I hope im clearer! Thank you, Emmanuel On 1 Apr 2013, at 20:13, Johannes Schindelin <[hidden email]> wrote: > Hi Emmanuel, > > On Mon, 1 Apr 2013, Emmanuel Levy wrote: > >> I wrote a simple plugin that puts all pixel values of a selected ROI >> into a 1D table. What I can't figure out is how to pass the resulting 1D >> array to a macro calling the plugin? i.e., similarly to getStatistics, >> which makes a histogram array available in the macro calling the >> function for example. > > I fear that you are trying to do something with the macro language that it > was not designed for. Remember, the macro language is meant to be very > simple so it is easy to learn, it is not meant to be fast (and it is > indeed not fast) nor a fully-fledged scripting language. Javascript is. > > Sure, you may get Wayne to extend the macro language, but everytime the > syntax gets extended, the macro interpreter becomes more brittle since the > original design was not intended to be extended in that way. > > In your case, the easiest may be a work-around: you *can* set the ROI > thusly: > > dummy = new float[myT.length]; > image.setRoi(new PointRoi(myT, dummy, dummy.length)); > > Ciao, > Johannes ... [show rest of quote] -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Loading... |
Reply to author |
Edit post |
Move post |
Delete this post |
Delete this post and replies |
Change post date |
Print post |
Permalink |
Raw mail |
1783 posts
|
On Monday 01 Apr 2013 19:04:11 Emmanuel Levy wrote:
> Thanks, I understand that this does sound a bit strange but the reason is > that i started working on a macro a long time ago and it would require a > significant amount of work to port the whole thing to Javascript. Currently you can't pass an array the way you want. You could, write the array to a file, and read it from the macro. Or make an image of n columns and 1 row and set the pixel values from the array and read it from the macro. Or set and get values to the so called "image properties" with the ImpProps class. Cheers Gabriel -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Loading... |
Reply to author |
Edit post |
Move post |
Delete this post |
Delete this post and replies |
Change post date |
Print post |
Permalink |
Raw mail |
1631 posts
|
In reply to this post by Emmanuel Levy
Hi Emmanue,
On Mon, 1 Apr 2013, Emmanuel Levy wrote: > On 1 Apr 2013, at 20:13, Johannes Schindelin <[hidden email]> wrote: > > > On Mon, 1 Apr 2013, Emmanuel Levy wrote: > > > >> I wrote a simple plugin that puts all pixel values of a selected ROI > >> into a 1D table. What I can't figure out is how to pass the resulting 1D > >> array to a macro calling the plugin? i.e., similarly to getStatistics, > >> which makes a histogram array available in the macro calling the > >> function for example. > > > > [...] > > > > In your case, the easiest may be a work-around: you *can* set the ROI > > thusly: > > > > dummy = new float[myT.length]; > > image.setRoi(new PointRoi(myT, dummy, dummy.length)); > > [...] > > I'm not sure I explained my question clearly, all I want is to pass an > array of values back to the macro language to process it, not set or > modify a ROI. ... [show rest of quote] I understood your question. And I pointed out that you can use the ROI to transport an array to the macro: after setting the ROI as I illustrated, getSelectionCoordinates(myT, dummy) will put the array values into the *macro* array called myT. > E.g., just like one has access to the value of "hist" after calling > getStatistics, id like to have access to myT. getStatistics is not really a macro function, it is a *built-in* function. There are a couple of such functions which allow passing variables by reference (even uninitialized ones), e.g. getStatistics and getSelectionCoordinates. Such functions illustrate exactly my point about making the core of the macro language brittle: its design does not include by-reference passing, just by-value passing. Now we have a mix, and no way to define by-reference passing outside the few pre-defined functions in the macro core. Having said that, there is actually a way to extend the macro language: by calling Functions.registerExtensions(). It is a little clumsy to use, but in theory, something like this should work: -- snip -- import ij.macro.ExtensionDescriptor; import ij.macro.Functions; import ij.macro.MacroExtension; import ij.plugin.PlugIn; public class Macro_Test_Extension implements PlugIn, MacroExtension { private float[] array = { 1, 2, 3 }; @Override public void run(String arg) { Functions.registerExtensions(this); } private ExtensionDescriptor[] descriptors = { ExtensionDescriptor.newDescriptor("getArray", this, ARG_OUTPUT | ARG_ARRAY) }; @Override public ExtensionDescriptor[] getExtensionFunctions() { return descriptors; } @Override public String handleExtension(String name, Object[] args) { if (name.equals("getArray")) { Double[] copy = new Double[array.length]; for (int i = 0; i < copy.length; i++) { copy[i] = new Double(array[i]); } ((Double[][])args[0])[0] = copy; } return ""; } } -- snap -- Alas, it does not. The problem is -- as I mentioned earlier -- that the macro language was not designed to handle such things and the extension mechanism was only bolted onto it. Therefore, array output variables are not supported. And as I pointed out, you probably get Wayne to add support for that, but the macro language will become more and more brittle that way, and your macro will not get faster. At some stage you will have to convert it to Javascript anyway, and the later you do it, the more work it will be. Ciao, Johannes -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Loading... |
Reply to author |
Edit post |
Move post |
Delete this post |
Delete this post and replies |
Change post date |
Print post |
Permalink |
Raw mail |
36 posts
|
Hi Johannes and Gabriel,
I agree that adding a built-in function is not the logical way. I guess time has come to start JS or Java then. Thanks again, Emmanuel On 1 Apr 2013, at 22:18, Johannes Schindelin <[hidden email]> wrote: > Hi Emmanue, > > On Mon, 1 Apr 2013, Emmanuel Levy wrote: > >> On 1 Apr 2013, at 20:13, Johannes Schindelin <[hidden email]> wrote: >> >>> On Mon, 1 Apr 2013, Emmanuel Levy wrote: >>> >>>> I wrote a simple plugin that puts all pixel values of a selected ROI >>>> into a 1D table. What I can't figure out is how to pass the resulting 1D >>>> array to a macro calling the plugin? i.e., similarly to getStatistics, >>>> which makes a histogram array available in the macro calling the >>>> function for example. >>> >>> [...] >>> >>> In your case, the easiest may be a work-around: you *can* set the ROI >>> thusly: >>> >>> dummy = new float[myT.length]; >>> image.setRoi(new PointRoi(myT, dummy, dummy.length)); >> >> [...] >> >> I'm not sure I explained my question clearly, all I want is to pass an >> array of values back to the macro language to process it, not set or >> modify a ROI. > > I understood your question. And I pointed out that you can use the ROI to > transport an array to the macro: after setting the ROI as I illustrated, > getSelectionCoordinates(myT, dummy) will put the array values into the > *macro* array called myT. > >> E.g., just like one has access to the value of "hist" after calling >> getStatistics, id like to have access to myT. > > getStatistics is not really a macro function, it is a *built-in* function. > There are a couple of such functions which allow passing variables by > reference (even uninitialized ones), e.g. getStatistics and > getSelectionCoordinates. > > Such functions illustrate exactly my point about making the core of the > macro language brittle: its design does not include by-reference passing, > just by-value passing. Now we have a mix, and no way to define > by-reference passing outside the few pre-defined functions in the macro > core. > > Having said that, there is actually a way to extend the macro language: by > calling Functions.registerExtensions(). It is a little clumsy to use, but > in theory, something like this should work: > > -- snip -- > import ij.macro.ExtensionDescriptor; > import ij.macro.Functions; > import ij.macro.MacroExtension; > > import ij.plugin.PlugIn; > > public class Macro_Test_Extension implements PlugIn, MacroExtension { > private float[] array = { 1, 2, 3 }; > > @Override > public void run(String arg) { > Functions.registerExtensions(this); > } > > private ExtensionDescriptor[] descriptors = { > ExtensionDescriptor.newDescriptor("getArray", this, > ARG_OUTPUT | ARG_ARRAY) > }; > > @Override > public ExtensionDescriptor[] getExtensionFunctions() { > return descriptors; > } > > @Override > public String handleExtension(String name, Object[] args) { > if (name.equals("getArray")) { > Double[] copy = new Double[array.length]; > for (int i = 0; i < copy.length; i++) { > copy[i] = new Double(array[i]); > } > ((Double[][])args[0])[0] = copy; > } > return ""; > } > } > -- snap -- > > Alas, it does not. The problem is -- as I mentioned earlier -- that the > macro language was not designed to handle such things and the extension > mechanism was only bolted onto it. Therefore, array output variables are > not supported. > > And as I pointed out, you probably get Wayne to add support for that, but > the macro language will become more and more brittle that way, and your > macro will not get faster. > > At some stage you will have to convert it to Javascript anyway, and the > later you do it, the more work it will be. > > Ciao, > Johannes ... [show rest of quote] -- ImageJ mailing list: http://imagej.nih.gov/ij/list.html |
Free forum by Nabble | Disable Popup Ads | Edit this page |