Jump to content

Small physics-scene with Babylon.js


Recommended Posts

Hello forum,

 

i am trying for hours to get this little physics scene running, but the cube is always falling through the basement, could you give me some advise please?

 

My code:

<!doctype html><html><head>    <script type="text/javascript" src="babylon.1.12-beta.js"></script>    <script type="text/javascript" src="hand-1.3.8.js"></script>    <script type="text/javascript" src="cannon.min.js"></script>    <style type="text/css">        html,        body,        div,        canvas {            width: 100%;            height: 100%;            padding: 0;            margin: 0;            overflow: hidden;        }    </style></head><body>    <canvas id="canvas"></canvas>    <script type="text/javascript">        var canvas = document.getElementById("canvas");        var engine = new BABYLON.Engine(canvas, true);        var scene = new BABYLON.Scene(engine);        scene.clearColor = new BABYLON.Color3(1, 1, .75); //set Background-Color        scene.enablePhysics(new BABYLON.Vector3(0, -9.81, 0));         //New Antialias Post        var postProcess = new BABYLON.FxaaPostProcess("fxaa", 1.0, null, null, engine, true);        var light = new BABYLON.DirectionalLight("Omni", new BABYLON.Vector3(-10, 10, 10), scene);        var light_fill = new BABYLON.PointLight("Point", new BABYLON.Vector3(-10, 80, 25), scene);        var camera = new BABYLON.DeviceOrientationCamera("DevOr_camera", new BABYLON.Vector3(0, 50, -300), scene);         //view field of the camera        camera.minZ = 0;        camera.maxZ = 10000;        camera.applyGravity = true;        camera.attachPostProcess(postProcess); //ATTACH POST PROCESS        var createRect = function (width, height, depth) {            var box = new BABYLON.Mesh.CreateBox("box", 10, scene);            box.scaling = new BABYLON.Vector3(width, height, depth);            return box;        };         //Creation of spheres        var object = createRect(1, 1, 1);        object.position.x = 0;        object.position.y = 50;        object.position.z = -200;        object.checkCollisions = true;                //set Physics for cube        object.setPhysicsState({            impostor: BABYLON.PhysicsEngine.BoxImpostor,            mass: 1,            friction: 0.4,            restitution: 0.3        });        var ground = createRect(50, .25, 50);        ground.checkCollisions = true;                //set physics for ground object        ground.setPhysicsState({            impostor: BABYLON.PhysicsEngine.BoxImpostor,            mass: 0,            friction: 0.7,            restitution: 0.7        });         //assign materials        object.material = new BABYLON.StandardMaterial("texture", scene);        object.material.diffuseTexture = new BABYLON.Texture("woodTex.jpg", scene);                ground.material = new BABYLON.StandardMaterial("texture_2",scene);        ground.material.diffuseTexture = new BABYLON.Texture("grassTex.jpg",scene);         // Attach the camera to the scene        scene.activeCamera.attachControl(canvas);         // Once the scene is loaded, just register a render loop to render it        engine.runRenderLoop(function () {            scene.render();        });    </script></body></html>
Link to comment
Share on other sites

Hi gdttp!  (I hope you don't mind me calling you that.  Your name is LONG!)  Welcome to the forum.

 

To be honest, babylon.1.12 beta has bugs in its implementation of cannon.js.  It is experiencing the same problems I had with 1.8.0... something to do with delta... which I don't understand.  The gravity is going sideways, too, just like it was when I had problems back then.

 

So, here is your project in zip form .  I adjusted a few things... which you can re-adjust if you like.  First, I switched to babylon.js version 1.11.0, which is included in the zip.  I moved the box object to 0,50,0, and made your ground a bit smaller.  I adjusted your directional light to aim Y -1 straight down.  (You might want to position that up in the air a bit... I forgot to do that).  :)

 

I turned off your point light, I remmed-out your post process thing, I temporarily turned off your textures (easy to turn on again) and I turned on an arcRotateCamera instead of a device orientation camera.  The main thing is... your box is now falling straight down, and giving a little restitution bounce when it hits the ground.  It doesn't fall through the ground anymore, or at least not often.

 

If you have questions, feel free to ask them here.  I am sure you already know about our API documentation:

 

http://doc.babylonjs.com

 

And our wiki Home Menu:

 

https://github.com/BabylonJS/Babylon.js/wiki

 

Again, welcome, good to have you with us, and good luck on your physics engine testing.

Link to comment
Share on other sites

Ok I figured out the problem :)

 

First of all you cannot use a camera.minZ = 0 (I will check that and enforce a value like 0.001 in this case) because it generates a division by zero

 

Then you found an ugly bug in my cannon.js driver :)

 

you can grab the new beta on github it should be good now!

Link to comment
Share on other sites

Wow, thats very quick. Thank you very much. I tried to implement shadows in my scene and i think i did it the same way it is done in this example:

 

https://github.com/BabylonJS/Babylon.js/wiki/17-Shadows

 

But the shadow looks very strange :(

<!DOCTYPE html><html xmlns="http://www.w3.org/1999/xhtml"><head>    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />    <!-- <script type="text/javascript" src="./js/babylon.1.12-beta3.js"></script> -->    <script type="text/javascript" src="JS/babylon.1.11.0.js"></script>    <script type="text/javascript" src="JS/hand-1.3.8.js"></script>    <script type="text/javascript" src="JS/cannon.min.js"></script>    <style type="text/css">        html,        body,        div,        canvas {            width: 100%;            height: 100%;            padding: 0;            margin: 0;            overflow: hidden;        }    </style></head><body>    <canvas id="canvas"></canvas>    <script type="text/javascript">        var canvas = document.getElementById("canvas");        var engine = new BABYLON.Engine(canvas, true);        var scene = new BABYLON.Scene(engine);        scene.clearColor = new BABYLON.Color3(1, 1, .75); //set Background-Color        scene.enablePhysics(new BABYLON.Vector3(0, -9.81, 0));         //New Antialias Post        //var postProcess = new BABYLON.FxaaPostProcess("fxaa", 1.0, null, null, engine, true);        var light = new BABYLON.DirectionalLight("Omni", new BABYLON.Vector3(-5, -5, -5), scene);        light.intensity = 2;        light.position = new BABYLON.Vector3(0, 0, 0);        var shadowGenerator = new BABYLON.ShadowGenerator(512,light);        var ac = new BABYLON.ArcRotateCamera("ac", 10, 0, 0, new BABYLON.Vector3(0, 0, 0), scene);        //ac.attachPostProcess(postProcess);        ac.target = new BABYLON.Vector3(0, 1, 0);        ac.alpha = 0;        ac.radius = 120;        ac.beta = Math.PI / 4;        ac.wheelPrecision = 10;        scene.activeCamera = ac;        scene.activeCamera.attachControl(canvas);        var createRect = function (width, height, depth) {            var box = new BABYLON.Mesh.CreateBox("box", 10, scene);            box.scaling = new BABYLON.Vector3(width, height, depth);            return box;        };         //Creation of object        var object = createRect(1, 1, 1);        shadowGenerator.getShadowMap().renderList.push(object);        object.position.y = 50;        object.rotation.z = 45;        object.checkCollisions = true;         //set Physics for cube        object.setPhysicsState({            impostor: BABYLON.PhysicsEngine.BoxImpostor,            mass: 1,            friction: 0.4,            restitution: 0.3        });        var ground = createRect(25, .25, 25);        ground.receiveShadows = true;        ground.checkCollisions = true;         //set physics for ground object        ground.setPhysicsState({            impostor: BABYLON.PhysicsEngine.BoxImpostor,            mass: 0,            friction: 0.7,            restitution: 0.7        });         //assign materials        object.material = new BABYLON.StandardMaterial("texture", scene);        //object.material.diffuseTexture = new BABYLON.Texture("Textures/wood.jpg", scene);        ground.material = new BABYLON.StandardMaterial("texture_2", scene);        //ground.material.diffuseTexture = new BABYLON.Texture("Textures/grass.jpg", scene);         //repeat mapping        //ground.material.diffuseTexture.uScale = 6.0;        //ground.material.diffuseTexture.vScale = 6.0;         // Once the scene is loaded, just register a render loop to render it        engine.runRenderLoop(function () {            document.onclick = checkOnClick;            function checkOnClick(event) {                var newMesh = createRect(1, 1, 1);                shadowGenerator.getShadowMap().renderList.push(newMesh);                var x = 0;                var y = Math.random() * 50;                var z = 0;                newMesh.position.x = x;                newMesh.position.y = y;                newMesh.position.z = z;                newMesh.material = new BABYLON.StandardMaterial("texture", scene);                //newMesh.material.diffuseTexture = new BABYLON.Texture("Textures/wood.jpg", scene);                newMesh.setPhysicsState({                    impostor: BABYLON.PhysicsEngine.BoxImpostor,                    mass: 2,                    friction: 0.7,                    restitution: 0.7                });            };            scene.render();        });    </script></body></html>
Link to comment
Share on other sites

Hi again!  Looks like you are having good fun.

 

The main problem with your shadows... was that it needed a line... shadowGenerator.useVarianceShadowMap = false;

 

I am newbie myself, so I don't know why that caused such a major difference in your scene.  Maybe some experts will tell us more about it.  Anyway, below is another version of your scene, with quite a few changes, but not too many.  You are doing well.  I just tweaked a few things.

<!DOCTYPE html><html xmlns="http://www.w3.org/1999/xhtml"><head>	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />	<!-- <script type="text/javascript" src="./js/babylon.1.12-beta3.js"></script> -->	<script type="text/javascript" src="JS/babylon.1.11.0.js"></script>	<script type="text/javascript" src="JS/hand-1.3.8.js"></script>	<script type="text/javascript" src="JS/cannon.min.js"></script>	<style type="text/css">		html,body,div,canvas {			width: 100%;			height: 100%;			padding: 0;			margin: 0;			overflow: hidden;		}	</style></head><body>	<canvas id="canvas"></canvas>	<script type="text/javascript">		document.onclick = checkOnClick;		var canvas = document.getElementById("canvas");		var engine = new BABYLON.Engine(canvas, true);		var scene = new BABYLON.Scene(engine);		scene.clearColor = new BABYLON.Color3(1, 1, .75); //set Background-Color		scene.enablePhysics(new BABYLON.Vector3(0, -9.81, 0));		//New Antialias Post		//var postProcess = new BABYLON.FxaaPostProcess("fxaa", 1.0, null, null, engine, true);		var light = new BABYLON.DirectionalLight("dir", new BABYLON.Vector3(0, -1, 0), scene);		light.intensity = .5;		light.position = new BABYLON.Vector3(-20, 80, 20); // up in the air and off to the side a bit.		// in version 1.12, this is a function called light.setDirectionToTarget(target).  For 1.11, we do it manually.		// Setting a light's direction is not very easy.  The below line sets direction to aim at 0,0,0 automatically.		light.direction = BABYLON.Vector3.Normalize(BABYLON.Vector3.Zero().subtract(light.position));		var shadowGenerator = new BABYLON.ShadowGenerator(1024,light); // 1024 for less jaggies on the shadow.		shadowGenerator.useVarianceShadowMap = false; // I don't know why this line was needed, but it was the main shadow problem.		// This extra light... lights up the sides of the boxes that are away from the directional light.		// hemispheric lights often aim at the sky... thus its direction is set to Y = 1.		var light2 = new BABYLON.HemisphericLight("Hemi0", new BABYLON.Vector3(0, 1, 0), scene);		light2.intensity = .3;		var ac = new BABYLON.ArcRotateCamera("ac", 10, 0, 0, new BABYLON.Vector3(0, 0, 0), scene);		//ac.attachPostProcess(postProcess);		ac.target = new BABYLON.Vector3(0, 1, 0);		ac.alpha = 0;		ac.radius = 120;		ac.beta = 1.00;		ac.wheelPrecision = 10;		scene.activeCamera = ac;		scene.activeCamera.attachControl(canvas);		var createRect = function (width, height, depth) {			var box = new BABYLON.Mesh.CreateBox("box", 1, scene);			box.scaling = new BABYLON.Vector3(width, height, depth);			return box;		};		//Creation of object		var object = createRect(5, 5, 5);		shadowGenerator.getShadowMap().renderList.push(object);		object.position.y = Math.floor((Math.random()*50)+25); //  a random number between 25 and 50		// Object rotations on objects with their physics state set... is done differently... because they use quaternions.		// But for all types of rotations, the numbers generally range from -6.28 to +6.28 radians. .707 radians = 45 degrees.		object.rotate(BABYLON.Axis.X, .7, BABYLON.Space.LOCAL);		object.rotate(BABYLON.Axis.Z, 1.3, BABYLON.Space.LOCAL);		object.checkCollisions = true;		//set Physics for cube		object.setPhysicsState({			impostor: BABYLON.PhysicsEngine.BoxImpostor,			mass: 1,			friction: 0.4,			restitution: 0.3		});		//create the ground		// var ground = createRect(150, .25, 150);		// here is our mostly-undocumented createGround command... kind of handy.		var ground = BABYLON.Mesh.CreateGround("grnd", 100, 100, 2, scene);		ground.receiveShadows = true;		ground.checkCollisions = true;		//set physics for ground object		ground.setPhysicsState({			impostor: BABYLON.PhysicsEngine.BoxImpostor,			mass: 0,			friction: 0.7,			restitution: 0.7		});		//assign materials		object.material = new BABYLON.StandardMaterial("texture", scene);		//object.material.diffuseTexture = new BABYLON.Texture("Textures/wood.jpg", scene);		ground.material = new BABYLON.StandardMaterial("texture_2", scene);		ground.material.backFaceCulling = false; // this is so you can see the bottom of the ground.		//ground.material.diffuseTexture = new BABYLON.Texture("Textures/grass.jpg", scene);		//repeat mapping		//ground.material.diffuseTexture.uScale = 6.0;		//ground.material.diffuseTexture.vScale = 6.0;		// render loop!		engine.runRenderLoop(function () {			scene.render();		});		// I moved this function outside-of the render loop.  Better to keep the renderloop tiny.		// The onClick check is way at the top.  It does not need to be in the render loop.		function checkOnClick(event) {			var newMesh = createRect(5, 5, 5);			shadowGenerator.getShadowMap().renderList.push(newMesh);			var x = 0;			// var y = Math.random() * 50;			var y = Math.floor((Math.random()*50)+25); //  a random number between 25 and 50			var z = 0;			newMesh.position.x = x;			newMesh.position.y = y;			newMesh.position.z = z;			newMesh.material = new BABYLON.StandardMaterial("texture", scene);			//newMesh.material.diffuseTexture = new BABYLON.Texture("Textures/wood.jpg", scene);			newMesh.setPhysicsState({				impostor: BABYLON.PhysicsEngine.BoxImpostor,				mass: 2,				friction: 0.7,				restitution: 0.7			});		};	</script></body></html>

Even though I changed the way your ground is created (from your box method to our createGround PLANE method), I left the ground imposter as BoxImposter.  This allows your boxes to fall-off the edge of the ground.  If you DON'T want the boxes to fall off the edge, change your ground's BoxImposter to be PlaneImposter instead.  I still want to do some more studying on your project... to see if I can learn why some things are acting strange, but this will get you rolling sooner.  Be sure to increase your restitution numbers on your ground and boxes... for more bounce (and maybe more fun).  Your box stacking thing is quite fun already, isn't it?  I enjoyed watching the box activity while i adjusted things.  Keep up the good work on the your fun experiments.  You are becoming a babylon.js expert rather quickly.  Be well!

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...