Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/verekia/tslfx
✨ TSLFX • Early-stage collection of VFX, utils, and SDFs for Three.js Shading Language (TSL)
https://github.com/verekia/tslfx
gamedev glsl threejs tsl vfx webgl webgpu wgsl
Last synced: about 1 month ago
JSON representation
✨ TSLFX • Early-stage collection of VFX, utils, and SDFs for Three.js Shading Language (TSL)
- Host: GitHub
- URL: https://github.com/verekia/tslfx
- Owner: verekia
- License: mit
- Created: 2024-12-21T13:20:20.000Z (about 2 months ago)
- Default Branch: main
- Last Pushed: 2024-12-29T05:14:53.000Z (about 1 month ago)
- Last Synced: 2024-12-29T05:21:34.747Z (about 1 month ago)
- Topics: gamedev, glsl, threejs, tsl, vfx, webgl, webgpu, wgsl
- Language: TypeScript
- Homepage: https://tslfx.v1v2.io
- Size: 190 KB
- Stars: 34
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# ✨ TSLFX ✨
Early-stage collection of VFX shaders, utils, and SDFs for Three.js Shading Language ([TSL](https://github.com/mrdoob/three.js/wiki/Three.js-Shading-Language)).
The effects work with the WebGPU renderer and its WebGL backend fallback. To set up your project with `WebGPURenderer`, check out [this repo](https://github.com/verekia/three-gpu-ecosystem-tests). The examples use React Three Fiber but the shaders can be used with vanilla Three.js or any other wrapper.
## Getting started
### Vanilla Three.js
```js
import { MeshBasicNodeMaterial } from 'three/webgpu'
import { impact } from 'tslfx'const { uniforms, nodes } = impact()
const material = new MeshBasicNodeMaterial()
material.colorNode = nodes.colorNodeconst animate = (delta: number) => {
// Update uniforms in your animation loop
uniforms.time.value += delta
}
```### React Three Fiber v9 RC
Somewhere top-level in your project, extend `MeshBasicNodeMaterial` and declare its type:
```ts
import { extend, type ThreeElement } from '@react-three/fiber'
import { MeshBasicNodeMaterial } from 'three/webgpu'extend({ MeshBasicNodeMaterial })
declare module '@react-three/fiber' {
interface ThreeElements {
meshBasicNodeMaterial: ThreeElement
}
}
```> [!TIP]
> I like to put these in an `extend.ts` file that I import in my main entry file (`_app.tsx` in Next.js for example).You can then use `meshBasicNodeMaterial` in your scene:
```js
import { useFrame } from '@react-three/fiber'
import { impact } from 'tslfx'const ImpactVFX = () => {
const { uniforms, nodes } = useMemo(() => impact(), [])useFrame((_, delta) => {
// Update uniforms here
uniforms.time.value += delta
})return (
)
}
```> [!CAUTION]
> You should **memoize any TSL logic** to not re-create nodes on every render.## VFX
- 💥 [Impact](https://tslfx.v1v2.io/impact)
- ⭕️ [Pulsing Ring](https://tslfx.v1v2.io/pulsing-ring)
- 🌈 [Gradient](https://tslfx.v1v2.io/gradient)
- 💧 [Water](https://tslfx.v1v2.io/water) (simplex noise)## SDFs
Some Signed Distance Functions (SDFs) ported from [Inigo Quilez's website](https://iquilezles.org/articles/distfunctions2d/) are included in the library:
```js
import { sdCircle, sdVesica, sdHeart } from 'tslfx'const circle = sdCircle(p, 0.5)
const vesica = sdVesica(p, 0.5, 0.2)
const heart = sdHeart(p)
```## Utils
### `pipe`
TSL functions that take 2 nodes as arguments can be piped together into a single expression without introducing extra variables or reassignments:
```js
import { blendColor } from 'three/tsl'
import { pipe } from 'tslfx'const colorNode = pipe(
blendColor,
effectA.colorNode,
effectB.colorNode,
effectC.colorNode
)
```## Noise
Some [MaterialX](https://materialx.org/)-based noises are directly [included in Three.js](https://github.com/mrdoob/three.js/blob/master/examples/webgpu_materialx_noise.html).
For example, the following code creates a basic water-like effect using `mx_noise_vec3`:
```js
import { color, float, mix, mx_noise_vec3, time, uv, vec3 } from 'three/tsl'const blue = color('#3871ff')
const lightBlue = color('#579dff')
const p = uv().sub(0.5).mul(8).add(0.5)const rawNoise = mx_noise_vec3(vec3(p, time.mul(0.5))).xxx
const adjustedNoise = float(0.5).add(float(0.5).mul(rawNoise))const colorNode = mix(blue, lightBlue, adjustedNoise)
```## Resources
- [GLSL to TSL transpiler](https://threejs.org/examples/?q=webgpu#webgpu_tsl_transpiler)
- [TSL examples](https://threejs.org/examples/?q=tsl)