解释有什么问题,说一下,不喜勿喷,
转载请注明:七岁 https://blog.csdn.net/qq_25909453/article/details/82704620
/**
* @author mrdoob / http://mrdoob.com/
*/
import { NotEqualDepth, GreaterDepth, GreaterEqualDepth, EqualDepth, LessEqualDepth, LessDepth, AlwaysDepth, NeverDepth, CullFaceFront, CullFaceBack, CullFaceNone, CustomBlending, MultiplyBlending, SubtractiveBlending, AdditiveBlending, NoBlending, NormalBlending, DoubleSide, BackSide } from '../../constants.js';
import { Vector4 } from '../../math/Vector4.js';
function WebGLState( gl, extensions, utils, capabilities ) {
/**
* 颜色缓冲
* @returns {{setMask: setMask, setLocked: setLocked, setClear: setClear, reset: reset}}
* @constructor
*/
function ColorBuffer() {
//是否加锁
var locked = false;
var color = new Vector4();
//当前能否写入颜色帧缓冲区
var currentColorMask = null;
//当前清除颜色,清除后的背景颜色
var currentColorClear = new Vector4( 0, 0, 0, 0 );
return {
/**
* 设置能否写入颜色帧缓冲区
* @param colorMask
*/
setMask: function ( colorMask ) {
//如果用户改变了颜色帧缓冲区的写入状态并且没有加锁
if ( currentColorMask !== colorMask && ! locked ) {
//重新设置颜色帧缓冲区的写入状态
gl.colorMask( colorMask, colorMask, colorMask, colorMask );
//记录当前颜色帧缓冲区的状态
currentColorMask = colorMask;
}
},
//设置是否加锁,如果lock为true,则表示一直已经加锁,颜色帧缓冲区的写入状态不能改变
setLocked: function ( lock ) {
locked = lock;
},
//设置背景颜色;premultipliedAlpha表示是否需要增加透明效果
setClear: function ( r, g, b, a, premultipliedAlpha ) {
if ( premultipliedAlpha === true ) {
r *= a; g *= a; b *= a;
}
color.set( r, g, b, a );
if ( currentColorClear.equals( color ) === false ) {
gl.clearColor( r, g, b, a );
currentColorClear.copy( color );
}
},
//重置相关设置
reset: function () {
locked = false;
currentColorMask = null;
currentColorClear.set( - 1, 0, 0, 0 ); // set to invalid state
}
};
}
//关于深度缓冲的设置
function DepthBuffer() {
//是否加锁
var locked = false;
//表示是否可以对深度缓冲区进行修改
var currentDepthMask = null;
var currentDepthFunc = null;
var currentDepthClear = null;
return {
//设置是否开启深度检测
setTest: function ( depthTest ) {
if ( depthTest ) {
enable( gl.DEPTH_TEST );
} else {
disable( gl.DEPTH_TEST );
}
},
//设置是否可以对深度缓冲区进行修改
setMask: function ( depthMask ) {
if ( currentDepthMask !== depthMask && ! locked ) {
gl.depthMask( depthMask );
currentDepthMask = depthMask;
}
},
/**
* 此函数的作用是确定深度值的比较方式。
每画一个物体,设备中将存储每个像素点的深度值,如果需要新绘制一个物体A,则对应像素处的深度值需要
和深度缓冲区的值进行比较,默认情况下,gl.depthFunc( GL_LESS),也就是在对于某个像素处,A的深度值小于
帧缓冲区中对应的深度值才会取A的颜色,否则不会发生改变
* @param depthFunc
*/
setFunc: function ( depthFunc ) {
if ( currentDepthFunc !== depthFunc ) {
if ( depthFunc ) {
switch ( depthFunc ) {
case NeverDepth:
gl.depthFunc( gl.NEVER );
break;
case AlwaysDepth:
gl.depthFunc( gl.ALWAYS );
break;
case LessDepth:
gl.depthFunc( gl.LESS );
break;
case LessEqualDepth:
gl.depthFunc( gl.LEQUAL );
break;
case EqualDepth:
gl.depthFunc( gl.EQUAL );
break;
case GreaterEqualDepth:
gl.depthFunc( gl.GEQUAL );
break;
case GreaterDepth:
gl.depthFunc( gl.GREATER );
break;
case NotEqualDepth:
gl.depthFunc( gl.NOTEQUAL );
break;
default:
gl.depthFunc( gl.LEQUAL );
}
} else {
gl.depthFunc( gl.LEQUAL );
}
currentDepthFunc = depthFunc;
}
},
//表示深度缓冲区设置是否可以进行更改
setLocked: function ( lock ) {
locked = lock;
},
//清除深度缓冲区,depth值为要设置的深度缓冲区的值,取值范围为【0-1】
setClear: function ( depth ) {
if ( currentDepthClear !== depth ) {
gl.clearDepth( depth );
currentDepthClear = depth;
}
},
//重置关于深度缓冲的相关设置
reset: function () {
locked = false;
currentDepthMask = null;
currentDepthFunc = null;
currentDepthClear = null;
}
};
}
/**
* 模板缓冲的相关设置,模板缓冲的值取值范围为[0-2的n次方-1],其中n代表模板缓冲值在2进制下
* @returns {{setTest: setTest, setMask: setMask, setFunc: setFunc, setOp: setOp, setLocked: setLocked, setClear: setClear, reset: reset}}
* @constructor
* 相关介绍;http://blog.csdn.net/wangdingqiaoit/article/details/52143197
*/
function StencilBuffer() {
var locked = false;
var currentStencilMask = null;
var currentStencilFunc = null;
var currentStencilRef = null;
var currentStencilFuncMask = null;
var currentStencilFail = null;
var currentStencilZFail = null;
var currentStencilZPass = null;
var currentStencilClear = null;
return {
//是否开启模板测试
setTest: function ( stencilTest ) {
if ( stencilTest ) {
enable( gl.STENCIL_TEST );
} else {
disable( gl.STENCIL_TEST );
}
},
//设置是否可以对模板缓冲区进行写入和修改
setMask: function ( stencilMask ) {
if ( currentStencilMask !== stencilMask && ! locked ) {
gl.stencilMask( stencilMask );
currentStencilMask = stencilMask;
}
},
//设置模板缓冲的比较方式
setFunc: function ( stencilFunc, stencilRef, stencilMask ) {
if ( currentStencilFunc !== stencilFunc ||
currentStencilRef !== stencilRef ||
currentStencilFuncMask !== stencilMask ) {
gl.stencilFunc( stencilFunc, stencilRef, stencilMask );
currentStencilFunc = stencilFunc;
currentStencilRef = stencilRef;
currentStencilFuncMask = stencilMask;
}
},
/*stencilFail代表的是模板测试失败,对应模板缓冲区的值应该进行的操作,可选的值有
GL_KEEP,GL_ZERO,GL_REPLACE,GL_INCR,GL_INCR_WRAP,GL_DECR,GL_DECR_WRAP,GL_INVERT
stencilZFail代表的是模板测试成功,但是深度检测没有通过后的操作,可选的值和上面的相同
stencilZPass代表的是模板测试和深度检测都通过时,可选择的值和上面相同*/
setOp: function ( stencilFail, stencilZFail, stencilZPass ) {
if ( currentStencilFail !== stencilFail ||
currentStencilZFail !== stencilZFail ||
currentStencilZPass !== stencilZPass ) {
gl.stencilOp( stencilFail, stencilZFail, stencilZPass );
currentStencilFail = stencilFail;
currentStencilZFail = stencilZFail;
currentStencilZPass = stencilZPass;
}
},
setLocked: function ( lock ) {
locked = lock;
},
setClear: function ( stencil ) {
if ( currentStencilClear !== stencil ) {
gl.clearStencil( stencil );
currentStencilClear = stencil;
}
},
reset: function () {
locked = false;
currentStencilMask = null;
currentStencilFunc = null;
currentStencilRef = null;
currentStencilFuncMask = null;
currentStencilFail = null;
currentStencilZFail = null;
currentStencilZPass = null;
currentStencilClear = null;
}
};
}
//
var colorBuffer = new ColorBuffer();
var depthBuffer = new DepthBuffer();
var stencilBuffer = new StencilBuffer();
//从系统最多支持的顶点属性个数
var maxVertexAttributes = gl.getParameter( gl.MAX_VERTEX_ATTRIBS );
var newAttributes = new Uint8Array( maxVertexAttributes );
var enabledAttributes = new Uint8Array( maxVertexAttributes );
var attributeDivisors = new Uint8Array( maxVertexAttributes );
var enabledCapabilities = {};
var compressedTextureFormats = null;
var currentProgram = null;
var currentBlending = null;
var currentBlendEquation = null;
var currentBlendSrc = null;
var currentBlendDst = null;
var currentBlendEquationAlpha = null;
var currentBlendSrcAlpha = null;
var currentBlendDstAlpha = null;
var currentPremultipledAlpha = false;
var currentFlipSided = null;
var currentCullFace = null;
var currentLineWidth = null;
var currentPolygonOffsetFactor = null;
var currentPolygonOffsetUnits = null;
//单个片段着色器能访问的纹理单元数,最低16,一般16或32
var maxTextures = gl.getParameter( gl.MAX_COMBINED_TEXTURE_IMAGE_UNITS );
var lineWidthAvailable = false;
var version = 0;
var glVersion = gl.getParameter( gl.VERSION );
if ( glVersion.indexOf( 'WebGL' ) !== - 1 ) {
//获取当前WebGL的版本
version = parseFloat( /^WebGL\ ([0-9])/.exec( glVersion )[ 1 ] );
//可用线宽度
lineWidthAvailable = ( version >= 1.0 );
} else if ( glVersion.indexOf( 'OpenGL ES' ) !== - 1 ) {
version = parseFloat( /^OpenGL\ ES\ ([0-9])/.exec( glVersion )[ 1 ] );
lineWidthAvailable = ( version >= 2.0 );
}
var currentTextureSlot = null;
var currentBoundTextures = {};
var currentScissor = new Vector4();
var currentViewport = new Vector4();
/**
* 创建纹理
* @param type
* @param target
* @param count
* @returns {*}
*/
function createTexture( type, target, count ) {
var data = new Uint8Array( 4 ); // 4 is required to match default unpack alignment of 4.
//创建纹理单元
var texture = gl.createTexture();
//将图片和纹理单元绑定
gl.bindTexture( type, texture );
/**
* 纹理映射;
* 官方文档:https://developer.mozilla.org/zh-CN/docs/Web/API/WebGLRenderingContext/texParameter
* 相关资料:https://www.web-tinker.com/article/20163.html
*/
//设置纹理缩小取样的方式为最近点采样
gl.texParameteri( type, gl.TEXTURE_MIN_FILTER, gl.NEAREST );
//设置纹理扩大取样的方式为最近点采样
gl.texParameteri( type, gl.TEXTURE_MAG_FILTER, gl.NEAREST );
for ( var i = 0; i < count; i ++ ) {
gl.texImage2D( target + i, 0, gl.RGBA, 1, 1, 0, gl.RGBA, gl.UNSIGNED_BYTE, data );
}
return texture;
}
var emptyTextures = {};
emptyTextures[ gl.TEXTURE_2D ] = createTexture( gl.TEXTURE_2D, gl.TEXTURE_2D, 1 );//初始化2D纹理
emptyTextures[ gl.TEXTURE_CUBE_MAP ] = createTexture( gl.TEXTURE_CUBE_MAP, gl.TEXTURE_CUBE_MAP_POSITIVE_X, 6 );//初始化立方体纹理
// init
//设置清除颜色
colorBuffer.setClear( 0, 0, 0, 1 );
//设置深度值
depthBuffer.setClear( 1 );
//设置模板值
stencilBuffer.setClear( 0 );
/**
* 开启深度检测
*/
enable( gl.DEPTH_TEST );
depthBuffer.setFunc( LessEqualDepth );
/**
* 是否开启正反面转换,通常情况下,当观察者从正面看三角形时ti,三角形的构造方式是逆时针的。
* 这样程序会将所有顺时针构造的三角形面当作被遮挡的面进行剔除。从而很大程度上避免了无用的系统开销
*/
setFlipSided( false );
/**设置剪裁面
* 设置背面剪裁的方式,一共有三种(1.只显示正面,2.只显示背面,3同时显示正面和背面)
*/
setCullFace( CullFaceBack );
//开启背面剪裁
enable( gl.CULL_FACE );
//开启混合
enable( gl.BLEND );
//设置混合方式
setBlending( NormalBlending );
//
/**
* 初始化属性数组,
*/
function initAttributes() {
for ( var i = 0, l = newAttributes.length; i < l; i ++ ) {
newAttributes[ i ] = 0;
}
}
/**
* 开启对应的属性
* @param attribute
*/
function enableAttribute( attribute ) {
enableAttributeAndDivisor( attribute, 0 );
}
/**
* 开启对应属性数组
* @param attribute 属性
* @param meshPerAttribute 每个属性的相关设置
*/
function enableAttributeAndDivisor( attribute, meshPerAttribute ) {
//attribute 是属性名称,用属性名称做Key, 1表示开启
newAttributes[ attribute ] = 1;
/**
* 如果当前没有开启次属性,那就开启它
*/
if ( enabledAttributes[ attribute ] === 0 ) {
gl.enableVertexAttribArray( attribute );//开启对应的属性
enabledAttributes[ attribute ] = 1;//设置为开始,1表示已经开启
}
/**
* 开启扩展
*/
if ( attributeDivisors[ attribute ] !== meshPerAttribute ) {
/**
* 是否是webGL2 ,是就直接使用上下文,不是就进行扩展
*/
var extension = capabilities.isWebGL2 ? gl : extensions.get( 'ANGLE_instanced_arrays' );
extension[ capabilities.isWebGL2 ? 'vertexAttribDivisor' : 'vertexAttribDivisorANGLE' ]( attribute, meshPerAttribute );
attributeDivisors[ attribute ] = meshPerAttribute;
}
}
/**注销属性
* 把没开启的属性设置成关闭
*/
function disableUnusedAttributes() {
for ( var i = 0, l = enabledAttributes.length; i !== l; ++ i ) {
if ( enabledAttributes[ i ] !== newAttributes[ i ] ) {
gl.disableVertexAttribArray( i );
enabledAttributes[ i ] = 0;
}
}
}
/**
* 开启属性
* @param id
*/
function enable( id ) {
if ( enabledCapabilities[ id ] !== true ) {
gl.enable( id );
enabledCapabilities[ id ] = true;
}
}
/**
* 注销属性
* @param id
*/
function disable( id ) {
if ( enabledCapabilities[ id ] !== false ) {
gl.disable( id );
enabledCapabilities[ id ] = false;
}
}
//得到压缩文本格式
function getCompressedTextureFormats() {
if ( compressedTextureFormats === null ) {
compressedTextureFormats = [];
if ( extensions.get( 'WEBGL_compressed_texture_pvrtc' ) ||
extensions.get( 'WEBGL_compressed_texture_s3tc' ) ||
extensions.get( 'WEBGL_compressed_texture_etc1' ) ||
extensions.get( 'WEBGL_compressed_texture_astc' ) ) {
//返回压缩的纹理格式,见文档:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/getParameter
var formats = gl.getParameter( gl.COMPRESSED_TEXTURE_FORMATS );
for ( var i = 0; i < formats.length; i ++ ) {
compressedTextureFormats.push( formats[ i ] );
}
}
}
return compressedTextureFormats;
}
/**
* 开启程序对象,如果当前程序对象等于program,则开启,返回true,否则返回false
* @param program
* @returns {boolean}
*/
function useProgram( program ) {
if ( currentProgram !== program ) {
gl.useProgram( program );
currentProgram = program;
return true;
}
return false;
}
/**
* 设置颜色混合的多种方式
* @param blending
* @param blendEquation
* @param blendSrc
* @param blendDst
* @param blendEquationAlpha
* @param blendSrcAlpha
* @param blendDstAlpha
* @param premultipliedAlpha
*/
function setBlending( blending, blendEquation, blendSrc, blendDst, blendEquationAlpha, blendSrcAlpha, blendDstAlpha, premultipliedAlpha ) {
if ( blending !== NoBlending ) {
enable( gl.BLEND );
} else {
disable( gl.BLEND );
}
if ( blending !== CustomBlending ) {
if ( blending !== currentBlending || premultipliedAlpha !== currentPremultipledAlpha ) {
switch ( blending ) {
case AdditiveBlending:
if ( premultipliedAlpha ) {
gl.blendEquationSeparate( gl.FUNC_ADD, gl.FUNC_ADD );
gl.blendFuncSeparate( gl.ONE, gl.ONE, gl.ONE, gl.ONE );
} else {
gl.blendEquation( gl.FUNC_ADD );
gl.blendFunc( gl.SRC_ALPHA, gl.ONE );
}
break;
case SubtractiveBlending:
if ( premultipliedAlpha ) {
gl.blendEquationSeparate( gl.FUNC_ADD, gl.FUNC_ADD );
gl.blendFuncSeparate( gl.ZERO, gl.ZERO, gl.ONE_MINUS_SRC_COLOR, gl.ONE_MINUS_SRC_ALPHA );
} else {
gl.blendEquation( gl.FUNC_ADD );
gl.blendFunc( gl.ZERO, gl.ONE_MINUS_SRC_COLOR );
}
break;
case MultiplyBlending:
if ( premultipliedAlpha ) {
gl.blendEquationSeparate( gl.FUNC_ADD, gl.FUNC_ADD );
gl.blendFuncSeparate( gl.ZERO, gl.SRC_COLOR, gl.ZERO, gl.SRC_ALPHA );
} else {
gl.blendEquation( gl.FUNC_ADD );
gl.blendFunc( gl.ZERO, gl.SRC_COLOR );
}
break;
default:
if ( premultipliedAlpha ) {
gl.blendEquationSeparate( gl.FUNC_ADD, gl.FUNC_ADD );
gl.blendFuncSeparate( gl.ONE, gl.ONE_MINUS_SRC_ALPHA, gl.ONE, gl.ONE_MINUS_SRC_ALPHA );
} else {
gl.blendEquationSeparate( gl.FUNC_ADD, gl.FUNC_ADD );
gl.blendFuncSeparate( gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA, gl.ONE, gl.ONE_MINUS_SRC_ALPHA );
}
}
}
currentBlendEquation = null;
currentBlendSrc = null;
currentBlendDst = null;
currentBlendEquationAlpha = null;
currentBlendSrcAlpha = null;
currentBlendDstAlpha = null;
} else {
blendEquationAlpha = blendEquationAlpha || blendEquation;
blendSrcAlpha = blendSrcAlpha || blendSrc;
blendDstAlpha = blendDstAlpha || blendDst;
if ( blendEquation !== currentBlendEquation || blendEquationAlpha !== currentBlendEquationAlpha ) {
gl.blendEquationSeparate( utils.convert( blendEquation ), utils.convert( blendEquationAlpha ) );
currentBlendEquation = blendEquation;
currentBlendEquationAlpha = blendEquationAlpha;
}
if ( blendSrc !== currentBlendSrc || blendDst !== currentBlendDst || blendSrcAlpha !== currentBlendSrcAlpha || blendDstAlpha !== currentBlendDstAlpha ) {
gl.blendFuncSeparate( utils.convert( blendSrc ), utils.convert( blendDst ), utils.convert( blendSrcAlpha ), utils.convert( blendDstAlpha ) );
currentBlendSrc = blendSrc;
currentBlendDst = blendDst;
currentBlendSrcAlpha = blendSrcAlpha;
currentBlendDstAlpha = blendDstAlpha;
}
}
currentBlending = blending;
currentPremultipledAlpha = premultipliedAlpha;
}
/**
* 设置材质
* @param material
* @param frontFaceCW
*/
function setMaterial( material, frontFaceCW ) {
material.side === DoubleSide
? disable( gl.CULL_FACE )
: enable( gl.CULL_FACE );
var flipSided = ( material.side === BackSide );
if ( frontFaceCW ) flipSided = ! flipSided;
setFlipSided( flipSided );
( material.blending === NormalBlending && material.transparent === false )
? setBlending( NoBlending )
: setBlending( material.blending, material.blendEquation, material.blendSrc, material.blendDst, material.blendEquationAlpha, material.blendSrcAlpha, material.blendDstAlpha, material.premultipliedAlpha );
depthBuffer.setFunc( material.depthFunc );
depthBuffer.setTest( material.depthTest );
depthBuffer.setMask( material.depthWrite );
colorBuffer.setMask( material.colorWrite );
setPolygonOffset( material.polygonOffset, material.polygonOffsetFactor, material.polygonOffsetUnits );
}
//
/**
* 设置多边形的绕线方式,这种方式用来设置那一面是正面,
* @param flipSided
*/
function setFlipSided( flipSided ) {
if ( currentFlipSided !== flipSided ) {
if ( flipSided ) {
gl.frontFace( gl.CW );//顺时针
} else {
gl.frontFace( gl.CCW );//逆时针
}
currentFlipSided = flipSided;
}
}
/**
*裁剪面,通过裁剪没用的面达到性能提高的目的
* @param cullFace 裁剪面参数
* 文档见:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/cullFace
*/
function setCullFace( cullFace ) {
if ( cullFace !== CullFaceNone ) {
//激活裁剪多边形
enable( gl.CULL_FACE );
if ( cullFace !== currentCullFace ) {
if ( cullFace === CullFaceBack ) {
gl.cullFace( gl.BACK );//裁剪掉背面
} else if ( cullFace === CullFaceFront ) {
gl.cullFace( gl.FRONT );//裁剪掉前面
} else {
gl.cullFace( gl.FRONT_AND_BACK );//前后两面都裁剪
}
}
} else {
disable( gl.CULL_FACE );//不进行裁剪,注销裁剪功能
}
currentCullFace = cullFace;
}
/**
* 设置线的宽度,没什么用,现在的webgl版本,包括OpenGL ES 2/3 最大最小宽度都是1;总的来说设置不了
* @param width
*/
function setLineWidth( width ) {
if ( width !== currentLineWidth ) {
if ( lineWidthAvailable ) gl.lineWidth( width );
currentLineWidth = width;
}
}
/**
* 设置多边形的深度偏移
* @param polygonOffset
* @param factor
* @param units
*/
function setPolygonOffset( polygonOffset, factor, units ) {
if ( polygonOffset ) {
//开启多边形的偏移,应该是深度偏移,原文档,原话Activates adding an offset to depth values of polygon's fragments. See
enable( gl.POLYGON_OFFSET_FILL );
if ( currentPolygonOffsetFactor !== factor || currentPolygonOffsetUnits !== units ) {
gl.polygonOffset( factor, units );
currentPolygonOffsetFactor = factor;
currentPolygonOffsetUnits = units;
}
} else {
disable( gl.POLYGON_OFFSET_FILL );
}
}
/**
* 设置模板测试
* @param scissorTest
*/
function setScissorTest( scissorTest ) {
if ( scissorTest ) {
/**
* Activates the scissor test that discards fragments that are outside of the scissor rectangle
*/
enable( gl.SCISSOR_TEST );
} else {
disable( gl.SCISSOR_TEST );
}
}
// texture
/**
* 激活指定纹理
* @param webglSlot
*/
function activeTexture( webglSlot ) {
//webglSlot 等于unfefined 时,指定最大纹理
if ( webglSlot === undefined ) webglSlot = gl.TEXTURE0 + maxTextures - 1;
if ( currentTextureSlot !== webglSlot ) {
gl.activeTexture( webglSlot );
currentTextureSlot = webglSlot;
}
}
/**
* 绑定纹理
* @param webglType (gl.TEXTURE_2D、gl.TEXTURE_CUBE_MAP, gl.TEXTURE_3D, or gl.TEXTURE_2D_ARRAY.)
* @param webglTexture 纹理对象
*/
function bindTexture( webglType, webglTexture ) {
if ( currentTextureSlot === null ) {
activeTexture();
}
var boundTexture = currentBoundTextures[ currentTextureSlot ];
if ( boundTexture === undefined ) {
boundTexture = { type: undefined, texture: undefined };
currentBoundTextures[ currentTextureSlot ] = boundTexture;
}
if ( boundTexture.type !== webglType || boundTexture.texture !== webglTexture ) {
//webglTexture 如果为空,则使用emptyTextures[ webglType ]
gl.bindTexture( webglType, webglTexture || emptyTextures[ webglType ] );
boundTexture.type = webglType;
boundTexture.texture = webglTexture;
}
}
/**
* 指定颜色格式
*/
function compressedTexImage2D() {
try {
//指定压缩格式的三维纹理图像
//文档见:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/compressedTexImage2D
gl.compressedTexImage2D.apply( gl, arguments );
} catch ( error ) {
console.error( 'THREE.WebGLState:', error );
}
}
/**
* 指定一个纹理图像,也就是把图片设置到纹理中
* 文档见:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/texImage2D
*/
function texImage2D() {
try {
gl.texImage2D.apply( gl, arguments );
} catch ( error ) {
console.error( 'THREE.WebGLState:', error );
}
}
//
/**
* 设置模板
* @param scissor
*/
function scissor( scissor ) {
if ( currentScissor.equals( scissor ) === false ) {
//设置模板的大小,一般用来把其它场景作为纹理使用时,就会用到模板缓冲区
gl.scissor( scissor.x, scissor.y, scissor.z, scissor.w );
currentScissor.copy( scissor );
}
}
/**
* 设置位置大小,这是webgl里的绘制大小,把场景作为纹理使用时可使用viewport来调节纹理的大小
* @param viewport
*/
function viewport( viewport ) {
if ( currentViewport.equals( viewport ) === false ) {
gl.viewport( viewport.x, viewport.y, viewport.z, viewport.w );
currentViewport.copy( viewport );
}
}
//
/**
* 重置
*/
function reset() {
for ( var i = 0; i < enabledAttributes.length; i ++ ) {
if ( enabledAttributes[ i ] === 1 ) {
//注销属性
gl.disableVertexAttribArray( i );
enabledAttributes[ i ] = 0;
}
}
enabledCapabilities = {};
compressedTextureFormats = null;
currentTextureSlot = null;
currentBoundTextures = {};
currentProgram = null;
currentBlending = null;
currentFlipSided = null;
currentCullFace = null;
colorBuffer.reset();//颜色缓冲区重置
depthBuffer.reset();//深度缓冲区重置
stencilBuffer.reset();//模板缓冲区重置
}
return {
buffers: {
color: colorBuffer,
depth: depthBuffer,
stencil: stencilBuffer
},
initAttributes: initAttributes,
enableAttribute: enableAttribute,
enableAttributeAndDivisor: enableAttributeAndDivisor,
disableUnusedAttributes: disableUnusedAttributes,
enable: enable,
disable: disable,
getCompressedTextureFormats: getCompressedTextureFormats,
useProgram: useProgram,
setBlending: setBlending,
setMaterial: setMaterial,
setFlipSided: setFlipSided,
setCullFace: setCullFace,
setLineWidth: setLineWidth,
setPolygonOffset: setPolygonOffset,
setScissorTest: setScissorTest,
activeTexture: activeTexture,
bindTexture: bindTexture,
compressedTexImage2D: compressedTexImage2D,
texImage2D: texImage2D,
scissor: scissor,
viewport: viewport,
reset: reset
};
}
export { WebGLState };