Усі події миші, які ми бачили досі, ґрунтуються на MouseEvent. MouseEvent несе в собі набір властивостей, що спрощують роботу з мишею.
Властивості screenX та screenY повертають відстань, на якій знаходиться курсор миші від лівого верхнього кута основного монітора.
Властивості clientX та clientY повертають позиції x та y курсора щодо лівого верхнього кута браузера (Технічно його області перегляду).
Для визначення, яка з кнопок була натиснута, існує властивість button. Ця властивість повертає 0 при натисканні лівої кнопки, 1 - при натисканні середньої та 2 - при натисканні правої.
Як згадувалося раніше, за допомогою об'єкта Event можна отримати координати події, наприклад, у момент кліка можна знайти координати цього кліка.
Нехай у змінній event лежить об'єкт Event. В цьому випадку координати кліка щодо вікна браузера можна знайти так: event.clientX для координати по горизонталі та event.clientY для координат по вертикалі.
Розглянемо приклад: прив'яжемо блоку подію onmousemove (спрацьовує при русі мишкою по елементу), і будемо показувати координати курсору під час руху миші:
#elem {
border: 1px solid black;
width: 200px;
height: 200px;
}
<div id="elem"></div>
var elem = document.getElementById('elem');
elem.onmousemove = func;
function func(event) {
this.innerHTML = event.clientX + ':' + event.clientY;
}
Поведіть мишкою по елементу – ви побачите, як змінюються координати:
Крім властивостей clientX та clientY існують також властивості pageX та pageY. Давайте подивимося різницю між ними.
Як працюють clientX та clientY: якщо у вас є вікно 1000 на 1000 пікселів, і миша знаходиться в центрі, то clientX та clientY будуть обидва рівні 500. Якщо ви прокрутите сторінку по горизонталі або вертикалі, не рухаючи курсор, значення clientX і clientY не зміняться, оскільки відраховуються щодо вікна, а чи не документа.
Як працюють pageX та pageY: якщо у вас є вікно 1000 на 1000 пікселів, і курсор знаходиться в центрі, то pageX і pageY дорівнюють 500. Якщо ви потім прокрутите сторінку на 250 пікселів вниз, то pageY дорівнюватиме 750.
Таким чином, pageX і pageY містять координати події з урахуванням прокручування.
Рух об'єкта на Web-сторінці здійснюється шляхом зміни властивостей, що задають координати. У CSS координати об'єкта задаються за допомогою властивостей left та top. Властивість left задає горизонтальну координату об'єкта, що у разі позиціонування в абсолютних координатах (position:absolute) задає відстань у пікселях від лівої межі екрана. Властивість top задає вертикальну координату об'єкта, яка у разі позиціонування в абсолютних координатах задає відстань у пікселях від верхньої межі екрана. Якщо задати елементу абсолютне позиціонування та змінювати його координати top та left, то елемент рухатиметься.
Метод setTimeout виконує вираз чи функцію після закінчення встановленої кількості мілісекунд.
Тут expression рядковий вираз, що містить ім'я функції, що викликається, msec числове значення в мілісекундах. Вираз виконується одноразово і його повторного виконання потрібен черговий виклик методу
Створимо документ, в якому малюнок bird.gif рухається вправо по сторінці 6 секунд і зупиняється, але його можна зупинити раніше, натиснувши кнопку STOP.
window.onload = function() {
const bird = document.getElementById("bird");
const startBtn = document.getElementById("startBtn");
const stopBtn = document.getElementById("stopBtn");
let animationId;
let startTime;
function animate(time) {
if (!startTime) startTime = time;
let progress = time - startTime;
if (progress < 6000) { // 6 секунд
bird.style.left = (progress / 6) + "px";
animationId = requestAnimationFrame(animate);
}
}
startBtn.addEventListener("click", () => {
cancelAnimationFrame(animationId); // якщо вже було
startTime = null;
animationId = requestAnimationFrame(animate);
});
stopBtn.addEventListener("click", () => {
cancelAnimationFrame(animationId);
});
};
Створимо документ, в якому малюнок p5_0.jpg шириною 1000 пікселів і є нижнім шаром. На верхньому шарі другий малюнок шириною 80 пікселів bird2.gif, який рухається вправо. Коли другий малюнок досягає краю першого малюнка, він зупиняється.
Для обох малюнків потрібно вказувати ширину. Інакше вона матиме значення 0 і її не можна використовувати.
Функція може бути не в голові документа, а в тілі. Виконаються функція лише тоді, коли буде звернення до неї.
let im1 = document.getElementById('im1');
let im2 = document.getElementById('im2');
let statusText = document.getElementById('status');
let progressBar = document.getElementById('progress');
let startBtn = document.getElementById('startBtn');
let stopBtn = document.getElementById('stopBtn');
let resetBtn = document.getElementById('resetBtn');
let x = 0;
let animationId = null;
const step = 2; // крок руху
let maxX = 0; // правий край фонового зображення
// Функція для оновлення максимальної позиції
function updateMaxX() {
// Чекаємо, поки зображення завантажаться
if (im1.complete && im2.complete) {
maxX = im1.width - im2.width;
console.log("Фон ширина:", im1.width, "Пташка ширина:", im2.width, "Max X:", maxX);
} else {
// Якщо зображення ще не завантажилися, встановлюємо за замовчуванням
maxX = 1000 - 80; // 1000px - 80px
console.log("Використовуються значення за замовчуванням");
}
}
function move() {
x += step;
if (x >= maxX) {
x = maxX; // Зупиняємо пташку біля краю
cancelAnimationFrame(animationId);
animationId = null;
statusText.textContent = "Пташка досягла краю!";
startBtn.disabled = true;
stopBtn.disabled = true;
im2.classList.remove('moving');
return;
}
im2.style.left = x + 'px';
animationId = requestAnimationFrame(move);
// Оновлюємо статус і прогрес бар
const progress = Math.round((x / maxX) * 100);
statusText.textContent = `Пташка летить: ${progress}%`;
progressBar.style.width = `${progress}%`;
}
startBtn.addEventListener('click', () => {
if (animationId) return; // Вже запущена
if (x >= maxX) return; // Вже досягнуто краю
updateMaxX(); // Оновлюємо максимальну позицію
im2.classList.add('moving');
move();
startBtn.disabled = true;
stopBtn.disabled = false;
});
stopBtn.addEventListener('click', () => {
if (!animationId) return;
cancelAnimationFrame(animationId);
animationId = null;
statusText.textContent = "Анімацію зупинено";
startBtn.disabled = false;
stopBtn.disabled = true;
im2.classList.remove('moving');
});
resetBtn.addEventListener('click', () => {
cancelAnimationFrame(animationId);
animationId = null;
x = 0;
im2.style.left = x + 'px';
im2.classList.remove('moving');
statusText.textContent = "Пташка повернута на початок!";
progressBar.style.width = '0%';
startBtn.disabled = false;
stopBtn.disabled = true;
updateMaxX(); // Оновлюємо максимальну позицію
});
// Ініціалізація при завантаженні
window.addEventListener('load', () => {
stopBtn.disabled = true;
// Чекаємо на завантаження зображень
im1.onload = updateMaxX;
im2.onload = updateMaxX;
// Викликаємо одразу на випадок, якщо зображення вже завантажені
updateMaxX();
});
Змінимо попередній документ так, щоб малюнок 2.gif рухався головною діагоналі малюнка p5_0.jpg вниз. При досягненні правого нижнього кута малюнок рухається вгору цією ж діагоналі. При досягненні верхнього лівого кута цей малюнок знову рухається вниз. І так далі.

Крок – відстань ліворуч і зверху від лівого верхнього кута нерухомого малюнка до малюнку, що рухається.
Якщо малюнок рухається вправо та вниз, то крок позитивний. Якщо малюнок рухається вліво та вгору, то крок негативний.

Створимо документ, в якому м'ячик (малюнок ball.gif) відскакує від стін квадрата 400px*400px

Якщо задати елементу абсолютне або відносне позиціонування та змінювати його координати top, left, bottom, right з часом, елемент рухатиметься.



Нехай м'яч переміщається при кліку на полі, туди, куди був клік, ось так:
Вимоги:
Код повинен вміти працювати з різними розмірами м'яча та поля, не прив'язуватися до будь-яких фіксованих значень.
Використовуйте властивості event.clientX/event.clientY для визначення координат миші під час кліку.
Спочатку ми маємо вибрати метод позиціонування м'яча.
Ми не можемо використовувати position:fixed, оскільки прокручування сторінки переміщатиме м'яч з поля. Правильніше використовувати position:absolute, і щоб зробити позиціонування дійсно надійним, зробимо саме поле (field) позиціонованим. Тоді м'яч буде позиціонований щодо поля. Далі ми маємо призначити коректні значення ball.style.left/top. Нині вони містять координати щодо поля

У нас є значення event.clientX/clientY – координати натискання мишки щодо вікна браузера;
Щоб отримати значення left для м'яча після натискання мишки щодо поля, ми повинні від координати натискання мишки відняти координату лівого краю поля та ширину кордону:
let left = event.clientX - fieldCoords.left - field.clientLeft;
Значення ball.style.left означає "лівий край елемента" (м'яча). І якщо ми призначимо такий left для м'яча, то його ліва межа, а не центр, буде під курсором миші.
Нам потрібно зрушити м'яч на половину його висоти вгору та половину його ширини вліво, щоб центр м'яча точно збігався з точкою натискання мишки.
У результаті значення для left буде таким:
let left = event.clientX - fieldCoords.left - field.clientLeft - ball.offsetWidth/2;
Вертикальна координата буде обчислюватися за тією ж логікою.
Слід пам'ятати, що ширина та висота м'яча має бути відома в той момент, коли ми отримуємо значення ball.offsetWidth. Це значення може бути задано в HTML або CSS.
Розмітка: <body style="height:2000px">
Натисніть поле для переміщення м'яча.
<br>
<div id="field">
<img src="ball.gif" id="ball">
</div>


