3d-wood-material

Installation
SKILL.md

3D Wood Material

Mechanism: one small periodic noise field, mip-filtered, is read at several different stretches and scales inside the fragment shader, so ring position, latewood, pores, fibres, rays and tool marks all come from the same wandering grain and feed colour, roughness and relief together, each fading out by its own screen footprint.

Boundary. This skill is the wood surface itself. For whole-scene light, rays and scoring wood renders, use 3d-wood-lighting-scorecard. For image-based PBR sets (downloaded maps, texel budgets, KTX2 delivery) use 3d-high-resolution-textures; reach for it when you need a photographed or scanned species. For silhouette, bevel and LOD geometry use 3d-high-poly-models; this skill only needs a rounded arris (below). Cloth, metal and paper have their own siblings.

Run demo.html first (Kibori bench, four species, four finishes, macro views, and a switch that swaps in the failure). PROMPT.md recreates it.

Recipe

  1. Patch, do not replace. Build MeshPhysicalMaterial({color:0xffffff, roughness:max(0.43,r), ior:1.43, specularIntensity:0.72}) and edit it in onBeforeCompile: #include <map_fragment> multiplies diffuseColor by the wood colour, #include <roughnessmap_fragment> sets roughnessFactor=clamp(roughness*W.rough,0.35,1), #include <normal_fragment_maps> replaces the normal with a screen-space bump of the wood height W.h. Lighting, shadows, IBL and tone-mapping stay stock. The vertex stage only passes object-space position vOP and the object normal.
  2. Bake one field. A 1024² RepeatWrapping, LinearMipmapLinear, NoColorSpace render target of periodic gradient noise (period 64, three octaves: .r base, .g fbm 0.60/0.27/0.13, .b a shifted copy). Reading it as texture(p/64) costs one tap. All timber shares it; per-board difference is a seed offset, not a texture.
  3. Grain axis. uAxis 0/1/2 picks the log axis; along is that coordinate and cross2 the other two. endgrain = pow(|n·axis|, 6) flips pores from streaks to open cells and dulls the colour on cut faces.
  4. Rings. Drift the pith with two slow fields, radius=|(cross2+(-drift, offAxis+0.48))*(1,0.56)|, growth=radius*ringFreq plus fbm wobble (±1.25 rings), ring=floor(growth), phase=fract. Each ring draws its own width from annual noise: lateWidth=0.065+annual*0.21. Latewood is a steep smoothstep(0.94-w, 0.97-w, phase) cut off by 1-smoothstep(0.965,1,phase). Small offAxis gives cathedral arcs; large offAxis gives straight quarter-sawn lines.
  5. Detail layers, each faded by its own footprint (fwidth of growth, length(dFdx,dFdy) of the pore, fibre and ray coordinates):
Installs
243
Repository
mengto/skills
GitHub Stars
6.9K
First Seen
Sep 30, 2026