An open API service indexing awesome lists of open source software.

https://github.com/zemd/react-slottable

A lightweight concept to customize subcomponents in React
https://github.com/zemd/react-slottable

component-architecture react react-components slots

Last synced: about 1 year ago
JSON representation

A lightweight concept to customize subcomponents in React

Awesome Lists containing this project

README

          

# React Slottable for customizable components

> A lightweight concept to customize subcomponents in React

[![](https://img.shields.io/npm/v/@zemd/react-slottable?color=%230000ff&labelColor=%23000)](https://www.npmjs.com/package/@zemd/react-slottable)

The package provides a lightweight approach to give your component users ability to customize it's subcomponents easily. The idea is highly inspired by [Material-UI](https://mui.com/x/common-concepts/custom-components/).

## Usage

## Installation

```bash
npm install --save-dev @zemd/react-slottable
pnpm add -D @zemd/react-slottable
```

## Writing components

The core concept of the library is **slot**. A **slot** is a part of a component that can be overridden and/or customized. For example, you want to create a `Calendar`, but you do not want to create a numerous amount of props to customize nested components. Instead, you can divide your components on **slots** and provide your users with the ability to customize them.

Let's create a simple `Button` component with `startDecorator` and `endDecorator` slots to show how it works:

```tsx
import { type PropsWithSlots, useSlot } from "@zemd/react-slottable";

type ButtonProps = PropsWithSlots<
React.PropsWithChildren<{
// here you define your regular component props
fullWidth?: boolean;
disabled?: boolean;
size?: "sm" | "md" | "xl";
variant?: "solid" | "outlined";
color?: "primary" | "secondary";
className?: string;
}>,
["startDecorator", "endDecorator"] // here you define your slots
>;

const DefaultDecorator: React.FC<{ className?: string }> = ({ className }) => {
return

Default decorator
;
};

export const Button: React.FC = (rootProps) => {
const { slots, slotProps, ...props } = rootProps;
const StartDecoratorSlot = useSlot("startDecorator", rootProps, {
slot: DefaultDecorator, // provide default decorator, but can be overridden by user
});
const EndDecoratorSlot = useSlot("startDecorator", rootProps);

return (

{/* ^^^ do not forget to handle not standard attributes, e.g. fullWidth ...*/}

{/* ^^^ you can provide default className ^^^ */}
{props.children}


);
};
```

Now your users can use this `Button`:

```tsx
const MyCustomLabelComponent: React.FC = () => {
return My custom label;
};

export function HomePage(): React.JSX.Element {
return (



Click me!


);
}
```

As you can see, `StartDecoratorSlot` was predefined with default component, which will be always shown until user overrides it. However, the `EndDecoratorSlot` was not predefined, so it will be empty until user provides a component for it.

## License

The `@zemd/react-slottable` is licensed under **[Apache License 2.0](https://www.apache.org/licenses/LICENSE-2.0)** 😇.

## 💙 💛 Donate

[![](https://img.shields.io/static/v1?color=blue&label=UNITED24&message=support+Ukraine)](https://u24.gov.ua/)