Last active
April 18, 2020 20:43
-
-
Save ArtemVeremienko/9f3afcfdc7d3e255f528cbce8d61bfb6 to your computer and use it in GitHub Desktop.
Drag superheroes around the field
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<h2>Расставьте супергероев по полю.</h2> | |
<p>Супергерои и мяч - это элементы с классом "draggable". Сделайте так, чтобы их можно было переносить.</p> | |
<p>Важно: ограничить перетаскивание границами окна. Если супергероя подносят к верхней или нижней границе страницы, | |
она должна автоматически прокручиваться.</p> | |
<p>Если страница помещается на вашем экране целиком и не имеет вертикальной прокрутки -- сделайте окно браузера | |
меньше, чтобы протестировать эту возможность.</p> | |
<p>В этой задаче достаточно справиться с вертикальной прокруткой. Обычно нет горизонтальной прокрутки, и она | |
обрабатывается аналогичным образом, если это необходимо.</p> | |
<p>Да, и ещё: супергерои ни при каких условиях не должны попасть за край экрана.</p> | |
<div id="field"> | |
</div> | |
<div class="hero draggable" id="hero1"></div> | |
<div class="hero draggable" id="hero2"></div> | |
<div class="hero draggable" id="hero3"></div> | |
<div class="hero draggable" id="hero4"></div> | |
<div class="hero draggable" id="hero5"></div> | |
<div class="hero draggable" id="hero6"></div> | |
<img src="https://en.js.cx/clipart/ball.svg" class="draggable"> | |
<div style="clear:both"></div> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
let isDragging = false; | |
document.addEventListener("mousedown", (event) => { | |
let dragElement = event.target.closest(".draggable"); | |
if (!dragElement) return; | |
event.preventDefault(); | |
dragElement.ondragstart = () => false; | |
let coords, shiftX, shiftY; | |
startDrag(dragElement, event.clientX, event.clientY); | |
function onMouseUp() { | |
finishDrag(); | |
} | |
function onMouseMove(event) { | |
moveAt(event.clientX, event.clientY); | |
} | |
function startDrag(element, clientX, clientY) { | |
if (isDragging) return; | |
isDragging = true; | |
document.addEventListener("mousemove", onMouseMove); | |
element.addEventListener("mouseup", onMouseUp); | |
shiftX = clientX - element.getBoundingClientRect().left; | |
shiftY = clientY - element.getBoundingClientRect().top; | |
element.style.position = "fixed"; | |
moveAt(clientX, clientY); | |
} | |
function finishDrag() { | |
if (!isDragging) return; | |
isDragging = false; | |
dragElement.style.top = | |
parseInt(dragElement.style.top) + pageYOffset + "px"; | |
dragElement.style.position = "absolute"; | |
document.removeEventListener("mousemove", onMouseMove); | |
dragElement.removeEventListener("mouseup", onMouseUp); | |
} | |
function moveAt(clientX, clientY) { | |
let newX = clientX - shiftX; | |
let newY = clientY - shiftY; | |
let newBottom = newY + dragElement.offsetHeight; | |
if (newBottom > document.documentElement.clientHeight) { | |
let docBottom = document.documentElement.getBoundingClientRect().bottom; | |
let scrollY = Math.min(docBottom - newBottom, 10); | |
if (scrollY < 0) scrollY = 0; | |
window.scrollBy(0, scrollY); | |
newY = Math.min( | |
newY, | |
document.documentElement.clientHeight - dragElement.offsetHeight | |
); | |
} | |
if (newY < 0) { | |
let scrollY = Math.min(-newY, 10); | |
if (scrollY < 0) scrollY = 0; | |
window.scrollBy(0, -scrollY); | |
newY = Math.max(newY, 0); | |
} | |
if (newX < 0) newX = 0; | |
if ( | |
newX > | |
document.scrollingElement.clientWidth - dragElement.offsetWidth | |
) { | |
newX = document.scrollingElement.clientWidth - dragElement.offsetWidth; | |
} | |
dragElement.style.left = newX + "px"; | |
dragElement.style.top = newY + "px"; | |
} | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
html, | |
body { | |
margin: 0; | |
padding: 0; | |
scroll-behavior: smooth; | |
} | |
#field { | |
background: url(https://js.cx/drag-heroes/field.png); | |
width: 800px; | |
height: 600px; | |
float: left; | |
} | |
/* герои и мяч (переносимые элементы) */ | |
.hero { | |
background: url(https://js.cx/drag-heroes/heroes.png); | |
width: 130px; | |
height: 128px; | |
float: left; | |
} | |
#hero1 { | |
background-position: 0 0; | |
} | |
#hero2 { | |
background-position: 0 -128px; | |
} | |
#hero3 { | |
background-position: -120px 0; | |
} | |
#hero4 { | |
background-position: -125px -128px; | |
} | |
#hero5 { | |
background-position: -248px -128px; | |
} | |
#hero6 { | |
background-position: -244px 0; | |
} | |
.draggable { | |
cursor: pointer; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment