overthinkings
of Ruben Daniels
July 12, 2007 at 1:36 pm
· Filed under Tech, Javeline
In the Ajax rich world of today drag&drop has grown to be it’s hallmark as well as a source of great annoyance among interaction designers. However it may be, drag&drop is an absolute requirement for any mature framework. Whilst working on Javeline PlatForm, Javeline’s Ajax framework, I noticed there are two distinct ways of dropping; a basic and advanced way. Looking at several Ajax frameworks I didn’t find the advanced drag&drop implementation and after a lot of blood, sweat and tears, I know why.
The simple dropping mechanism consists of finding a previously registered drop target by its coordinates and then notifying the handler of the drop action via some event system. This works quite well for simple containers that are positioned fully visible on the screen to drop an item on. For instance a simple shopping cart container.
Now, imagine something is dragged to a container already containing elements. Let say we want the dragged element to be inserted before the element we are currently hovering over. It’s clear that this needs a more advanced solution; we need to know which child element we were hovering over. Similar problems arise when the drop targets are movable (think of an application with windows for instance); drop containers can overlap eachother which cause problems for the basic system.

fig 1. Basic / Advanced Drag&Drop
Luckily there is a (non-standard) method we can use to help us find the element we drop on. I’m talking about the document.elemenFromPoint method. You just give it an x and y coordinate and it returns the top (z-index) element for you at that position.
After tests on the compatibility of www.ajax.org I found this method to be working on IE, Opera and Safari. I’m sure by now you see my problem; Firefox does not support that method. I have not found a simple workaround solution either. After googling I did find an entry with a solution, but it only worked in some contexts, excluding the drag&drop behaviour I needed it for. So I tried building my own.
If you are looking for the source code of the solution click here.
Pages: 1 2 3 4
Permalink
[…] Source:→ Homepage Technorati Tags: AJAX, Application, Multibrowser Drag&Drop Share This Close […]
Great work! A couple quick questions: What’s the license on this code? There’s no license specified in the file. (A liberal MIT or Public Domain would be very awesome!) Also, the file is chown’d as root - making it difficult to access in most situations. Thanks for making this available.
Great work on implementing this method.
It’s quite tricky to accomplish this behaviour, as the event dispatching implementation doesn’t work as expected. I have a need for this method as well, and since I didn’t really find anything on the web, I started to make my own as well.
I tested your method with my own testcase, and noticed it fails to find the right element when there are several elements on top of each other, styled either position:relative or absolute. The script doesn’t handle the scroll overflow correctly, and all elements below the red rectangle are selected in stead the red.
Here’s the testcase:
Option 1Option 2
Gold layer
Button 2
Button 1
Button 3
Option 1Option 2
100
50
150
This is a pretty obscure situation, but to get the most robust method these need to be taken into consideration as well.
I managed to get my own implementation of elementFromPoint to handle all the situations in my own testcase. The performance is not particularly fast, with that little testcase, it takes 32ms to find the element (it always traverses the whole document tree). I hope I can optimize it a bit…
Still, exellent work on this method and the Javeline Platform, it seem very well made and flexible!
…and of course wordpress stripped all my HTML code above. Of well, I guess I can send it to you if you want.
Luckily there is a (non-standard) method we can use to help us find the element we drop on. I’m talking about the document.elemenFromPoint method. You just give it an x and y coordinate and it returns the top (z-index) element for you at that position.
Question: why does this work, if the draggable thing you have is displayed above the element to which you’re dragging? Shouldn’t the thing you’re dragging have a higher z-index than the thing over which that draggable hovers?
Ruben wrote @ August 23rd, 2007 at 10:14 am
Hi Jeff,
In Javeline Platform’s dragdrop library I offset the drag indicator to outside the screen and then use elementFromPoint:
indicator.style.top = "10000px";
var el = document.elementFromPoint(e.clientX+document.documentElement.scrollLeft, e.clientY+document.documentElement.scrollTop);
That works for all implementations.
Rgds, Ruben
[…] Daniels have implemented document.elementFromPoint for Firefox which makes it a lot easier to create more advanced drag&drop implementations for Ajax […]
HTML-Tags:
<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <code> <em> <i> <strike> <strong>