How to simply render a Spatial?

Hi,



I am new to JME and have a specific need : render a simple scene on demand, and nothing else.

Is there a way to do this ?



I first thought there would something like a “Rendering” class with a render() function, which would take a Spatial and a Camera as argument and would return an image, but the only thing approaching this dream is the RenderManager class, and I just don’t understand how it works !



Did anyone ever managed to do this ?

I assume you want to render your scene “offscreen” so without showing it in your jME window - I’m currently working on a similar problem, I’ll post my code located on another machine soon

This code is designed for offscreen cloud texture rendering:



Uhm, I can’t figure out how to post some code here - uploaded it there http://paste.posativ.org/SJfFC6ni for the moment.



This is a SceneProcessor which allows me to hook in the rendering cycle to pre-render the cloud image (not implemented yet, only a demo scene in pure orange :wink: ) before applying it as a texture to the final scene…

1 Like

Look at TestRenderToMemory

http://code.google.com/p/jmonkeyengine/source/browse/trunk/engine/src/test/jme3test/post/TestRenderToMemory.java

the setupOffscreenView() method is what you’re looking for



Edit : @cmur2 example is nice too, a processor is the way to go.

1 Like

Oh thanks for your affirmation, while coding I was wondering if there is an easier way to achieve my desired effect since I don’t use methods like postQueue or postFrame etc… but I makes sense since I want jME to render my cloud image before the final scene.

@cmur BTW you should not render the clouds in the init method, it’s useless since this render result will never be used.



For your information : preframe is called before the actual render of the viewport, post queue is called just before the render, but after the scenegraph update (update spaptial transforms, and controls update) and the culling process occured.

postFrame is called just after the frame has been rendered.

Thank you for your quick answers !



These two examples are really helpful to understand how to use a SceneProcessor, thanks !



Have a second problem though, because I need it to render on demand (and get rid of the game loop !).

The only examples I found are based on the SimpleApplication class, which provides a game loop, and I want to control this loop by myself, without JME (the final goal is to manage my scene separately and render it after modification). My real problem is that I don’t manage to get all the needed resources (renderManager, assetManager, etc.) without using the JME Application class !



If someone has a solution, thanks !

No offense but… that sounds bad, if you want to do that you’re probably going in the wrong direction.



What do you want to do exactly, maybe we can point you to a correct solution keeping the game loop?.

I am integrating JME into an other project, which needs this “on-demand rendering” function. Because this other project has it’s own lifecycle, I have to do this without JME gameloop…



Thank you for helping me btw :slight_smile:

Either use vanilla OpenGL or just cope with the fact that its a separate thread (in the end you will have to treat OpenGL similar anyway). “on demand display” works just as well when you enqueue the changes to the update loop (so like any modern concurrent api works really).

So is there any way to trigger the update by myself, or to trigger it after my changes ?



Thank you for your answer :slight_smile:

No and you should not do it as I said. You also don’t come up with the idea to run the swing update thread yourself do you? Still you probably use swing for some application to display stuff. You do not need to call it yourself, just make sure you enqueue the display commands to the update loop.

If I build a simple Swing application, of course I won’t try to control the update loop, and it would be the same for jME. But I am not building a simple game with jME : I have very particular needs, and I thought jME would be flexible enough to do what I want, which is simply render a spatial when I ask it to do it.



Anyway, thanks for answering, I’ll make it a different way.

How many times more do i have to tell you that you do not need to stop the update loop for that? :roll:

Just enqueue a callable to the update loop that displays the spatial. As I try to tell you most modern apis work this way. They have a worker thread that you don’t even recognize and do the display there. Thats what the update loop is.

Sorry for misunderstanding! My bad english might have it’s part of responsibility… but thank you for being so patient!



Maybe anyone have any example of how to create or modify (modifications might be done at different moments) a scene and then, get a render by adding a callable in the render queue? I just want to avoid having a render after every single modification, and don’t really see how to use the queue (I am not familiar with this kind of functioning…)?

Actually, any example with this “enqueuing” system would be helpful, because I don’t really understand how it works.



Thank you very much, and sorry again…

Its exactly like swing, in swing you have to do this when you want to modify the UI from another thread:

[java]

java.awt.EventQueue.invokeLater(new Runnable() {



public void run() {

//MODIFY UI HERE, e.g.

slider.setValue(100);

}

});[/java]

In jME3, the same accounts:

[java]

application.enqueue(new Callable<Void>(){



public Void call() throws Exception {

//MODIFY SCENE HERE, e.g.

spatial.setLocalTranslation(0,0,0);

}



});[/java]



If you are not familiar with this I guess this is the time where you understand why some of your swing UI elements would not update properly or even crash your application when they got updated in your past applications.

1 Like

Hello.

Following the examples and discussion.

I am trying to do this also, and while i can enqueue updates, scene refreshes even if nothing has to be rendered. (no modification to scene or anything). In my case, this is a waste of CPU and GPU that i will need to waste on real needs, whatever the size of the waste.

Did i made a mistake or is this supposed to be the normal way in JME3?



Any way to replicate JME2 's behavior, like this one? http://hub.jmonkeyengine.org/groups/general-2/forum/topic/updaterender-on-demand/

Just set the frame rate low or block the update loop with a wait()

1 Like

Wait() looks like a good idea. I would unlock only if my system needs refresh and check each frame if i let it running or not. Seems doable, even if a bit hacky in my mind.

Have to try that. Thanks a bunch.

Everything works great, thank you for your answers !