on… handlers

Native-style on<event> attributes. Inside component markup they work for every event name, native or custom. On a plain page, REALM adds handler attributes and properties for the custom events its components send.

<button onclick="save(item)">Save</button>
<rating-stars onrate="saveRating(event.detail.value)"></rating-stars>

In component markup

The attribute value is JavaScript, compiled together with the component script (no eval at event time). It runs as a listener on that element.

Name Value
event The event object
this The element the attribute is on
Loop variables The as and index names of every enclosing repeat / <repeat-list>
Script names Every top-level name of the component script
Helpers The script helpers (host, dispatch, refs, …)
Any other name Looked up when the handler runs: parent components first, then globalThis

On a plain page

Browsers only support handler attributes for native event names. For each REALM component, REALM finds the custom events it sends and adds:

<rating-stars onrate="console.log(event.detail.value)"></rating-stars>
<script>
  document.querySelector("rating-stars").onrate = (event) => {
    if (event.detail.value < 2) return false;
  };
</script>
Detail Behaviour
Event names Read from the component script: dispatch("name", new CustomEvent("name" and new Event("name"
Native names Names that already have an on… property on HTMLElement (change, input, toggle, close, …) are left to the browser
this The element
return false Calls preventDefault()
Syntax errors The attribute is ignored
Attributes set before the element was defined Compiled when it connects

Page handler attributes run in the page scope, so a strict Content Security Policy blocks them like any inline handler.

Example

Previewindex.htmllike-button.html
Like () No likes yet.
<!doctype html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>on… handlers demo</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@realmorg/realm@alpha/dist/realm.css">
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@realmorg/ui@alpha/dist/theme.css">
  <script type="module" src="https://cdn.jsdelivr.net/npm/@realmorg/realm@alpha/dist/realm.js"></script>
</head>
<body>
  <import-element from="https://cdn.jsdelivr.net/npm/@realmorg/ui@alpha/components/button.html"></import-element>

  <import-element from="./like-button.html"></import-element>

  <like-button onlike="document.getElementById('like-log').value = 'Liked ' + event.detail.count + ' times'"></like-button>
  <output id="like-log">No likes yet.</output>
</body>
</html>
<custom-element name="like-button">
  <script>
    const likes = useState({ count: 0 });

    function like() {
      likes.count++;
      dispatch("like", { count: likes.count });
    }
  </script>

  <ui-button variant="outline" onclick="like()">Like (<slot name="#likes.count"></slot>)</ui-button>
</custom-element>

Edit this page on GitHub · View as Markdown