Events

Events are a convenient way to communicate between different components on the page.

Dispatching events

To define an event, create a method on your component that returns your event payload and decorate it with Event like so:

import { WebComponent, Event } from '@webcomp/core';

class ThemeSelectButton extends WebComponent {
  @Event('THEME_CHANGED')
  changeTheme() {
    // ...Optionally do stuff
    return this.state.theme;
  }

  render() {
    return <button class="theme-btn" onClick={this.changeTheme}>Like</button>
  }
}

Alternatively, instead of the decorator, you can use trigger method, available on every component:

import { WebComponent } from '@webcomp/core';

class ThemeSelectButton extends WebComponent {
  changeTheme = () => {
    // ...Optionally do stuff
    this.trigger('THEME_CHANGE', this.state.theme); 
  }

  render() {
    return <button class="theme-btn" onClick={this.changeTheme}>Like</button>
  }
}

Listening to events

Every component has a .on method for subscribing to events. To listen to an event, you can do the following:

import { WebComponent } from '@webcomp/core';

class ThemedElement extends WebComponent {
  componentDidMount() {
    this.on('THEME_CHANGED', this.handleEvent); // Handlers are autobound
  }
  
  handleEvent(payload) {
    this.setState({
      selectedTheme: payload
    });
  }

  render() {
    return <div class={this.state.selectedTheme}>...</div>
  }
}

Unwrapping promises

When dispatching events, you can pass a promise as event payload. WebComp will wait for the promise to resolve and dispatch the event with the result of that promise as a payload. This works with both @Event decorator and this.trigger. I.e:

import { WebComponent } from '@webcomp/core';

class MyElement extends WebComponent {
  componentDidMount() {
    this.on('GET_DATA', this.handleEvent);
  }

  handleData = ({ data }) => {
    this.setState({ data });
  }

  getData = async () => {
    const res = await fetch('/api/user/profile')
    this.trigger(res.json());
  }

  render() {
    return (
      <div>
        <button onClick={this.getData}>Get Data</button>
      </div>
    )
  }
}

Last updated