Recently I’ve been tinkering with the “camera in another mode” idea again (one of my previous topics). And I’ve just set up everything. Models and animations load just fine, but, if I try to attach a particleEmmiter from another class the program will crash and tell me I’m not allowed to update the node from another thread.
It’s been driving me nuts, for I cannot find any errors or anything like that. Can someone help?
Your code looks fine from here.
Well… It’s changed a bit since the last time I’ve posted the first time.
Now it looks like this:
public class ViewModel {
public ParticleEmitter debrisEffect;
public Camera privateCamera;
public Node newNode = new Node("View Model Node");
public ViewPort privateViewPort;
public ViewModel() {
CreateSeperateReality();
/** Explosion effect. Uses Texture from jme3-test-data library! */
debrisEffect = new ParticleEmitter("Debris", ParticleMesh.Type.Triangle, 10);
Material debrisMat = new Material(Main.app.getAssetManager(), "Common/MatDefs/Misc/Particle.j3md");
debrisMat.setTexture("Texture", Main.app.getAssetManager().loadTexture("Effects/Explosion/Debris.png"));
debrisEffect.setMaterial(debrisMat);
debrisEffect.setImagesX(3); debrisEffect.setImagesY(3); // 3x3 texture animation
debrisEffect.setRotateSpeed(4);
debrisEffect.setSelectRandomImage(true);
debrisEffect.getParticleInfluencer().setInitialVelocity(new Vector3f(0, 4, 0));
debrisEffect.setStartColor(new ColorRGBA(1f, 1f, 1f, 1f));
debrisEffect.setGravity(0f,6f,0f);
debrisEffect.getParticleInfluencer().setVelocityVariation(.60f);
newNode.attachChild(debrisEffect);
debrisEffect.emitAllParticles();
}
public void CreateSeperateReality() {
privateCamera = Main.app.getCamera().clone();
privateCamera.setViewPort(0, 1, 0, 1);
/** A white, spot light source. */
PointLight lamp = new PointLight();
lamp.setPosition(new Vector3f(-3,5,2));
lamp.setColor(ColorRGBA.White);
newNode.addLight(lamp);
privateViewPort = Main.app.getRenderManager().createMainView("Top Left", privateCamera);
privateViewPort.setClearFlags(true, true, true);
privateViewPort.attachScene(newNode);
System.out.println("viewPort UP!");
}
public void UpdateViewModel(float tpf) {
newNode.updateLogicalState(tpf);
newNode.updateGeometricState();
}
(Actually the first part is pretty similar)
Meanwhile in Another Class
public void shoot() { // called everytime the player shoots
playAnimation("shoot"); //dont worry about this
particleEffect.setParticlesPerSec(10); // placeholder name
particleEffect.emitAllParticles();
// particle effects already set up
}
Because the shoot() method is being called from another class, the program will crash telling me that:.
But if I called it in the ViewModel Class then everything would run fine.
No, the issue is that you are not calling these in the right place:
You should be managing your viewport with an app state. Then we’d have something to talk about. (And there are half-a-dozen threads on this, one even in the last week if you want to read up.) Else we have to see too much code to figure out what you are doing.
But I can say with certainty that if you are calling those two methods together then you will have problems.
newNode.updateGeometricState();
Should normally be called as close to rendering as possible… so in an app state you’d call that in AppState.render()
hmmm…
so if I am on the same path as you (correct saying?) then what you are saying is that I should be updating the newNode in a appState and I should run updateGeometricState in AppState.render?
I’m saying all of the viewport management should be done in an app state. Your life will get a lot easier.
Do viewport enable/disable when the app state enables/disables (extend BaseAppState and do it in onEnable() and onDisable())
yourRootNode.updateLogicalState() in AppState.update()
yourRootNode.updateGeometricState() in AppState.render()
create the viewport in AppState.initialize()
destroy it in AppState.cleanup()
This was discussed on the forum really recently in another topic. I don’t remember what search parameters will get it and I respond to a lot of posts but you could always scroll back through my replies to see if you can find it. Though the above information actually may be more complete than what I posted there.
Can you send me some of the threads?
I would have to go through the same amount of work to find them that you would… the difference is that I don’t need them and I already gave you enough information to solve your problem.
should I extend to AbstractAppState or BaseAppState, and what are the differences between the two?
Extend BaseAppState… it provides a lot more built in functionality as clearly spelled out in its javadoc. (Always have the javadoc one click away.)
AbstractAppState is barely worth bothering with in most cases.
ok, ok, seems legit, but what is the main cause of the game crashing error? And if I moved everything over to a BaseAppState how would that fix the situation
The error said you were updating at the wrong time. I said you were updating at the wrong time.
So… I think you are updating at the wrong time and need to update at the right time as I already said.
So update at the right time. Don’t updateGeometricState() at the wrong time but at the right time. In other words, update at the proper time and not too soon because if you update at the wrong time and then modify something before rendering then you will get the error that you updated at the wrong time. And then you HAVE TO UPDATE AT THE RIGHT TIME.
nvm, I fixed it. Thx for your help