<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Jean-Marc Le Roux</title>
	<atom:link href="http://blogs.aerys.in/jeanmarc-leroux/feed/" rel="self" type="application/rss+xml" />
	<link>http://blogs.aerys.in/jeanmarc-leroux</link>
	<description>Web, RIAs and chocolate spaghettis...</description>
	<lastBuildDate>Wed, 13 Mar 2013 16:15:42 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.5.1</generator>
		<item>
		<title>Stage3D Online Conference Slides</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/02/22/stage3d-online-conference-slides/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/02/22/stage3d-online-conference-slides/#comments</comments>
		<pubDate>Fri, 22 Feb 2013 19:06:39 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[ActionScript 3.0]]></category>
		<category><![CDATA[event]]></category>
		<category><![CDATA[Flash 11]]></category>
		<category><![CDATA[iPad]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[Nexus 7]]></category>
		<category><![CDATA[slides]]></category>
		<category><![CDATA[sponza]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2420</guid>
		<description><![CDATA[It was really awesome to be invited to talk about Minko today during the Stage3D online conference organized by Sergey Gonchar. He has done an excellent job in organizing this and I hope people enjoyed attending it as much as I enjoyed being a part of it. You can watch the entire conference here. As [...]]]></description>
				<content:encoded><![CDATA[<p>It was really awesome to be invited to talk about Minko today during the Stage3D online conference organized by Sergey Gonchar. He has done an excellent job in organizing this and I hope people enjoyed attending it as much as I enjoyed being a part of it.</p>
<p><center><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_file_formats_comparison.jpg" rel="shadowbox[sbpost-2420];player=img;"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_file_formats_comparison-150x150.jpg" alt="minko_file_formats_comparison" width="150" height="150" class="size-thumbnail wp-image-2421" /></a> <a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_editor_workflow.jpg" rel="shadowbox[sbpost-2420];player=img;"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_editor_workflow-150x150.jpg" alt="minko_editor_workflow" width="150" height="150" class="size-thumbnail wp-image-2424" /></a> <a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_editor_triggers.jpg" rel="shadowbox[sbpost-2420];player=img;"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_editor_triggers-150x150.jpg" alt="minko_editor_triggers" width="150" height="150" class="size-thumbnail wp-image-2423" /></a> <a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_darksider.jpg" rel="shadowbox[sbpost-2420];player=img;"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_darksider-150x150.jpg" alt="minko_darksider" width="150" height="150" class="size-thumbnail wp-image-2422" /></a></center></p>
<p>You can watch the entire conference <a href="http://experts.adobeconnect.com/p1onkz5af6o/">here</a>.</p>
<p>As I promised, here are <a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_stage3d_20130222.pptx">the slides to this presentation</a>. They are pretty heavy because they embed some videos. Here is the outline of the content of the presentation:</p>
<ul>
<li>Community SDK</li>
<ul>
<li>Scripting</li>
<li>Shaders and GPU programming</li>
<li>Scene editor</li>
</ul>
<li>Professional SDK</li>
<ul>
<li>Physics</li>
<li>Optimizations for the web and mobile devices</li>
</ul>
</ul>
<p><center><iframe width="640" height="360" src="http://www.youtube.com/embed/kdt6YVwCaa0?rel=0" frameborder="0" allowfullscreen></iframe></center></p>
<p>At the end of the presentation, I also demonstrated how <strong>Minko can load and display Crytek's Sponza smoothly on the iPad and the Nexus 7 in just a few minutes of work thanks to the editor and the optimizations granted by the MK format</strong>. You will soon here more about this very demonstration wiht a clean video demonstrating the app. but also the publishing process. This is incredibly cool since Sponza is quite a big scene with more than 50 textures including normal maps, alpha maps and specular maps for a total of 200+MB (only 70MB when published to MK).</p>
<p>Don't forget to have a look at all the online resources for Minko:</p>
<ul>
<li><a href="http://hub.aerys.in/index.php/Minko:Downloads">Minko's downloads page</a></li>
<li><a href="http://github.com/aerys/minko">Minko's GitHub repository</a></li>
<li><a href="http://github.com/aerys/minko-examples">Minko's examples GitHub repository</a></li>
<li>The <a href="http://hub.aerys.in/index.php/Minko:Tutorials">tutorials</a> and the <a href="http://hub.aerys.in/minko/reference/index.html">online developers reference</a></li>
<li><a href="http://answers.aerys.in">Answers</a>, the official support forum</li>
</ul>
<p>As stated in the presentation, Minko's editor public beta should start next week. So stay tuned!</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/02/22/stage3d-online-conference-slides/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>New video: normal mapping and specular maps</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/02/14/new-video-normal-mapping-and-specular-maps/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/02/14/new-video-normal-mapping-and-specular-maps/#comments</comments>
		<pubDate>Thu, 14 Feb 2013 13:42:11 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[Minko Studio]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2412</guid>
		<description><![CDATA[Normal mapping has been available for a long time inside Minko. At first as part of the minko-lighting plugin and now in the core framework (in the dev branch only for now). The support for specular maps was added recently. Combining normal mapping and specular maps really gives good results. To show how far you [...]]]></description>
				<content:encoded><![CDATA[<p>Normal mapping has been available for a long time inside Minko. At first as part of the minko-lighting plugin and now in the core framework (in the dev branch only for now). The support for specular maps was added recently. Combining normal mapping and specular maps really gives good results. To show how far you can get, here is a little video demonstrating both techniques in the Minko editor:</p>
<p><center><iframe width="640" height="360" src="http://www.youtube.com/embed/J5vnYg5t-2I?rel=0" frameborder="0" allowfullscreen></iframe></center></p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/02/14/new-video-normal-mapping-and-specular-maps/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>New Documentation for Collada</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/02/11/new-documentation-for-collada/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/02/11/new-documentation-for-collada/#comments</comments>
		<pubDate>Mon, 11 Feb 2013 12:42:50 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[3D Studio Max]]></category>
		<category><![CDATA[Collada]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[Stage3D]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2405</guid>
		<description><![CDATA[Minko's Collada plugin makes it possible to easily import Collada (*.dae) files using the assets loading API. Working with the API is quite simple and there already is a detailed tutorial about that. But the Collada format has its flaws and it is sometimes very complicated to get your exported files to work properly. That's [...]]]></description>
				<content:encoded><![CDATA[<p>Minko's Collada plugin makes it possible to easily import Collada (*.dae) files using the assets loading API. Working with the API is quite simple and there already is <a href="http://hub.aerys.in/index.php/Minko:Load_Scenes">a detailed tutorial about that</a>. But <strong>the Collada format has its flaws and it is sometimes very complicated to get your exported files to work properly</strong>.</p>
<p>That's why I've compiled a new documentation article that explains how to properly export Collada files from 3D Studio Max:</p>
<p><a href="http://hub.aerys.in/index.php/Minko:Export_Collada_Files_From_3D_Studio_Max">Export Collada files from 3D Studio Max on Aerys Hub</a></p>
<p><strong>The article details the export procedure</strong> itself but also provides <strong>guidelines to make sure the exported file will display properly with Minko</strong>. It also give details about the supported features, including material, <strong>material properties and how the engine will use them</strong>. Similar articles will be released for different editors and formats according to the community's needs.</p>
<p>Of course, as soon as the Minko editor and the MK format will be available we will strongly discourage the use of Collada files in production for many reasons (mainly performances). But you will still need to import those Collada files into the editor first... So here is a little video to show how simple importing assets is with the editor:</p>
<p><center><iframe width="640" height="360" src="http://www.youtube.com/embed/Uf_2LWoRMXE?rel=0" frameborder="0" allowfullscreen></iframe></center></p>
<p>Yes: <strong>it's as simple as a drag'n'drop</strong>! You will also notice that the textures load automatically and that the editor will let you play the animations and make sure everything works out of the box. The editor will be available in open beta in March...</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/02/11/new-documentation-for-collada/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Anamorphic Lens Flare</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/02/02/anamorphic-lens-flare/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/02/02/anamorphic-lens-flare/#comments</comments>
		<pubDate>Sat, 02 Feb 2013 02:35:01 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Minko]]></category>
		<category><![CDATA[demo]]></category>
		<category><![CDATA[experiment]]></category>
		<category><![CDATA[Flash 11]]></category>
		<category><![CDATA[hardware acceleration]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[shader]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2385</guid>
		<description><![CDATA[Update: I've just pushed a new SWF with a much better enhanced effect. I've tweaked things like the number of vertical/horizontal blur passes - which are now up to 3/6 - but also the flares' brightness, contrast and dirt texture. I think it looks way better now! Tonight's experiment was focused on post-processing. My goal [...]]]></description>
				<content:encoded><![CDATA[<p><strong>Update:</strong> I've just pushed a new SWF with a much better enhanced effect. I've tweaked things like the number of vertical/horizontal blur passes - which are now up to 3/6 - but also the flares' brightness, contrast and dirt texture. I think it looks way better now!</p>
<p>Tonight's experiment was focused on post-processing. My goal was to implement a simple anamorphic lens flare post-processing effect using Minko. It was actually quite simple to do. Here is the result:</p>
<p><a  rel="shadowbox;width=800;height=500" href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/AnamorphicLensFlareExample.html"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/02/minko_anamorphic_lens_flare_vipermarkII_2-1024x583.jpg" alt="minko_anamorphic_lens_flare_vipermarkII_2" width="550" height="313" class="aligncenter size-large wp-image-2396" /></a></p>
<p>The 1st pass applies a luminance threshold filter:</p>

<div class="wp_syntax"><table><tr><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #9900cc; font-weight: bold;">class</span> LuminanceThresholdPass <span style="color: #0033ff; font-weight: bold;">extends</span> Shader
<span style="color: #000000;">&#123;</span>
    <span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #6699cc; font-weight: bold;">var</span> _postProcessing <span style="color: #000066; font-weight: bold;">:</span> PostProcessingShaderPart<span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
    <span style="color: #0033ff; font-weight: bold;">public</span> <span style="color: #339966; font-weight: bold;">function</span> LuminanceThresholdPass<span style="color: #000000;">&#40;</span>renderTarget  <span style="color: #000066; font-weight: bold;">:</span> RenderTarget  = <span style="color: #0033ff; font-weight: bold;">null</span><span style="color: #000066; font-weight: bold;">,</span>
                                           priority      <span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">Number</span>        = <span style="color: #000000; font-weight:bold;">0.0</span><span style="color: #000000;">&#41;</span>
    <span style="color: #000000;">&#123;</span>
        <span style="color: #0033ff; font-weight: bold;">super</span><span style="color: #000000;">&#40;</span>renderTarget<span style="color: #000066; font-weight: bold;">,</span> priority<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        _postProcessing = <span style="color: #0033ff; font-weight: bold;">new</span> PostProcessingShaderPart<span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">this</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #000000;">&#125;</span>
&nbsp;
    <span style="color: #0033ff; font-weight: bold;">override</span> <span style="color: #0033ff; font-weight: bold;">protected</span> <span style="color: #339966; font-weight: bold;">function</span> getVertexPosition<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span>SFloat
    <span style="color: #000000;">&#123;</span>
        <span style="color: #0033ff; font-weight: bold;">return</span> _postProcessing<span style="color: #000066; font-weight: bold;">.</span>vertexPosition<span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #000000;">&#125;</span>
&nbsp;
    <span style="color: #0033ff; font-weight: bold;">override</span> <span style="color: #0033ff; font-weight: bold;">protected</span> <span style="color: #339966; font-weight: bold;">function</span> getPixelColor<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">:</span>SFloat
    <span style="color: #000000;">&#123;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> rgb			<span style="color: #000066; font-weight: bold;">:</span> SFloat	= _postProcessing<span style="color: #000066; font-weight: bold;">.</span>backBufferPixel<span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> rgbToLuminance 	<span style="color: #000066; font-weight: bold;">:</span> SFloat 	= float3<span style="color: #000000;">&#40;</span><span style="color: #000000; font-weight:bold;">0.2126</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">0.7152</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">0.0722</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> luminance		<span style="color: #000066; font-weight: bold;">:</span> SFloat	= dotProduct3<span style="color: #000000;">&#40;</span>rgb<span style="color: #000066; font-weight: bold;">,</span> rgbToLuminance<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        <span style="color: #0033ff; font-weight: bold;">return</span> multiply<span style="color: #000000;">&#40;</span>
            _postProcessing<span style="color: #000066; font-weight: bold;">.</span>backBufferPixel<span style="color: #000066; font-weight: bold;">,</span>
            greaterEqual<span style="color: #000000;">&#40;</span>luminance<span style="color: #000066; font-weight: bold;">,</span> sceneBindings<span style="color: #000066; font-weight: bold;">.</span>getParameter<span style="color: #000000;">&#40;</span><span style="color: #990000;">'luminanceThreshold'</span><span style="color: #000066; font-weight: bold;">,</span> <span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#41;</span><span style="color: #000000;">&#41;</span>
        <span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #000000;">&#125;</span>
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>Then I use a multipass Gaussian blur with 4 passes: 3 horizontal passes and 1 vertical passes. <strong>The trick is to apply those 5 passes (1 luminance threshold pass + 4 blur passes) on a texture which is a lot taller than wide</strong> (32x1024 in this case). This way, everything gets streched when the flare are composited with the rest of the backbuffer.</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/02/02/anamorphic-lens-flare/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>JIT Shaders For Better Performance</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/01/29/jit-shaders-for-better-performance/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/01/29/jit-shaders-for-better-performance/#comments</comments>
		<pubDate>Tue, 29 Jan 2013 13:49:29 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[ActionScript 3.0]]></category>
		<category><![CDATA[Flash 11]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[shader]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2338</guid>
		<description><![CDATA[The subject is really vast and complex and I've been trying to write an article about this for quite some time now. Recently, I made a small patch to enhance this technique and I thought it was a good occasion to try to summarize how it works and the benefits of it. In order to [...]]]></description>
				<content:encoded><![CDATA[<p>The subject is really vast and complex and I've been trying to write an article about this for quite some time now. Recently, I made a small patch to enhance this technique and I thought it was a good occasion to try to summarize how it works and the benefits of it. In order to talk about this new enhancement, I would like to draw the big picture first.</p>
<h3>The Problem</h3>
<p>That might look like a complicated post title... but this is rather complex than really complicated. Here is how it starts: <strong>rendering a 3D object require to execute a graphics rendering program - or "shader" - on the GPU</strong>. To make it simple, let's just say this program will compute the final color of each pixel on the screen. Thus, <strong>the operations performed by this shader will vary according to how you want your object to look like. </strong>For example rendering with a solid flat color requires different operations than rendering with per-pixel lighting.</p>
<p>Any programming beginner will understand that such program will test conditions - for example whether to use lighting or not - and perform some operations according to the result of this test. Yes: that's pretty much exactly what an "if" statement is. <strong>It might look like programming trivia to you. And it would be if this program was not meant to be executed on the GPU...</strong></p>
<p>You see, the GPU does not like branching. Not one bit (literally)! <strong>For the sake of parallelization, the GPU expects the program to have a fixed number of operations</strong>. This is the only efficient way to ensure computations can be distributed over a large number of pipelines without having to care too much about their synchronization. Thus, <strong>the GPU does not know branching and each program has a fixed number of instructions that will always be executed in the same order</strong>.</p>
<p><strong>Conclusion: shader programs cannot use "if" statements</strong>. And of course, loops are out of the game too since they are pretty much pimped out "if" statements. Can you imagine what such logic would imply on your daily programming tasks? If you simply try to, <strong>you will quickly understand that instead of writing one program that can handle many different situations you will have to write many different programs that will handle a single situation</strong>. And then manually choose which one should be launched according to your initial setup...</p>
<h3>Workarounds...</h3>
<h4>Mutables</h4>
<p>The simplest workaround is to <strong>find "some way" to make sure useless computations do not affect the actual rendering operations</strong>. For example, you can "virtually disable" lighting by setting all lights diffuse/specular components to 0.</p>
<p>As you can imagine, this is really a suboptimal option. Performance wise, it's actually the worst possible idea: a lot of computations happen and most of them are likely to be useless in most cases.</p>
<h4>If/else shader intrinsic instructions</h4>
<p>After a few years, shaders evolved and featured more and more instructions. Those instructions are now usable through higher level languages such as CG or GLSL. <strong>Those languages feature "if" statements</strong> (and even loops too). How are they compiled into shader code that can run on a GPU? Do they overcome the challenges implied by parallelization?</p>
<p>No. They actually fit in in a very straight forward and simple way. <strong>As a shader program must feature a single fixed list of instructions, the two parts of a if/else statement will both be executed</strong>. The hardware will then decide which one should be muted according to the actual result of the test performed by the conditional instructions.</p>
<p>The bright side is that you can use this technique to have <strong>a single shader program that handles multiple scenarios</strong>. The dark side is that <strong>this shader is still very inefficient</strong> and might eventually break the limit number of instructions for a single program. On some older hardware, the corresponding hardware instructions simply do not exist...</p>
<p>So <strong>even this "brand new" feature that will be introduced in Flash 11.7 and its "extended" profile is far from sufficient</strong>.</p>
<h4>Pre-compilation</h4>
<p>Some engines will use high level shader programming languages (like CG or GLSL) and <strong>a pre-compilation workflow to generate all the possible outcomes</strong>. Then, the right shader is loaded at runtime according to the rendering setup. This is the case of the Source Engine, created by Valve and used in famous games like Half Life 2, Team Fortress 2 or Portal.</p>
<p><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/shaders_precompilation.png" rel="shadowbox[sbpost-2338];player=img;"><img class="aligncenter size-full wp-image-2366" title="shaders_precompilation" alt="" src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/shaders_precompilation.png" width="600" height="154" /></a></p>
<p>This solution is <strong>efficient performance wise: there is always a shader that will do exactly and strictly the required operations</strong> according to the rendering setup. Plus it does not have to rely on some hardware features availability. But pre-compilation implies <strong>a very heavy and inefficient assets workflow</strong>.</p>
<h3>Minko's Solution</h3>
<p>We've seen the common workarounds and each of them has very strong cons. The most robust implementation seems to be the pre-compilation option despite the obvious workflow issues. Especially when we're talking web/mobile applications! But the past 10 years have seen the rise of <strong>a technique that could solve this problem: Just In Time (JIT) compilation</strong>. This technique is mostly used by Virtual Machines - such as the JVM (Java Virtual Machine), the AVM2 (Actionscript Virual Machine) or V8 (Chrome's JavaScript virtual machine). It's purpose is to <strong>compile the virtual machine bytecode into actual machine opcodes at runtime in order to get better performances</strong>.</p>
<p><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_shader_workflow.jpg" rel="shadowbox[sbpost-2338];player=img;"><img class="aligncenter size-medium wp-image-2351" title="minko_shader_workflow" alt="" src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_shader_workflow-300x208.jpg" width="300" height="208" /></a></p>
<p>How would the same principle apply to shaders? If you consider your application as the VM and your shader code as this VM execution language, then it all falls into place! Indeed, your 3D application could simply compile some higher level language shader code into actual machine shader code according to the available data. For example, some shader might compile differently according to whether lighting is enabled or not or even according to the number of lights.</p>
<p><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_shader_execution.jpg" rel="shadowbox[sbpost-2338];player=img;"><img class="aligncenter size-medium wp-image-2353" title="minko_shader_execution" alt="" src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_shader_execution-300x189.jpg" width="300" height="189" /></a></p>
<p>With Minko, we tried to keep it as simple as possible. Therefore, we worked very hard to find a way to be able to write shaders using AS3. As the figure above explains, the AS3 shader code you write is not executed on the GPU (because that's simply not possible). Instead, <strong>the application acts as a Virtual Machine and as it gets executed at runtime, this AS3 shader code transparently generates what we call an Abstract Shader Graph (ASGs)</strong>. You can see it as an <a href="http://en.wikipedia.org/wiki/Abstract_syntax_tree">Abstract Syntax Tree</a> for shaders (you can even ask Minko to <a href="http://hub.aerys.in/index.php/Minko:Get_ActionScript_Shaders_Compilation_Logs">output ASGs in the console</a>as they get generated using a debug flag). <strong>This ASG in then optimized and compiled into actual shader code for the GPU.</strong></p>
<p>For example: everytime you call the add() method in your AS3 shader code, it will create a corresponding ASG node. This very node will be linked with the rest of the ASG as you use it in other operations until it is finally used as the result of the shader. This result node becomes the "entry point" of the ASG.</p>
<p>Here is what a very simple ASG that just handles a solid flat color rendering looks like:</p>
<p><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_graphviz_diffuseColor.jpg" rel="shadowbox[sbpost-2338];player=img;"><img class="aligncenter size-full wp-image-2358" title="minko_graphviz_diffuseColor" alt="" src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_graphviz_diffuseColor.jpg" width="351" height="295" /></a></p>
<p>Here is what a (complicated) ASG that handle multiple lights looks like:</p>
<p><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/Minko_graphviz_6spots.png" rel="shadowbox[sbpost-2338];player=img;"><img class="aligncenter size-large wp-image-2355" title="Minko_graphviz_6spots" alt="" src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/Minko_graphviz_6spots-1024x503.png" width="550" height="270" /></a></p>
<p><strong>Your AS3 shader code is executed at runtime on the CPU to generate this ASG that will be compiled into actual shader code that will run on the GPU</strong> (in the case of Flash it will actually output AGAL bytecode that will be translated into shader machine code by the Flash Player). As such, <strong>you can easily perform "if" statements that will shape the ASG. You can even use loops, functions and OOP!</strong> You just have to make sure the shader is re-evaluated anytime the output might be different (for example when the condition tested in a "if" changes). But that's for another time...</p>
<p><strong>Using JIT shaders, Minko can efficiently dynamically compile shaders shaped by the actual rendering settings occuring at runtime. Thus, it combines the high performance of a pre-compilation solution while leveraging all the flexibility of JIT compilation.</strong> In my next articles, I will explain how JIT shaders compilation can be efficiently automated and how multi-pass rendering can also be made more efficient thanks to this approach.</p>
<p>If you have questions, hit the comments or post in <a href="http://answers.aerys.in/categories/minko">the Minko category on Aerys Answers</a>!</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/01/29/jit-shaders-for-better-performance/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Teasing: Simple Minko Physics Stacking Stress Test</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/01/16/teasing-simple-minko-physics-stacking-stress-test/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/01/16/teasing-simple-minko-physics-stacking-stress-test/#comments</comments>
		<pubDate>Wed, 16 Jan 2013 00:28:47 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[physics]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2319</guid>
		<description><![CDATA[Minko physics is probably one of the most awaited features for this new year. I will not cover it extensively right now - I'll rather post a few demos in a later post - but if you must know it was designed to be the fastest 3D physics engine for ActionScript 3 and the Flash [...]]]></description>
				<content:encoded><![CDATA[<p>Minko physics is probably one of the most awaited features for this new year. I will not cover it extensively right now - I'll rather post a few demos in a later post - but if you must know <strong>it was designed to be the fastest 3D physics engine for ActionScript 3 and the Flash platform</strong>.</p>
<p><strong>I will share extensive details about this new physics engine during the <a href="http://gonchar.me/stage3d/">Stage3D online conference in February</a>. Make sure you attend: it's online and it's free! <img src='http://blogs.aerys.in/jeanmarc-leroux/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </strong></p>
<h3>The Demo</h3>
<p>Anyway, I just wanted to tease the community with <strong>one of the stress tests we're using here to benchmark the engine</strong>. It's a <strong>really simple test</strong> and it uses only a very <strong>very</strong> small subset of the available features.</p>
<p>Here you go (just press "space" to throw some balls):</p>
<p><a rel="shadowbox;width=800;height=500" href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/StackExample.html"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2013/01/minko_physics_stackexample.jpg" alt="" title="minko_physics_stackexample" width="600" height="325" class="aligncenter size-full wp-image-2323" /></a></p>
<p><span id="more-2319"></span></p>
<h3>About Scalability</h3>
<p><strong>There are actually quite a few interactive objects active at once in this scene: more than 350!</strong> And if you throw some balls (using "space"), it should go even higher. Yet the application should run very smoothly on a decent computer: the framerate doesn't get below 24 fps on my 2011 laptop using a core i7@1.5Ghz/Intel HD 3000.</p>
<p><strong>The number of contact points/collisions and therefore the stacking appears to be the main bottleneck here. And that's a very good thing since it's precisely the point of this stress test.</strong></p>
<p>When the application starts, you might also notice that the framerate doesn't reach 60 fps until a few seconds. This is because <strong>colliders need this time to stabilize and "fall asleep"</strong> when they finally stop moving for long enough. After a few seconds, you should get 60 fps. If you don't, it means your GPU is the bottleneck since <strong>sleeping physics colliders are actually virtually free</strong>. This also means <strong>the engine can easily handle very large physical worlds and detect/compute collisions in a very optimized fashion</strong>.</p>
<h3>Future Improvements</h3>
<p>You might think that the fact we're using boxes might makes things a lot faster for the physics engine. Yet <strong>we've implemented nothing special for boxes collisions tests so this is a real glimpse at the actual general performances of the engine</strong>. Other stress tests will enlight that of course, and we might implement box/box optimization in the future to get even more performances.</p>
<p>When you press space to throw a ball, you might also notice a performance drop. This is unlikely to have anything to do with physics. I think it's rather related to the fact that adding new scene nodes will require to <a href="http://blogs.aerys.in/jeanmarc-leroux/2013/01/02/3d-matrices-update-optimization/">rebuild the local to world transforms tree into a linearized list</a>. This might be avoided by re-using the "fallen" balls instead of building new ones everytime "space" is pressed.</p>
<p>Of course, feel free to discuss this demo and share your results in the comments or on <a href="http://answers.aerys.in/">Answers</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/01/16/teasing-simple-minko-physics-stacking-stress-test/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>3D Matrices Update Optimization</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2013/01/02/3d-matrices-update-optimization/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2013/01/02/3d-matrices-update-optimization/#comments</comments>
		<pubDate>Wed, 02 Jan 2013 11:11:45 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Flash]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[Snippets]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[ActionScript 3.0]]></category>
		<category><![CDATA[Flash 11]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[optimization]]></category>
		<category><![CDATA[scene graph]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2302</guid>
		<description><![CDATA[4x4 matrices are the heart of any 3D engine as far as math is concerned. And in any engine, how those matrices are computed and made available through the API are two critical points regarding both performances and ease of development. Minko was quite generous regarding the second point, making it easy and simple to [...]]]></description>
				<content:encoded><![CDATA[<p>4x4 matrices are the heart of any 3D engine as far as math is concerned. And in any engine, how those matrices are computed and made available through the API are two critical points regarding both performances and ease of development. Minko was quite generous regarding the second point, making it easy and simple to access and watch local to world (and world to local) matrices on any scene node. Yet, the update strategy of those matrices was.. naïve, to say the least.</p>
<h3>TL;DR</h3>
<p>There is a new 3D transforms API available in <a href="https://github.com/aerys/minko/tree/dev">the dev branch</a> that provides a <del datetime="2013-01-02T18:56:01+00:00">50000%</del> 25000% boost on scene nodes' matrices update in the best cases, making it possible to display <del datetime="2013-01-02T18:56:01+00:00">50x</del> 25x more animated objects. You can read <a href="http://answers.aerys.in/discussion/265/new-transforms-api-available-in-dev-branch">more about the changes on Answers</a>.</p>
<p><span id="more-2302"></span></p>
<h3>The Problem</h3>
<p>Here is how it worked until very recently: each scene node was the target of a TransformController. The job of this controller was to listen to the changes of the ISceneNode.transform property in order to update the localToWorld and worldToLocal properties accordingly. Of course, as those properties rely on the parent's transform, the controller also listen to it and that's where trouble starts: modifying the transform of a node will trigger a lot of signals executions, implying a lot of overhead.</p>
<p>The worse case scenario is vertex skinning: the skeleton has to be updated top to bottom (because there is no other way to do it really...). And each update on a node will trigger updates on all of its descendants, leading to a factorial complexity and a huge overhead.</p>
<p>The good point with this method is that all the scene nodes transforms are always available and "synchronized" with each other. The very bad point is that it does a lot of unnecessary computations using recursive signals that imply a huge function calls overhead.</p>
<h3>The Solution</h3>
<p>We had three priorities:</p>
<ol>
<li>Provide a new, robust and fast 3D transformation matrices computation strategy.</li>
<li>Keep API changes to a minimum.</li>
<li>Make sure we don't remove any feature.</li>
</ol>
<p><strong>To fasten the local to world matrices computation, we decided to update them in a batched fashion</strong>: all the local to world matrices of a (sub)scene had to be updated in a single method call using a single loop. It forbids updating the (sub)scene as a tree data structure, since it would mean recursion - and a big function call overhead - or using stacks - which is not the strong point of AS3. Therefore, we had to linearize the (sub)scene in order to get a list of transforms. <strong>To do this, we simply do a breadth first traversal of the (sub)scene tree when it has changed in order to get a flat list of matrices.</strong> We also store a few other things in other lists - such as the number of children or the id of parent of each node - in order to preserve the data we need to traverse that very list as a linearized tree structure.</p>
<p>This job is done by the TransformController.updateTransformsList() method:</p>

<div class="wp_syntax"><table><tr><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #339966; font-weight: bold;">function</span> updateTransformsList<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span> <span style="color: #000066; font-weight: bold;">:</span> <span style="color: #0033ff; font-weight: bold;">void</span>
<span style="color: #000000;">&#123;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">root</span> 	<span style="color: #000066; font-weight: bold;">:</span> ISceneNode 	= _target<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">root</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> nodes 	<span style="color: #000066; font-weight: bold;">:</span> Vector<span style="color: #000066; font-weight: bold;">.</span> 	= <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #004993;">root</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> nodeId 	<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> 		= <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
    _nodeToId = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #004993;">Dictionary</span><span style="color: #000000;">&#40;</span><span style="color: #0033ff; font-weight: bold;">true</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
    _transforms = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _localToWorldTransformsInitialized = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _localToWorldTransforms = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _worldToLocalTransforms = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _numChildren = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _firstChildId = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _idToNode = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    _parentId = <span style="color: #0033ff; font-weight: bold;">new</span> <span style="color: #000000;">&#91;</span><span style="color: #000066; font-weight: bold;">-</span><span style="color: #000000; font-weight:bold;">1</span><span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
    <span style="color: #0033ff; font-weight: bold;">while</span> <span style="color: #000000;">&#40;</span>nodes<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">length</span><span style="color: #000000;">&#41;</span>
    <span style="color: #000000;">&#123;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> node 	<span style="color: #000066; font-weight: bold;">:</span> ISceneNode 	= nodes<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">shift</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> group 	<span style="color: #000066; font-weight: bold;">:</span> Group 	= node <span style="color: #0033ff; font-weight: bold;">as</span> Group<span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        _nodeToId<span style="color: #000000;">&#91;</span>node<span style="color: #000000;">&#93;</span> = nodeId<span style="color: #000066; font-weight: bold;">;</span>
        _idToNode<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = node<span style="color: #000066; font-weight: bold;">;</span>
        _transforms<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = node<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">transform</span><span style="color: #000066; font-weight: bold;">;</span>
        _localToWorldTransforms<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = <span style="color: #0033ff; font-weight: bold;">new</span> Matrix4x4<span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">lock</span><span style="color: #000000;">&#40;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
        _localToWorldTransformsInitialized<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = <span style="color: #0033ff; font-weight: bold;">false</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        <span style="color: #0033ff; font-weight: bold;">if</span> <span style="color: #000000;">&#40;</span>group<span style="color: #000000;">&#41;</span>
        <span style="color: #000000;">&#123;</span>
            <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">numChildren</span> 	<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> = group<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">numChildren</span><span style="color: #000066; font-weight: bold;">;</span>
            <span style="color: #6699cc; font-weight: bold;">var</span> firstChildId 	<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> = nodeId <span style="color: #000066; font-weight: bold;">+</span> nodes<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">length</span> <span style="color: #000066; font-weight: bold;">+</span> <span style="color: #000000; font-weight:bold;">1</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
            _numChildren<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = <span style="color: #004993;">numChildren</span><span style="color: #000066; font-weight: bold;">;</span>
            _firstChildId<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = firstChildId<span style="color: #000066; font-weight: bold;">;</span>
            <span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> childId <span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> = <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">;</span> childId <span style="color: #000066; font-weight: bold;">&amp;</span>lt<span style="color: #000066; font-weight: bold;">;</span> <span style="color: #004993;">numChildren</span><span style="color: #000066; font-weight: bold;">;</span> <span style="color: #000066; font-weight: bold;">++</span>childId<span style="color: #000000;">&#41;</span>
            <span style="color: #000000;">&#123;</span>
                _parentId<span style="color: #000000;">&#91;</span><span style="color: #004993;">uint</span><span style="color: #000000;">&#40;</span>firstChildId <span style="color: #000066; font-weight: bold;">+</span> childId<span style="color: #000000;">&#41;</span><span style="color: #000000;">&#93;</span> = nodeId<span style="color: #000066; font-weight: bold;">;</span>
                nodes<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">push</span><span style="color: #000000;">&#40;</span>group<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">getChildAt</span><span style="color: #000000;">&#40;</span>childId<span style="color: #000000;">&#41;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
            <span style="color: #000000;">&#125;</span>
        <span style="color: #000000;">&#125;</span>
        <span style="color: #0033ff; font-weight: bold;">else</span>
        <span style="color: #000000;">&#123;</span>
            _numChildren<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">;</span>
            _firstChildId<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #000000;">&#125;</span>
&nbsp;
        <span style="color: #000066; font-weight: bold;">++</span>nodeId<span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #000000;">&#125;</span>
&nbsp;
    _worldToLocalTransforms<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">length</span> = _localToWorldTransforms<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">length</span><span style="color: #000066; font-weight: bold;">;</span>
    _invalidList = <span style="color: #0033ff; font-weight: bold;">false</span><span style="color: #000066; font-weight: bold;">;</span>
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>In order to avoid unnecessary computations, we decided to update them on a frame-to-frame basis. <strong>To make sure this update happens just before rendering and that all matrices are actually up to date, we've added the Scene.renderingBegin signal</strong>. As you might have guesses, this signals is simply executed right before the scene starts the actual rendering operations when Scene.render() is called (so it's called after Scene.enterFrame, which is the signal which should be used to update the scene).</p>
<p>This is the job of the TransformController.updateLocalToWorld() method:</p>

<div class="wp_syntax"><table><tr><td class="code"><pre class="actionscript3" style="font-family:monospace;"><span style="color: #0033ff; font-weight: bold;">private</span> <span style="color: #339966; font-weight: bold;">function</span> updateLocalToWorld<span style="color: #000000;">&#40;</span>nodeId <span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> = <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000000;">&#41;</span> <span style="color: #000066; font-weight: bold;">:</span> <span style="color: #0033ff; font-weight: bold;">void</span>
<span style="color: #000000;">&#123;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> numNodes 		<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> 		= _transforms<span style="color: #000066; font-weight: bold;">.</span><span style="color: #004993;">length</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> childrenOffset		<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span>		= <span style="color: #000000; font-weight:bold;">1</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> rootLocalToWorld	<span style="color: #000066; font-weight: bold;">:</span> Matrix4x4	= _localToWorldTransforms<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> rootTransform		<span style="color: #000066; font-weight: bold;">:</span> Matrix4x4	= _transforms<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">root</span>			<span style="color: #000066; font-weight: bold;">:</span> ISceneNode	= _idToNode<span style="color: #000000;">&#91;</span>childId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
    <span style="color: #0033ff; font-weight: bold;">if</span> <span style="color: #000000;">&#40;</span>rootTransform<span style="color: #000066; font-weight: bold;">.</span>_hasChanged <span style="color: #000066; font-weight: bold;">||</span> <span style="color: #000066; font-weight: bold;">!</span>_localToWorldTransformsInitialized<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000000;">&#41;</span>
    <span style="color: #000000;">&#123;</span>
        rootLocalToWorld<span style="color: #000066; font-weight: bold;">.</span>copyFrom<span style="color: #000000;">&#40;</span>rootTransform<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        <span style="color: #0033ff; font-weight: bold;">if</span> <span style="color: #000000;">&#40;</span>nodeId <span style="color: #000066; font-weight: bold;">!</span>= <span style="color: #000000; font-weight:bold;">0</span><span style="color: #000000;">&#41;</span>
            rootLocalToWorld<span style="color: #000066; font-weight: bold;">.</span>append<span style="color: #000000;">&#40;</span>_localToWorldTransforms<span style="color: #000000;">&#91;</span>_parentId<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000000;">&#93;</span><span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        rootTransform<span style="color: #000066; font-weight: bold;">.</span>_hasChanged = <span style="color: #0033ff; font-weight: bold;">false</span><span style="color: #000066; font-weight: bold;">;</span>
        _localToWorldTransformsInitialized<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span> = <span style="color: #0033ff; font-weight: bold;">true</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #004993;">root</span><span style="color: #000066; font-weight: bold;">.</span>localToWorldTransformChanged<span style="color: #000066; font-weight: bold;">.</span>execute<span style="color: #000000;">&#40;</span><span style="color: #004993;">root</span><span style="color: #000066; font-weight: bold;">,</span> rootLocalToWorld<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
    <span style="color: #000000;">&#125;</span>
&nbsp;
    <span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #000000;">&#40;</span><span style="color: #000066; font-weight: bold;">;</span> nodeId <span style="color: #000066; font-weight: bold;">&lt;</span> numNodes<span style="color: #000066; font-weight: bold;">;</span> <span style="color: #000066; font-weight: bold;">++</span>nodeId<span style="color: #000000;">&#41;</span>
    <span style="color: #000000;">&#123;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> localToWorld 	<span style="color: #000066; font-weight: bold;">:</span> Matrix4x4	= _localToWorldTransforms<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">numChildren</span>		<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span>		= _numChildren<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> firstChildId	<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span>		= _firstChildId<span style="color: #000000;">&#91;</span>nodeId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> lastChildId		<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span>		= firstChildId <span style="color: #000066; font-weight: bold;">+</span> <span style="color: #004993;">numChildren</span><span style="color: #000066; font-weight: bold;">;</span>
        <span style="color: #6699cc; font-weight: bold;">var</span> isDirty		<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">Boolean</span>	= localToWorld<span style="color: #000066; font-weight: bold;">.</span>_hasChanged<span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        localToWorld<span style="color: #000066; font-weight: bold;">.</span>_hasChanged = <span style="color: #0033ff; font-weight: bold;">false</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
        <span style="color: #0033ff; font-weight: bold;">for</span> <span style="color: #000000;">&#40;</span><span style="color: #6699cc; font-weight: bold;">var</span> childId <span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">uint</span> = firstChildId<span style="color: #000066; font-weight: bold;">;</span> childId <span style="color: #000066; font-weight: bold;">&lt;</span> lastChildId<span style="color: #000066; font-weight: bold;">;</span> <span style="color: #000066; font-weight: bold;">++</span>childId<span style="color: #000000;">&#41;</span>
        <span style="color: #000000;">&#123;</span>
            <span style="color: #6699cc; font-weight: bold;">var</span> childTransform		<span style="color: #000066; font-weight: bold;">:</span> Matrix4x4		= _transforms<span style="color: #000000;">&#91;</span>childId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
            <span style="color: #6699cc; font-weight: bold;">var</span> childLocalToWorld	<span style="color: #000066; font-weight: bold;">:</span> Matrix4x4		= _localToWorldTransforms<span style="color: #000000;">&#91;</span>childId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
            <span style="color: #6699cc; font-weight: bold;">var</span> childIsDirty		<span style="color: #000066; font-weight: bold;">:</span> <span style="color: #004993;">Boolean</span>		= isDirty <span style="color: #000066; font-weight: bold;">||</span> childTransform<span style="color: #000066; font-weight: bold;">.</span>_hasChanged
                <span style="color: #000066; font-weight: bold;">||</span> <span style="color: #000066; font-weight: bold;">!</span>_localToWorldTransformsInitialized<span style="color: #000000;">&#91;</span>childId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
            <span style="color: #0033ff; font-weight: bold;">if</span> <span style="color: #000000;">&#40;</span>childIsDirty<span style="color: #000000;">&#41;</span>
            <span style="color: #000000;">&#123;</span>
                <span style="color: #6699cc; font-weight: bold;">var</span> <span style="color: #004993;">child</span>	<span style="color: #000066; font-weight: bold;">:</span> ISceneNode	= _idToNode<span style="color: #000000;">&#91;</span>childId<span style="color: #000000;">&#93;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
                childLocalToWorld
                <span style="color: #000066; font-weight: bold;">.</span>copyFrom<span style="color: #000000;">&#40;</span>childTransform<span style="color: #000000;">&#41;</span>
                    <span style="color: #000066; font-weight: bold;">.</span>append<span style="color: #000000;">&#40;</span>localToWorld<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
&nbsp;
                childTransform<span style="color: #000066; font-weight: bold;">.</span>_hasChanged = <span style="color: #0033ff; font-weight: bold;">false</span><span style="color: #000066; font-weight: bold;">;</span>
                _localToWorldTransformsInitialized<span style="color: #000000;">&#91;</span>childId<span style="color: #000000;">&#93;</span> = <span style="color: #0033ff; font-weight: bold;">true</span><span style="color: #000066; font-weight: bold;">;</span>
                <span style="color: #004993;">child</span><span style="color: #000066; font-weight: bold;">.</span>localToWorldTransformChanged<span style="color: #000066; font-weight: bold;">.</span>execute<span style="color: #000000;">&#40;</span><span style="color: #004993;">child</span><span style="color: #000066; font-weight: bold;">,</span> childLocalToWorld<span style="color: #000000;">&#41;</span><span style="color: #000066; font-weight: bold;">;</span>
            <span style="color: #000000;">&#125;</span>
        <span style="color: #000000;">&#125;</span>
    <span style="color: #000000;">&#125;</span>
<span style="color: #000000;">&#125;</span></pre></td></tr></table></div>

<p>You can read the changelog and more details about the <a href="http://answers.aerys.in/discussion/265/new-transforms-api-available-in-dev-branch">list of API changes on Aerys Answers</a>.</p>
<h3>Future Improvements</h3>
<p>We could make the TransformController.updateLocalToWorld() method a bit faster by avoiding taking identity matrices into account or do a special case for matrices that have nothing but a translation.</p>
<p>Memory wise, we could also avoid using the _localToWorldTransformsInitialized vector all together and check whether _localToWorld[nodeId] is null or not.</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2013/01/02/3d-matrices-update-optimization/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Flash 11.5/AIR 3.5 capable Flex SDK</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2012/11/07/flash-11-5air-3-5-capable-flex-sdk/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2012/11/07/flash-11-5air-3-5-capable-flex-sdk/#comments</comments>
		<pubDate>Wed, 07 Nov 2012 19:08:16 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Uncategorized]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2294</guid>
		<description><![CDATA[The awesome guy at swgeek was kind enough to build a Flash 11.5/AIR 3.5 capable Flex SDK. You just have to install this SDK and you're ready to go for projects targeting the new APIs provided by this new Flash releases. This Flex SDK can be downloaded directly on their site: Combined version of the [...]]]></description>
				<content:encoded><![CDATA[<p>The awesome guy at <a href="http://www.swfgeek.net">swgeek</a> was kind enough to build a Flash 11.5/AIR 3.5 capable Flex SDK. You just have to install this SDK and you're ready to go for projects targeting the new APIs provided by this new Flash releases.</p>
<p>This Flex SDK can be downloaded directly on their site:</p>
<p><a href="http://www.swfgeek.net/2012/11/07/combined-version-of-the-flex-4-6-and-air-3-5-sdk-for-the-lazy-ones/">Combined version of the Flex 4.6 and AIR 3.5 SDK for the lazy ones</a> on swfgeek.</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2012/11/07/flash-11-5air-3-5-capable-flex-sdk/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Minko Weekly Roundup #4</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2012/11/02/minko-weekly-roundup-4/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2012/11/02/minko-weekly-roundup-4/#comments</comments>
		<pubDate>Fri, 02 Nov 2012 10:25:45 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[3D]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[Stage3D]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2285</guid>
		<description><![CDATA[Features The JointsDebugController makes it possible to display the joints and bones of a skinned mesh in order to check if everything works as expected. The VertexPositionDebugController will display the position of each vertex of a mesh. The VertexNormalDebugController will display the normal of each vertex. You can use it with the VertexNormalShader to display [...]]]></description>
				<content:encoded><![CDATA[<h3>Features</h3>
<ul>
<li>The <a href="https://github.com/aerys/minko/blob/master/src/aerys/minko/scene/controller/debug/JointsDebugController.as">JointsDebugController</a> makes it possible to display the joints and bones of a skinned mesh in order to check if everything works as expected.</li>
<p><a href="http://hub.aerys.in/index.php/Minko:JointsDebugController_Example"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2012/11/minko_jointsdebugcontroller-300x226.jpg" alt="" title="minko_jointsdebugcontroller" width="300" height="226" class="aligncenter size-medium wp-image-2289" /></a></p>
<li>The <a href="https://github.com/aerys/minko/blob/master/src/aerys/minko/scene/controller/debug/VertexPositionsDebugController.as">VertexPositionDebugController</a> will display the position of each vertex of a mesh.</li>
<li>The <a href="https://github.com/aerys/minko/blob/master/src/aerys/minko/scene/controller/debug/VertexNormalsDebugController.as">VertexNormalDebugController</a> will display the normal of each vertex. You can use it with the VertexNormalShader to display and debug the normals of a mesh.</li>
</ul>
<p><a href="http://hub.aerys.in/index.php/Minko:VertexIterator_Example"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2012/11/minko_vertexiterator_example-300x165.jpg" alt="" title="minko_vertexiterator_example" width="300" height="165" class="aligncenter size-medium wp-image-2292" /></a></p>
<h3>Examples</h3>
<ul>
<li><a href="http://hub.aerys.in/index.php/Minko:VertexIterator_Example">VertexIterator Example</a></li>
<li><a href="http://hub.aerys.in/index.php/Minko:JointsDebugController_Example">JointsDebugController Example</a></li>
</ul>
<h3>Answers</h3>
<ul>
<li><a href="Mapping Flex UI components to textures in Minko">Mapping Flex UI components to textures in Minko</a>: an interesting thread about how to emulate mouse-enabled 2D components - such as Flex components - mapped as 3D textures</li>
</ul>
<h3>Tutorials</h3>
<ul>
<li><a href="http://hub.aerys.in/index.php/Minko:Display_The_Position_And_The_Normal_Of_Each_Vertex">Display the position and the normal of each vertex</a></li>
<li><a href="http://hub.aerys.in/index.php/Minko:Display_The_Bones_And_Joints_Of_A_Skeleton">Display the bones and joints of a skeleton</a></li>
<li><a href="http://hub.aerys.in/index.php/Minko:Select_Scene_Nodes_With_XPath">Select scene nodes with XPath</a></li>
</ul>
<h3>Fixes</h3>
<ul>
<li>minko-collada will now load the vertex RGBA data when it's available</li>
<li>min/max computation is always possible upon creation of a VertexStream regardless of its StreamUsage</li>
<li>frustum culling will now also test the center of the bounding box and not only the 8 corners</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2012/11/02/minko-weekly-roundup-4/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Minko Weekly Roundup #3</title>
		<link>http://blogs.aerys.in/jeanmarc-leroux/2012/10/03/minko-weekly-roundup-3/</link>
		<comments>http://blogs.aerys.in/jeanmarc-leroux/2012/10/03/minko-weekly-roundup-3/#comments</comments>
		<pubDate>Wed, 03 Oct 2012 11:53:42 +0000</pubDate>
		<dc:creator>Promethe</dc:creator>
				<category><![CDATA[Aerys]]></category>
		<category><![CDATA[Minko]]></category>
		<category><![CDATA[Minko 2]]></category>
		<category><![CDATA[Minko Studio]]></category>
		<category><![CDATA[Stage3D]]></category>

		<guid isPermaLink="false">http://blogs.aerys.in/jeanmarc-leroux/?p=2242</guid>
		<description><![CDATA[Projects Wieliczka Salt Mine website and apps Created by the Polish agency GoldenSubmarine, the Wieliczka Salt Mine web site offers an interative experience with HD 360° panoramas built with Minko. Thanks to Adobe AIR, the application is also available on mobile platforms such as the iPad, the iPhone and Android. This awesome project was just [...]]]></description>
				<content:encoded><![CDATA[<h3>Projects</h3>
<h4>Wieliczka Salt Mine website and apps</h4>
<p><center><a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2012/09/zapraszamy.png" rel="shadowbox[sbpost-2242];player=img;"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2012/09/zapraszamy-300x169.png" alt="" title="zapraszamy" width="300" height="169" class="size-medium wp-image-2265" /></a> <a href="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2012/09/zapraszamy_2.png" rel="shadowbox[sbpost-2242];player=img;"><img src="http://blogs.aerys.in/jeanmarc-leroux/wp-content/uploads/2012/09/zapraszamy_2-300x169.png" alt="" title="zapraszamy_2" width="300" height="169" class="alignnone size-medium wp-image-2273" /></a></center></p>
<p>Created by the Polish agency <a href="http://www.goldensubmarine.com">GoldenSubmarine</a>, <a href="http://www.wieliczka-saltmine.com/">the Wieliczka Salt Mine web site</a> offers an <a href="http://www.kopalnia.pl/en/zapraszamy">interative experience with HD 360° panoramas</a> built with Minko. Thanks to Adobe AIR, the application is also available on mobile platforms such as the <a href="http://itunes.apple.com/app/the-salt-mine/id547636839">iPad</a>, the <a href="http://itunes.apple.com/app/wieliczka-mine/id547928426">iPhone</a> and <a href="https://play.google.com/store/apps/details?id=air.com.goldensubmarine.wieliczkamine">Android</a>.</p>
<p><center><iframe width="560" height="315" src="http://www.youtube.com/embed/od74X1aXIyg?rel=0" frameborder="0" allowfullscreen></iframe></center></p>
<p>This awesome project was just rewarded with the <a href="http://www.thefwa.com/mobile/the-salt-mine">"FWA Mobile of the Day" award</a>! This is the very first FWA for a project built with Minko so we are very proud of course!</p>
<h3>Videos</h3>
<p><center><iframe width="560" height="315" src="http://www.youtube.com/embed/2imwYF0BWOI?rel=0" frameborder="0" allowfullscreen></iframe></center></p>
<p>This video presents yet another example of a very cool shader built by developer <a href="https://twitter.com/chloridrik">Jeremy Sellam</a> from the Les Chinois, a French digital agency based in Paris, France. It was built with <a href="http://hub.aerys.in/index.php/Minko:Tools">the public beta of the ShaderLab</a> of course!</p>
<h3>Features</h3>
<h4>ByteArray streams</h4>
<p>Geometry is now stored in ByteArray objects. It reduces the memory consumption and should provide a significant performances boost. Especially on mobile devices. You can read more about this feature on <a href="http://blogs.aerys.in/jeanmarc-leroux/2012/09/07/new-minko-feature-bytearray-streams/">my previous blog post</a>.</p>
<h4>Parametric frustum culling</h4>
<p>Minko now implements frustum culling in a very flexible fashion. You can chose on what planes and using what volume (sphere or box) frustum culling is computed. For example, to use the bounding sphere on all planes but the box only on the near/far planes, you can write:</p>

<div class="wp_syntax"><table><tr><td class="code"><pre class="actionscript3" style="font-family:monospace;">mesh<span style="color: #000066; font-weight: bold;">.</span>frustumCulling = FrustumCulling<span style="color: #000066; font-weight: bold;">.</span>SPHERE <span style="color: #000066; font-weight: bold;">|</span> FrustumCulling<span style="color: #000066; font-weight: bold;">.</span>BOX_NEAR <span style="color: #000066; font-weight: bold;">|</span> FrustumCulling<span style="color: #000066; font-weight: bold;">.</span>BOX_FAR<span style="color: #000066; font-weight: bold;">;</span></pre></td></tr></table></div>

<p>Such flexibility should make it possible to optimize performances to every use case. It's also nice to consider computations are kept to a minimum by storing world space versions of the bounding sphere/box. You can view the entire code for this feature in the <a href="https://github.com/aerys/minko/blob/2.0b/src/aerys/minko/scene/controller/mesh/VisibilityController.as">VisibilityController</a>.</p>
<h4>Per-triangle ray casting</h4>
<p>Geometry.cast() now makes it possible to get the triangle ID (the first indice of the triangle) that crosses the specified ray. Combined with Mesh.cast() and Group.cast(), it makes it very easy to perform ray-casting at any level, from the root of the scene to the geometry level.</p>
<h4>Local/world gizmos in Minko Studio</h4>
<p>Gizmos are the key to any WYSIWYG editor. We've enhanced Minko Studio's gizmos not only by adding scale/rotation gizmos but also the possiblity to chose whether those gizmos should be used in local or world space. </p>
<h4>Smooth shadows in Minko Studio</h4>
<p>Shadows are a very important part of any real-time 3D immersive application. Thus, being able to control the quality of the shadows while keeping interactive framerates is very important. The minko-lighting plugin already introduced soft shadows a few weeks ago, and now the corresponding options are available right inside Minko Studio! It's now easier than ever to fine tune the lighting engine in order to get the best performance/quality ratio.</p>
<h3>Documentation</h3>
<p>Minko now has a new, clean and fast growing wiki: the <a href="hub.aerys.in">developers Hub</a>. You will find a lots a old and new tutorials. But also lots a new <a href="http://hub.aerys.in/index.php/Minko:Examples">examples and projects done with Minko</a>!</p>
<ul>
<li><a href="http://blogs.aerys.in/jeanmarc-leroux/?p=2217">Add pixel-perfect 3D mouse interactivity</a></li>
<li>The <a href="https://github.com/aerys/minko-examples/tree/master/src/aerys/minko/example/core/keyboardscript">KeyboardScriptExample</a> demonstrates how to build a very <a href="https://github.com/aerys/minko-examples/blob/master/src/aerys/minko/example/core/keyboardscript/FocusScript.as">simple script to handle focus 3D objects</a> and <a href="https://github.com/aerys/minko-examples/blob/master/src/aerys/minko/example/core/keyboardscript/KeyboardMoveScript.as">move them with the keyboard</a>. This example really highlights how easy it is to create controllers and have them working on any scene, thus making it possible to code things once and re-use them at any time!</li>
</ul>
<h3>Fixes</h3>
<ul>
<li>Geometry.fillNormalsData() and Geometry.fillTangentsData will reset the corresponding buffers to make sure normals/tangents are not incremented everytime they are supposed to be updated.</li>
<li>Picking has been completely refactored: all the known bugs have been fixed and we are now using a <a href="https://github.com/aerys/minko-picking/issues/1">1*1 BitmapData</a>/scissor rectangle to get better performances.</li>
<li>The Collada loader will now inspect 3D transforms in order to handle negative scales properly. It will also invert the z axis at the vertex level in order to perform right to left handed coordinates conversion. It fixes problems occuring when loading animations build using symmetry.</li>
</ul>
<p>Don't forget to "watch" <a href="https://github.com/aerys/minko">Minko's github repository</a> to get your daily dose of new features and fixes!</p>
]]></content:encoded>
			<wfw:commentRss>http://blogs.aerys.in/jeanmarc-leroux/2012/10/03/minko-weekly-roundup-3/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
