Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
12 changes: 6 additions & 6 deletions 2-ui/3-event-details/4-mouse-drag-and-drop/article.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,19 +18,19 @@ The basic Drag'n'Drop algorithm looks like this:
2. Then on `mousemove` move it by changing `left/top` with `position:absolute`.
3. On `mouseup` - perform all actions related to finishing the drag'n'drop.

These are the basics. Later we'll see how to other features, such as highlighting current underlying elements while we drag over them.
These are the basics. Later we'll see how to add other features, such as highlighting current underlying elements while we drag over them.

Here's the implementation of dragging a ball:

```js
ball.onmousedown = function(event) {
ball.onmousedown = function(event) {
// (1) prepare to moving: make absolute and on top by z-index
ball.style.position = 'absolute';
ball.style.zIndex = 1000;

// move it out of any current parents directly into body
// to make it positioned relative to the body
document.body.append(ball);
document.body.append(ball);

// centers the ball at (pageX, pageY) coordinates
function moveAt(pageX, pageY) {
Expand Down Expand Up @@ -93,14 +93,14 @@ So we should listen on `document` to catch it.

## Correct positioning

In the examples above the ball is always moved so, that it's center is under the pointer:
In the examples above the ball is always moved so that its center is under the pointer:

```js
ball.style.left = pageX - ball.offsetWidth / 2 + 'px';
ball.style.top = pageY - ball.offsetHeight / 2 + 'px';
```

Not bad, but there's a side-effect. To initiate the drag'n'drop, we can `mousedown` anywhere on the ball. But if "take" it from its edge, then the ball suddenly "jumps" to become centered under the mouse pointer.
Not bad, but there's a side effect. To initiate the drag'n'drop, we can `mousedown` anywhere on the ball. But if "take" it from its edge, then the ball suddenly "jumps" to become centered under the mouse pointer.

It would be better if we keep the initial shift of the element relative to the pointer.

Expand Down Expand Up @@ -219,7 +219,7 @@ That's why the initial idea to put handlers on potential droppables doesn't work

So, what to do?

There's a method called `document.elementFromPoint(clientX, clientY)`. It returns the most nested element on given window-relative coordinates (or `null` if given coordinates are out of the window).
There's a method called `document.elementFromPoint(clientX, clientY)`. It returns the most nested element on given window-relative coordinates (or `null` if given coordinates are out of the window). If there are multiple overlapping elements on the same coordinates, then the topmost one is returned.

We can use it in any of our mouse event handlers to detect the potential droppable under the pointer, like this:

Expand Down