{"id":193,"date":"2011-02-11T16:01:11","date_gmt":"2011-02-11T15:01:11","guid":{"rendered":"http:\/\/www.aymericlamboley.fr\/blog\/?p=193"},"modified":"2014-11-01T15:11:17","modified_gmt":"2014-11-01T14:11:17","slug":"box2d-with-the-worldconstructionkit","status":"publish","type":"post","link":"http:\/\/www.aymericlamboley.fr\/blog\/box2d-with-the-worldconstructionkit\/","title":{"rendered":"Box2D with the WorldConstructionKit"},"content":{"rendered":"<p>Before the weekend, I suggest to dig into the Box2D API for Flash with the great <a href=\"http:\/\/www.sideroller.com\/wck\/\"><strong>WorldConstructionKit<\/strong><\/a>.<br \/>\nBox2D is a physical engine wrote in C++ and translated into many languages such as Java, Objective-C, AS3, JavaScript&#8230;<\/p>\n<p>For ActionScript3, there are 2 ports : Boris the brave&#8217;s port, and the WCK. You can find a performance comparison <a href=\"http:\/\/blog.allanbishop.com\/box2d-as3-port-showdown\/#more-390\">here<\/a> made by Allan Bishop.<br \/>\nThe WCK is the best thanks to the Alchemy port : it translates the C++ into something which can be understable by Flash. More information <a href=\"http:\/\/labs.adobe.com\/technologies\/alchemy\/\"><strong>here<\/strong><\/a>.<\/p>\n<p>The WCK provides a &#8220;a toolset \/ framework for rapidly developing physics based games \/ websites within the Flash IDE. WCK allows you to layout your 2d worlds \/ game levels entirely within Flash and have them hook into the physics simulation without writing any code.&#8221;<\/p>\n<p><!--more--><\/p>\n<p>Here are some demos I made with it :<br \/>\n<a href=\"http:\/\/www.aymericlamboley.fr\/blog\/wp-content\/uploads\/2011\/02\/circle.swf\" rel=\"lightbox[flash 550 400]\"><strong>A simple circle <\/strong><\/a>made without any code, only with MovieClip on the Stage and propreties added by the WCK components (dynamic object -> the circle vs static objects -> the wall). If you wish the camera followed the circle, just add the name of your MovieClip in the focusOn property of your World; don&#8217;t forget to check the scrolling&#8217;s property too.<\/p>\n<p><a href=\"http:\/\/www.aymericlamboley.fr\/blog\/wp-content\/uploads\/2011\/02\/FlashMario.swf\" rel=\"lightbox[flash 550 400]\"><strong>A simple Mario game<\/strong><\/a>. In this case, for sure, there is some programming. (Do not forget to click into the windows before pressing any keys)<\/p>\n<p>The code of the AI :<\/p>\n<pre lang=\"actionscript3\" line=\"1\">package {\r\n\r\n\timport Box2DAS.Common.V2;\r\n\timport Box2DAS.Dynamics.StepEvent;\r\n\r\n\timport shapes.Box;\r\n\r\n\timport flash.events.Event;\r\n\r\n\t\/**\r\n\t * @author Aymeric\r\n\t *\/\r\n\t \r\n\tpublic class Momie extends Box {\r\n\r\n\t\tprivate var _arriere:Boolean;\r\n\r\n\t\tpublic function Momie() {\r\n\r\n\t\t\tthis.addEventListener(Event.ADDED_TO_STAGE, _init);\r\n\t\t}\r\n\r\n\t\tprivate function _init(evt:Event):void {\r\n\r\n\t\t\tthis.removeEventListener(Event.ADDED_TO_STAGE, _init);\r\n\t\t}\r\n\r\n\t\tpublic override function create():void {\r\n\t\t\treportBeginContact = true;\r\n\t\t\treportEndContact = true;\r\n\t\t\tsuper.create();\r\n\r\n\t\t\tlistenWhileVisible(world, StepEvent.STEP, _parseInput);\r\n\t\t}\r\n\r\n\t\tprivate function _parseInput(evt:Event):void {\r\n\r\n\t\t\tif (_arriere == false) {\r\n\t\t\t\tif (this.x < 800) {\r\n\t\t\t\t\tb2body.ApplyImpulse(new V2(0.2, 0), b2body.GetWorldCenter());\r\n\t\t\t\t} else {\r\n\t\t\t\t\t_arriere = true;\r\n\t\t\t\t\tthis.gotoAndPlay(\"marche_gauche\");\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\r\n\t\t\t\tif (this.x > 30) {\r\n\t\t\t\t\tb2body.ApplyImpulse(new V2(-0.2, 0), b2body.GetWorldCenter());\r\n\t\t\t\t\t\r\n\t\t\t\t} else {\r\n\t\t\t\t\t_arriere = false;\r\n\t\t\t\t\tthis.gotoAndPlay(\"marche_droite\");\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t}\r\n\t}\r\n}<\/pre>\n<p>Nothing too complex, but note that the character moved thanks to some force vector working with impulsion. Not as simple than an old x++ \ud83d\ude09<\/p>\n<p>And now the Hero :<\/p>\n<pre lang=\"actionscript3\" line=\"1\">package {\r\n\r\n\timport Box2DAS.Collision.*;\r\n\timport Box2DAS.Common.*;\r\n\timport Box2DAS.Dynamics.*;\r\n\r\n\timport misc.*;\r\n\r\n\timport shapes.*;\r\n\r\n\timport wck.*;\r\n\r\n\timport flash.events.*;\r\n\timport flash.utils.Timer;\r\n\t\r\n\t\/**\r\n\t * @author Aymeric\r\n\t *\/\r\n\r\n\tpublic class Heros extends Box {\r\n\r\n\t\tpublic var contacts:ContactList;\r\n\r\n\t\tprivate var _momie:Momie;\r\n\t\tprivate var _memoireSens:String;\r\n\t\tprivate var _timer:Timer;\r\n\r\n\t\tpublic function Heros() {\r\n\r\n\t\t\tthis.addEventListener(Event.ADDED_TO_STAGE, _init);\r\n\t\t}\r\n\r\n\t\tprivate function _init(evt:Event):void {\r\n\r\n\t\t\tthis.removeEventListener(Event.ADDED_TO_STAGE, _init);\r\n\t\t}\r\n\r\n\t\tpublic override function create():void {\r\n\r\n\t\t\treportBeginContact = true;\r\n\t\t\treportEndContact = true;\r\n\t\t\t\/\/ fixedRotation = true;\r\n\t\t\tsuper.create();\r\n\t\t\tlistenWhileVisible(world, StepEvent.STEP, parseInput, false, 10);\r\n\t\t\tlistenWhileVisible(this, ContactEvent.BEGIN_CONTACT, handleContact);\r\n\t\t\tcontacts = new ContactList();\r\n\t\t\tcontacts.listenTo(this);\r\n\t\t}\r\n\r\n\t\tpublic function handleContact(ctcEvt:ContactEvent):void {\r\n\r\n\t\t\t_momie = ctcEvt.other.m_userData as Momie;\r\n\t\t\tvar piece:Circle = ctcEvt.other.m_userData as Circle;\r\n\t\t\tif (_momie) {\r\n\t\t\t\t\/\/ Util.addChildAtPosOf(world, new Boum(), p);\r\n\r\n\t\t\t\t_momie.gotoAndStop(\"mort\");\r\n\t\t\t\t_momie.removeAllListeners();\r\n\r\n\t\t\t\t_timer = new Timer(500, 1);\r\n\t\t\t\t_timer.addEventListener(TimerEvent.TIMER_COMPLETE, _supprimerMomie);\r\n\t\t\t\t_timer.start();\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tif (piece) {\r\n\t\t\t\tpiece.remove();\r\n\t\t\t\tpiece = null;\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tprivate function _supprimerMomie(tEvt:TimerEvent):void {\r\n\t\t\t\r\n\t\t\t_momie.remove();\r\n\t\t\t_momie = null;\r\n\r\n\t\t\t_timer.removeEventListener(TimerEvent.TIMER_COMPLETE, _supprimerMomie);\r\n\t\t\t_timer = null;\r\n\t\t}\r\n\r\n\t\tpublic function parseInput(e:Event):void {\r\n\t\t\tvar manifold:b2WorldManifold = null;\r\n\t\t\tvar dot:Number = -1;\r\n\t\t\tif (!contacts.isEmpty()) {\r\n\t\t\t\tcontacts.forEach(function(keys:Array, c:ContactEvent) {\r\n\t\t\t\t\tvar wm:b2WorldManifold = c.getWorldManifold();\r\n\t\t\t\t\tif (wm.normal) {\r\n\t\t\t\t\t\tvar d:Number = wm.normal.dot(gravity);\r\n\t\t\t\t\t\tif (!manifold || d > dot) {\r\n\t\t\t\t\t\t\tmanifold = wm;\r\n\t\t\t\t\t\t\tdot = d;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t});\r\n\t\t\t\tcontacts.clean();\r\n\t\t\t}\r\n\t\t\tvar left:Boolean = Input.kd('A', 'LEFT');\r\n\t\t\tvar right:Boolean = Input.kd('D', 'RIGHT');\r\n\t\t\tvar jump:Boolean = Input.kp(' ', 'UP');\r\n\t\t\tvar v:V2;\r\n\r\n\t\t\tif (jump && manifold) {\r\n\r\n\t\t\t\tv = manifold.normal.clone().multiplyN(-7);\r\n\t\t\t\tb2body.ApplyImpulse(v, b2body.GetWorldCenter());\r\n\r\n\t\t\t} else if (left) {\r\n\r\n\t\t\t\tif (this.currentLabel != \"marche_gauche\") {\r\n\t\t\t\t\tthis.gotoAndPlay(\"marche_gauche\");\r\n\t\t\t\t}\r\n\t\t\t\tb2body.ApplyImpulse(new V2(-0.2, 0), b2body.GetWorldCenter());\r\n\t\t\t\t_memoireSens = \"gauche\";\r\n\r\n\t\t\t} else if (right) {\r\n\r\n\t\t\t\tif (this.currentLabel != \"marche_droite\") {\r\n\t\t\t\t\tthis.gotoAndPlay(\"marche_droite\");\r\n\t\t\t\t}\r\n\t\t\t\tb2body.ApplyImpulse(new V2(0.2, 0), b2body.GetWorldCenter());\r\n\t\t\t\t_memoireSens = \"droite\";\r\n\r\n\t\t\t} else {\r\n\t\t\t\tif (_memoireSens == \"gauche\") {\r\n\t\t\t\t\tthis.gotoAndPlay(\"init_gauche\");\r\n\t\t\t\t} else {\r\n\t\t\t\t\tthis.gotoAndPlay(\"init_droite\");\r\n\t\t\t\t}\r\n\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n}<\/pre>\n<p>There are some collisions problem to handle, I haven&#8217;t found the best resolution yet&#8230;<\/p>\n<p>To conclude I found that the WCK is really a great tool to create a dynamic world ! I&#8217;m sure that a breakout game is really easy to make with the WCK, but if you want to make something very complex, you must learn Box2D and have some knowledges of C++.<\/p>\n<p>Recently, I tried the <a href=\"http:\/\/citrusengine.com\/\">Citrus Engine<\/a> and find it awesome. It is a game engine based on Box2D (but not the WCK), but I&#8217;m sad, it is no more supported&#8230; However maybe, I will make a school project with it.<br \/>\nStay tuned !<\/p>\n<p><a target=\"_blank\" href=\"http:\/\/www.aymericlamboley.fr\/blog\/wp-content\/uploads\/2011\/02\/BOX2D.zip\">The zip files of the little game.<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Before the weekend, I suggest to dig into the Box2D API for Flash with the great WorldConstructionKit. Box2D is a physical engine wrote in C++ and translated into many languages such as Java, Objective-C, AS3, JavaScript&#8230; For ActionScript3, there are 2 ports : Boris the brave&#8217;s port, and the WCK. You can find a performance &hellip; <a href=\"http:\/\/www.aymericlamboley.fr\/blog\/box2d-with-the-worldconstructionkit\/\" class=\"more-link\">Continue reading <span class=\"screen-reader-text\">Box2D with the WorldConstructionKit<\/span> <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0},"categories":[4,115,11,114],"tags":[8,15,27,26,28],"_links":{"self":[{"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/posts\/193"}],"collection":[{"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/comments?post=193"}],"version-history":[{"count":7,"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/posts\/193\/revisions"}],"predecessor-version":[{"id":1304,"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/posts\/193\/revisions\/1304"}],"wp:attachment":[{"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/media?parent=193"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/categories?post=193"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/www.aymericlamboley.fr\/blog\/wp-json\/wp\/v2\/tags?post=193"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}