UNPKG

p2s

Version:

A JavaScript 2D physics engine.

166 lines (149 loc) 5.34 kB
<html> <head> <style> body { font-family: "Comic Sans MS", sans-serif; } .red-block, .green-block { padding:5px; border: 2px solid black; border-radius:4px; } .red-block { background-color: #f46; } .green-block { background-color: #4b6; } </style> </head> <body> <!-- Create DOM elements to animate --> <div class="p2-dynamic-body red-block" style="position:absolute;left:175px;width:50px;height:50px;"> Cool! </div> <div class="p2-dynamic-body red-block"style="position:absolute;left:75px;width:50px;height:50px;"> DOM </div> <div class="p2-dynamic-body red-block"style="position:absolute;left:230px;width:50px;height:50px;"> Such </div> <div class="p2-dynamic-body red-block"style="position:absolute;left:280px;width:50px;height:50px;"> Physics </div> <div class="p2-dynamic-body red-block"style="position:absolute;left:100px;width:30px;height:50px;"> LOL </div> <div class="p2-static-body green-block" style="position:absolute;top:100px;left:100px;width:100px;height:100px"> p2.js </div> <script type="text/javascript" src="../../build/p2.js"></script> <script type="text/javascript"> // Create a World var world = new p2.World({ gravity : [0,-5], broadphase : new p2.SAPBroadphase() }); var fixedTimeStep = 1 / 30; var physicsToDOMScale = 30; // Multiply physics coordinate with this and you get the number of pixels in the dom // Create dynamic bodies var elements = document.querySelectorAll('.p2-dynamic-body'); for(var i=0; i<elements.length; i++){ var element = elements[i]; createBody(element, 1); } // Create static bodies var staticElements = document.querySelectorAll('.p2-static-body'); for(var i=0; i<staticElements.length; i++){ var element = staticElements[i]; createBody(element, 0); } // Add planes for browser window "walls" var body = document.body, html = document.documentElement; var height = Math.max( body.scrollHeight, body.offsetHeight, html.clientHeight, html.scrollHeight, html.offsetHeight ); var planeBottomBody = new p2.Body({ position: [0, - (height) / physicsToDOMScale] }); planeBottomBody.addShape(new p2.Plane()); world.addBody(planeBottomBody); var planeTopBody = new p2.Body({ position: [0, 0] }); planeTopBody.addShape(new p2.Plane(),[0,0],Math.PI); world.addBody(planeTopBody); var planeLeftBody = new p2.Body(); planeLeftBody.addShape(new p2.Plane(),[0,0],-Math.PI/2); world.addBody(planeLeftBody); var planeRightBody = new p2.Body({ position: [ (document.body.getBoundingClientRect().width) / physicsToDOMScale,0] }); planeRightBody.addShape(new p2.Plane(),[0,0],Math.PI/2); world.addBody(planeRightBody); // Create a body from an element in the DOM, with the given mass function createBody(element, mass){ var rect = element.getBoundingClientRect(); var body = new p2.Body({ mass : mass, position: [ (rect.left + rect.width / 2) / physicsToDOMScale, -(rect.top + rect.height / 2) / physicsToDOMScale ], angle:0 }); var shape = new p2.Box({ width: rect.width / physicsToDOMScale, height: rect.height / physicsToDOMScale }); body.addShape(shape); world.addBody(body); element.style.position = 'absolute'; element.style.top = 0; element.style.left = 0; element.style.transformOrigin = '50% 50%'; updateTransform(body, element); } // The animation loop var lastTimeMilliSeconds; function update(timeMilliSeconds){ requestAnimationFrame(update); if(lastTimeMilliSeconds){ var deltaTime = (timeMilliSeconds - lastTimeMilliSeconds) / 1000; world.step(fixedTimeStep, deltaTime, 5); updateTransforms(); } lastTimeMilliSeconds = timeMilliSeconds; } function updateTransform(body, element){ // Convert physics coordinates to pixels var x = physicsToDOMScale * (body.interpolatedPosition[0] - body.shapes[0].width/2); var y = -physicsToDOMScale * (body.interpolatedPosition[1] + body.shapes[0].height/2); // Set element style var style = 'translate(' + x + 'px, ' + y + 'px) rotate(' + (-body.interpolatedAngle * 57.2957795) + 'deg)'; element.style.transform = style; element.style.WebkitTransform = style + ' translateZ(0)'; // Force HW Acceleration element.style.MozTransform = style; element.style.OTransform = style; element.style.msTransform = style; } // Update all element transforms function updateTransforms(){ // Update dynamic bodies for ( i = 0; i < elements.length; i++ ) { var body = world.bodies[i]; var element = elements[i]; updateTransform(body, element); } // Update static bodies for ( i = 0; i < staticElements.length; i++ ) { var body = world.bodies[elements.length + i]; var element = staticElements[i]; updateTransform(body, element); } } // Start animation requestAnimationFrame(update); </script> </body> </html>