Jump to content

animate or morph mesh dynamically


Recommended Posts


I just started working about giving to the developper the way to animate or morph a parametric mesh (as she/he can't really know how the vertices are set).

Before going in the higher logic of smartly dividing  the parametric mesh into subparts, I'm just trying to animate it.

I get inspired by this Altreality's former example : http://playground.babylonjs.com/#1AVEYO#13

Well, I just create a wave ribbon here : http://playground.babylonjs.com/#1UZIZC

and animate then it with updateVerticesData() methods (line 62) : http://playground.babylonjs.com/#1UZIZC#1

This works pretty well (60 fps) in my Chromium browser... for 2-3 minutes only.

Then the framerate suddenly falls down to 7/8 fps and something (don't get what) seems to crumble (GC calls ? GPU calls ?).

Finally after 6-8 minutes, Chromium (v41) crashes !

Any idea about what and why (didn't see anything pertinent with debugLayer) ?

Link to comment
Share on other sites

That looks pretty cool already!!! But I have the same issue with the latest chrome. After a few minutes the frame rate drops dramatically. (didn't wait for the crash here, though)


Firefox seams to have a similar issue, but a lot slower? The frame rate is changing often sometimes going up, but most of the time going down. It crashed when it hit 22 frames per second, but as I said, it took a lot longer than chrome.


(I don't have a solution, just confirming the issue :P

Link to comment
Share on other sites

Thank you for reporting...

So you crashed your FF too ? Well, it's not a browser bug then, but a bug in my code (or in BJS)

I just can't crash FF v36 here for now.


Anyone can reproduce it with IE ?


or a clue to debug ?

Link to comment
Share on other sites

In my code, I don't allocate array in the rendering loop.

I use the same positions array and the pre-created once normals array.

I read the code of ComputeNormals() : there's no push or array creation, normals are set per array index (normals = value). So I guess this method doesn't allocate any extra memory.


Maybe are there temporary arrays created in the updateVertices() method ? don't know, need to check ...

Link to comment
Share on other sites

Tube animation : http://www.babylonjs-playground.com/#29CXFN


Well, it's quite more complex than for a simple shape or a flat ribbon because every coordinate has to be recomputed each frame. Indeed, I want that the developer will just have to pass an animated path (the tube axis) - remember : simple for everyone ;)  - or a radius and the tube should be then recomputed (no mesh re-creation, the same mesh morphed).


For now, it's just a prototype :

Mesh data don't need extra memory allocation but, as path, radius, tesselation aren't tube mesh stored properties yet, these values imply new small memory allocations each frame for coordinate computations (ex a new path3D object is created each frame), then garbage collected.

This little things could be optimized.

However runs at 60 fps in chromium and FF here :)


I didn't handle uvs either.


I need to have a discuss with DK about how to implement this in BJS :

add new properties on certain parametric mesh types ?

add a new dedicated method to certain parametric mesh types : tube.morph(path, radius), tube.update(path, radius), tube.animate(path, radius) ?


add some static method and pass it the mesh : morphTube(tubeObject, path, radius) ?

Link to comment
Share on other sites

not finished..

Remember the tube had a radius function also, well : http://www.babylonjs-playground.com/#29CXFN#3



a little closure line 136 to embed to the k value in the radiusFunction ;)


What I want to do ?

See line 40 : the developer codes only his own updatePath() or updateRadius() function updating a path or a radius. That's enough.

Then he calls some tube.animate() or MorphTube(tube) or whatever (to be decided according to BJS philosophy) in the render loop and that's it.


Next, I will do the same for ribbon and extrusion (quite same algo, I will factorize it)

Link to comment
Share on other sites

Way nice, Jerome.  We knew this day was coming.  jMesh Industries - "Proudly Making A Mesh Of Everything"  :)


Remember me talking about how much I like cannons that "pucker-up" before they fire?  (cartoon cannons). 


Well, I think that little challenge is now solved.  Ol' Jerome has many puckers happening in the cannon tube.  :)


Jerome, you haven't fired a physics-active mesh through the air with applyImpulse, tumbling it across a physics-active floor and into a physics-active pile of boxes, have you?  Ever puckered a cannon?  ;)


It gets short and fat before firing (anticipation), and then gets long and thin just after the shot.


Yep, we'll need particle smoke from the end of the barrel, too.  FUN!!


Remember the cartoons... when a character would have to travel through a pipe?  And the pipe would bulge to the shape of the character as it travels through the pipe.  FUN!


Snake skin.  Push a 4000 meter Torus Knot through a tiny jMesh tube... and watch the tube conform to the shape of the knot as it moves through the tube!  WOW! 


But no.  Nothing THAT easy.  We need to shove a spiney spherical harmonic mesh thru a tiny jMesh tube.  Yeah!  ;)  That will test it's snake skin, eh?


What's that?  You can't get a precise enough bounding box on a spherical harmonic mesh... to make your tube skin conform to its shape?  Well, pft.  ;)

Link to comment
Share on other sites

Hey Wingy

Nice idea, this cartoon cannon  :P Love it !


There is no physics here, only a vertex position update each frame without any vertex shader use.

My goal is just to provide to the developer a way to update an already created parametric mesh (as he can't guess how many vertices there are and where they are) instead of disposing it and re-creating a new one slightly different, what is a bad practice in a render loop.

Imagine a mesh rope swinging from the ceiling... or a puckering cartoon cannon  :D


The developer only gives a path (an axis) and a radius (or a radius function) to build a tube.

So I want him just to give another path and another radius (or the same) to update the tube.

Not to know anything about vertex positions, which are quite complex to compute in the case of  a tube.


I will do the same for the ribbon (almost done actually, I just need to achieve the DOUBLESIDE problem) and we will soon be able to update smoothly any kind of ribbon, so ... a SH  ;)


I will recode the SH demo so a given SH will smoothly (I hope) morph to the next random parameter values instead of creating and destroying intermediate SH on the fly.

Link to comment
Share on other sites

:)  Yeah, I know that there is no physics active in your demos.  I was trying to get you do a bunch of work for me... for a remake of a game called Artillery Duel.  I thought you might want to try a scene that uses cannon pucker... as a demo scene to showcase your new animation features.  The only physics necessary is to launch the cannonball into the air, and have it bounce and impact things nicely.  No physics is involved in the tube itself.


But I can make the cannon pucker test/demo, too.  You've made it much easier for me to do.  :)  Thanks!


I don't know if SH will see so easy to animate.  The 'm' values are creation-time variables, I bet.  No simple cosine animating of the m-numbers without complete re-draw, I suspect.  But it's ok.  Morph-animating SH is really not very important or useful, imho.  And a tube skin... whose bulges conform to the shapes of other mesh that get pushed through the too-small-diameter tube... well, that would be quite difficult to accomplish, I would think.


Yep, I think I understand how this works.  One path and radius is for the initial draw.  The second potentially-different path with potentially-different radii... is the animation-influencer path/radii.  Thanks for the explanation... well done.  Good luck on the doubleside endeavor, Captain J. 

Link to comment
Share on other sites

  And a tube skin... whose bulges conform to the shapes of other mesh that get pushed through the too-small-diameter tube... well, that would be quite difficult to accomplish, I would think.



imho, the easiest solution for this would be extrusion : extrude a circle for a while (well it's a tube), then change the shape to be extruded to the shape of the mesh you want to be pushed in the tube, then continue with an extruded circle  :)


or  just stick a tube, an extruded shape along a short path and finally another tube


Imagine : a tube part, then a squared shape extruded (would fake a cube blocked in the tube, for instance) and finally a last tube part.


I need to implement extruded mesh update too : path, scale, rotation. gasp ! So much to do  :lol:

Maybe actual extrusion (advanced mode) could have a new feature : shapeFunction ... the ability to change dynamically the shape along the path (keeping the same number of vertex though)

Link to comment
Share on other sites

Interesting thinking, J!  You are SO MUCH FUN to discuss mad-scientist ideas-with.  :)


Jerome, I've done more reading of your docs... than examining of your classes/code.  Do you do error/log reports when users do illegal things? 


For example, if the animation (2nd) path/radii has more or less path points than the initial path, would the user be told that?  Have you been thinking about when/where to report things in the console?


I'm not trying to criticize anything.  I'm trying to learn "best practices" and see how others do things.


We sometimes see errors in playgrounds... like "c is not defined", where "c" could be a, b, c, d, e, f, you name it.  We pros know that means we don't have the correct number of parameters in some framework function call.  But for youngsters, that is a predominently information-less error report.  Even for us pros, that error report doesn't tell us WHICH framework function call is short on parameters.  It's likely the one that we edited just before the RUN that produced the error.  :)


If you have a moment, can you tell me YOUR thoughts on validity checking... and when it should be done... versus the speed-slowdowns that validity/datatype checking can cause? 


In my opinion, slowdowns caused by validity checking during scene "assembly"  is not such a big deal.  Slowness during that time... is not overly annoying.  But validity checking during functions that need to run fast... I tend to avoid.  You too, probably.


The ribbon system is not an overly friendly system, at least not until users get their brains in ribbon-mode.  :)  I'm curious if you struggle with when, where, and how-often... you report something to a user.  Thoughts?  (thx)


ANY programmer who has thoughts on "when/what to report", I'd love to hear them.  Feel free to use The Wingnut Chronicles to comment on this, if you wish to avoid derailing Jerome's initial topic.  I should have done the same.  But Jerome seems forgiving.  :)

Link to comment
Share on other sites


Really good question about logs upon illegal/wrong actions

I was exactly wondering what to do about this topic.


For now, my thoughts are :


- there is no log in other BJS methods (in the very big majority of them) on wrong actions : just try to pass wrong parameter values to many mesh creation methods, it just does nothing or bugs ...

- wrong actions are potentially so numerous (wrong number of arguments, wrong types of arguments, wrong order, wrong sign, etc, etc), I guess it's quite heavy to test any case.

- I try to design my tools with the best mix I can in terms of adaptativity and efficiency (I hope), this means they should be as light and fast as possible but able to adjust to many different cases without crashing ... assuming some opinionated behaviors, ex : ribbons stop at first of shortest paths, priority is given on normals over uvs, etc. These assumptions are then explained in the documentation.


So, for now, I think I will rather focus on documentation (what should be passed, why this value rather than this one, how it is internally processed then, etc) than implement a checking/logging system.

I'm aware it's not as user-friendly as a console log message : "the second value must be greater than the third one"

In brief, I will provide the way to understand and to use it... and then will appeal to the user's intelligence.


example, for the tube update, I will probably write a doc about this good path usage :


- have a single path array, created once outside the render loop, so you won't allocate memory each frame,

- don't create Vector3 objects either in this render loop... avoid any object there creation in general,

- so set Vector3 values into your path array with index array accesses : path.x = new_val, path.y = new_val, path.z = new_val.

This way, you are sure to keep the same array, so the same array length and you don't allocate any new memory.




I would prefer to have a good reporting API, but for the reasons mentionned above, I will rather opt for a good documentation instead.


BTW, as the BJS API is not usually really verbose in console logging, we could have a dedicated documentation part about how to code/debug with BJS :

In the PG, if you get a "c is not defined" error, it's due a wrong number of parameters in a method call, so comment all your method calls except one and retry, you will find out which is the one causing the error
Link to comment
Share on other sites

Join the conversation

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

Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

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

×   Your previous content has been restored.   Clear editor

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


  • Recently Browsing   0 members

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