Better and Less YAML with Reuse™¶
Flexible Horseshoe Card layouts can grow quickly. When building larger cards myself, I often ended up with a lot of repeated YAML. Many items used the same positions, styles, colors, or layout rules, while only one or two fields changed.
That made the configuration harder to read and slower to update. A small visual change could mean editing the same value in several places.
Reuse™ was added to make that easier.
Instead of repeating full YAML blocks, you define the shared part once and reuse it wherever needed. The card expands this into a complete internal configuration before rendering. The rendered result is the same, but the external YAML stays shorter, cleaner, and easier to maintain.
For practical card examples, see Card Examples.
The problem¶
A common layout pattern is a small group of repeated items. In this example, the card contains three horizontal lines with the same position logic, length, and style.

Without reuse, the same values must be repeated for every line:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | |
This works, but it is not ideal while designing a card. If the length, style, starting position, or spacing changes, you have to update the same values in multiple places.
YAML anchors can reduce some duplication:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | |
However, anchors are not a complete solution:
- YAML anchors cannot calculate repeated spacing.
- Anchor names must be unique across the entire YAML file.
- The syntax is harder for many users to read.
- Overriding values can cause duplicate-key warnings in the Home Assistant YAML loader.
Example duplicate-key warning:
Logger: annotatedyaml.constructors
Source: util/yaml/loader.py:65
YAML file /config/lovelace/views/whatever.yaml contains duplicate key "ypos".
That is why the card includes its own reuse system.
The Reuse™ approach¶
The same three lines can be written as one base line and two reused lines:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | |
This keeps the pattern easy to see:
| Item | Meaning | Result |
|---|---|---|
first | Base line | ypos: 64 |
second | Same as first, 1 step lower | ypos: 75 |
third | Same as first, 2 steps lower | ypos: 86 |
Internally, the card expands this into full items before rendering:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | |
The external configuration stays compact. The internal configuration is still complete.
Main features¶
| Feature | Purpose |
|---|---|
same_as | Reuse an earlier item from the same section |
same_as_d... | Reuse an item and add a numeric offset |
constants | Define reusable static values or configuration fragments |
calc() | Use static calculations in numeric fields. Required to use constants |
ref() | Copy a value from constants into the configuration |
All of these are static configuration features. They are processed during card setup, not during every render.
Reusing items with same_as¶
same_as copies an earlier item from the same section.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | |
The smaller circle copies xpos and ypos from base, but overrides radius and styles.
Automatic ids or named ids¶
For reuse to work, each item in a section should have a unique id. There are two options.
Each item can have an explicit id:
1 2 3 4 5 6 7 8 9 | |
If no id is defined, the card automatically assigns one based on the item index:
1 2 3 4 5 6 7 8 9 10 | |
same_as: 0 and same_as: "0" both refer to the first item.
Automatic ids are fine for short examples. For larger card configurations, named ids are usually easier to understand.
Delta fields¶
A reused item can override a field directly:
1 2 3 4 5 6 7 8 9 | |
For repeated numeric changes, a delta field is often clearer:
1 2 3 4 5 6 7 8 9 | |
A delta field uses this pattern:
same_as_d<field>: <number>
The delta is added to the inherited value.
| Delta field | Target field | Meaning |
|---|---|---|
same_as_dxpos | xpos | Add to the inherited xpos |
same_as_dypos | ypos | Add to the inherited ypos |
same_as_dlength | length | Add to the inherited length |
same_as_dradius | radius | Add to the inherited radius |
The pattern is generic. You can use same_as_d<field> with any inherited numeric field.
Example with circles:
1 2 3 4 5 6 7 8 9 | |
Result: inner.radius becomes 35.
Static calculations with calc() and constants¶
YAML itself does not calculate values. So the next line is nothing more than text, not a formula
1 | |
Use calc() when a numeric value should be calculated during card setup.
This makes the intent clear: both icons are placed around the center point.
1 2 3 4 5 6 7 8 | |
1 2 3 4 5 6 7 8 9 10 11 | |
Result in both cases:
| Item | Calculation | Result |
|---|---|---|
left | xpos: calc(50 - 4) | xpos: 46 |
right | xpos: calc(50 + 4) | xpos: 54 |
Static only
calc() is evaluated once during configuration setup. It is not a JavaScript template and is not evaluated during runtime updates.
Constants and ref()¶
Use constants for shared static values or configuration fragments.
Use ref() to copy one of those constants into the configuration.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | |
This keeps shared values in one place.
If the center position, icon spacing, or line style changes later, you only need to update the constant.
Chained reuse or one base item¶
There are two useful ways to create repeated items.
Use one base item when every item follows a fixed pattern from the same source:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | |
This means:
second = first + 1 step
third = first + 2 steps
Use chained reuse when each item builds on the previous item:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | |
This means for ypos:
second = first + 11
third = second + 11
For fixed grids or repeated spacing, reusing one base item is often clearer. For progressive changes, chained reuse can be more compact.
Larger items: horseshoes¶
Reuse becomes more valuable when the repeated item is larger.
A simple line only has a few fields. A horseshoe can contain scale settings, state settings, tick marks, labels, colors, widths, minimum and maximum values, and display options.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | |
Only the differences are shown in the reused horseshoes. The shared visual setup stays in base.
Bigger repeated blocks benefit the most
Reusing a three-line block saves a little YAML. Reusing a horseshoe with nested settings can save a lot of YAML and makes later changes much safer.
When to use reuse¶
Use reuse when a layout has a clear pattern:
- repeated lines, circles, icons, names, or states
- multiple horseshoes with the same visual setup
- shared styles or color stops
- fixed spacing between items
- positions calculated from a shared center point
- several values derived from one constant
Do not use reuse everywhere. For a single unique item, normal YAML is often clearer.