Events
== Description ==
This pages described how to program events handling in client-side execution.
The traditional
[[http://www.mozilla.org/docs/dom/domref/dom_shortTOC.html| JavaScript API]]
is available to HOP, however, it is known to be un-portable. In particular,
events are handled differently in IE and [[http://www.mozilla.org|Mozilla]]
browsers. HOP provides an event handler API that aims at being portable.
That is you can use any of the functions described above on the main
popular Web browsers ([[http://www.mozilla.org|Mozilla]],
[[http://www.mozilla.org|Firefox]],
[[http://www.apple.com/macosx/features/safari|Safari]],
[[http://www.opera.com|Opera]], [[http://www.konqueror.org|Konqueror]],
and IE7.
== Synopsis ==
=== server ===
(hop-event-signal! name value)
(hop-event-broadcast! name value)
=== client ===
(add-event-listener! obj name handler capture)
(remove-event-listener! obj name handler capture)
(stop-event-propagation evt default)
(event-mouse-x evt)
(event-mouse-y evt)
(event-mouse-button evt)
(event-key-code evt)
(event-value evt)
(event-response-text evt)
== Examples ==
add-event-listener!, remove-event-listener!, event-mouse-, event-key-code
== Event propagation ==
When an event occurs on a DOM element (henceforth the //target//),
the target's event handler is invoked. In addition, in order to
give target's ancestors opportunities to invoke their own handler, event
are //propagated//. The propagation uses three phases:
- The **capturing** phase: when an event occurs, the event traverses
the DOM from the document to the target node. //Capturing// event handlers
(see ++add-event-listener!++) of the nodes (but the target itself) are
invoked during that stage.
- The **target** phase: the event handler of the target of an event is
invoked.
- The **bubbling** phase: as much as possible (that is when they are
applicable) event are bubbled up to node ancestors. That is, after a
event handler is called, if the node's ancestor also support that event
handler, the event is bubble up to that handler.
Bubbling can manually stopped by invoking ++stop-event-propagation++
from an event handler.
== Server Events ==
~~ Note: ,( :style { font-weight: bold } [
A current ,( :style { font-weight: bold; color: red } [bug]) in Firefox's Flash plugin prevents server event values
to contain ,( :style { font-weight: bold; color: red } [strings])
containing ,( :style { font-weight: bold; color: red } "\"") characters.])
~~ HOP implements //server events//. That is, contrary to the classical Web
model, HOP servers may **push** information to clients. Clients that defined
listeners for server events will get notified when such events are emitted.
~~ Server events are represented by string of characters. The function
++add-event-listener!++ is used to register to such events. The listener
is associated to the //server// object. The example
below shows a client registering the server event named ++FOO++.
(add-event-listener! server "FOO" (lambda (evt) (alert "FOO received")))
To emit such an event, server code has to invoke either the function
++hop-event-signal!++ or ++hop-event-broadcast!++:
(hop-event-broadcast! "FOO" (cons 1 2))
The value associated to a server event can be obtained using the
++event-value++ getter. Several listeners can be added to a same server
event. The **bubbling** phase describe in the previous section also
applies to server events.
~~ The document can also receive server events. The expression:
(add-event-listener! server document (lambda (evt) (alert evt.name)))
will force the document to get a notification for each server event that
whose listener has set the ++capture++ flag to ++#t++.
~~ When a client is ready to received server events, it triggers a
++ready++ event that can be intercepted by the root document.
~~ When a client is disconnected from a server, it triggers a
++down++ event that can be intercepted by the root document.
== Server ==
=== ++(hop-event-signal! name val)++ ===
hop-event-signal!
^ arguments ^ type ^ short description ^
| name | string | the name of the event. |
| val | _ | any value. |
The function ++hop-event-signal!++ signals to **one** client that have
added a listener to the server event named ++name++ the new value ++val++.
=== ++(hop-event-broadcast! name val)++ ===
hop-event-broadcast!
^ arguments ^ type ^ short description ^
| name | string | the name of the event. |
| val | _ | any value. |
The function ++hop-event-signal!++ signals to **all** clients that have
added a listener to the server event named ++name++ the new value ++val++.
== Client ==
=== ++(add-event-listener! obj name handler capture) ===
=== ++(remove-event-listener! obj name handler capture) ===
add-event-listener!
remove-event-listener!
^ arguments ^ type ^ short description ^
| obj | element | an element of the DOM. |
| name | string | the name of the event. |
| procedure | procedure | a procedure of one argument. |
| capture | boolean | block the event bubbling. |
These functions respectively register and unregister event handlers.
* The first argument is the element that holds the event handler.
* The second argument is the name of the event. It can be one of regular
DOM events:
* ++abort++: image loading interrupted.
* ++blur++: element loses input focus.
* ++change++: selection in a ++
=== ++(stop-event-propagation evt default)++ ===
stop-event-propagation
^ arguments ^ type ^ short description ^
| evt | event | the event. |
| default | boolean | allows or disallows default event action. |
The function ++stop-event-propagation++ prevents the event named ++name++
to bubble up to ancestor of the node holding the event handler.
The argument ++default++ when ++#t++ allows the default browers' event handler
to be executed.
=== ++(event-mouse-x evt)++ ===
=== ++(event-mouse-y evt)++ ===
=== ++(event-mouse-button evt)++ ===
=== ++(event-key-code evt)++ ===
=== ++(event-value evt)++ ===
event-mouse-x
event-mouse-y
event-mouse-button
event-key-code
event-value
event-response-text
^ arguments ^ type ^ short description ^
| evt | event | the event. |
Return information about the event that occurred. It is **highly
recommended** to use these functions instead of directly accessing
events' fields. These functions ensure browser compatibility that
simple fields access do not provide.
~~ The function ++event-mouse-button++ return the pressed or released
button number, the left-most mouse button being numbered ++1++.