Haunted — это библиотека для создания веб-компонентов на базе современного JavaScript с использованием реактивного состояния. Одним из ключевых аспектов работы с компонентами является передача данных от родителя к дочернему компоненту. В Haunted это реализуется через свойства (properties) и события (events).
Свойства в Haunted используются для передачи данных внутрь компонента
и реактивного обновления интерфейса при их изменении. Создание свойств
осуществляется с помощью функции component и встроенного
хука useState или через стандартные getter/setter.
Пример базового компонента с свойствами:
import { component, html } from 'haunted';
function Child({ name, age }) {
return html`<p>Имя: ${name}, Возраст: ${age}</p>`;
}
customElements.define('my-child', component(Child));
В родительском компоненте свойства передаются напрямую через HTML-атрибуты:
import { component, html } from 'haunted';
function Parent() {
const childName = 'Алексей';
const childAge = 25;
return html`<my-child name="${childName}" age="${childAge}"></my-child>`;
}
customElements.define('my-parent', component(Parent));
Ключевые моменты:
.property или Object.assign.userName →
user-name.Haunted поддерживает деструктуризацию объектов свойств напрямую в аргументах функции компонента. Это упрощает доступ к передаваемым данным и делает код чище:
function Profile({ user }) {
const { name, email } = user;
return html`<div>${name} — ${email}</div>`;
}
customElements.define('user-profile', component(Profile));
Передача объекта через свойство:
const user = { name: 'Мария', email: 'maria@example.com' };
html`<user-profile .user="${user}"></user-profile>`;
Обратите внимание на точку перед атрибутом .user — это
синтаксис для передачи объекта напрямую, а не строки.
Для реактивного обновления дочернего компонента при изменении
значения в родителе используют useState или
useReducer:
import { component, html, useState } from 'haunted';
function Parent() {
const [count, setCount] = useState(0);
return html`
<button @click="${() => setCount(count + 1)}">Увеличить</button>
<counter-display .value="${count}"></counter-display>
`;
}
function CounterDisplay({ value }) {
return html`<p>Счётчик: ${value}</p>`;
}
customElements.define('parent-component', component(Parent));
customElements.define('counter-display', component(CounterDisplay));
Особенности:
.value="${count}" гарантирует передачу
числа как JavaScript-значения, а не строки.Помимо передачи данных вниз, часто требуется отправлять события
вверх, к родителю. Для этого в Haunted используют стандартный механизм
CustomEvent.
Пример:
function Child({ onIncrement }) {
return html`<button @click="${() => onIncrement()}">Добавить</button>`;
}
customElements.define('increment-button', component(Child));
function Parent() {
const [value, setValue] = useState(0);
const handleIncrement = () => setValue(value + 1);
return html`
<p>Значение: ${value}</p>
<increment-button .onIncrem ent="${handleIncrement}"></increment-button>
`;
}
customElements.define('counter-parent', component(Parent));
Важные детали:
.property="${function}".dispatchEvent внутри дочернего компонента для полной
совместимости с DOM:function Child() {
const increment = () => {
const event = new CustomEvent('increment', { bubbles: true, composed: true });
this.dispatchEvent(event);
};
return html`<button @click="${increment}">Добавить</button>`;
}
customElements.define('increment-child', component(Child));
В родителе подписка на событие осуществляется через
@increment:
html`<increment-child @increment="${() => setValue(value + 1)}"></increment-child>`;
Haunted позволяет передавать не только данные, но и целые компоненты или функции рендера. Это полезно для создания гибких шаблонов и контейнеров:
function Container({ content }) {
return html`<div class="container">${content()}</div>`;
}
function App() {
const content = () => html`<p>Динамический текст</p>`;
return html`<container-component .content="${content}"></container-component>`;
}
customElements.define('container-component', component(Container));
customElements.define('app-root', component(App));
.property для объектов и
функций: это предотвращает непреднамеренное преобразование
значений в строки.Передача данных в дочерние компоненты в Haunted сочетает преимущества реактивности с простотой стандартного DOM, позволяя создавать чистые и легко поддерживаемые интерфейсы.