Was macro invoked by menu or shortcut?

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

Was macro invoked by menu or shortcut?

vischer
Hello All,

I often have situations where the user has to position the mouse at a certain
location, and then call a macro via shortcut, for example:

macro "Circle at CursorPos [F1]"{
        getCursorLoc(x, y, z, flags);
        makeOval(x-10, y-10, 20, 20);
}

       
If a user intuitively tries out the macro via menu, I would like to display a message:
        exit("Position cursor and call macro via shortcut [F1]");
Is there any way to find out how the macro was called? Or if not, could it be easily installed (Wayne?).


Norbert

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

Re: Was macro invoked by menu or shortcut?

Michael Schmid
Hi Norbert,

no direct answer to your question - I think it is not possible to determine how the macro was invoked.
(The lastKeyCommand and keyPressedTime variables in ImageJ.java are private and you can't access them.  If accessible, they would provide a way to detect how the macro was invoked, but it would be rather bad programming style.).

Anyhow, I think that you can't guarantee that the user knows that the cursor should be at a certain position when pressing 'F1' (if/he/she does not know that it should not be called from the menu).

When not writing in ImageJ macro language but rather in java or javascript you could use ij.menus.getMacrosMenu(), find its MenuItems and disable your menu item there.  Also a not-so-nice hack.

Two solutions for macros:

(1) A macro tool; the user would select it and click on the site(s) of interest.

(2) Starting the macro from a shortcut or the menu, with the cursor at any position, and then a loop, asking the user to click at the site(s) of interest:

  var leftClick=16;
  while (!isKeyDown("space")) {
    showMessage('click to select sites, press space when done');
    getCursorLoc(x, y, z, flags);
    if (flags&leftClick !=0) {
      //do whatever you want
    }
  }
  // do whatever you like after all the selections are done

You might modify this macro, so that the user does not need to click but can rather press 'alt' or 'space' at the sites of interest. If there is no post-processing after all the clicks, it might be aborted with esc (which aborts with any macro).


Michael
________________________________________________________________
On Oct 2, 2012, at 13:00, Norbert Vischer wrote:

> Hello All,
>
> I often have situations where the user has to position the mouse at a certain
> location, and then call a macro via shortcut, for example:
>
> macro "Circle at CursorPos [F1]"{
> getCursorLoc(x, y, z, flags);
> makeOval(x-10, y-10, 20, 20);
> }
>
>
> If a user intuitively tries out the macro via menu, I would like to display a message:
> exit("Position cursor and call macro via shortcut [F1]");
> Is there any way to find out how the macro was called? Or if not, could it be easily installed (Wayne?).
>
>
> Norbert

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

Re: Was macro invoked by menu or shortcut?

vischer
Hi Michael,

> Michael Schmid wrote:
> Two solutions for macros:
>
> (1) A macro tool; the user would select it and click on the site(s) of interest.
>
> (2) Starting the macro from a shortcut or the menu, with the cursor at any position, and then a loop, asking the user to click at the site(s) of interest:
>
>  var leftClick=16;
>  while (!isKeyDown("space")) {
>    showMessage('click to select sites, press space when done');
>    getCursorLoc(x, y, z, flags);
>    if (flags&leftClick !=0) {
>      //do whatever you want
>    }
>  }
>  // do whatever you like after all the selections are done

thanks for mentioning these possibilities.
However, I didn't explain in detail how we use these macros:
The menu has here only the informative task to show the meaning of the keys, not for executing anything. The keys do the action, for example choose one of ten different shortcuts to set a marker of that category.

There is no faster way than using one hand to position the mouse without clicking, and use the other hand to type a  key to mark that category - it is like a mouse with ten buttons.

Using macro tools will not reach this speed. And this approach does not need to enter and exit a "while" loop.
Now we want to avoid that the menu is used for executing the macro (which would i place a marker at a random position without being noticed); the user should rather be reminded about proper usage.
Because in the past this has worked so efficiently, I believe it would be of general interest if ImageJ would supply information the type of event (mouse or key).

Norbert

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

Re: Was macro invoked by menu or shortcut?

vischer
In reply to this post by Michael Schmid
Hi Michael,

> Michael Schmid wrote:
> Two solutions for macros:
>
> (1) A macro tool; the user would select it and click on the site(s) of interest.
>
> (2) Starting the macro from a shortcut or the menu, with the cursor at any position, and then a loop, asking the user to click at the site(s) of interest:
>
> var leftClick=16;
> while (!isKeyDown("space")) {
>   showMessage('click to select sites, press space when done');
>   getCursorLoc(x, y, z, flags);
>   if (flags&leftClick !=0) {
>     //do whatever you want
>   }
> }
> // do whatever you like after all the selections are done

thanks for mentioning these possibilities.
However, I want to explain in more detail how we use these macros:
We simulate a "ten-button-mouse", where the ten buttons are on the keyboard, and the menu has only the informative task to show the meaning of the keys rather than executing via the mouse. The keys do the action, for example press one of the ten keys to set a marker of that category.

There is no faster way than using one hand to position the mouse without clicking, and use the other hand to type a key to mark that category.

Using macro tools will not reach this speed. And our approach does not need to enter and exit a "while" loop.
Now we want extra security - and avoid that the menu is used for executing any of the ten macros (which would place a marker at a random position without being noticed); the user should rather be reminded about proper usage.
Because our "ten-button-mouse" has worked so efficiently in the past, I believe it would be of general interest, and knowing the event type (mouse or key) would give extra security.

Norbert

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

Re: Was macro invoked by menu or shortcut?

dscho
In reply to this post by vischer
Hi Norbert,

On Tue, 2 Oct 2012, Norbert Vischer wrote:

> I often have situations where the user has to position the mouse at a
> certain location, and then call a macro via shortcut, for example:
>
> macro "Circle at CursorPos [F1]"{
> getCursorLoc(x, y, z, flags);
> makeOval(x-10, y-10, 20, 20);
> }
>
> If a user intuitively tries out the macro via menu, I would like to
> display a message:
> exit("Position cursor and call macro via shortcut [F1]");
> Is there any way to find out how the macro was called? Or if not, could
> it be easily installed (Wayne?).

This is where the macro language shows its limitations. Sure, it could be
extended, but what you really want is what the AbstractTool provides in
Fiji.

The best way to start writing it is to start the Script Editor with
File>New>Script, click on Templates>Java>Bare Tool and modify the code to
your heart's extent. In particular, you most likely want to record the
current location in fields:

        protected int x, y;

        @Override
        public void mouseMoved(MouseEvent e) {
                x = getOffscreenX(e);
                y = getOffscreenY(e));
                e.consume(); // prevent ImageJ from handling this event
        }

And then you call the macro from the key handling:

        @Override
        public void keyPressed(KeyEvent e) {
                switch (e.getKeyCode()) {
                case VK_F1:
                        IJ.runMacro("makeOval(" + (x - 10)
                                + ", " + (y - 10) + ", 20, 20);");
                        e.consume(); // prevent ImageJ from handling this
                        break;
                }
        }

But maybe Wayne extends the PlugInTool (which was apparently modeled after
AbstractTool, unfortunately leaving out some vital functionality) so that
it handles key events, too. Then it will be possible to do the same with
default ImageJ 1.x.

Ciao,
Johannes

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

Re: Was macro invoked by menu or shortcut?

vischer
In reply to this post by vischer
Thanks Wayne for adding the command
        getInfo("command.name");
to 1.47d31 daily build.

If the command starts with "^", it was called via shortcut key.
Below is an example for single-key annotations.

Norbert



//Demo to use single keystrokes for various non-destructive annotations.
//From version 1.47d31, commands are forced to be executed via shortcut key only.
//N. Vischer, 3-oct-2012

macro "Annotate Good [F1]"{
        annotate("Good", "green");
}

macro "Annotate Bad [F2]"{
        annotate("Bad", "red");
}

macro "Annotate Neutral [F3]"{
        annotate("Neutral", "orange");
}


function annotate(str, color){
        cmd = getInfo("command.name");
        if (cmd != "" && !(startsWith(cmd, "^")))
                exit("Command must be invoked via shortcut key, while cursor is at desired position");
        getCursorLoc(x, y, z, flags);
        makeText(str, x, y);
        run("Properties... ", "stroke=&color font=12");
        run("Add Selection...");
        run("Select None");
}

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