Skip to content

Commit

Permalink
use cubemap with ocean and bump aframe to master
Browse files Browse the repository at this point in the history
  • Loading branch information
kfarr committed May 11, 2020
1 parent 0bfd5a2 commit 6237d64
Show file tree
Hide file tree
Showing 2 changed files with 115 additions and 64 deletions.
17 changes: 14 additions & 3 deletions index.html
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
<html>
<head>
<script src="https://aframe.io/releases/1.0.4/aframe.min.js"></script>
<!-- <script src="https://aframe.io/releases/1.0.4/aframe.min.js"></script> -->
<script src="https://cdn.jsdelivr.net/gh/aframevr/aframe@710dfc0ab24c9bd86ff54f5a7e6f9b1f64920fa2/dist/aframe-master.min.js"></script>

<script src="src/lib/aframe-atlas-uvs-component.min.js"></script>
<script src="src/lib/aframe-orbit-controls.min.js"></script>
<script src="src/lib/aframe-cubemap-component.js"></script>
Expand Down Expand Up @@ -55,6 +57,15 @@
</nav>
<a-scene renderer="colorManagement: true; highRefreshRate: true; foveationLevel: 3; physicallyCorrectLights: true; logarithmicDepthBuffer: false;" fogoff="type: linear; color: #D5C69B; far: 200" gltf-model="dracoDecoderPath: src/lib/;">
<a-assets>
<a-cubemap id="skycube">
<img src="assets/images/skybox/posx.jpg">
<img src="assets/images/skybox/negx.jpg">
<img src="assets/images/skybox/posy.jpg">
<img src="assets/images/skybox/negy.jpg">
<img src="assets/images/skybox/posz.jpg">
<img src="assets/images/skybox/negz.jpg">
</a-cubemap>

<!-- audio -->
<audio id="ambientmp3" src="assets/audio/SSL_16_11_AMB_EXT_SF_ALAMO_SQ.mp3" preload="none"></audio>
<audio id="tram-pass-mp3" src="assets/audio/Tram-Pass-By-Fast-shortened.mp3" preload="auto"></audio>
Expand Down Expand Up @@ -89,7 +100,7 @@
<img id="markings-atlas" src="assets/materials/lane-markings-atlas_1024.png" />

<!-- sky - equirectangular still used for envmap -->
<img id="sky" position="0 -140 0" src="assets/CGSkies_0343_doubled_2048.jpg" />
<!-- <img id="sky" position="0 -140 0" src="assets/CGSkies_0343_doubled_2048.jpg" /> -->

<!-- raw photogrammetry textures - unused by default -->
<a-mixin id="bike-lane-t0" geometry="width:1.8;height:150;primitive:plane" material="repeat:2 150;src:assets/materials/bikelane_Base_Color.jpg;normalTextureRepeat:2 150;normalMap:assets/materials/bikelane_Normal.jpg"></a-mixin>
Expand Down Expand Up @@ -182,7 +193,7 @@
<a-entity light="type: ambient; color: #FFF; intensity: 2"></a-entity>
<a-entity light="type: directional; color: #FFF; intensity: 0.6" position="0.5 1 -1"></a-entity>

<a-ocean-plane height="100" width="100" position="0 -1 0" material="sphericalEnvMap: #sky;"></a-ocean-plane>
<a-ocean-plane height="100" width="100" position="0 -1 0" material="envMap: #skycube;"></a-ocean-plane>

<a-entity id="skybox" cubemap="folder: assets/images/skybox/"></a-entity>

Expand Down
162 changes: 101 additions & 61 deletions src/lib/aframe-cubemap-component.js
Original file line number Diff line number Diff line change
@@ -1,100 +1,140 @@
/* global AFRAME, THREE */
if (typeof AFRAME === 'undefined') {
throw new Error('Component attempted to register before AFRAME was available.');
if (typeof AFRAME === "undefined") {
throw new Error(
"Component attempted to register before AFRAME was available."
);
}

/**
* Cubemap component for A-Frame.
*
* Adapted from "Skybox and environment map in Three.js" by Roman Liutikov
* https://web.archive.org/web/20160206163422/https://blog.romanliutikov.com/post/58705840698/skybox-and-environment-map-in-threejs
*
*/
AFRAME.registerComponent('cubemap', {
AFRAME.registerComponent("cubemap", {
schema: {
folder: {
type: 'string'
type: "string",
},
edgeLength: {
type: 'int',
default: 5000
type: "int",
default: 5000,
},
ext: {
type: 'string',
default: 'jpg'
type: "string",
default: "jpg",
},
transparent: {
type: 'boolean',
default: false
}
},

/**
* Called when component is attached and when component data changes.
* Generally modifies the entity based on the data.
* Called once when the component is initialized.
* Used to set up initial state and instantiate variables.
*/
update: function (oldData) {
init: function () {
// entity data
var el = this.el;
var data = this.data;

// Path to the folder containing the 6 cubemap images
var srcPath = data.folder;

// Cubemap image files must follow this naming scheme
// from: http://threejs.org/docs/index.html#Reference/Textures/CubeTexture
var urls = [
'posx', 'negx',
'posy', 'negy',
'posz', 'negz'
];
// Apply extension
urls = urls.map(function(val) {
return val + "." + data.ext;
});

// Code that follows is adapted from "Skybox and environment map in Three.js" by Roman Liutikov
// http://blog.romanliutikov.com/post/58705840698/skybox-and-environment-map-in-threejs
const el = this.el;
const data = this.data;

var shader = THREE.ShaderLib['cube']; // init cube shader from built-in lib
// A Cubemap can be rendered as a mesh composed of a BoxBufferGeometry and
// ShaderMaterial. EdgeLength will scale the mesh
this.geometry = new THREE.BoxBufferGeometry(1, 1, 1);

// Create shader material
var skyBoxShader = new THREE.ShaderMaterial({
// Now for the ShaderMaterial.
const shader = THREE.ShaderLib["cube"];
// Note: cloning the material is necessary to prevent the cube shader's
// uniforms from being mutated. If the material was not cloned, all cubemaps
// in the scene would share the same uniforms (and look identical).
this.material = new THREE.ShaderMaterial({
fragmentShader: shader.fragmentShader,
vertexShader: shader.vertexShader,
uniforms: shader.uniforms,
depthWrite: false,
side: THREE.BackSide,
transparent: data.transparent
}).clone();
// Threejs seems to have removed the 'tCube' uniform.
// Workaround from: https://stackoverflow.com/a/59454999/6591491
Object.defineProperty(this.material, "envMap", {
get: function () {
return this.uniforms.envMap.value;
},
});
// A dummy texture is needed (otherwise the shader will be invalid and spew
// a million errors)
this.material.uniforms["envMap"].value = new THREE.Texture();
this.loader = new THREE.CubeTextureLoader();

// Set skybox dimensions
var edgeLength = data.edgeLength;
var skyBoxGeometry = new THREE.CubeGeometry(edgeLength, edgeLength, edgeLength);
// We can create the mesh now and update the material with a texture later on
// in the update lifecycle handler.
this.mesh = new THREE.Mesh(this.geometry, this.material);
this.mesh.scale.set(data.edgeLength, data.edgeLength, data.edgeLength);
el.setObject3D("cubemap", this.mesh);
},

// Create loader, set folder path, and load cubemap textures
var loader = new THREE.CubeTextureLoader();
loader.setPath(srcPath);
loader.load(urls, function(texture) {
// Clone ShaderMaterial (necessary for multiple cubemaps)
var skyBoxMaterial = skyBoxShader.clone();
// Threejs seems to have removed the 'tCube' uniform.
// Workaround from: https://stackoverflow.com/a/59454999/6591491
Object.defineProperty(skyBoxMaterial, "envMap", {
get: function () {
return this.uniforms.envMap.value;
},
/**
* Called when component is attached and when component data changes.
* Generally modifies the entity based on the data.
*/
update: function (oldData) {
// entity data
const el = this.el;
const data = this.data;
const rendererSystem = el.sceneEl.systems.renderer;

if (data.edgeLength !== oldData.edgeLength) {
// Update the size of the skybox.
this.mesh.scale.set(data.edgeLength, data.edgeLength, data.edgeLength);
}

if (data.ext !== oldData.ext || data.folder !== oldData.folder) {
// Load textures.
// Path to the folder containing the 6 cubemap images
const srcPath = data.folder;
// Cubemap image files must follow this naming scheme
// from: http://threejs.org/docs/index.html#Reference/Textures/CubeTexture
var urls = ["posx", "negx", "posy", "negy", "posz", "negz"];
// Apply extension
urls = urls.map(function (val) {
return val + "." + data.ext;
});
texture.encoding = THREE.sRGBEncoding;
skyBoxMaterial.uniforms["envMap"].value = texture; // Apply cubemap textures to shader uniforms

// Set entity's object3D
el.setObject3D('cubemap', new THREE.Mesh(skyBoxGeometry, skyBoxMaterial));
});
// Set folder path, and load cubemap textures
this.loader.setPath(srcPath);
this.loader.load(urls, onTextureLoad.bind(this));

function onTextureLoad(texture) {
if (srcPath !== this.data.folder) {
// The texture that just finished loading no longer matches the folder
// set on this component. This can happen when the user calls setAttribute()
// to change folders multiple times in quick succession.
texture.dispose();
return;
}
// Have the renderer system set texture encoding as in A-Frame core.
// https://github.com/bryik/aframe-cubemap-component/issues/13#issuecomment-626238202
rendererSystem.applyColorCorrection(texture);

// Apply cubemap texture to shader uniforms and dispose of the old texture.
const oldTexture = this.material.uniforms["envMap"].value;
this.material.uniforms["envMap"].value = texture;
if (oldTexture) {
oldTexture.dispose();
}

// Tell the world that the cubemap texture has loaded.
el.emit("cubemapLoaded");
}
}
},

/**
* Called when a component is removed (e.g., via removeAttribute).
* Generally undoes all modifications to the entity.
*/
remove: function () {
this.el.removeObject3D('cubemap');
}
this.geometry.dispose();
this.material.uniforms["envMap"].value.dispose();
this.material.dispose();
this.el.removeObject3D("cubemap");
},
});

0 comments on commit 6237d64

Please sign in to comment.