My Three.js website uses lil-gui to display a small menu with 2 options:
- Background color (change the color)
- Sky (displays a sky)
Adding the sky seems to override the background color, so there’s no need to change it, but if 1. is selected, then I want to disable 2. and also remove the tick in the checkbox.
My code:
function createGUI() {
...
skyEnabled = false;
const propsGeneral = {
"backgroundColorOption": backgroundColor.getHexString(),
get "skyOption"() { return skyEnabled },
set "skyOption"(v) {
/*if(justTriggeredCheckbox) {
justTriggeredCheckbox = false;
} else {*/
v ? enableSky() : disableSky();
//}
}
};
gui.addColor(propsGeneral, "backgroundColorOption")
.onChange(val => { changeBackgroundColor(val); });
skyCheckbox = gui.add(propsGeneral, "skyOption");
...
}
function disableSky() {
//justTriggeredCheckbox = true;
scene.remove(sky);
scene.environment = null;
skyEnabled = false;
skyCheckbox.setValue(false);
}
function changeBackgroundColor(c) {
if(!(c instanceof THREE.Color)) {
c = new THREE.Color(c);
}
scene.background = c;
disableSky();
}
Problem:
If I change the background color, then skyCheckbox.setValue(false) causes an infinite loop (because is triggers disableSky(), which triggers it again and again) and it crashes with a “too much recursion” error.
I added justTriggeredCheckbox, which helps but it looks kind of ugly. Is there a better (“official”?) way to do this?
I know that Unity used to have the same problem but they eventually added an internal check, so it wouldn’t cause a loop if setValue is called in code.