Skip to content

Commit

Permalink
Move sortFunctions.js module into systems/renderer.js
Browse files Browse the repository at this point in the history
  • Loading branch information
diarmidmackenzie committed Jul 29, 2023
1 parent 9462f1c commit d640779
Show file tree
Hide file tree
Showing 4 changed files with 137 additions and 141 deletions.
56 changes: 0 additions & 56 deletions src/core/scene/sortFunctions.js

This file was deleted.

63 changes: 59 additions & 4 deletions src/systems/renderer.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
var registerSystem = require('../core/system').registerSystem;
var utils = require('../utils/');
var THREE = require('../lib/three');
var sortFunctions = require('../core/scene/sortFunctions');

var debug = utils.debug;
var warn = debug('components:renderer:warn');
Expand Down Expand Up @@ -51,7 +50,7 @@ module.exports.System = registerSystem('renderer', {

// These properties are always the same, regardless of rendered oonfiguration
renderer.sortObjects = true;
renderer.setOpaqueSort(sortFunctions.sortOpaqueDefault);
renderer.setOpaqueSort(sortOpaqueDefault);
},

update: function () {
Expand All @@ -67,9 +66,9 @@ module.exports.System = registerSystem('renderer', {
warn('`sortObjects` property is deprecated. Use `renderer="sortTransparentObjects: true"` instead.');
}
if (data.sortTransparentObjects) {
renderer.setTransparentSort(sortFunctions.sortTransparentSpatial);
renderer.setTransparentSort(sortTransparentSpatial);
} else {
renderer.setTransparentSort(sortFunctions.sortTransparentDefault);
renderer.setTransparentSort(sortTransparentDefault);
}
},

Expand Down Expand Up @@ -97,3 +96,59 @@ module.exports.System = registerSystem('renderer', {
}
}
});

// Custom A-Frame sort functions.
// Variations of Three.js default sort orders here:
// https://github.com/mrdoob/three.js/blob/ebbaecf9acacf259ea9abdcba7b6fb25cfcea2ab/src/renderers/webgl/WebGLRenderLists.js#L1
// See: https://github.com/aframevr/aframe/issues/5332

// Default sort for opaque objects:
// - respect groupOrder & renderOrder settings
// - sort front-to-back by z-depth from camera (this should minimize overdraw)
// - otherwise leave objects in default order (object tree order)

function sortOpaqueDefault (a, b) {
if (a.groupOrder !== b.groupOrder) {
return a.groupOrder - b.groupOrder;
} else if (a.renderOrder !== b.renderOrder) {
return a.renderOrder - b.renderOrder;
} else if (a.z !== b.z) {
return a.z - b.z;
} else {
return 0;
}
}

// Default sort for transparent objects:
// - respect groupOrder & renderOrder settings
// - otherwise leave objects in default order (object tree order)
function sortTransparentDefault (a, b) {
if (a.groupOrder !== b.groupOrder) {
return a.groupOrder - b.groupOrder;
} else if (a.renderOrder !== b.renderOrder) {
return a.renderOrder - b.renderOrder;
} else {
return 0;
}
}

// Spatial sort for transparent objects:
// - respect groupOrder & renderOrder settings
// - sort back-to-front by z-depth from camera
// - otherwise leave objects in default order (object tree order)
function sortTransparentSpatial (a, b) {
if (a.groupOrder !== b.groupOrder) {
return a.groupOrder - b.groupOrder;
} else if (a.renderOrder !== b.renderOrder) {
return a.renderOrder - b.renderOrder;
} else if (a.z !== b.z) {
return b.z - a.z;
} else {
return 0;
}
}

// exports needed for Unit Tests
module.exports.sortOpaqueDefault = sortOpaqueDefault;
module.exports.sortTransparentDefault = sortTransparentDefault;
module.exports.sortTransparentSpatial = sortTransparentSpatial;
80 changes: 0 additions & 80 deletions tests/core/sortFunctions.test.js

This file was deleted.

79 changes: 78 additions & 1 deletion tests/systems/renderer.test.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
/* global assert, suite, test, setup, teardown, THREE */
var {sortOpaqueDefault,
sortTransparentDefault,
sortTransparentSpatial} = require('core/scene/sortFunctions');
sortTransparentSpatial} = require('systems/renderer');

suite('renderer', function () {
function createScene () {
Expand Down Expand Up @@ -230,4 +230,81 @@ suite('renderer', function () {
console.warn = oldConsoleWarn;
});
});

suite('sortFunctions', function () {
var objects;
var objectsRenderOrder;
var objectsGroupOrder;

setup(function () {
objects = [
{ name: 'a', renderOrder: 0, z: 1 },
{ name: 'b', renderOrder: 0, z: 3 },
{ name: 'c', renderOrder: 0, z: 2 }
];

objectsRenderOrder = [
{ name: 'a', renderOrder: 1, z: 1 },
{ name: 'b', renderOrder: 0, z: 3 },
{ name: 'c', renderOrder: -1, z: 2 }
];

objectsGroupOrder = [
{ name: 'a', groupOrder: 0, renderOrder: 1, z: 1 },
{ name: 'b', groupOrder: 0, renderOrder: 0, z: 3 },
{ name: 'c', groupOrder: 1, renderOrder: -1, z: 2 }
];
});

function checkOrder (objects, array) {
array.forEach((item, index) => {
assert.equal(objects[index].name, item);
});
}

test('Opaque sort sorts front-to-back', function () {
objects.sort(sortOpaqueDefault);
checkOrder(objects, ['a', 'c', 'b']);
});

test('Opaque sort respects renderOrder', function () {
objectsRenderOrder.sort(sortOpaqueDefault);
checkOrder(objectsRenderOrder, ['c', 'b', 'a']);
});

test('Opaque sort respects groupOrder, then renderOrder', function () {
objectsGroupOrder.sort(sortOpaqueDefault);
checkOrder(objectsGroupOrder, ['b', 'a', 'c']);
});

test('Transparent default sort sorts in DOM order', function () {
objects.sort(sortTransparentDefault);
checkOrder(objects, ['a', 'b', 'c']);
});

test('Transparent default sort respects renderOrder', function () {
objectsRenderOrder.sort(sortTransparentDefault);
checkOrder(objectsRenderOrder, ['c', 'b', 'a']);
});

test('Transparent default sort respects groupOrder, then renderOrder', function () {
objectsGroupOrder.sort(sortTransparentDefault);
checkOrder(objectsGroupOrder, ['b', 'a', 'c']);
});

test('Transparent spatial sort sorts back-to-front', function () {
objects.sort(sortTransparentSpatial);
checkOrder(objects, ['b', 'c', 'a']);
});

test('Transparent spatial sort respects renderOrder', function () {
objectsRenderOrder.sort(sortTransparentSpatial);
checkOrder(objectsRenderOrder, ['c', 'b', 'a']);
});

test('Transparent spatial sort respects groupOrder, then renderOrder', function () {
objectsGroupOrder.sort(sortTransparentSpatial);
checkOrder(objectsGroupOrder, ['b', 'a', 'c']);
});
});
});

0 comments on commit d640779

Please sign in to comment.