summaryrefslogtreecommitdiffstatshomepage
path: root/www/content/attributes/hx-on.md
blob: 1c882b7e81a01d55e1bb326be6a22ded076c06f8 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
+++
title = "hx-on"
description = """\
  The hx-on attributes in htmx allow you to write inline JavaScript event handlers directly on HTML elements, \
  supporting both standard DOM events and htmx-specific events with improved locality of behavior."""
+++

The `hx-on*` attributes allow you to embed scripts inline to respond to events directly on an element; similar to the 
[`onevent` properties](https://developer.mozilla.org/en-US/docs/Web/Events/Event_handlers#using_onevent_properties) found in HTML, such as `onClick`.

The `hx-on*` attributes improve upon `onevent` by enabling the handling of any arbitrary JavaScript event,
for enhanced [Locality of Behaviour (LoB)](/essays/locality-of-behaviour/) even when dealing with non-standard DOM events. For example, these
attributes allow you to handle [htmx events](/reference#events).

With `hx-on` attributes, you specify the event name as part of the attribute name, after a colon.  So, for example, if
you want to respond to a `click` event, you would use the attribute `hx-on:click`:

```html
<div hx-on:click="alert('Clicked!')">Click</div>
```

Note that this syntax can be used to capture all htmx events, as well as most other custom events, in addition to the
standard DOM events.

One gotcha to note is that DOM attributes do not preserve case. This means, unfortunately, an attribute like
`hx-on:htmx:beforeRequest` **will not work**, because the DOM lowercases the attribute names.  Fortunately, htmx supports
both camel case event names and also [kebab-case event names](@/docs.md#events), so you can use `hx-on:htmx:before-request` instead.

In order to make writing htmx-based event handlers a little easier, you can use the shorthand double-colon `hx-on::` for htmx
events, and omit the "htmx" part:

```html
<!-- These two are equivalent -->
<button hx-get="/info" hx-on:htmx:before-request="alert('Making a request!')">
    Get Info!
</button>

<button hx-get="/info" hx-on::before-request="alert('Making a request!')">
    Get Info!
</button>

```

If you wish to handle multiple different events, you can simply add multiple attributes to an element:
```html
<button hx-get="/info"
        hx-on::before-request="alert('Making a request!')"
        hx-on::after-request="alert('Done making a request!')">
    Get Info!
</button>
```

Finally, in order to make this feature compatible with some templating languages (e.g. [JSX](https://react.dev/learn/writing-markup-with-jsx)) that do not like having a colon (`:`)
in HTML attributes, you may use dashes in the place of colons for both the long form and the shorthand form:

```html
<!-- These two are equivalent -->
<button hx-get="/info" hx-on-htmx-before-request="alert('Making a request!')">
    Get Info!
</button>

<button hx-get="/info" hx-on--before-request="alert('Making a request!')">
    Get Info!
</button>

```

### hx-on (deprecated)
The value is an event name, followed by a colon `:`, followed by the script:

```html
<button hx-get="/info" hx-on="htmx:beforeRequest: alert('Making a request!')">
    Get Info!
</button>
```

Multiple handlers can be defined by putting them on new lines:
```html
<button hx-get="/info" hx-on="htmx:beforeRequest: alert('Making a request!')
                              htmx:afterRequest: alert('Done making a request!')">
    Get Info!
</button>
```


### Symbols

Like `onevent`, two symbols are made available to event handler scripts:

* `this` - The element on which the `hx-on` attribute is defined
* `event` - The event that triggered the handler

### Notes

* `hx-on` is _not_ inherited, however due to
  [event bubbling](https://developer.mozilla.org/en-US/docs/Learn/JavaScript/Building_blocks/Events#event_bubbling_and_capture),
  `hx-on` attributes on parent elements will typically be triggered by events on child elements
* `hx-on:*` and `hx-on` cannot be used together on the same element; if `hx-on:*` is present, the value of an `hx-on` attribute
   on the same element will be ignored. The two forms can be mixed in the same document, however.