YABEE problem and hacky solution

So I just switched from unity to panda3d and am porting my game.

YABEE is definitely the best blender exporter I’ve seen for a graphics engine (dat HowTo pdf!)

But I have a problem that I had to hack my way through.

Problem:
Actor objects will throw out all meshes except one when loading an Egg file with multiple skeletons (I believe this is what is happening) let me illustrate.

Here is my happy (but poorly drawn) wizard in blender:

This shows how his skeleton is split:

Here’s how he looks in pview when I export him (the animation is working too, couldn’t show that):

But here’s how he looks in game when I use the actor class:

model = loader.loadModel("fullWizTest")
self.pandaActor = Actor(model,{"walk": "fullWizTest-walk.egg"})

or

self.pandaActor = Actor("fullWizTest",{"walk": "fullWizTest-walk.egg"})


The animation for the feet still works, but obviously his upper torso is missing, presenting a problem.

Hacky Solution:

Export the chest by itself:

Then load the chest by itself as well as the other model:

model = loader.loadModel("fullWizTest")
chest = loader.loadModel("fullWizChest")
self.pandaActor = Actor(model,{"walk": "fullWizTest-walk.egg"})
self.pandaActor2 = Actor(chest,{"walk": "fullWizChest-walk.egg", "cast": "fullWizChest-cast.egg"})

I also had to find the hat and head (they were separated also) apparently the exist in the original files still, they just aren’t showing up on screen.

head = model.findAllMatches("*").getPath(0).findAllMatches("*head*").getPath(0)
hat = model.findAllMatches("*").getPath(0).findAllMatches("*hat*").getPath(0)

I added all these objects to the same node and then to the world. The torso came out right on top of the legs with no adjusting, the hat and head took some adjusting with setPos()

Now all the character’s parts are in the game:

I’m not sure why this is happening, and I read a few places that you’re supposed to be able to export like this (multiple skeletons/meshes) as long as it’s one skeleton to one mesh. Also in the exporter GUI there’s a checkbox to “Merge Actor” which gave me the idea to merge the skeletons (the tooltip suggests this will work) so
I joined the two skeletons (keeping the meshes separate), redid the weights and animations for the torso, but when I tried to export this I got an error:

Sorry that this isn’t more descriptive. It’s 5am and I just wanted to get some info down before I pass out. I’m going to update this tomorrow or the next day with more information. Hopefully I can figure this out and I won’t have to use this hacky method, or maybe I can make the hacky method less hacky.

Oh yeah, the reason I have separate meshes is so that the material shows up correctly. I’m a bad 3d artist, so I had to make the textures in pieces having multiple textures. If I join all the meshes, the exporter jarbles all the materials together giving a really weird look (only tested in pview) I tried using the “bake” option, but it looks weird too (scaling off) maybe I could play around with that more.

I think your actor might be animated to move outside of his static bounding volume. This can cause the kind of effect you see here, where different parts are “culled” and disappear from different points of view.

If that’s the case, the easy solution is to pass setFinal=True to the Actor constructor. That should solve the problem of individual pieces disappearing. If you want to disable culling for the Actor completely (because, for instance, the entire actor disappears from certain points of view), then do:

actor.node().setBounds(OmniBoundingVolume())
actor.node().setFinal(True)

David

hmm i tried:

		model = loader.loadModel("fullWizTest")
		self.pandaActor = Actor(model,{"walk": "fullWizTest-walk.egg"},setFinal=True)

and:

		model = loader.loadModel("fullWizTest")
		self.pandaActor = Actor(model,{"walk": "fullWizTest-walk.egg"},setFinal=True)
		
		self.pandaActor.node().setBounds(OmniBoundingVolume())
		self.pandaActor.node().setFinal(True)

neither work correctly. The torso and head and hat still disappear. Also just tried “show” on the hat and head nodes, to no avail. Was thinking of just going down the list of nodepath functions and trying them all. Maybe I’ll find it.

If the parts are still disappearing, then it’s not a culling problem, and I doubt that any of the NodePath methods will help you here. It might be some problem with the animation conversion–maybe the animation data is crushing the missing pieces to scale 0 or something like that. But still, the underlying code that binds the animation is the same in pview as in the Actor class, so I don’t understand why you’re getting different behaviors between the two–can you elaborate on this?

Maybe it will help if you post your egg files.

David

This may be an irrelevant observation, but in case it helps I’ll note that in the fourth screenshot of the first post (the first in-game screenshot, I believe), it appears that the wizard’s head is actually present in the scene, but incorrectly positioned: look towards the top of the screenshot; part of the beard and hat seem to be visible behind the grey object.

Perhaps some strange scale is being applied, either to the parts or the armature?

I had a weird dream last night where I was still using Unity and this bug had something to do with the default 0.01 scale import on the editor… strange dream.

Anyway,

I can’t believe I missed the hat and beard in that screen shot! I can’t replicate that result. I think I might’ve just had my hack to get the hat and head still in the code when I took the screen shot (along with the actor loading code) but I set the positions of the head and hat high up to get them out of the view (unsuccessfully). In any case, it’s either irrelevant or not reproducible, so you guys should disregard it.

Here’s a link to the egg file.
http://scottgriffy.com/fullWizTest.egg
http://scottgriffy.com/fullWizTest-walk.egg

I boiled it down to this simple code:

from direct.showbase.ShowBase import ShowBase
from direct.actor.Actor import Actor

class MyApp(ShowBase):

	def __init__(self):
		ShowBase.__init__(self)
		
		model = loader.loadModel("fullWizTest")
		model.setPos(2, 0, 0)
		model.reparentTo(render)
		pandaActor = Actor("fullWizTest")
		pandaActor.setPos(-2, 0, 0)
		pandaActor.reparentTo(render)
		self.camera.lookAt(model)
		self.camera.lookAt(model)

 
app = MyApp()
app.run()

Result:

And I zoomed out to make sure there were no floating hats and heads.

I think that we can disregard the “walk” egg file because I loaded the actor with out it and it still cuts off everything.

And when I put in:

print pandaActor.getNodes()
print model.getNodes()

I get:

[PandaNode skirt, PandaNode render]
[ModelRoot fullWizTest.egg, PandaNode render]

So only the skirt is attached to the actor… interesting… I re-exported the egg file from blender to make sure I didn’t screw anything up, it’s still animating in pview, full body, and still not showing up in game.

If I load the model directly everything looks fine (without the Actor class). Can I do animations without the actor class? That would be fine and less hacky than my current solution.

Sorry for the late response and thanks for helping me.

I think it would be much easier if you tried to fix the original issue of joining things making the textures wrong.

However, I took a look at the error you got in yabee. Near as I can tell this error means you have an armature modifier applied to some object but haven’t specified an armature to modify by. Yabee doesn’t check that, so it just crashes. When you joined the armatures, this probably deleted the link in the modifier on one mesh but kept the modifier. You could try that again and ensure both meshes have their modifiers pointing to the joint armature.