Skip to content
Snippets Groups Projects
Commit 739d7614 authored by Alexander Rose's avatar Alexander Rose
Browse files

render loop optimization, loop over list instead of map

parent 5f672568
No related branches found
No related tags found
No related merge requests found
...@@ -107,7 +107,8 @@ namespace Renderer { ...@@ -107,7 +107,8 @@ namespace Renderer {
} }
let currentProgramId = -1 let currentProgramId = -1
const renderObject = (r: Renderable<RenderableValues & BaseValues>, variant: RenderVariant) => { const renderObject = (r: Renderable<RenderableValues & BaseValues>, variant: RenderVariant, opaque: boolean) => {
if (r.state.opaque !== opaque) return
const program = r.getProgram(variant) const program = r.getProgram(variant)
if (r.state.visible) { if (r.state.visible) {
if (currentProgramId !== program.id) { if (currentProgramId !== program.id) {
...@@ -161,15 +162,20 @@ namespace Renderer { ...@@ -161,15 +162,20 @@ namespace Renderer {
ValueCell.update(globalUniforms.uFogFar, camera.state.fogFar) ValueCell.update(globalUniforms.uFogFar, camera.state.fogFar)
ValueCell.update(globalUniforms.uFogNear, camera.state.fogNear) ValueCell.update(globalUniforms.uFogNear, camera.state.fogNear)
const { renderables } = scene
currentProgramId = -1 currentProgramId = -1
gl.disable(gl.BLEND) gl.disable(gl.BLEND)
gl.enable(gl.DEPTH_TEST) gl.enable(gl.DEPTH_TEST)
scene.eachOpaque((r) => renderObject(r, variant)) for (let i = 0, il = renderables.length; i < il; ++i) {
renderObject(renderables[i], variant, true)
}
gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA) gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA)
gl.enable(gl.BLEND) gl.enable(gl.BLEND)
scene.eachTransparent((r) => renderObject(r, variant)) for (let i = 0, il = renderables.length; i < il; ++i) {
renderObject(renderables[i], variant, false)
}
gl.finish() gl.finish()
} }
......
...@@ -14,38 +14,20 @@ import { Vec3 } from 'mol-math/linear-algebra'; ...@@ -14,38 +14,20 @@ import { Vec3 } from 'mol-math/linear-algebra';
import { BoundaryHelper } from 'mol-math/geometry/boundary-helper'; import { BoundaryHelper } from 'mol-math/geometry/boundary-helper';
const boundaryHelper = new BoundaryHelper(); const boundaryHelper = new BoundaryHelper();
function calculateBoundingSphere(renderableMap: Map<RenderObject, Renderable<RenderableValues & BaseValues>>, boundingSphere: Sphere3D): Sphere3D { function calculateBoundingSphere(renderables: Renderable<RenderableValues & BaseValues>[], boundingSphere: Sphere3D): Sphere3D {
// let count = 0
// const center = Vec3.set(boundingSphere.center, 0, 0, 0)
// renderableMap.forEach(r => {
// if (r.boundingSphere.radius) {
// Vec3.add(center, center, r.boundingSphere.center)
// ++count
// }
// })
// if (count > 0) {
// Vec3.scale(center, center, 1 / count)
// }
// let radius = 0
// renderableMap.forEach(r => {
// if (r.boundingSphere.radius) {
// radius = Math.max(radius, Vec3.distance(center, r.boundingSphere.center) + r.boundingSphere.radius)
// }
// })
// boundingSphere.radius = radius
boundaryHelper.reset(0.1); boundaryHelper.reset(0.1);
renderableMap.forEach(r => { for (let i = 0, il = renderables.length; i < il; ++i) {
if (!r.boundingSphere.radius) return; const r = renderables[i]
if (!r.boundingSphere.radius) continue;
boundaryHelper.boundaryStep(r.boundingSphere.center, r.boundingSphere.radius); boundaryHelper.boundaryStep(r.boundingSphere.center, r.boundingSphere.radius);
}); }
boundaryHelper.finishBoundaryStep(); boundaryHelper.finishBoundaryStep();
renderableMap.forEach(r => { for (let i = 0, il = renderables.length; i < il; ++i) {
if (!r.boundingSphere.radius) return; const r = renderables[i]
if (!r.boundingSphere.radius) continue;
boundaryHelper.extendStep(r.boundingSphere.center, r.boundingSphere.radius); boundaryHelper.extendStep(r.boundingSphere.center, r.boundingSphere.radius);
}); };
Vec3.copy(boundingSphere.center, boundaryHelper.center); Vec3.copy(boundingSphere.center, boundaryHelper.center);
boundingSphere.radius = boundaryHelper.radius; boundingSphere.radius = boundaryHelper.radius;
...@@ -55,6 +37,7 @@ function calculateBoundingSphere(renderableMap: Map<RenderObject, Renderable<Ren ...@@ -55,6 +37,7 @@ function calculateBoundingSphere(renderableMap: Map<RenderObject, Renderable<Ren
interface Scene extends Object3D { interface Scene extends Object3D {
readonly count: number readonly count: number
readonly renderables: ReadonlyArray<Renderable<RenderableValues & BaseValues>>
readonly boundingSphere: Sphere3D readonly boundingSphere: Sphere3D
update: (keepBoundingSphere?: boolean) => void update: (keepBoundingSphere?: boolean) => void
...@@ -62,13 +45,12 @@ interface Scene extends Object3D { ...@@ -62,13 +45,12 @@ interface Scene extends Object3D {
remove: (o: RenderObject) => void remove: (o: RenderObject) => void
clear: () => void clear: () => void
forEach: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => void forEach: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => void
eachOpaque: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => void
eachTransparent: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => void
} }
namespace Scene { namespace Scene {
export function create(ctx: WebGLContext): Scene { export function create(ctx: WebGLContext): Scene {
const renderableMap = new Map<RenderObject, Renderable<RenderableValues & BaseValues>>() const renderableMap = new Map<RenderObject, Renderable<RenderableValues & BaseValues>>()
const renderables: Renderable<RenderableValues & BaseValues>[] = []
const boundingSphere = Sphere3D.zero() const boundingSphere = Sphere3D.zero()
let boundingSphereDirty = true let boundingSphereDirty = true
...@@ -82,13 +64,17 @@ namespace Scene { ...@@ -82,13 +64,17 @@ namespace Scene {
update: (keepBoundingSphere?: boolean) => { update: (keepBoundingSphere?: boolean) => {
Object3D.update(object3d) Object3D.update(object3d)
renderableMap.forEach(r => r.update()) for (let i = 0, il = renderables.length; i < il; ++i) {
renderables[i].update()
}
if (!keepBoundingSphere) boundingSphereDirty = true if (!keepBoundingSphere) boundingSphereDirty = true
}, },
add: (o: RenderObject) => { add: (o: RenderObject) => {
if (!renderableMap.has(o)) { if (!renderableMap.has(o)) {
renderableMap.set(o, createRenderable(ctx, o)) const renderable = createRenderable(ctx, o)
renderables.push(renderable)
renderableMap.set(o, renderable)
boundingSphereDirty = true boundingSphereDirty = true
} else { } else {
console.warn(`RenderObject with id '${o.id}' already present`) console.warn(`RenderObject with id '${o.id}' already present`)
...@@ -98,29 +84,28 @@ namespace Scene { ...@@ -98,29 +84,28 @@ namespace Scene {
const renderable = renderableMap.get(o) const renderable = renderableMap.get(o)
if (renderable) { if (renderable) {
renderable.dispose() renderable.dispose()
renderables.splice(renderables.indexOf(renderable), 1)
renderableMap.delete(o) renderableMap.delete(o)
boundingSphereDirty = true boundingSphereDirty = true
} }
}, },
clear: () => { clear: () => {
renderableMap.forEach(renderable => renderable.dispose()) for (let i = 0, il = renderables.length; i < il; ++i) {
renderables[i].dispose()
}
renderables.length = 0
renderableMap.clear() renderableMap.clear()
boundingSphereDirty = true boundingSphereDirty = true
}, },
forEach: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => { forEach: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => {
renderableMap.forEach(callbackFn) renderableMap.forEach(callbackFn)
}, },
eachOpaque: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => {
renderableMap.forEach((r, o) => { if (r.state.opaque) callbackFn(r, o) })
},
eachTransparent: (callbackFn: (value: Renderable<any>, key: RenderObject) => void) => {
renderableMap.forEach((r, o) => { if (!r.state.opaque) callbackFn(r, o) })
},
get count() { get count() {
return renderableMap.size return renderables.length
}, },
renderables,
get boundingSphere() { get boundingSphere() {
if (boundingSphereDirty) calculateBoundingSphere(renderableMap, boundingSphere) if (boundingSphereDirty) calculateBoundingSphere(renderables, boundingSphere)
boundingSphereDirty = false boundingSphereDirty = false
return boundingSphere return boundingSphere
} }
......
...@@ -71,7 +71,7 @@ export class RepresentationRegistry<D> { ...@@ -71,7 +71,7 @@ export class RepresentationRegistry<D> {
} }
remove(name: string) { remove(name: string) {
this._list.splice(this._list.findIndex(e => e.name === name)) this._list.splice(this._list.findIndex(e => e.name === name), 1)
this._map.delete(name) this._map.delete(name)
} }
......
...@@ -79,7 +79,7 @@ export class ThemeRegistry<T extends ColorTheme<any> | SizeTheme<any>> { ...@@ -79,7 +79,7 @@ export class ThemeRegistry<T extends ColorTheme<any> | SizeTheme<any>> {
} }
remove(name: string) { remove(name: string) {
this._list.splice(this._list.findIndex(e => e.name === name)) this._list.splice(this._list.findIndex(e => e.name === name), 1)
this._map.delete(name) this._map.delete(name)
console.log('removed', name, this._list, this._map) console.log('removed', name, this._list, this._map)
} }
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment