#### <sup>[Ollin](../../index.md) → [Examples](../index.md) → Shaders</sup>

---

## Shaders

| [![BlackHole](https://media.ollin.art/examples/Shaders/BlackHole/still-640.jpg?v=8be167a9)](blackhole.md) | [![ComplexPlane](https://media.ollin.art/examples/Shaders/ComplexPlane/still-640.jpg?v=50d83a38)](complexplane.md) | [![DomainWarp](https://media.ollin.art/examples/Shaders/DomainWarp/still-640.jpg?v=9c7c951f)](domainwarp.md) | [![HelloShader](https://media.ollin.art/examples/Shaders/HelloShader/still-640.jpg?v=63468476)](helloshader.md) |
|---|---|---|---|
| [BlackHole](blackhole.md) | [ComplexPlane](complexplane.md) | [DomainWarp](domainwarp.md) | [HelloShader](helloshader.md) |
| [![ImaginaryLog](https://media.ollin.art/examples/Shaders/ImaginaryLog/still-640.jpg?v=5a1029c5)](imaginarylog.md) | [![Meromorphic](https://media.ollin.art/examples/Shaders/Meromorphic/still-640.jpg?v=cddb858d)](meromorphic.md) | [![ShaderBlend](https://media.ollin.art/examples/Shaders/ShaderBlend/still-640.jpg?v=8a803d48)](shaderblend.md) | [![ShaderFilter](https://media.ollin.art/examples/Shaders/ShaderFilter/still-640.jpg?v=2f2995ce)](shaderfilter.md) |
| [ImaginaryLog](imaginarylog.md) | [Meromorphic](meromorphic.md) | [ShaderBlend](shaderblend.md) | [ShaderFilter](shaderfilter.md) |
| [![ShaderPaint](https://media.ollin.art/examples/Shaders/ShaderPaint/still-640.jpg?v=ec1d468b)](shaderpaint.md) | [![VisualCatalog](https://media.ollin.art/examples/Shaders/VisualCatalog/still-640.jpg?v=45257941)](visualcatalog.md) | [![VisualSynth](https://media.ollin.art/examples/Shaders/VisualSynth/still-640.jpg?v=21aaaa70)](visualsynth.md) |  |
| [ShaderPaint](shaderpaint.md) | [VisualCatalog](visualcatalog.md) | [VisualSynth](visualsynth.md) |  |

These examples show how to write your own GPU code. A `Shader` is a `shade(uv, info)`
function. Ollin wraps it, compiles it, and runs it through the effect graph as a source,
a filter, or a two-input combine, with the whole shader library spliced in, or as the
paint a shape is filled or stroked with. A `Visual`
chain builds the same per-pixel program from chained Swift calls, so you do not need
to write Metal. See [Shaders](../../docs/shaders/shaders.md),
the [shader library reference](../../docs/shaders/shaderlibrary.md), and
[Visuals](../../docs/shaders/visuals.md).

| Example | What it shows |
|---|---|
| [HelloShader](helloshader.md) | the smallest user shader, written both ways: an inline `Shader("...")` plasma beside the same shader loaded from a `.metal` file with `Shader(resource:in:)`. The file version hot-reloads on save under OllinLive, with no swiftc pass |
| [ShaderFilter](shaderfilter.md) | a shader as a one-input filter: it draws a scene into a layer, then re-samples the layer with a wave and posterizes it (`sample(info, uv)`) |
| [ShaderBlend](shaderblend.md) | a shader as a two-input combine: an animated diagonal wipe with a rippling seam (`sample` + `sampleAux`) |
| [ShaderPaint](shaderpaint.md) | a shader as paint: `fill(shader)` and `stroke(shader)` run `shade` at every pixel a shape covers, `uv` across the shape's own box, `info.distance` from its edge, `info.along` a stroke, and `info.position` on the canvas; a disk ringed from its edge, a turning star striped in its own frame, a ribbon whose pulse travels it, and tiles sharing one grain |
| [VisualSynth](visualsynth.md) | the `Visual` chain API: a source, warps, color moves, and modulations compile into one GPU pass, and every number can animate without a recompile |
| [VisualCatalog](visualcatalog.md) | the `Visual` chain catalog on one switchable contact sheet: sources, warps, color adjustments, two-chain combines, and per-pixel modulations, chosen by a family parameter, with every tile labeled with the calls it chains |
| [DomainWarp](domainwarp.md) | runtime shader parameters: `Shader(_, params:)` takes floats that MSL reads back as `param(info, n)`, which animates a hand-written domain-warp marble with no recompile |
| [ComplexPlane](complexplane.md) | the shader library's `complex` module beside the CPU `Complex` value: a shader colors every pixel by the phase and size of the ratio of two moving points (`complexPlane`, `cdiv`, `domainColor`), and `draw()` works out the circles that ratio is made of and lays them over the layer, where they land on the shader's rulings |
| [ImaginaryLog](imaginarylog.md) | the imaginary part of a logarithm as a picture: `clog` of the ratio of two turning points through a cosine `palette` that never completes a cycle, so the branch cut between the points shows as a soft seam, and `draw()` can mark that segment with `Complex` |
| [Meromorphic](meromorphic.md) | a ratio of two cubic polynomials built from six roots that `draw()` moves as `Complex` values, multiplied out with `cmul` and painted by the phase of its `clog` through a palette whose frequency is a parameter: tame at one, bands piling up around the poles when wild |
| [BlackHole](blackhole.md) | light bent round a black hole by the orbit equation for light, traced backward from every pixel: the shadow, the far side of the disk standing over the hole and under it, stars smeared into arcs, and one star behind the hole seen as a ring. The disk shines as a black body at the temperature its radius gives it, shifted blue-white where it turns toward the camera and red where it turns away. The physics lives in `physics.metal`, which the picture's `blackhole.metal` includes and the tests read on its own |
