O webu
JavaScriptové události myši

Při vytváření JavaScriptové aplikace existuje spoustu událostí a postupů, jak zpracovávat akce vyvolané myší (kursorem/ukazatelem/prstem).

Kliknutí myši

onclick

Základní kliknutí, rozumí se tím stisknutí a uvolnění levého tlačítka myši. To uvolnění je důležité. Když se po stisknutí myši s kursorem trochu pohne, událost onclick se nevyvolá. To může být výhoda i nevýhoda.

  1. Uživatel si může kliknutí rozmyslet a při stisknutém tlačítku pohnout kursorem a akci tak zrušit.
  2. Zároveň při rychlém klikání může první případ vyvolat omylem. Proto v situaci, kdy je očekáváno rychlejší klikání, může být výhodnější onmousedown. Rychlejšího vyvolání události onmousedown (oproti onclicku) je možné využít pro zrychlení AJAXvé aplikace, kde načítání proběhne už při stisknutí tlačítka. Nečeká se na uvolnění.
Kliknout

Stejného efektu jako atributem onclick lze docílit pseudo-protokolem javascript: u odkazu <a>.

Není to ovšem moc ideální řešení z pohledu zařízení, co nepodporují JS, vznikne v nich nesmyslný odkaz.

Při vytváření klikacích prvků je dobré myslet na uživatele ovládající web klávesnicí. Nebude-li mít element s onclickem atribut tabindex, nepůjde na něj spolehlivě ve všech prohlížečích odTabovat. Více v testu události onclick.

onmousedown

Vyvolá se ihned po stisknutí libovolného tlačítka myši. Je to tedy způsob, jak odchytit pravé tlačítko nebo kolečko.

Kliknout

Většinou jsou čísla tlačítek následující:

  • 1 — levé tlačítko,
  • 2 — prostřední tlačítko / kolečko,
  • 3 — pravé tlačítko.

Odchytnout pravé tlačítko je většinou možné i přes událost kontextové nabídky (oncontextmenu). Fungujete díky tomu, že pravé tlačítko zpravidla kontextovou nabídku vyvolává.

onmouseup

Vyvolá se po uvolnění libovolného tlačítka na elementem. Vyvolá se i v případě, že se tlačítko stiskne někde jinde, přejede se nad element a uvolní.

Kliknout

Jinak, co se týče rozlišování, které tlačítko bylo uvolněno, funguje stejně jako onmousedown.

ondblclick

Aktivuje se dvojklikem levého tlačítka (dvojité rychlé kliknutí).

Kliknout

Pravé tlačítko nebo kolečko myši dvojlik nevyvolá.

Objekt event

Pro zjištění podrobností o kliknutí nebo pro zablokování výchozích akcí slouží objekt event, jeho použití a sjednocení napříč prohlížeči vypadá následovně:

<span onmousedown='funkce(event)'>Kliknout</span>
function funkce(e) {
  e = e || window.event;
}
  • Kód tlačítka je v e.which,
  • Souřadnice kursoru v době kliknutí je nutné dále sjednocovat.

Stornování výchozí akce

Někde je vhodné stornovat výchozí akci prohlížeče, což je například kontextová nabídka nebo ikona pro posouvání po stránce vyvolaná stisknutím kolečka; případně prokliknutí odkazu nebo odeslání formuláře.

Klíčem je příkaz return false.

Před stornováním je třeba důkladně rozmyslet, zda narušení výchozí funkčnosti prohlížeče nebude návštěvníka obtěžovat.

(Mimochodem, CSS vlastnost pointer-events umí stornovat jen vlastní CSS/JS události. Ty výchozí z prohlížeče nikoliv.)

Zablokování odeslání formuláře

Příkaz return false dokáže zrušit víceméně všechny události.

Zamezit poslání formuláře je možné buď v onclicku u jednotlivých odesílacích polí (<input type=submit>/<button type=submit>), nebo spolehlivěji v události onsubmit celého formuláře.

<form action="?akce" onsubmit="vlastniFunkce(); return false">

Zablokování odkazu

Není problém vystornovat přechod na adresu hrefu z odkazů.

Hodnotu false může vracet i přímo vlastniFunkce (ukázka):

function vlastniFunkce() {
  // nějaký kód
  return false;
}
<a href='http://jecas.cz' onclick='return vlastniFunkce()'>Odkaz</a>

Zablokování a odchytnutí pravého tlačítka

Kontextovou nabídku po stitknutí pravého tlačítka můžeme zablokovat událostí oncontextmenu.

<span oncontextmenu="return false">Kliknout</span>

Že bylo pravé tlačítko stisknuto následně odchytne událost onmousedown (ukázka).

Zablokování kolečka

Chceme-li tlačítko kolečka zapojit do ovládání aplikace, je potřeba stornovat jeho běžnou funkci — zobrazení čtyřsměrné šipky pro posouvání po stránce pohybem kursoru.

Kolečko / prostřední tlačítko je trochu problematické, protože ne každý návštěvník dokáže vyvolat jeho stisknutí.

Blokaci vytvoří return false v události onmousedown (ukázka). Nefunguje v Opeře 12.

Pohyb myši

Kromě mačkání tlačítek je možné reagovat i na posouvání kursoru.

onmouseover

Vyvolá se v momentě najetí myší na element. V CSS je alternativa pseudotřída :hover.

Najet.

Pomocí onmouseover/onmouseout lze i zjišťovat směr odjetí/přijetí kursoru.

České vysvětlení atributu onmouseover sepsal před lety Miloš F. Pechar.

onmouseout

Opak onmouseoveru. Vyvolá se při odjetí.

onmousemove

Vyvolává se neustále při pohybování se myší nad elementem.

Objekt event

I u posouvání kursoru je možné další užitečné věci jako třeba posici kursoru zjistit z eventu.

„Praktické“ použití zjišťování posice při posouvání myši je u CSS baterky.

Výběr textu

Taktéž pro vybírání textu na stránce tažením myši se stisknutým tlačítkem existuje událost.

onselectstart

Vyvolá se při označování textu.

Vybrat text

Chová se dost rozdílně napříč prohlížeči:

  • V Opeře 12 a Firefoxu nedělá nic.
  • Ve Webkitu se spustí už při stisknutí levého i pravého tlačítka, nemusí se ani nic označit.
  • V IE se spustí v okamžiku, kdy se alespoň něco vybere.

V IE a Chrome tak lze pomocí return false znemožnit výběr textu (ukázka).

Zablokování výběru textu

K tomu nakonec událost onselectstart není ani příliš potřeba. Stornováním onmousedownu dosáhneme v zásadě téhož ve všech prohlížečích:

Text, který nejde vybrat. Blokuje to onmousedown="return false".

V IE a staré Opeře 12 funguje atribut unselectable nastavený na on.

Text, který nejde vybrat. Blokuje to unselectable="on".

Zablokování v CSS

V CSS k blokování výběru slouží vlastnost user-select. Funguje od IE 10, nefunguje v Opeře 12. V ostatních prohlížečích funguje jen s CSS prefixy (ukázka).

Kromě vlastnosti user-select by mohlo jít označování zakamuflovat pseudo-elementem ::selection (ukázka).

elment::selection {background-color: transparent}

Používat ::selection je možné od IE 9, ve Firefoxu s -moz- prefixem.

Rolování kolečkem

onmousewheel

Provede se při roztočení kolečka nad daným elementem.

Roztočit kolečko

Z eventu je možné zjistit směr, jakým se roluje (nahoru/dolů).

Co se týče rolování kolečkem, tak existují obrovské rozdíly napříč prohlížeči.

  • Firefox nezná událost onmousewheel. Dá se v něm ale využít událost DOMMouseScroll nebo nová událost onweel.
  • Směr rolování se získává z wheelDelta (Webkit umí rozlišit směr rolování (vodorovně/svisle) na základě hodnot wheelDeltaX a wheelDeltaY).
  • Ve starších IE a ve Firefoxu při použití DOMMouseScroll je směr ve vlastnosti detail.
  • Firefox a Webkit při použití onweel zná dokonce deltaX, deltaY, deltaZ (ukázka).

Kód určující, kterým směrem se roluje, funkční ve všech prohlížečích, by mohl vypadat následovně — živá ukázka.

Drag and drop události

Další události, které je možné vyvolat myší, jsou ty pro přetahování elementů po stránce bez většího množství JS kódu.

Funkční s omezeními od IE 8 (není možné přetahovat soubory z operačního systému do prohlížeče a podobně). Ve starších prohlížečích je posouvání elementů možné docílit přes onmousedown (zapne přesouvání), onmousemove (provede přesouvání) a onmouseup (ukončí přesouvání) (ukázka).

ondragstart

Vyvolá se při započatí tažení (ukázka).

<div
  draggable="true"
  ondragstart="event.dataTransfer.setData('Text', 'Obsah, který se přesune')"
>
  Obsah je možné přesunovat.
</div>

Atribut draggable umožňuje samotné přetahování elementu. Pomocí event.dataTransfer.setData se potom nastaví obsah, který se má přesouvat.

Pro přesun HTML obsahu si lze s Text typem vystačit (jiné typy ostatně nefungují ve starších IE).

Ovlivnit podobu kursoru, který signalisuje, zda se bude obsah přesouvat/kopírovat, je možné přes event.dataTransfer.effectAllowed (možné hodnoty).

Pří řešení drag & dropu způsobem pro IE 7 a starší bez drag/drop událostí je vhodné ondragstart vystornovat:

<element ondragstart="return false">
ondragenter

Vyvolá se v okamžiku, kdy nad elementem potáhneme přesouvatelný objekt. Hodí se tedy například k signalisaci, že je možné tažený obsah upustit.

ondragover

Něco jako onmousemove — vyvolává se, když se nad elementem hýbe s přetahovaným obsahem. Užitečné k samotnému umožnění dropu přes event.preventDefault().

ondragleave

Aktivuje se, když se při tažení opustí element s touto událostí. Může například zrušit signalisaci, kterou vyvolá ondragstart.

Ukázka kombinace ondragenter a ondragleave.

ondrag

Událost se vyvolává neustále při pohybu přesouvaného elementu.

ondrop

Vyvolá se při upuštění obsahu nad elementem, který drop podporuje. Podpora dropnutí se umožní zabráněním výchozí akce — preventDefault().

<div ondragover="event.preventDefault()" ondrop="alert('Položeno')">
</div>

V události ondrop je možné získat dříve nastavený obsah pomocí:

event.dataTransfer.getData("text/plain");
ondragend

Nastavuje se pro přesouvatelný (draggable) element a spustí se při ukončení přesouvání elementu. Je jedno, jakým způsobem přetahování skončilo (úspěšným/neúspěšným dropem, stornováním klávesy Esc apod.).

Příklad drag and dropu

Ukázka přesouvání obsahu. V zásadě existují dva způsoby, jak přesouvat/kopírovat obsah.

  • Při započatí přesouvání (ondragstart) nastavit metodou event.dataTransfer.setData potřebný HTML obsah. A při dokončení (ondrop) ho vyvolat přes event.dataTransfer.getData a umístit do elementu.
  • Přesouvat v event.dataTransfer jen identifikátor přetahovatelného elementu. A po skončení dragování si ho najít nějakou metodou DOMu.

Samostatná ukázka. Přesouvací kursor se zapíše přes cursor: move.

Obsah je možné přesunovat.

Vyvolaná událost:

Hotové řešení Sortable usnadní vytváření drag and drop aplikací (nepoužívá jQuery).

Dotykové události (ontouch*)

Pro dotyková zařízení existuje obdoba onmouse* událostí.

ontouchstart

Obdoba onmousedown. Spustí se, jak už název vypovídá, při dotyku.

Dotyků může být více, proto se věci jako souřadnice nedolují z eventu, ale z event.touches s indexem dle pořadí dotyku (první dotyk bude v event.touches[0]).

ontouchmove

Obdoba onmousemove.

ontouchend

Obdoba onmouseup. Souřadnice pro události ontouchmove i ontouchend jsou v event.changedTouches[0].

Využitím dotykových událostí je možné vytvořit třeba tzv. swipování — Add Finger-Swipe Support to Webpages.