# Home and catalog slots (https://docs.salla.dev/twilight/react/slots/home-and-catalog)



Use these slots when you want a banner, promo strip or widget on the home page, above or below a product listing, around the brands index, or on the 404 page, without forking the route. New to slots? Read [Slots](https://docs.salla.dev/twilight/react/slots) and [Page frame slots](https://docs.salla.dev/twilight/react/slots/page-frame) first.

None of the slots on this page pass a context of their own. Your handler receives only `twilight` (store, theme, currency and more).

## Home page [#home-page]

Route: [Home](https://docs.salla.dev/twilight/react/routes/home).

<PageLayout
  title="Home page"
  url="/"
  nodes="[
  { slot: 'home:start' },
  { slot: 'home:content' },
  { block: 'Block 1: slider, banners and so on', size: 'md' },
  { block: 'Block 2', size: 'md' },
  { block: 'Block N', size: 'md' },
  { slot: 'home:end' },
]"
/>

| Slot           | Position                                                   | Context | Notes                                                                                                        |
| -------------- | ---------------------------------------------------------- | ------- | ------------------------------------------------------------------------------------------------------------ |
| `home:start`   | First thing in the page, before every home block.          | none    | Good for a top announcement strip.                                                                           |
| `home:content` | Directly after `home:start`, still before the first block. | none    | Sits next to `home:start`, so the two render back to back. Use it for a second, independent injection point. |
| `home:end`     | After the last home block.                                 | none    | The slots render even when the page has no blocks.                                                           |

<Callout type="warn" title="Blocks are not slots">
  Home blocks (sliders, banners, product lists) come from the theme's `twilight.json` catalog and the store's page builder, not from slots. To change a block, see [Add a home block](https://docs.salla.dev/twilight/react/recipes/add-a-home-block). There is no slot between two blocks.
</Callout>

## Product list pages [#product-list-pages]

The same page component renders every product listing: [category](https://docs.salla.dev/twilight/react/routes/category), [brand](https://docs.salla.dev/twilight/react/routes/brand), [tag](https://docs.salla.dev/twilight/react/routes/tag), [search](https://docs.salla.dev/twilight/react/routes/search) and the [products](https://docs.salla.dev/twilight/react/routes/products) lists (latest, best sellers, offers, order again). A handler registered once shows on all of them.

<PageLayout
  title="Product list page"
  url="/category-name/c123"
  nodes="[
  { block: 'Breadcrumb, and the brand banner on brand pages', size: 'xs' },
  { slot: 'product:list.start' },
  { cols: [
    { w: 1, nodes: [{ block: 'Filters', size: 'xl', note: 'when the page has filters' }] },
    { w: 3, nodes: [
      { block: 'Title, sort and filter controls', size: 'xs' },
      { slot: 'product:list.items.start' },
      { block: 'Product grid', grid: 4 },
      { slot: 'product:list.items.end' },
    ] },
  ] },
  { block: 'Category testimonials', size: 'sm', note: 'category pages, when enabled' },
  { slot: 'product:list.end' },
]"
/>

| Slot                       | Position                                                                                                                   | Context | Notes                                                                                |
| -------------------------- | -------------------------------------------------------------------------------------------------------------------------- | ------- | ------------------------------------------------------------------------------------ |
| `product:list.start`       | After the breadcrumb (and after the brand banner and header on a brand page), before the filters and the grid. Full width. | none    | Best place for a promo strip above the whole listing.                                |
| `product:list.items.start` | In the main column, after the page title and the sort and filter controls, immediately before the product grid.            | none    | Narrower than `product:list.start`: it sits beside the filter sidebar, not above it. |
| `product:list.items.end`   | In the main column, immediately after the product grid.                                                                    | none    | Directly under the grid.                                                             |
| `product:list.end`         | Last item in the page container, after the mobile filters drawer and the category testimonials block.                      | none    | Full width, at the bottom of the listing.                                            |

The slots render on every listing, including ones with no filters and ones with no products. The context does not say which listing you are on. To show something only on some listings, read the current route in your handler, for example with TanStack Router's `useLocation`.

### Example: promo strip above a listing [#example-promo-strip-above-a-listing]

```tsx title="app/hooks/index.tsx"
import { hookRegistry } from '@salla.sa/twilight-theme-engine/hooks';

export function registerThemeHooks() {
  hookRegistry.register(
    'product:list.start',
    () => (
      <div className="mb-6 rounded-md bg-primary p-3 text-center text-sm font-bold text-primary-reverse">
        Free delivery on orders over 200 SAR
      </div>
    ),
    50
  );
}
```

Call `registerThemeHooks()` once at module scope, as in [Add content to a slot](https://docs.salla.dev/twilight/react/recipes/add-content-to-a-slot).

## Brands page [#brands-page]

Route: [Brands](https://docs.salla.dev/twilight/react/routes/brands). Both slots sit inside the alphabetical list, so they render only when the store has at least one brand. With no brands the page shows an empty state and neither slot renders.

<PageLayout
  title="Brands page"
  url="/brands"
  nodes="[
  { block: 'Breadcrumb and page title', size: 'xs' },
  { block: 'Letter navigation: A B C D ...', size: 'xs' },
  { slot: 'brands:index.items.start', note: 'only with brands' },
  { block: 'Section A and B: brand cards', grid: 4 },
  { slot: 'brands:index.items.end', note: 'only with brands' },
]"
/>

| Slot                       | Position                                                      | Context | Notes                                 |
| -------------------------- | ------------------------------------------------------------- | ------- | ------------------------------------- |
| `brands:index.items.start` | After the letter navigation, before the first letter section. | none    | Skipped when the store has no brands. |
| `brands:index.items.end`   | After the last letter section.                                | none    | Skipped when the store has no brands. |

The brands index does not render the `product:list.*` slots. A single brand's page (with its products) does.

## Not-found page [#not-found-page]

Route: [Not found](https://docs.salla.dev/twilight/react/routes/not-found). The three slots render inside the error page, between the message and the "Back to Home" link. While a short link is still being resolved the page renders nothing, so no slot appears.

<PageLayout
  title="Not-found page"
  url="/no-such-page"
  nodes="[
  { block: '404, title and message', size: 'md' },
  { slot: 'notfound:start' },
  { slot: 'notfound:content' },
  { slot: 'notfound:end' },
  { block: 'Back to Home button', size: 'xs' },
]"
/>

| Slot               | Position                                        | Context | Notes                                                                                 |
| ------------------ | ----------------------------------------------- | ------- | ------------------------------------------------------------------------------------- |
| `notfound:start`   | Directly under the message text.                | none    | All three slots render back to back, so ordering between them is the only difference. |
| `notfound:content` | After `notfound:start`.                         | none    | Good for a search box or a list of popular categories.                                |
| `notfound:end`     | After `notfound:content`, before the home link. | none    | Appears above the "Back to Home" button.                                              |

### Example: help links on the 404 page [#example-help-links-on-the-404-page]

```tsx title="app/components/NotFoundHelp.tsx"
import { useHook } from '@salla.sa/twilight-theme-engine/hooks/useHook';

export function NotFoundHelp() {
  useHook('notfound:content', () => (
    <p className="mb-6 text-gray-500">
      Looking for something? Try the <a href="/search">search page</a> or{' '}
      <a href="/contact-us">contact us</a>.
    </p>
  ));
  return null;
}
```

Render `<NotFoundHelp />` once under your layout so the handler stays registered for the whole visit.

## Next [#next]

* [Product page slots](https://docs.salla.dev/twilight/react/slots/product-page)
* [Cart and checkout slots](https://docs.salla.dev/twilight/react/slots/cart-and-checkout)
* [useHook](https://docs.salla.dev/twilight/react/hooks/use-hook) and [HookSlot](https://docs.salla.dev/twilight/react/hooks/hook-slot)
