3d-cloth-material
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
Chinese3D Cloth Material
3D 布料材质
Mechanism: hang the cloth as rows whose tangent angle is the fold signal, so arc length equals the rest coordinate and the weave never stretches. Then let a thread-level weave, sheen, hem thickness and light through the gaps do the reading of "fabric".
sNearest neighbours: chooses texel density, mipmaps and delivery for any material; use it for the budget and stay here for what makes cloth different (weave interlacement, folds, sheen, hems). , and cover their own surfaces; this skill owns woven and sewn fabric only. It is not a cloth simulation: for a character's flowing cape or a flag that collides, simulate (Verlet or Blender cloth) and bake, then keep the material rules below.
3d-high-resolution-textures3d-wood-material3d-paper-material3d-metal-materialExtracted from KIBORI 木彫, a dark WebGL workshop where a roll of indigo canvas (the dōgu-maki) lies under a warm key light and had to survive a macro close-up. Ported from there: the weave bake, the stitch shader, half-circle hem turn-under, wear on thread tops, the sheen constants. Newly built for this skill (Kibori has one indigo canvas, not three fabrics): the tangent-angle fold curve, satin and twill interlacements, silk/wool/linen tables, tabs on the rod, raw-edge fray, fold AO, backlit transmission, wind. is the reference.
demo.htmlDemo: Three.js r169 · WebGL · GLSL ( + ), vanilla JavaScript, no post chain.
MeshPhysicalMaterialonBeforeCompile原理: 将布料悬挂为逐行结构,并以切线角表示褶皱信号,使弧长等于静止坐标 ,因此织纹永不拉伸。随后借助线级织纹、Sheen、折边厚度以及穿过缝隙的光线来呈现“织物”质感。
s最相关的 skill: 负责任何材质的纹素密度、Mipmap 和资源交付方式;用它来控制预算,并留在本 skill 中处理布料特有的部分(编织交错、褶皱、Sheen、折边)。、 和 负责各自的表面;本 skill 仅负责编织和缝制织物。它不是布料模拟:若需角色飘逸的披风或会与物体碰撞的旗帜,应先进行模拟(Verlet 或 Blender cloth)并烘焙,然后继续遵循以下材质规则。
3d-high-resolution-textures3d-wood-material3d-paper-material3d-metal-material提取自 KIBORI 木彫——一个深色 WebGL 工坊,暖色主光下放着一卷靛蓝色帆布(dōgu-maki),并且必须经得住微距特写。由此移植了:织纹烘焙、针脚着色器、半圆形折边内翻、线顶磨损以及 Sheen 常量。为本 skill 新建(Kibori 只有一种靛蓝帆布,而不是三种布料):切线角褶皱曲线、缎纹与斜纹交错、丝绸/羊毛/亚麻参数表、挂杆上的挂袢、毛边流苏、褶皱 AO、背光透射以及风动。 为参考实现。
demo.html演示:Three.js r169 · WebGL · GLSL( + ),原生 JavaScript,无后处理链。
MeshPhysicalMaterialonBeforeCompileThe rules, each with the failure it prevents
各项规则及其所防止的问题
- Integrate folds from an angle, not a height. , then
α(s) = a·(sinθ + 0.16 sin(2θ+0.8)) + …,x += ds·cos α. Failure: a height fieldz += ds·sin αgives arc length 1 + slope², so the weave swims and stretches 30–80% on every fold. With the angle formz = A·sin(kx)in metres is exact. Keepuv = (s, v)rad; past that it clamps into flat plateaus and folds become tubes with black seams.|α| < 1.45 - Uv is material metres, never re-fitted per frame. Do not recompute uv from the moving surface. Failure: weave shimmers and crawls in wind. Set so one texel tile is
texture.repeat = 1/(threads × pitch)threads; linen 1.6 mm, silk 0.7 mm, wool 2.6 mm pitch.NT - Bake interlacement, not noise. Each thread has its own width (0.80–0.97), tone and a slub (Gaussian thickening up to 0.34). Warp height blends over/under across cell borders by . Plain =
0.5·smoothstep(0.05, 0.5, |t|), twill 2/1 =(A+B)&1, 5-harness satin =(A+B)%3 < 2warp-over.(2A+B)%5 != 0must be a multiple of the repeat (32, 24, 40) or the tile shows a seam. Failure: a tiled noise normal map reads as stucco or leather.NT - Spun yarn gets a twist. Add to each thread height (twist 0.10–0.14 for linen and wool, 0 for silk). Failure: linen looks like wire mesh.
0.22·twist·sin(2π(5·along + 1.3·across)) - Two dyes, per-thread tone. Colour ; silk uses shot 1.0 (madder red warp, gold weft), the rest 0. Tone
mix(warpDye, weftDye, weftOnTop·shot), cavitymix(0.86, 1.14, threadTone), blotch + warp-direction streaksmix(0.5, 1, smoothstep(0.05, 0.85, height)). Failure: one flat albedo on a woven map looks printed.1 + var·((blot−0.5)·0.62 + (streak−0.5)·0.22) - Sheen is the fabric, and it must be small. ,
sheen 0.5–1.0, andsheenRoughness 0.28 (silk) – 0.82 (wool). Failure: near-whitesheenColor = dye lightened × 0.62blows out to a milky rim under a warm key. Never setsheenColorto exactly 0 at runtime (0.0001); crossing zero recompiles the program and hitches 200+ ms.sheen - Silk gets anisotropy, wool gets fuzz. Silk ; linen
anisotropy 0.85, roughness 0.36rough with sheen 0.55; wool0.90rough with sheen 1.0. Keep0.96above 0 at creation (0.0001) so the define never flips.anisotropy - Fold occlusion is not optional. Cast and receive the key's shadow map (,
normalBias 0.012,bias −0.0004shadows) and add a vertex AO from the fold depthDoubleSideon indirect light. Failure: without both, valleys light up like the crests and the folds look painted.0.62 + 0.38·smoothstep(−0.075, 0.035, zFold) - Edges have thickness. Turn every free edge under on a half circle, ,
P = edge + out·r·sinφ − N·r(1−cosφ),φ ∈ [0, 0.94π]= 1.1 mm silk, 2.2 mm linen, 4.6 mm wool. Return the bottom hem up the back atrwith flipped normals. Failure: a zero-thickness cut edge is the loudest tell for CG cloth in a close-up.2r + 0.2 mm - Stitch in the shader, in cloth metres. Thread arches between holes (over 74% of the pitch), the needle groove and pucker feed the normal by finite difference, faded by
4·x(1−x). Hem 3 cm up, sides 2.2 cm in, seamfwidthwith a proud ridge that puckers every 4 pitches. Failure: geometry stitches z-fight and alias; texture-painted ones do not follow the folds.±7 mm - Raw edge: draw out the weft. Beyond the cut, discard fragments except the warp threads (), each with a random length
|fract(u/pitch)−0.5| < 0.36. Failure: an alpha fringe texture has no thread structure.F·(0.3+0.7·hash) - Thin cloth passes light. with
emissive += trans · lightColour · dye·(1.7,1.2,0.85) · pow(max(0, −N·L), 1.15) · gap · thinso threads block and gaps pass. Silk 1.05, linen 0.6, wool 0.06. Failure: without it a lit window behind a curtain does nothing.gap = mix(1, 0.42, height) - Wear where cloth is touched. → mix dye toward a pale colour by
wear = clamp(aWear·(0.25+height) + (fbm−0.5)·0.3, 0, 1). Hems +0.4, crests +0.3. Failure: uniform dye reads brand new.wear·threadTop
- 从角度而非高度积分褶皱。 ,然后
α(s) = a·(sinθ + 0.16 sin(2θ+0.8)) + …、x += ds·cos α。失败:高度场z += ds·sin α的弧长为 1 + slope²,因此每个褶皱处的织纹都会游移并拉伸 30–80%。采用角度形式后,z = A·sin(kx)以米为单位可精确对应。保持uv = (s, v)rad;超过后会钳制为平坦平台,褶皱会变成带黑缝的管状。|α| < 1.45 - UV 是材质米制坐标,绝不逐帧重新拟合。 不要根据移动中的表面重新计算 UV。失败:织纹在风中会闪烁并爬行。设置 ,使每个贴图周期包含
texture.repeat = 1/(threads × pitch)根纱线;亚麻间距为 1.6 mm,丝绸为 0.7 mm,羊毛为 2.6 mm。NT - 烘焙交错结构,而不是噪声。 每根纱线都有自己的宽度(0.80–0.97)、色调和粗节(高斯增粗最高 0.34)。经纱高度通过 在单元边界处混合上下关系。平纹 =
0.5·smoothstep(0.05, 0.5, |t|),斜纹 2/1 =(A+B)&1,5 枚缎纹 =(A+B)%3 < 2表示经纱在上。(2A+B)%5 != 0必须是 repeat 的倍数(32、24 或 40),否则图块会显示接缝。失败:平铺噪声法线贴图看起来像灰泥或皮革。NT - 短纤纱线需要捻度。 将 添加到每根纱线的高度中(亚麻和羊毛的 twist 为 0.10–0.14,丝绸为 0)。失败:亚麻会看起来像金属网。
0.22·twist·sin(2π(5·along + 1.3·across)) - 使用两种染料和逐纱线色调。 颜色为 ;丝绸使用 shot 1.0(茜红经线、金色纬线),其余为 0。色调为
mix(warpDye, weftDye, weftOnTop·shot),凹陷区域为mix(0.86, 1.14, threadTone),斑块与经向条纹为mix(0.5, 1, smoothstep(0.05, 0.85, height))。失败:在编织贴图上使用单一平坦的 albedo 会显得像印花。1 + var·((blot−0.5)·0.62 + (streak−0.5)·0.22) - Sheen 才体现织物感,而且必须很弱。 ,
sheen 0.5–1.0,并且sheenRoughness 0.28(丝绸)– 0.82(羊毛)。失败:接近白色的sheenColor = 染料提亮值 × 0.62在暖色主光下会过曝成乳白色边缘。运行时绝不要将sheenColor精确设为 0(应设为 0.0001);跨过零点会重新编译程序,并造成超过 200 ms 的卡顿。sheen - 丝绸使用各向异性,羊毛使用绒毛。 丝绸为 ;亚麻为
anisotropy 0.85, roughness 0.36roughness、sheen 0.55;羊毛为0.90roughness、sheen 1.0。创建时保持0.96大于 0(0.0001),确保 define 不会发生翻转。anisotropy - 褶皱遮蔽不可省略。 投射并接收主光的 shadow map(、
normalBias 0.012、bias −0.0004阴影),并根据褶皱深度DoubleSide在间接光上添加 vertex AO。失败:如果缺少两者,褶皱谷底会像峰顶一样明亮,褶皱看起来像是画上去的。0.62 + 0.38·smoothstep(−0.075, 0.035, zFold) - 边缘必须具有厚度。 每条自由边都沿半圆向内翻折,,
P = edge + out·r·sinφ − N·r(1−cosφ),φ ∈ [0, 0.94π]= 丝绸 1.1 mm、亚麻 2.2 mm、羊毛 4.6 mm。将底部折边沿背面回折到r,并翻转法线。失败:零厚度切边是 CG 布料特写中最明显的破绽。2r + 0.2 mm - 在着色器中以布料米制坐标缝制。 纱线在针孔之间形成拱形(,覆盖间距的 74%),针槽和褶皱通过有限差分影响法线,并由
4·x(1−x)淡出。折边向上 3 cm,侧边向内 2.2 cm,接缝位于 ±7 mm,并带有一道凸起脊线,每 4 个间距产生一次褶皱。失败:几何针脚会发生 Z-fighting 和 alias;贴图绘制的针脚则无法跟随褶皱。fwidth - 毛边:抽出纬纱。 在切口之外,除经纱线程()外丢弃所有片元,每根经纱的长度为随机值
|fract(u/pitch)−0.5| < 0.36。失败:alpha 边缘贴图没有真实的纱线结构。F·(0.3+0.7·hash) - 薄布可以透光。 ,其中
emissive += trans · lightColour · dye·(1.7,1.2,0.85) · pow(max(0, −N·L), 1.15) · gap · thin,让纱线阻挡光线、缝隙透过光线。丝绸为 1.05,亚麻为 0.6,羊毛为 0.06。失败:没有该效果时,窗帘后方被照亮的窗户不会产生任何透光效果。gap = mix(1, 0.42, height) - 布料被接触的位置产生磨损。 ,然后通过
wear = clamp(aWear·(0.25+height) + (fbm−0.5)·0.3, 0, 1)将染料混合为浅色。折边增加 0.4,褶皱峰顶增加 0.3。失败:均匀的染色会显得全新。wear·threadTop
Constants
常量
| linen | silk | wool | |
|---|---|---|---|
| weave / NT / pitch | plain / 32 / 1.6 mm | 5-harness satin / 40 / 0.7 mm | twill / 24 / 2.6 mm |
| normal strength S · normalScale | 2.6 · 1.15 | 1.5 · 0.6 | 2.9 · 1.45 |
| roughness · sheen · sheenR | 0.90 · 0.55 · 0.55 | 0.36 · 0.5 · 0.28 | 0.96 · 1.0 · 0.82 |
| fold λ · amax · wind gain | 0.34 m · 0.98 · 1.0 | 0.40 · 1.02 · 1.9 | 0.32 · 0.86 · 0.55 |
| edge | raw fray 3 cm | hem 3.5 cm | hem 5 cm |
Cloth 2.0 × 1.95 m, grid 160 × 120 (≈ 21k verts, 45k tris). Key SpotLight 0xffd0a0 × 3.0, angle 0.44, decay 0; cool fill 1.0; window back light 0.2–1.8; environment intensity 0.42; ACES, exposure 1.0.
| 亚麻 | 丝绸 | 羊毛 | |
|---|---|---|---|
| 编织方式 / NT / 间距 | 平纹 / 32 / 1.6 mm | 5 枚缎纹 / 40 / 0.7 mm | 斜纹 / 24 / 2.6 mm |
| 法线强度 S · normalScale | 2.6 · 1.15 | 1.5 · 0.6 | 2.9 · 1.45 |
| roughness · sheen · sheenR | 0.90 · 0.55 · 0.55 | 0.36 · 0.5 · 0.28 | 0.96 · 1.0 · 0.82 |
| 褶皱 λ · amax · 风增益 | 0.34 m · 0.98 · 1.0 | 0.40 · 1.02 · 1.9 | 0.32 · 0.86 · 0.55 |
| 边缘 | 3 cm 毛边 | 3.5 cm 折边 | 5 cm 折边 |
布料尺寸 2.0 × 1.95 m,网格 160 × 120(≈ 21k 个顶点,45k 个三角形)。主 SpotLight 为 0xffd0a0 × 3.0,angle 0.44,decay 0;冷色补光为 1.0;窗户背光为 0.2–1.8;环境强度为 0.42;ACES,exposure 1.0。
Gotchas, symptom first
常见问题:先看症状
- Weave crawls or shimmers when it moves → uv was rebuilt from arc length or scrolled; keep it as the rest metres.
- Horizontal moire stripes at wide view → bump/crease term uses of a high-frequency noise; keep crease octaves below 17 cycles/m and scale by 0.016. Mipmaps + 16× anisotropy handle the weave itself.
dFdx - Folds are flat panels with black slits → clamped. Lower
|α|soamax, do not add more darkness.a·env·1.28 < 1.45 - Everything glows orange when backlit → transmission colour multiplied by a warm light and a warm dye. Tint by , not
(1.7,1.2,0.85).(2.1,1.35,0.72) - envMapIntensity does nothing → in r163+ it only applies with ; with
material.envMapusescene.environment.scene.environmentIntensity - shader is shared between two meshes with different uniforms → set
onBeforeCompile, and put uniforms on the material, not the mesh.customProgramCacheKey - Winding wrong on a hem strip (lit inside-out) → pick each strip's index order from the sign of its first triangle normal against the attribute normal, once, after the first update.
- Turn-under leaves a dark gap → the return strip must sit at , not
2r + 0.2 mm.r - Shadow acne on a double-sided sheet → , not a bigger
normalBias; a large bias detaches the fold shadows.bias
- 织纹在移动时爬行或闪烁 → UV 是根据弧长重建或被滚动的;应保持为静止状态下的米制坐标。
- 远景出现水平摩尔条纹 → bump/crease 项使用了高频噪声的 ;折痕倍频应保持在每米 17 个周期以下,并按 0.016 缩放。织纹本身由 Mipmap + 16× anisotropy 处理。
dFdx - 褶皱变成带黑缝的平板 → 被钳制。降低
|α|,使amax,不要继续增加暗度。a·env·1.28 < 1.45 - 逆光时一切发橙 → transmission 颜色同时乘以暖色光和暖色染料。按 着色,不要使用
(1.7,1.2,0.85)。(2.1,1.35,0.72) - 无效 → 在 r163+ 中,它仅在存在
envMapIntensity时生效;使用material.envMap时应设置scene.environment。scene.environmentIntensity - 着色器被两个具有不同 uniforms 的 mesh 共享 → 设置
onBeforeCompile,并将 uniforms 放在 material 上,而不是 mesh 上。customProgramCacheKey - 折边条带绕序错误,内部受光反了 → 在首次更新后,依据第一个三角形法线相对于属性法线的符号,为每条带选择索引顺序,并且只执行一次。
- 向内翻折留下黑色缝隙 → 回折条带必须位于 ,而不是
2r + 0.2 mm。r - 双面薄片出现 shadow acne → 使用 ,不要增大
normalBias;过大的 bias 会让褶皱阴影脱离物体。bias
Lifecycle
生命周期
prefers-reduced-motiont = 7.3document.hiddenlastdtResizeObserverpositionnormalprefers-reduced-motiont = 7.3document.hiddenlastdtResizeObserverpositionnormalCost (measured, headless Chrome for Testing, Apple GPU, 1440×900 at DPR 2)
成本(实测,无头 Chrome for Testing,Apple GPU,1440×900,DPR 2)
- Cloth CPU (folds + normals + hems + tabs + fringe): 3.7–4.9 ms at 160×120. Halving the row count (190 → 120) bought −40%, and no fold was lost, because folds vary slowly down the drop.
- Whole frame: 10–11 ms wide, 15 ms macro. The macro's extra 4 ms is the fragment shader (weave + stitch + fbm) over the whole screen, not geometry.
- Boot: 0.8 s to first frame including three 512² weave bakes. Fabric switch 25 ms. Layer toggles 14 ms.
- Not the bottleneck: triangle count, the 2048 shadow map, tabs, fringe (520 strands).
- 布料 CPU(褶皱 + 法线 + 折边 + 挂袢 + 流苏):在 160×120 下为 3.7–4.9 ms。将行数减半(190 → 120)带来了 −40% 的提升,且没有丢失任何褶皱,因为褶皱沿垂落方向变化缓慢。
- 整帧:广角为 10–11 ms,微距为 15 ms。微距额外增加的 4 ms 来自覆盖整个屏幕的片元着色器(织纹 + 针脚 + fbm),而非几何体。
- 启动:0.8 s 到达首帧,包括三次 512² 织纹烘焙。布料切换为 25 ms。图层开关为 14 ms。
- 并非瓶颈:三角形数量、2048 shadow map、挂袢、流苏(520 根)。
Score against the rubric (0 = flat coloured plane, 5 = convincing at arm's length, 10 = photographic macro)
评分标准得分(0 = 平坦着色平面,5 = 手臂长度距离下具有说服力,10 = 照片级微距)
Weave structure 7 · Sheen and dye 6.5 · Fold shape and drape 6 (a hanging curtain, not free cloth with self-contact) · Edges, stitches, seams 7.5 · Light transmission 6 · Wear 5.5 · Motion 5.5 (wind is analytic, no collision) · Performance 8. Overall 6.5. What would lift it: real self-collision folds (simulate and bake), fibre halo geometry on wool, a second normal scale for creases.
织纹结构 7 · Sheen 与染色 6.5 · 褶皱形态与垂坠 6(悬挂窗帘,而非带自接触的自由布料)· 边缘、针脚、接缝 7.5 · 光线透射 6 · 磨损 5.5 · 运动 5.5(风为解析式,无碰撞)· 性能 8。总分 6.5。可提升之处:真实的自碰撞褶皱(模拟并烘焙)、羊毛的纤维光晕几何体,以及用于折痕的第二组法线缩放。