< Back to Examples

Car Configurator

Open Scene in the Editor

This example shows how to have a car within an environment, and update its materials.

HTML + Javascript

As you can see, we can create html elements and add callbacks to them to modify the materials in just a few lines.

The most important ones are:

embed.on('scene_load', ()=>{

Here we wait for the scene to load. Once it has loaded, we can get the nodes we need to modify, with:

car_roof_material_node = scene.node('/MAT/car_roof')

This is the node that controls the material applied to the roof of the car. Once we have it, look at the callback assign to the button elements with the onclick attribute. For instance, the first one for the roof is:

onclick='set_roof(this, {color: [0.02,0.02,0.02]})'

This will call the method set_roof, with the argument {color: [0.02,0.02,0.02]}. This in turns will call

node.param(param_name).set(param_value)

which, if we replaced param_name and param_value by the argments, would become:

node.param('color').set([0.02,0.02,0.02])

And this is what will change the color of the roof.

Here is the full html+javascript for the configurator above:

<!DOCTYPE html>
<html>
<head>
<script src="https://unpkg.com/polygonjs-embed@1.0.7/dist/polygonjs-embed.min.js"></script>
<style>
	html, body {height:100%;margin:0px} iframe {display:block;}
	body {font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen, Ubuntu, Cantarell, "Fira Sans", "Droid Sans", "Helvetica Neue", sans-serif }
	.controls-container {position:absolute;text-align:left;padding:10px}
	label {display: inline-block; width: 60px}
	.button {display: inline-block; margin-right: 5px; width: 16px; height:16px; border-radius: 16px; border: 2px solid lightgrey; cursor: pointer; position: relative; top: 4px}
	.button:hover {opacity: 0.8}
	.button.black {background-color: black; }
	.button.white {background-color: white; }
	.button.red   {background-color: red; }
	.button.blue  {background-color: blue; }
	.button.purple   {background-color: purple; }
	.button.silver  {background-color: silver; }
	.button.active  {border-color: green; }
</style>
</head>

<body>

	<div class='controls-container'>

	<div>
	<label> Roof: </label>
	<span class='button black' id='roof_black' onclick='set_roof(this, {color: [0.02,0.02,0.02]})'></span>
	<span class='button white' id='roof_white' onclick='set_roof(this, {color: [0.51,0.51,0.51]})'></span>
	<span class='button blue'  id='roof_blue'  onclick='set_roof(this, {color: [0.1,0.02,0.45]})'></span>
	</div>

	<div>
	<label> Body: </label>
	<span class='button black' id='body_black' 	 onclick='set_body(this, {color: [0,0,0]})'></span>
	<span class='button white' id='body_white' 	 onclick='set_body(this, {color: [0.7,0.7,0.7]})'></span>
	<span class='button red' id='body_red' 		 onclick='set_body(this, {color: [0.51,0,0]})'></span>
	<span class='button purple' id='body_purple' onclick='set_body(this, {color: [0.3,0.1,0.36]})'></span>
	</div>

	<div>
	<label> Wheels: </label>
	<span class='button silver' id='wheels_silver' onclick='set_wheels(this, {color: [1,1,1], metalness: 1, roughness: 0})'></span>
	<span class='button black' id='wheels_black'   onclick='set_wheels(this, {color: [0,0,0], metalness: 0.85, roughness: 0.5})'></span>
	<span class='button blue' id='wheels_blue'     onclick='set_wheels(this, {color: [0.05,0.1,0.4], metalness: 0.85, roughness: 0.5})'></span>
	</div>

	</div>

	<!-- load your scene iframe (from the editor, go to File->Embed, and toggle on 'Embed Active' to see your iframe html) -->
	<iframe frameborder='0' height='100%' width='100%' src='https://embed.polygonjs.com/scenes/a2e5b91c-00d4-4d3e-afff-b3cb5aa8be65?timestamp=1563363420' id='polygonjs-embed-iframe'></iframe>

	<script>
		// create the embed, with the id of the iframe
		var embed = new POLY.Embed('polygonjs-embed-iframe')
		var scene;
		var car_body_material_node;
		var car_wheels_material_node;

		var roof_button_ids = ['roof_black', 'roof_white', 'roof_blue']
		var body_button_ids = ['body_black', 'body_white', 'body_red', 'body_purple']
		var wheels_button_ids = ['wheels_silver', 'wheels_black', 'wheels_blue']

		// wait for the scene to load
		embed.on('scene_load', ()=>{
			scene = embed.scene()

			// get the nodes we need
			car_roof_material_node = scene.node('/MAT/car_roof')
			car_body_material_node = scene.node('/MAT/car_body')
			car_wheels_material_node = scene.node('/MAT/car_wheels')

			// init the first look
			document.getElementById('roof_black').click()
			document.getElementById('body_purple').click()
			document.getElementById('wheels_silver').click()
		})

		function set_roof(button_to_disable, options){
			set_node_params(car_roof_material_node, options)
			deactivate_buttons_except(roof_button_ids, button_to_disable)
		}
		function set_body(button_to_disable, options){
			set_node_params(car_body_material_node, options)
			deactivate_buttons_except(body_button_ids, button_to_disable)
		}
		function set_wheels(button_to_disable, options){
			set_node_params(car_wheels_material_node, options)
			deactivate_buttons_except(wheels_button_ids, button_to_disable)
		}

		function set_node_params(node, options){
			let param_value;
			for(let param_name of Object.keys(options)){
				param_value = options[param_name]

				// this is what will update the node, changing the material properties
				node.param(param_name).set(param_value)
			}
		}

		function deactivate_buttons_except(button_list, button_to_disable){
			let button;
			for(let body_button_id of button_list){
				button = document.getElementById(body_button_id)
				button.classList.remove('active')
			}
			button_to_disable.classList.add('active')
		}
	</script>

</body>

</html>

< Back to Examples