Drag group

Scott Rossi scott at tactilemedia.com
Sun Jan 12 17:47:02 EST 2003


Recently, Ryno Swart wrote:

> One problem has me stumped.
> 
> I put a series of buttons (7) into the group, which I can now drag
> horizontally, and pass all kinds of messages to. What frustrates me now
> is that when I hover over or click on any given button, all is well;
> but once I move the mouse to drag, the buttons jump under the mouse so
> that the dragging takes place on the centre of the group. I would like
> the cursor to remain over the point that I moused down onto.
> 
> I suppose I could place the drag script inside each button, but then I
> would have no room for my button scripts, and I do find the idea of
> building within 10 lines particularly elegant.
> 
> Could you suggest some solution? Later on I hope to drag up to 20
> images in this way.

You can indeed use a master script to handle all the drag actions.  First of
all, you need to reference the "the target" in your master script, instead
of "me".  Second, there is a revision to the drag script that you might have
missed which basically puts the initial mouse click location into the
uAllowDrag property for later reference.

set the uAllowDrag of me to \
   the mouseH - left of me & "," &\
   the mouseV - top of me

One way to manage dragging without adding any scripts to your draggable
objects is to use a naming convention (like "dragbutton1", "dragbutton2",
etc) and enable the drag script by virtue of the object name:

if "dragbutton" is in short name of the target...

Thus you could place the following in the card or stack script, and would
need no scripts at all in the draggable objects:

on mouseDown
  if "dragbutton" is in short name of the target then
    set the uAllowDrag of me to \
        the mouseH - left of the target & "," & \
        the mouseV - top of the target & "," & \
        the width of the target & "," & \
        the height of the target
  else pass mouseDown
end mouseDown

on mouseMove x,y
  if "dragbutton" is in short name of the target then
    if the uAllowDrag of me is empty then exit mouseMove
    subtract item 1 of the uAllowDrag of me from x
    subtract item 2 of the uAllowDrag of me from y
    put item 3 of the uAllowDrag of me into W
    put item 4 of the uAllowDrag of me into H
    set the topLeft of the target to \
        min(right of grc 1-W,max(x,left of grc 1)),\
        min(bottom of grc 1-H,max(y,top of grc 1))
  else pass mouseMove
end mouseMove

on mouseUp
  if "dragbutton" is in short name of target then
      set the uAllowDrag of me to empty
  else pass mouseUp
end mouseUp

on mouseRelease
  if "dragbutton" is in short name of target then
      mouseUp
  else pass mouseRelease
end mouseRelease

The benefit of the above is that it's easy to manage -- a single script that
handles all draggable objects.  The disadvantage is if you have to handle
mouse events for other non-draggable objects in your stack -- you need to
separate the handlers so mouse events for non-draggable objects are taken
care of.  This can get a bit cluttered and difficult to manage if you have a
lot of objects that respond to mouse events.

My preference is to put the base mouse event scripts into the draggable
objects and a master mouseMove handler in the card or stack.  For me, this
is a cleaner approach.

In the script of a draggable object:

on mouseDown
   set the uAllowDrag of this stack to \
        the mouseH - left of me & "," & \
        the mouseV - top of me & "," & \
        the width of me & "," & \
        the height of me
end mouseDown

on mouseUp
  set the uAllowDrag of this stack to empty
end mouseUp

on mouseRelease
  mouseUp
end mouseRelease


In the stack script:

on mouseMove x,y
  if the uAllowDrag of me is empty then exit mouseMove
  subtract item 1 of the uAllowDrag of me from x
  subtract item 2 of the uAllowDrag of me from y
  put item 3 of the uAllowDrag of me into W
  put item 4 of the uAllowDrag of me into H
  set the topLeft of the target to \
      min(right of grc 1-W,max(x,left of grc 1)),\
      min(bottom of grc 1-H,max(y,top of grc 1))
end mouseMove


Good luck.

Regards,

Scott Rossi
Creative Director

Tactile Media, Multimedia & Design
Email: scott at tactilemedia.com
Web: www.tactilemedia.com




More information about the use-livecode mailing list