使用自定义shader渲染的材质。 shader是一个用GLSL编写的小程序 ,在GPU上运行。 您可能需要使用自定义shader,如果你要:
#pragma unroll_loop_start
for (int i = 0; i < 10; i++) {
// ...
}
#pragma unroll_loop_end
const material = new v3d.ShaderMaterial({
uniforms: {
time: { value: 1.0 },
resolution: { value: new v3d.Vector2() }
},
vertexShader: document.getElementById('vertexShader').textContent,
fragmentShader: document.getElementById('fragmentShader').textContent
});
webgl / animation / cloth
webgl / buffergeometry / custom / attributes / particles
webgl / buffergeometry / selective / draw
webgl / custom / attributes
webgl / custom / attributes / lines
webgl / custom / attributes / points
webgl / custom / attributes / points2
webgl / custom / attributes / points3
webgl / depth / texture
webgl / gpgpu / birds
webgl / gpgpu / protoplanet
webgl / gpgpu / water
webgl / hdr
webgl / interactive / points
webgl / kinect
webgl / lights / hemisphere
webgl / marchingcubes
webgl / materials / bumpmap / skin
webgl / materials / envmaps
webgl / materials / lightmap
webgl / materials / parallaxmap
webgl / materials / shaders / fresnel
webgl / materials / skin
webgl / materials / texture / hdr
webgl / materials / wireframe
webgl / modifier / tessellation
webgl / postprocessing / dof2
webgl / postprocessing / godrays
您可以为每种材质指定两种不同类型的shaders::
shader中有三种类型的变量: uniforms, attributes, 和 varyings:
注意:在shader 内部,uniforms和attributes就像常量;你只能使用JavaScript代码通过缓冲区来修改它们的值。
WebGLRenderer默认情况下为shader提供了许多attributes和uniforms; 这些变量定义在shader程序编译时被自动添加到片元着色器和顶点着色器代码的前面,你不需要自己声明它们。 这些变量的描述请参见WebGLProgram。
这些uniforms或attributes(例如,那些和照明,雾等相关的)要求属性设置在材质上, 以便 WebGLRenderer来拷贝合适的值到GPU中。 如果你想在自己的shader中使用这些功能,请确保设置这些标志。
如果你不希望WebGLProgram 向你的shader代码中添加任何东西, 你可以使用RawShaderMaterial 而不是这个类。
自定义attributes和uniforms必须在GLSL着色器代码中声明(在 vertexShader 和/或 fragmentShader 中)。 自定义uniforms必须定义为 ShaderMaterial 的 uniforms 属性, 而任何自定义attribtes必须通过BufferAttribute实例来定义。 注意 varyings 只需要在shader代码中声明(而不必在材质中)。
要声明一个自定义属性,更多细节请参考BufferGeometry页面, 以及 BufferAttribute 页面关于BufferAttribute 接口。
当创建attributes时,您创建的用来保存属性数据的每个类型化数组(typed array)必须是您的数据类型大小的倍数。 比如,如果你的属性是一个v3d.Vector3类型,并且在你的缓存几何模型BufferGeometry中有3000个顶点, 那么你的类型化数组的长度必须是3000 * 3,或者9000(一个顶点一个值)。每个数据类型的尺寸如下表所示:
GLSL 类型 | JavaScript 类型 | 尺寸 |
---|---|---|
float | Number | 1 |
vec2 | v3d.Vector2 | 2 |
vec3 | v3d.Vector3 | 3 |
vec3 | v3d.Color | 3 |
vec4 | v3d.Vector4 | 4 |
请注意,属性缓冲区 不会 在其值更改时自动刷新。要更新自定义属性, 需要在模型的BufferAttribute中设置needsUpdate为true。 (查看BufferGeometry了解细节)。
要声明一个自定义的Uniform,使用uniforms属性:
uniforms: {
time: { value: 1.0 },
resolution: { value: new v3d.Vector2() }
}
在Object3D.onBeforeRender中,建议根据object和camera来更新自定义Uniform的值。 因为 Material 可以被meshes,Scene的matrixWorld以及Camera共享, 会在WebGLRenderer.render中更新,并会对拥有私有cameras的scene的渲染造成影响。
parameters — (可选)用于定义材质外观的对象,具有一个或多个属性。 材质的任何属性都可以从此处传入(包括从Material继承的任何属性)。
共有属性请参见其基类Material。
定义此材质是否支持剪裁; 如果渲染器传递clippingPlanes uniform,则为true。默认值为false。
当渲染的几何体不包含这些属性但材质包含这些属性时,这些默认值将传递给shaders。这可以避免在缓冲区数据丢失时出错。
this.defaultAttributeValues = {
'color': [1, 1, 1],
'uv': [0, 0],
'uv2': [0, 0]
};
使用 #define 指令在GLSL代码为顶点着色器和片段着色器定义自定义常量;每个键/值对产生一行定义语句:
defines: {
FOO: 15,
BAR: true
}
这将在GLSL代码中产生如下定义语句:
#define FOO 15
#define BAR true
一个有如下属性的对象:
this.extensions = {
derivatives: false, // set to use derivatives
fragDepth: false, // set to use fragment depth values
drawBuffers: false, // set to use draw buffers
shaderTextureLOD: false // set to use shader texture LOD
};
定义材质颜色是否受全局雾设置的影响; 如果将fog uniforms传递给shader,则为true。默认值为false。
片元着色器的GLSL代码。这是shader程序的实际代码。在上面的例子中, vertexShader 和 fragmentShader 代码是从DOM(HTML文档)中获取的; 它也可以作为一个字符串直接传递或者通过AJAX加载。
Defines the GLSL version of custom shader code. Only relevant for WebGL 2 in order to define whether to specify GLSL 3.0 or not. Valid values are v3d.GLSL1 or v3d.GLSL3. Default is null.
如果设置,则调用gl.bindAttribLocation 将通用顶点索引绑定到属性变量。默认值未定义。
材质是否受到光照的影响。默认值为 false。如果传递与光照相关的uniform数据到这个材质,则为true。默认是false。
控制线框宽度。默认值为1。
由于OpenGL Core Profile与大多数平台上WebGL渲染器的限制,无论如何设置该值,线宽始终为1。
When set to true, morph target attributes are available in the vertex shader. Default is false.
When set to true, morph normal attributes are available in the vertex shader. Default is false.
定义材质是否使用平面着色进行渲染。默认值为false。
定义材质是否使用蒙皮; 如果将蒙皮属性传递给shader,则为true。默认值为false。
如下形式的对象:
{ "uniform1": { value: 1.0 }, "uniform2": { value: 2 } }
指定要传递给shader代码的uniforms;键为uniform的名称,值(value)是如下形式:
{ value: 1.0 }
这里 value 是uniform的值。名称必须匹配 uniform 的name,和GLSL代码中的定义一样。
注意,uniforms逐帧被刷新,所以更新uniform值将立即更新GLSL代码中的相应值。
Can be used to force a uniform update while changing uniforms in Object3D.onBeforeRender(). Default is false.
Defines whether vertex coloring is used. Default is false.
顶点着色器的GLSL代码。这是shader程序的实际代码。 在上面的例子中,vertexShader 和 fragmentShader 代码是从DOM(HTML文档)中获取的; 它也可以作为一个字符串直接传递或者通过AJAX加载。
将几何体渲染为线框(通过GL_LINES而不是GL_TRIANGLES)。默认值为false(即渲染为平面多边形)。
控制线框宽度。默认值为1。
由于OpenGL Core Profile与大多数平台上WebGL渲染器的限制,无论如何设置该值,线宽始终为1。
共有方法请参见其基类Material。
创建该材质的一个浅拷贝。需要注意的是,vertexShader和fragmentShader使用引用拷贝; attributes的定义也是如此; 这意味着,克隆的材质将共享相同的编译WebGLProgram; 但是,uniforms 是 值拷贝,这样对不同的材质我们可以有不同的uniforms变量。