I have a number of security cameras in my game that ultimately render to a texture that is then presented to the player as a monitor within the world.
I’ve found that when I have 3 or more of these within the world the frame rate starts to drop. I’ve already got these cameras rendering at quite low resolution but the resolution doesn’t seem to be the limiting factor. Are there any options to reduce the quality of these secondary cameras within the scene. One option I’ve been looking for is to reduce their framerate without changing the main game frame rate. Is there any such option?
This is a minimal example of my set up; the traditional blue cube and a secondary camera filming it and putting the captured image back into the world:
package test;
import com.jme3.app.SimpleApplication;
import com.jme3.material.Material;
import com.jme3.math.*;
import com.jme3.renderer.Camera;
import com.jme3.renderer.ViewPort;
import com.jme3.scene.Geometry;
import com.jme3.scene.shape.*;
import com.jme3.texture.*;
import java.util.UUID;
public class Main extends SimpleApplication {
public static int IMAGE_SIZE =256;
@Override
public void simpleInitApp() {
rootNode.attachChild(getBoxToLookAt());
Camera offCamera= new Camera(IMAGE_SIZE,IMAGE_SIZE);
offCamera.setLocation(new Vector3f(2,2,2));
offCamera.lookAt(new Vector3f(0,0,0), Vector3f.UNIT_Y);
ViewPort offView = getRenderManager().createMainView(UUID.randomUUID().toString(), offCamera);
offView.setClearFlags(true, true, true);
Texture2D drawableTexture = new Texture2D(IMAGE_SIZE,IMAGE_SIZE, Image.Format.RGBA8);
FrameBuffer offBuffer = new FrameBuffer(IMAGE_SIZE,IMAGE_SIZE, 1);
//setup framebuffer's cam
offCamera.setFrustumPerspective(90f, 1f, 0.2f, 1000f);
drawableTexture.setMinFilter(Texture.MinFilter.Trilinear);
drawableTexture.setMagFilter(Texture.MagFilter.Bilinear);
//setup framebuffer to use texture
offBuffer.setDepthBuffer(Image.Format.Depth);
offBuffer.setColorTexture(drawableTexture);
//set viewport to render to offscreen framebuffer
offView.setOutputFrameBuffer(offBuffer);
offView.attachScene(this.rootNode);
offView.setBackgroundColor(ColorRGBA.White);
//set up quad showing what the camera can see
Geometry screen = getQuadToRenderImageOn();
screen.getMaterial().setTexture("ColorMap", drawableTexture);
screen.setLocalTranslation(0,2,0);
rootNode.attachChild(screen);
cam.lookAt(screen.getWorldTranslation(), Vector3f.UNIT_Y);
}
private Geometry getBoxToLookAt(){
Box b = new Box(1, 1, 1);
Geometry geom = new Geometry("Box", b);
Material mat = new Material(assetManager,
"Common/MatDefs/Misc/Unshaded.j3md");
mat.setColor("Color", ColorRGBA.Blue);
geom.setMaterial(mat);
return geom;
}
private Geometry getQuadToRenderImageOn(){
Quad q = new Quad(1, 1);
Geometry geom = new Geometry("Box", q);
Material mat = new Material(assetManager,
"Common/MatDefs/Misc/Unshaded.j3md");
geom.setMaterial(mat);
return geom;
}
public static void main(String[] args){
Main main = new Main();
main.start();
}
}
Its clear to me that I will need to turn on and off my cameras intelligently based on if the player is likely to be able to see them, but I’d like to be able to have at least 3 visible without it causing the frame rate to drop. Is there a way to achieve that by sacrificing quality?