Measuring parentpatcher's "scrolling drift"?

Julien Vincenot's icon

Hello,

In order to test if the mouse is on a given object or not, I have made a little device based on [js].

I cannot use [hover] because the actual objects for which I need this test to take place cannot be expected to have a scripting name…

I have a getsize function in JS such as :

function getsize()

{

var boxPos = this.patcher.box.rect; // [x1, y1, x2, y2]

var winPos = this.patcher.parentpatcher.wind.location; // [x, y, width, height]

var zoom = this.patcher.parentpatcher.getattr("zoomfactor");

var globalX = winPos[0] + (boxPos[0] * zoom) + 35;

var globalY = winPos[1] + (boxPos[1] * zoom) + 35;

var width = (boxPos[2] - boxPos[0]) * zoom;

var height = (boxPos[1] - boxPos[3]) * zoom;

outlet(0, [ globalX, globalX + width, globalY, globalY - height ]);

}

I added +35 empirically, I assume because of the toolbar (I'm not really sure how to handle that otherwise…).Inside the abstraction (which is just a test, I need this detection device in several objects), I compare the coordinates with a mousestate and then I get 0 or 1. Easy.

The tricky part for me was the zoom, it seemed I handled it well with the getattr("zoomfactor") and multiplying the coordinates

But remains for me a BIG issue : how to detect the object when the patching window is being scrolled away from the starting point? In this case, no matter what zoom % I have (even default 100%) the real box position and the mousestate cannot align anymore. As show in this video :

scrolling-issue.m4v

Is there any way to retrieve the parent patcher scrolling drift? I'm not sure how to call that in English…

If you know an idea to detect if toolbar is on/off in parent patcher as well, I'm also interested…

Thanks !

TFL's icon

Check the [mousestate] mode message. mode 1 gives you coordinates relative to the patcher, just like the objects position, so scroll shouldn't be an issue.

What do you mean by "because the actual objects for which I need this test to take place cannot be expected to have a scripting name"?

Julien Vincenot's icon

Sorry if it wasn't clear : I have a family of objects that interact with each other in a very non-Max way, to program in another language (Lisp) in a modular way. Objects are instantiated freely by users, and patches can use hundreds of those objects, so I cannot expect users to add manually a scripting name for each box — that would be the only way to use the hover object in my context. Basically I needed a hover-like mechanism without scripting name, handled from within each object individually.

You pointed me exactly in the right direction : I was taking the problem the wrong way, instead of using the "winPos" (this.patcher.parentpatcher.wind.location), all I needed was to using the "boxPos" one (this.patcher.box.rect).

And for mousestate, instead of mode 1 (mouse position relative to mousestate's patcher) I need to use mode 2 (relative to frontmost patcher). This fixes everything : the toolbar doesn't require an extra value, since the top left corner of patch background is always [0, 0] ; the zoom is handled as before, and the scrolling is treated properly.

Thank you so much !

Roman Thilenius's icon

in case the objects have known and fixed positions(?) and do not overlap, you can easily abuse [lcd] or [jit.pwindow] to get the mouse position.
then if x is in a certain range and if y is within a certain range, read entry 17 from a coll. and if the patcher is zoomed, all these values are simply to be scaled likewise.

offset with [mousestate] is indeed a bit difficult, since you can not get a mother pather to output its position by thispatcher. (it most likely works with js or java, but no idea about that.)

Julien Vincenot's icon

No precisely it's like a patching aid so objects may move and be re-arranged a lot so I cannot assume it's stable. But it's ok I got my solution it's working perfectly now.