# SVG-liukuvärit: lineaarinen, säteittäinen, viivat ja maskit

[Canonical HTML page](https://gradiently.design/fi/guide/svg-gradients)

SVG:llä on oma liukuvärijärjestelmänsä, CSS-liukuvärejä vanhempi ja kykenevä asioihin, joihin ne eivät pysty: viivan värittämiseen, sanan täyttämiseen, yhden liukuvärin jakamiseen monelle muodolle ja minkä tahansa häivyttämiseen maskilla.

## The short version

- SVG-liukuväri määritellään kerran linearGradient- tai radialGradient-elementtinä, jolla on stop-lapsia ja id, ja se otetaan käyttöön asettamalla fill tai stroke arvoon url(#id).
- Oletuksena SVG-liukuvärin koordinaatit käyttävät objectBoundingBox-yksiköitä, joissa 0 ja 1 ovat maalattavan muodon reunat.
- gradientUnits="userSpaceOnUse" sijoittaa liukuvärin piirroksen omiin koordinaatteihin, jolloin yksi liukuväri voi ulottua usean muodon yli ja liukuvärit toimivat myös täysin suorilla viivoilla.
- spreadMethod päättää, mitä liukuvärin päiden ulkopuolella tapahtuu: pad pitää päätyvärit, reflect peilaa sekoituksen ja repeat aloittaa sen alusta.
- SVG-maski käyttää kirkkautta, joten valkoisesta mustaan kulkeva liukuväri maskin sisällä häivyttää sen, mihin maskia käytetään.

**SVG-liukuväri** on maali, jonka määrittelet kerran ja jota käytät mihin tahansa SVG:n muotoon, viivaan tai tekstiin. Kirjoitat `<linearGradient>`- tai `<radialGradient>`-elementin `<defs>`-elementin sisään, annat sille `<stop>`-lapset väreiksi ja `id`:n ja asetat sitten muodon `fill`- tai `stroke`-arvoksi `url(#id)`. Toisin kuin CSS-tausta, se voi värittää viivan tai yksittäisen sanan, ja se skaalautuu piirroksen mukana.

```html
<svg viewBox="0 0 200 120" xmlns="http://www.w3.org/2000/svg">
  <defs>
    <linearGradient id="dusk" x1="0" y1="0" x2="1" y2="1">
      <stop offset="0" stop-color="#1e1b4b" />
      <stop offset="0.55" stop-color="#7c3aed" />
      <stop offset="1" stop-color="#f472b6" />
    </linearGradient>
  </defs>
  <rect width="200" height="120" rx="16" fill="url(#dusk)" />
</svg>
```

Vino liukuväri pyöristetyssä suorakulmiossa. x1, y1, x2 ja y2 piirtävät liukuvärin viivan vasemmasta yläkulmasta oikeaan alakulmaan.

Sama sekoitus CSS:nä: `linear-gradient(135deg, #1e1b4b 0%, #7c3aed 55%, #f472b6 100%)`

Yllä oleva SVG ja tämä CSS-liukuväri vastaavat toisiaan neliössä. Suorakulmiossa SVG-versio venyy muodon mukana, katso gradientUnits alempana.

## linearGradient ja sen pysäytyspisteet

`x1`, `y1`, `x2` ja `y2` asettavat liukuvärin viivan alun ja lopun. Jokainen `<stop>` saa `offset`-arvon väliltä 0 ja 1 (tai 0 % ja 100 %), `stop-color`-arvon ja valinnaisen `stop-opacity`-arvon. `stop-color` on myös CSS-ominaisuus, joten voit teemoittaa liukuvärejä tyylitiedostosta, esimerkiksi `stop { stop-color: var(--accent); }`.

| Attribuutti | Oletus | Mitä se tekee |
| --- | --- | --- |
| `x1 y1 x2 y2` | `0 0 1 0`, vasemmalta oikealle | Liukuvärin viivan alku- ja loppupiste |
| `gradientUnits` | `objectBoundingBox` | Ovatko koordinaatit suhteessa muotoon vai piirrokseen |
| `spreadMethod` | `pad` | Mitä päiden ulkopuolella tapahtuu: `pad`, `reflect` tai `repeat` |
| `gradientTransform` | ei mitään | Kierrä, skaalaa tai vinouta liukuväriä, esim. `rotate(30)` |
| `href` | ei mitään | Peri pysäytyspisteet ja asetukset toisesta liukuväristä |

linearGradientin tärkeimmät attribuutit. radialGradient jakaa kaikki paitsi ensimmäisen rivin.

`href` säästää toistolta. Määrittele pysäytyspisteesi kerran perusliukuvärissä ja luo sitten muunnelmia, jotka viittaavat siihen ja muuttavat vain suuntaa tai yksiköitä. [MDN:n linearGradient-viite](https://developer.mozilla.org/en-US/docs/Web/SVG/Element/linearGradient) käy läpi jokaisen attribuutin.

## radialGradient: keskipiste, säde ja polttopiste

Säteittäinen liukuväri saa keskipisteen (`cx`, `cy`) ja säteen (`r`), joiden kaikkien oletus on 0.5, joten se täyttää muodon keskeltä. Sillä on myös jotain, mikä CSS:ltä puuttuu: erillinen polttopiste (`fx`, `fy`), josta ensimmäinen väri alkaa. Polttopisteen siirtäminen sivuun keskeltä saa pallon näyttämään yhdeltä sivulta valaistulta.

```html
<radialGradient id="orb" cx="0.5" cy="0.5" r="0.5" fx="0.32" fy="0.28">
  <stop offset="0" stop-color="#e0f2fe" />
  <stop offset="0.45" stop-color="#0ea5e9" />
  <stop offset="1" stop-color="#082f49" />
</radialGradient>

<circle cx="60" cy="60" r="50" fill="url(#orb)" />
```

Ylös ja vasemmalle siirretty polttopiste muuttaa litteän ympyrän kiiltäväksi palloksi.

Valaistu pallo, CSS-likiarvo: `radial-gradient(circle at 32% 28%, #e0f2fe, #0ea5e9 35%, #082f49 80%)`

CSS voi siirtää keskipistettä mutta ei erottaa keskipistettä ja polttopistettä, joten tämä on vain likiarvo SVG-pallosta. Vertaa: [CSS:n säteittäiset liukuvärit](https://gradiently.design/fi/guide/css-radial-gradient).

## gradientUnits: objectBoundingBox vai userSpaceOnUse

Oletusarvolla `objectBoundingBox` 0 ja 1 tarkoittavat kulloinkin maalattavan muodon reunoja, joten jokainen muoto saa koko liukuvärin venytettynä sopivaksi. Arvolla `userSpaceOnUse` koordinaatit ovat SVG:n omissa yksiköissä, joten liukuväri pysyy paikallaan ja muodot paljastavat sen osan, jonka ne peittävät. Näin pylväsrivi voi jakaa yhden jatkuvan liukuvärin.

### objectBoundingBox

- Koordinaatit 0 ja 1 väliltä jokaisen muodon poikki
- Jokainen muoto näyttää koko liukuvärin
- Liukuväri venyy muodon mittasuhteiden mukana
- Ei toimi täysin vaaka- tai pystysuoralla viivalla

### userSpaceOnUse

- Koordinaatit piirroksen omissa yksiköissä
- Muodot paljastavat oman siivunsa yhdestä liukuväristä
- Kulmat pysyvät oikeina muodosta riippumatta
- Toimii suorilla viivoilla ja ohuilla ääriviivoilla

> **Näkymätön suora viiva** Vaakasuoran `<line>`-elementin rajauslaatikon korkeus on nolla, eikä rajauslaatikkoyksiköitä voi laskea nollasta, joten oletusliukuväri sen viivassa ei piirrä mitään. Aseta `gradientUnits="userSpaceOnUse"` ja anna oikeat koordinaatit.

## Liukuvärit viivoissa ja tekstissä

`stroke="url(#id)"` maalaa ääriviivat, ja näin piirretään liukuvärikuvakkeet, edistymisrenkaat ja kaavioviivat. `<text>`-elementissä `fill="url(#id)"` värittää kirjaimet, ja sanat pysyvät valittavina ja haettavina. Lisää URL:n perään tasainen väri, esimerkiksi `fill="url(#dusk) #7c3aed"`, niin sitä käytetään, jos liukuväriä ei löydy.

```html
<svg viewBox="0 0 320 120" xmlns="http://www.w3.org/2000/svg">
  <defs>
    <linearGradient id="line" gradientUnits="userSpaceOnUse" x1="20" y1="0" x2="300" y2="0">
      <stop offset="0" stop-color="#22d3ee" />
      <stop offset="1" stop-color="#a855f7" />
    </linearGradient>
  </defs>
  <path d="M20 90 C 90 20, 160 110, 300 30" fill="none" stroke="url(#line)" stroke-width="6" stroke-linecap="round" />
  <text x="20" y="115" font-size="20" font-weight="700" fill="url(#line) #7c3aed">Growth</text>
</svg>
```

Yksi liukuväri piirroksen yksiköissä, jonka käyrä ja sana jakavat. Molemmat kulkevat syaanista violettiin saman vaakasuuntaisen matkan.

Jos haluat liukuväritekstiä HTML:ään etkä SVG:hen, [liukuväriteksti CSS:llä](https://gradiently.design/fi/guide/css-gradient-text) on yleensä yksinkertaisempi. Tartu SVG-tekstiin, kun sanat ovat osa kuvitusta tai logoa tai niiden pitää seurata polkua.

## spreadMethod: pad, reflect ja repeat

Kun liukuvärin viiva on muotoa lyhyempi, `spreadMethod` päättää, mikä täyttää loput. `pad` pitää päätyvärit, `reflect` peilaa sekoituksen edestakaisin ja `repeat` aloittaa sen alusta kovalla reunalla. Tässä jokainen liukuväri kulkee 30 %:sta 70 %:iin leveydestä.

- pad: `linear-gradient(90deg, #0f766e 30%, #fde68a 70%)`
- reflect: `repeating-linear-gradient(90deg, #fde68a -10%, #0f766e 30%, #fde68a 70%)`
- repeat: `repeating-linear-gradient(90deg, #0f766e 30%, #fde68a 70%)`

Sinivihreästä hiekkaan kolmella spread-menetelmällä, toistettuna CSS:llä, jotta voit verrata niitä rinnakkain.

## Häivyttäminen SVG-maskeilla

Maski käyttää kirkkautta: valkoiset alueet näyttävät maskatun, mustat piilottavat sen, ja harmaat ovat siltä väliltä. Valkoisesta mustaan kulkeva liukuväri `<mask>`-elementin sisällä häivyttää siis minkä tahansa muodon tai kuvan pehmeästi olemattomiin, ja näin pehmennät valokuvan reunan tai saat kaavioviivan häipymään alustaan.

```html
<defs>
  <linearGradient id="fade" x1="0" y1="0" x2="0" y2="1">
    <stop offset="0.4" stop-color="#fff" />
    <stop offset="1" stop-color="#000" />
  </linearGradient>
  <mask id="soft-bottom">
    <rect width="100%" height="100%" fill="url(#fade)" />
  </mask>
</defs>

<image href="photo.jpg" width="100%" height="100%" mask="url(#soft-bottom)" />
```

Valokuva näkyy kokonaan yläosassa ja häipyy alimman 60 %:n matkalla.

HTML-elementeille CSS:n `mask-image: linear-gradient(#000 40%, transparent)` tekee saman työn, mutta käyttää alfaa kirkkauden sijaan. Maskitekniikan varassa toimivat myös läpinäkyvät [CSS-liukuvärireunukset](https://gradiently.design/fi/guide/css-gradient-border).

### Vältä

- Saman liukuvärin `id`:n käyttö kahdessa upotetussa SVG:ssä samalla sivulla
- Liukuvärimääritysten spriten piilottaminen arvolla `display: none`
- Oletusyksiköt suorilla viivoilla
- Hyvin pitkät, tasaiset, tummat liukuvärit ilman tekstuuria

### Tee näin

- Yksilölliset id:t tai yksi jaettu määrityssprite
- Piilota spritet mieluummin nollaleveydellä ja nollakorkeudella
- `userSpaceOnUse` viivoille ja jaetuille liukuväreille
- Lisää rakeisuutta suuriin häivytyksiin, katso [CSS-kohinatekstuuri](https://gradiently.design/fi/guide/css-noise-texture)

## FAQ

### Miten lisään liukuvärin SVG:hen?

Määrittele `<defs>`-elementin sisään `<linearGradient>` tai `<radialGradient>`, jolla on `<stop>`-lapset ja `id`, ja aseta sitten muodon `fill`- tai `stroke`-arvoksi `url(#id)`.

### Miksi SVG-liukuvärini ei näy viivassa?

Suoran vaaka- tai pystyviivan rajauslaatikon koko on nolla, joten oletusyksiköt `objectBoundingBox` eivät toimi. Käytä `gradientUnits="userSpaceOnUse"` oikeilla koordinaateilla.

### Miten kierrän SVG-liukuväriä?

Muuta arvoja `x1`, `y1`, `x2` ja `y2` tai lisää `gradientTransform="rotate(45 0.5 0.5)"`, niin se kiertyy rajauslaatikon keskipisteen ympäri.

### Voinko muuttaa SVG-liukuvärin värejä CSS:llä?

Kyllä. `stop-color` ja `stop-opacity` ovat CSS-ominaisuuksia, joten säännöt kuten `stop { stop-color: var(--accent); }` toimivat upotetussa SVG:ssä.

### Miksi SVG-liukuvärini katosi, kun piilotin SVG:n?

Määritykset SVG:ssä, jolla on `display: none`, eivät välttämättä piirry. Piilota sprite mieluummin nollaleveydellä ja nollakorkeudella tai absoluuttisella sijoittelulla.
