# ScrollerBase

The low-level scroll engine (a Svelte 5 port of svelte-scroller) exposing background/foreground slots and scroll bindings. Powers Scroller.

**Category:** Components/Graphics/ScrollerBase

**Import:** `import { ScrollerBase } from '@reuters-graphics/graphics-components'`

## Props

| Prop | Type | Default | Required | Description |
|------|------|---------|:--------:|-------------|
| `top` | `number` | `0` |  | Config |
| `bottom` | `number` | `1` |  | The inverse of top — once the bottom of the foreground passes this point, the background becomes unfixed. **Value between 0 and 1.** |
| `threshold` | `number` | `0.5` |  | Once a section crosses this point, it becomes 'active'. **Value between 0 and 1.** |
| `query` | `string` | `'div.step-foreground-container'` |  | A CSS selector that describes the individual sections of your foreground. |
| `parallax` | `boolean` | `false` |  | If `true`, the background will scroll such that the bottom edge reaches the bottom at the same time as the foreground. This effect can be unpleasant for people with high motion sensitivity, so use it advisedly. |
| `backgroundSnippet` | `Snippet` | — | ✓ | The background snippet. |
| `foregroundSnippet` | `Snippet` | — | ✓ | The foreground snippet. |
| `index` | `number` | `$bindable(0)` |  | Bindings |
| `offset` | `number` | `$bindable(0)` |  | How far the section has scrolled past the threshold, as a value between 0 and 1. **Bindable**. |
| `progress` | `number` | `$bindable(0)` |  | How far the foreground has travelled, where 0 is the top of the foreground crossing top, and 1 is the bottom crossing bottom. **Bindable**. |
| `count` | `number` | `$bindable(0)` |  | Number of sections |
| `visible` | `boolean` | `$bindable(false)` |  | Whether the foreground is visible |

## Examples

### Demo

```svelte
<ScrollerDemo />
```

## Documentation

# ScrollerBase

The `ScrollerBase` component powers the [`Scroller` component](?path=/story/components-graphics-scroller--docs), which creates a basic storytelling graphic with preset layout options. `ScrollerBase` contains the bare minimum code necessary for a scrollytelling section, and allows for customisation beyond what the [`Scroller` component](?path=/story/components-graphics-scroller--docs) allows.

`ScrollerBase` is a Svelte 5 version of the [svelte-scroller](https://github.com/sveltejs/svelte-scroller).

> **Important❗:** Make sure the HTML element containing each foreground is a div with the class `step-foreground-container`. If you're modifying this to something else, pass the appropriate selector to the `query` prop.

[Demo](?path=/story/components-graphics-scrollerbase--demo)

```svelte
<script lang="ts">
  import { ScrollerBase } from '@reuters-graphics/graphics-components';

  // Optional: Bind your own variables to use them in your code.
  let count = $state(1);
  let index = $state(0);
  let offset = $state(0);
  let progress = $state(0);
  let top = $state(0.1);
  let threshold = $state(0.5);
  let bottom = $state(0.9);
</script>

<ScrollerBase
  {top}
  {threshold}
  {bottom}
  bind:count
  bind:index
  bind:offset
  bind:progress
  query="div.step-foreground-container"
>
  {#snippet backgroundSnippet()}
    <!-- Add custom background HTML or component -->
    <p class="mb-0">
      Current step: <strong>{index + 1}/{count}</strong>
    </p>
    <progress class="mb-4" value={(index + 1) / count}></progress>

    <p class="mb-0">Offset in current step</p>
    <progress class="mb-4" value={offset}></progress>

    <p class="mb-0">Total progress</p>
    <progress class="mb-4" value={progress}></progress>
  {/snippet}
  {#snippet foregroundSnippet()}
    <!-- Add custom foreground HTML or component -->
    <div class="step-foreground-container">Step 1</div>
    <div class="step-foreground-container">Step 2</div>
    <div class="step-foreground-container">Step 3</div>
    <div class="step-foreground-container">Step 4</div>
    <div class="step-foreground-container">Step 5</div>
  {/snippet}
</ScrollerBase>

<style lang="scss">
  @use '@reuters-graphics/graphics-components/dist/scss/mixins' as mixins;

  .step-foreground-container {
    height: 100vh;
    width: 50%;
    background-color: rgba(0, 0, 0, 0.2);
    padding: 1em;
    margin: 0 0 2em 0;
    position: relative;
    left: 50%;
  }
</style>
```
