liveBook · Manning

Handler

As explained in React Quickly, Second Edition

Event handling is the process of responding to events generated by user interactions or changes in a web document.

A button click, a form submission, or a video starting to play can change what an application displays. In React, handle a supported event by assigning a function to the corresponding JSX property: `<button onClick={onClick}>Increment</button>`. Choose the event, choose the element that dispatches it, and give React a function to call. React manages that listener as the component mounts and unmounts. section 8.1.1 section 8.1

Make a counter respond

With `const [count, setCount] = useState(0)`, define `const onClick = () => setCount(value => value + 1)` and render `<button onClick={onClick}>Increment</button>` beside the count. Passing `onClick` assigns the function; writing `onClick()` there would call it immediately instead. A short handler can also be inline: `onClick={() => setCount(value => value + 1)}`. Put a longer handler in a named variable to keep the JSX readable. section 8.1.1 section 8.2.1

A handler receives an event object even if it does not declare a parameter. Use `evt.target` to find the element that triggered the event or `evt.type` to distinguish event types. The same function can handle two counter buttons by checking which button was clicked, although separate handlers are equally valid. For a reusable button component, consider wrapping a callback if its caller should not receive the button’s event object. section 8.2.2 section 8.6

Place handlers where the intended interaction occurs:

  • Use `onSubmit` on a form rather than only `onClick` on its button, so pressing Enter also works. Call `evt.preventDefault()` when submission must not perform the browser’s default page reload. section 8.4.2
  • Use bubbling to handle events from several descendants at an ancestor. For example, `onFocus` on each fieldset and `onBlur` on the form can track which part of a contact form is active without listeners on every input. section 8.3
  • Use an `onClickCapture` property when a handler must run during capture rather than the usual bubbling phase. Capture handlers are rarely needed. section 8.3.2

React’s JSX properties do not cover every event target or event type. To update a window-size display after a resize, attach a native listener inside an effect: `window.addEventListener("resize", onResize)`. Return a cleanup function that calls `window.removeEventListener("resize", onResize)`. The same approach can handle an unsupported event such as `transitionstart` on a DOM node obtained through a ref. Unlike a JSX listener, a manually attached listener is yours to remove. section 8.8.1 section 8.8.2

Listing 8.13 An expandable menu
import { useRef, useState, useEffect } from "react";
function Menu() {
  const [isExpanded, setExpanded] = useState(false);
  useEffect(() => {
    if (!isExpanded) {
      return;
    }
    const onWindowClick = () => setExpanded(false);
    const onMenuClick = (evt) => evt.stopPropagation();      #1
    const menu = menuRef.current;                            #2
    window.addEventListener("pointerdown", onWindowClick);
    menu.addEventListener("pointerdown", onMenuClick);       #3
    return () => {
      window.removeEventListener(                            #4
        "pointerdown", onWindowClick                         #4
      );                                                     #4
      menu.removeEventListener(                              #4
        "pointerdown", onMenuClick                           #4
      );                                                     #4
    };
  }, [isExpanded]);
  const menuRef = useRef();                                  #5
  return (
    <main>
      <button onClick={() => setExpanded(true)}>Show menu</button>
      {isExpanded && (
        <div
          ref={menuRef}                                      #6
          style={{ border: "1px solid black", padding: "1em" }}
        >
          This is the menu
        </div>
      )}
    </main>
  );
}
function App() {
  return <Menu />;
}
export default App;

An expandable menu combines a React button click with temporary native `pointerdown` listeners. Its menu listener stops the event from reaching the window listener, so clicking inside does not close the menu; cleanup removes both listeners. section 8.8.3

How React Quickly, Second Edition covers it

How deep it goes
Works through handler definitions, event objects, propagation, default actions, and manual listener cleanup, with capture handlers flagged as uncommon.
Examples
Uses counters, a video player, a contact form, a login form, a window-size display, and an expandable menu.
What it assumes
Assumes basic JavaScript functions and React components while reviewing function-definition options for handlers.
What you can do after
Build it from scratch: attach JSX handlers for interactions and add cleaned-up native listeners when React cannot manage the target or event.
How it connects
Links event handling to JSX, state, event propagation, form submission, DOM listeners, refs, and effects.

Also explained in

Compare how 22 books explain handler →

Related concepts

This explainer was generated by Manning's knowledge graph from the text of React Quickly, Second Edition. The section links point to the parts of the book it draws on.