[SOLVED] OBJLoader in Layers

Hey all, fairly new to Javascript but I am trying to combine the Web GL layers example with the OBJ Loader.

So far I have most of the functionality I need, such as an orbital camera, layers I can switch on and off and custom background.

	<head>
	<title>three.js webgl - layers</title>
	<meta charset="utf-8">
	<meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
	<style>
		body {
			font-family: Monospace;
			background-color: #f0f0f0;
			margin: 0px;
			overflow: hidden;
		}

		#info {
			position: absolute;
			top: 10px;
			width: 100%;
			text-align: center;
			z-index: 0; // to not conflict with dat.gui
			display:block;
		}
	</style>
</head>
<body>



	<script src="../build/three.js"></script>

	<script src="js/libs/stats.min.js"></script>
	<script src='js/libs/dat.gui.min.js'></script>
	<script src="js/controls/OrbitControls.js"></script>
	<script src="js/loaders/GLTFLoader.js"></script>
	<script src="js/WebGL.js"></script>


	<script>
		if ( WEBGL.isWebGLAvailable() === false ) {

			document.body.appendChild( WEBGL.getWebGLErrorMessage() );

		}
		var container;
		var camera, scene, renderer;
		var controls 
		var radius = 100, theta = 0;
		
		init();
		animate();

		function init() {

			container = document.createElement( 'div' );
			document.body.appendChild( container );

			camera = new THREE.PerspectiveCamera( 30, window.innerWidth / window.innerHeight, 1, 10000 );
			camera.position.set( 1000, 50, 1500 );
			camera.lookAt( 0, 0, 0 );
			camera.layers.enable( 0 ); // enabled by default
			camera.layers.enable( 1 );
			camera.layers.enable( 2 );
			



			scene = new THREE.Scene();
			scene.background = new THREE.Color( 0x022000 );

			var light = new THREE.PointLight( 0xffffff, 1 );
			light.layers.enable( 0 );
			light.layers.enable( 1 );
			light.layers.enable( 2 );

			scene.add( camera );
			camera.add( light );

			var colors = [ 0xff0000, 0x00ff00, 0x0000ff ];
			var geometry = new THREE.BoxBufferGeometry( 20, 20, 20 );
			var layer;

			for ( var i = 0; i < 300; i ++ ) {

				layer = ( i % 3 );

				var object = new THREE.Mesh( geometry, new THREE.MeshLambertMaterial( { color: colors[ layer ] } ) );

				object.position.x = Math.random() * 800 - 400;
				object.position.y = Math.random() * 800 - 400;
				object.position.z = Math.random() * 800 - 400;

				object.rotation.x = Math.random() * 2 * Math.PI;
				object.rotation.y = Math.random() * 2 * Math.PI;
				object.rotation.z = Math.random() * 2 * Math.PI;

				object.scale.x = Math.random() + 0.5;
				object.scale.y = Math.random() + 0.5;
				object.scale.z = Math.random() + 0.5;

				object.layers.set( layer );

				scene.add( object );
				



			}


			raycaster = new THREE.Raycaster();

			renderer = new THREE.WebGLRenderer();
			renderer.setPixelRatio( window.devicePixelRatio );
			renderer.setSize( window.innerWidth, window.innerHeight );
			container.appendChild(renderer.domElement);


			var layers = { red: true, green: true, blue: true };

			//
			// Init gui
			var gui = new dat.GUI();
			gui.add( layers, 'red' ).onChange( function () { camera.layers.toggle( 0 ); } );
			gui.add( layers, 'green' ).onChange( function () { camera.layers.toggle( 1 ); } );
			gui.add( layers, 'blue' ).onChange( function () { camera.layers.toggle( 2 ); } );

			window.addEventListener( 'resize', onWindowResize, false );
			
			var controls = new THREE.OrbitControls( camera, renderer.domElement );
			controls.maxPolarAngle = Math.PI * 0.99;
			controls.minDistance = 1000;
			controls.maxDistance = 5000;

		}
		


		function onWindowResize() {

			camera.aspect = window.innerWidth / window.innerHeight;
			camera.updateProjectionMatrix();

			renderer.setSize( window.innerWidth, window.innerHeight );

		}

		//

		function animate() {

			requestAnimationFrame( animate );

			render();
			stats.update();

		}

		function render() {





			renderer.render( scene, camera );

		}

	</script>

</body>
Does anyone know how I might switch the blocks to OBJs?

I’ve created a fiddle from your code and enhanced it a bit. The code now uses OBJLoader in order to load a model from the three.js repository. The asset is used instead of the box. Hope this helps.

Thank you @Mugen87, this is great. I hate to ask of more, but would it be possible to add a different 3D model on each layer?

In this case, you basically have three calls of OBJLoader.load(). The code of the onLoad() callback is identical except that you don’t have to compute the layer variable on the fly. You can assign a fix value to the objects per model.

I don’t fully understand @Mugen87. I managed to reduce the amount of models to 1, and to get it centered. However, when I add another loader I get errors which seem to be unrelated. I am likely implementing this all wrong, going to keep looking.

var container;
var camera, scene, renderer;
var controls 
var radius = 100, theta = 0;

init();
animate();

function init() {

  container = document.createElement( 'div' );
  document.body.appendChild( container );

  camera = new THREE.PerspectiveCamera( 30, window.innerWidth / window.innerHeight, 1, 10000 );
  camera.position.set( 1000, 50, 1500 );
  camera.lookAt( 0, 0, 0 );
  camera.layers.enable( 0 ); // enabled by default
  camera.layers.enable( 1 );
  camera.layers.enable( 2 );

  scene = new THREE.Scene();
  scene.background = new THREE.Color( 0x022000 );

  var light = new THREE.PointLight( 0xffffff, 1 );
  light.layers.enable( 0 );
  light.layers.enable( 1 );
  light.layers.enable( 2 );

  scene.add( camera );
  camera.add( light );


  
  var loader = new THREE.OBJLoader();
  loader.load( 'assets/emerald.obj', function ( obj ) {
  
 {
       var layer = 0
    var object = obj.children[ 0 ].clone();
      scene.add( object );
    
    }
	
	  loader.load( 'assets/tree.obj', function ( obj ) {
  
 {
       var layer = 1
    var object = obj.children[ 1 ].clone();
      scene.add( object );
    
    }

	
	
	
	
  
  } );

  raycaster = new THREE.Raycaster();

  renderer = new THREE.WebGLRenderer();
  renderer.setPixelRatio( window.devicePixelRatio );
  renderer.setSize( window.innerWidth, window.innerHeight );
  container.appendChild(renderer.domElement);


  var layers = { red: true, green: true, blue: true };

  //
  // Init gui
  var gui = new dat.GUI();
  gui.add( layers, 'red' ).onChange( function () { camera.layers.toggle( 0 ); } );
  gui.add( layers, 'green' ).onChange( function () { camera.layers.toggle( 1 ); } );
  gui.add( layers, 'blue' ).onChange( function () { camera.layers.toggle( 2 ); } );

  window.addEventListener( 'resize', onWindowResize, false );

  var controls = new THREE.OrbitControls( camera, renderer.domElement );
  controls.maxPolarAngle = Math.PI * 0.99;
  controls.minDistance = 1000;
  controls.maxDistance = 5000;

}

function onWindowResize() {

  camera.aspect = window.innerWidth / window.innerHeight;
  camera.updateProjectionMatrix();

  renderer.setSize( window.innerWidth, window.innerHeight );

}

//

function animate() {

  requestAnimationFrame( animate );

  render();

}

function render() {

  renderer.render( scene, camera );

}

What kind of errors? Can you please be more specific? For example, posting the error messages is a good start.

BTW: Just declaring the layer variable is not enough. You also have to set the layer via object.layers.set( layer );.

Thank you Mugen, they were syntax errors, I got them sorted out and found two methods of adding OBJs to layers. One method ensures they load to specific layers so that they can be toggled with labeled dat.gui menus. Now to texture them is the next challenge.