# Custom Properties

Custom properties let end users personalize your wallpaper through the Fluxlay app settings UI — sliders, color pickers, toggles, and dropdowns — without touching code.

## 1. Define Properties in the Manifest

Add a `properties` section to your `fluxlay.yaml`:

```yaml title="fluxlay.yaml"
schemaVersion: 1
name: My Wallpaper
slug: my-wallpaper
version: 0.1.0
kind: web

properties:
  speed:
    type: number
    label: Animation Speed
    default: 1.0
    min: 0.1
    max: 5.0
    step: 0.1
  volume:
    type: range
    label: Volume
    default: 50
    min: 0
    max: 100
    step: 1
  accentColor:
    type: color
    label: Accent Color
    default: "#3b82f6"
  darkMode:
    type: boolean
    label: Dark Mode
    default: true
  title:
    type: text
    label: Title
    default: ""
    maxLength: 40
  layout:
    type: select
    label: Layout
    default: grid
    options:
      - value: grid
        label: Grid
      - value: list
        label: List
      - value: masonry
        label: Masonry
  tags:
    type: multi-select
    label: Visible Tags
    default: [time]
    min: 1
    max: 3
    options:
      - value: time
        label: Time
      - value: date
        label: Date
      - value: weather
        label: Weather
  background:
    type: image
    label: Background Image
    accept: ["image/*"]
    maxBytes: 5242880
  font:
    type: font
    label: Font
    default: Inter
    sources: [system, google]
    category: sans-serif
```

## 2. Read Properties in Your Wallpaper

Use the `useProperties()` hook to access the current values:

```tsx
import { useProperties } from "@fluxlay/react";

interface Props {
  speed: number;
  accentColor: string;
  darkMode: boolean;
  layout: string;
}

function Wallpaper() {
  const { speed, accentColor, darkMode, layout } = useProperties<Props>();

  return (
    <div
      style={{
        backgroundColor: darkMode ? "#1a1a2e" : "#ffffff",
        color: accentColor
      }}
    >
      <p>Speed: {speed}x</p>
      <p>Layout: {layout}</p>
    </div>
  );
}
```

The hook automatically:

- Fetches the initial values (defaults merged with user customizations)
- Subscribes to real-time updates when the user changes a value

## 3. Test in the App

1. Run `fluxlay dev` to start the dev server.
2. Open the Fluxlay desktop app settings.
3. Your properties appear in the wallpaper's settings card.
4. Adjust values — the wallpaper updates in real time.

## Validation

The manifest is validated at build time. Common validation rules:

- **schemaVersion**: must declare `1`.
- **number** / **range**: `default` must be between `min` and `max`. `range` renders as a slider; `min` and `max` are required.
- **color**: `default` must be a valid hex color (`#rgb`, `#rrggbb`, or `#rrggbbaa`).
- **text**: when `maxLength` is set, `default` length must not exceed it.
- **select**: `default` must match one of the `options` values.
- **multi-select**: every item in `default` must be in `options`; `min` / `max` constrain the selection count.
- **image** / **file**: `accept` uses MIME patterns (e.g. `image/*`, `application/pdf`). The SDK exposes the host OS absolute path (or `null` when the user has not picked a file).
- **font**: `sources` is `system` and/or `google`. When `google` is included, the manifest must declare a `network` entry granting access to Google Fonts.

## Notes

- User customizations are saved per wallpaper slug and persist across app restarts.
- Properties with no user customization use the manifest default.

See the [useProperties Reference](/en/studio/developer/reference/sdk/use-properties.md) for full API details.
