ThreeJS renderBufferDirect 源码

  • 设置场景
const _emptyScene = {
        background: null,
        fog: null,
        environment: null,
        overrideMaterial: null,
        isScene: true,
};
if ( scene === null ) scene = _emptyScene; // renderBufferDirect second parameter used to be fog (could be null)
复制代码
  • setProgram函数获取Program
const program = setProgram( camera, scene, material, object );
复制代码
  • setMaterial+是否正面渲染 来设置状态机的状态
state.setMaterial( material, frontFaceCW );
复制代码
  • index与position
// 获取索引和顶点数据
let index = geometry.index;
const position = geometry.attributes.position;
复制代码
  • 计算顶点drawStart, drawCount与webgl类同
//计算需要绘制顶点个数
const dataCount = ( index !== null ) ? index.count : position.count;
const rangeStart = geometry.drawRange.start * rangeFactor;
const rangeCount = geometry.drawRange.count * rangeFactor;
const groupStart = group !== null ? group.start * rangeFactor : 0;
const groupCount = group !== null ? group.count * rangeFactor : Infinity;
const drawStart = Math.max( rangeStart, groupStart );
const drawEnd = Math.min( dataCount, rangeStart + rangeCount, groupStart + groupCount ) - 1;
const drawCount = Math.max( 0, drawEnd - drawStart + 1 );
复制代码
  • 分mesh point line sprite
//设置绘制模式和绘制方法
if ( object.isMesh ) {
        if ( material.wireframe === true ) {
                state.setLineWidth( material.wireframeLinewidth * getTargetPixelRatio() );
                renderer.setMode( _gl.LINES );
        } else {
                renderer.setMode( _gl.TRIANGLES );
        }
} else if ( object.isLine ) {
        let lineWidth = material.linewidth;
        if ( lineWidth === undefined ) lineWidth = 1; // Not using Line*Material
        state.setLineWidth( lineWidth * getTargetPixelRatio() );
        if ( object.isLineSegments ) {
                renderer.setMode( _gl.LINES );
        } else if ( object.isLineLoop ) {
                renderer.setMode( _gl.LINE_LOOP );
        } else {
                renderer.setMode( _gl.LINE_STRIP );
        }
} else if ( object.isPoints ) {
        renderer.setMode( _gl.POINTS );
} else if ( object.isSprite ) {
        renderer.setMode( _gl.TRIANGLES );
}
复制代码
  • draw三种draw的方式
if ( object.isInstancedMesh ) {
        renderer.renderInstances( drawStart, drawCount, object.count );
} else if ( geometry.isInstancedBufferGeometry ) {
        const instanceCount = Math.min( geometry.instanceCount, geometry._maxInstanceCount );
        renderer.renderInstances( drawStart, drawCount, instanceCount );
} else {
        renderer.render( drawStart, drawCount );
}
复制代码
  • 原文

this.renderBufferDirect = function ( camera, scene, geometry, material, object, group ) {
        if ( scene === null ) scene = _emptyScene; // renderBufferDirect second parameter used to be fog (could be null)
        const frontFaceCW = ( object.isMesh && object.matrixWorld.determinant() < 0 );
        // 获取着色器程序
        const program = setProgram( camera, scene, material, object );
        // 设置绘制所需状态
        state.setMaterial( material, frontFaceCW );
        // 获取索引和顶点数据
        let index = geometry.index;
        const position = geometry.attributes.position;
        // 判断有无索引和顶点数据
        if ( index === null ) {
                if ( position === undefined || position.count === 0 ) return;
        } else if ( index.count === 0 ) {
                return;
        }
        // 线框模式
        let rangeFactor = 1;
        if ( material.wireframe === true ) {
                index = geometries.getWireframeAttribute( geometry );
                rangeFactor = 2;
        }
        //设置变形动画
        if ( material.morphTargets || material.morphNormals ) {
                morphtargets.update( object, geometry, material, program );
        }
        //绑定顶点数据
        bindingStates.setup( object, material, program, geometry, index );
        let attribute;
        let renderer = bufferRenderer;
        if ( index !== null ) {
                attribute = attributes.get( index );
                renderer = indexedBufferRenderer;
                renderer.setIndex( attribute );
        }
        //计算需要绘制顶点个数
        const dataCount = ( index !== null ) ? index.count : position.count;
        const rangeStart = geometry.drawRange.start * rangeFactor;
        const rangeCount = geometry.drawRange.count * rangeFactor;
        const groupStart = group !== null ? group.start * rangeFactor : 0;
        const groupCount = group !== null ? group.count * rangeFactor : Infinity;
        const drawStart = Math.max( rangeStart, groupStart );
        const drawEnd = Math.min( dataCount, rangeStart + rangeCount, groupStart + groupCount ) - 1;
        const drawCount = Math.max( 0, drawEnd - drawStart + 1 );
        if ( drawCount === 0 ) return;
        //设置绘制模式和绘制方法
        if ( object.isMesh ) {
                if ( material.wireframe === true ) {
                        state.setLineWidth( material.wireframeLinewidth * getTargetPixelRatio() );
                        renderer.setMode( _gl.LINES );
                } else {
                        renderer.setMode( _gl.TRIANGLES );
                }
        } else if ( object.isLine ) {
                let lineWidth = material.linewidth;
                if ( lineWidth === undefined ) lineWidth = 1; // Not using Line*Material
                state.setLineWidth( lineWidth * getTargetPixelRatio() );
                if ( object.isLineSegments ) {
                        renderer.setMode( _gl.LINES );
                } else if ( object.isLineLoop ) {
                        renderer.setMode( _gl.LINE_LOOP );
                } else {
                        renderer.setMode( _gl.LINE_STRIP );
                }
        } else if ( object.isPoints ) {
                renderer.setMode( _gl.POINTS );
        } else if ( object.isSprite ) {
                renderer.setMode( _gl.TRIANGLES );
        }
        if ( object.isInstancedMesh ) {
                renderer.renderInstances( drawStart, drawCount, object.count );
        } else if ( geometry.isInstancedBufferGeometry ) {
                const instanceCount = Math.min( geometry.instanceCount, geometry._maxInstanceCount );
                renderer.renderInstances( drawStart, drawCount, instanceCount );
        } else {
                renderer.render( drawStart, drawCount );
        }
};
复制代码
© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享