Stretch JmeCanvasContext? or OpenGL shader to a jMonkey shader?

I am trying to create a application with a resolution 640 x 480 but displayed in a JFrame or Applet that is 800 x 600. I want each pixcle in the application doubled so instead of 1 x1 they are 2 x 2 does this make since? the idea is to create a pixcilized 3D environment giving the effect of an old low resolution game in a window that is of a reasonable size.

Heres an example of the effect I am looking for…



Secret of Mana I think was originally 320 x 240 but this image is 640 x 480





What I attempted was to set the AppSettings resolution to 640 x 480 and the JmeCanvasContext preferred size to 800 x 600. [FAIL]



EDIT:

Ok I found something that would work but I don’t know how to convert a OpenGL shader to a jMonkey shader a point in the right direction would be helpful.

Link to shader I found → http://www.geeks3d.com/20101029/shader-library-pixelation-post-processing-effect-glsl/

you don’t really need a shader here.



What i would do is to resize the cam to 640x480 and render the scene to a frame buffer. set the mag filter of the texture to nearest

then render a full sreen quad at full resolution and map the texture on it.

You can use the ColorOverlayFilter Material.

I made a quick test here



[java]

package mygame;



import com.jme3.app.SimpleApplication;

import com.jme3.light.DirectionalLight;

import com.jme3.material.Material;

import com.jme3.math.ColorRGBA;

import com.jme3.math.Vector3f;

import com.jme3.post.SceneProcessor;

import com.jme3.renderer.Camera;

import com.jme3.renderer.RenderManager;

import com.jme3.renderer.Renderer;

import com.jme3.renderer.ViewPort;

import com.jme3.renderer.queue.RenderQueue;

import com.jme3.scene.Spatial;

import com.jme3.scene.control.AbstractControl;

import com.jme3.scene.control.Control;

import com.jme3.texture.FrameBuffer;

import com.jme3.texture.Image.Format;

import com.jme3.texture.Texture.MagFilter;

import com.jme3.texture.Texture2D;

import com.jme3.ui.Picture;



public class PixelationTest extends SimpleApplication {



public static void main(String[] args) {

PixelationTest app = new PixelationTest ();

app.start();

}



@Override

public void simpleInitApp() {

Spatial s = assetManager.loadModel(“Models/Teapot/Teapot.obj”);

s.setLocalScale(5);



/** A white, directional light source */

DirectionalLight sun = new DirectionalLight();

sun.setDirection((new Vector3f(-0.5f, -0.5f, -0.5f)).normalizeLocal());

sun.setColor(ColorRGBA.White);

rootNode.addLight(sun);



cam.resize(320, 240, true);



s.addControl(new AbstractControl() {



@Override

protected void controlUpdate(float tpf) {

getSpatial().rotate(0, tpf, 0);

}



@Override

protected void controlRender(RenderManager rm, ViewPort vp) {

}



public Control cloneForSpatial(Spatial spatial) {

return null;

}

});

flyCam.setMoveSpeed(50);

rootNode.attachChild(s);

MyProcessor proc = new MyProcessor(1024, 768);

viewPort.addProcessor(proc);

}



@Override

public void simpleUpdate(float tpf) {

}



@Override

public void simpleRender(RenderManager rm) {

//TODO: add render code

}



class MyProcessor implements SceneProcessor {



ViewPort vp;

int renderWidth;

int renderHeight;

Picture fsQuad = new Picture(“fullscreenquad”);

FrameBuffer buffer;

Texture2D sceneTexture;

Camera filterCam = new Camera(1, 1);



public MyProcessor(int renderWidth, int renderHeight) {

this.renderWidth = renderWidth;

this.renderHeight = renderHeight;



}



public void initialize(RenderManager rm, ViewPort vp) {

this.vp = vp;

int width = vp.getCamera().getWidth();

int height = vp.getCamera().getHeight();

//creating the frame buffer

buffer = new FrameBuffer(width, height, 1);

buffer.setDepthBuffer(Format.Depth);

//creating the texture

sceneTexture = new Texture2D(width, height, Format.RGBA8);

//setting the mag filter to nearest (that’s where we get the pixelisation effect)

sceneTexture.setMagFilter(MagFilter.Nearest);

buffer.setColorTexture(sceneTexture);



fsQuad.setMaterial(new Material(assetManager, “Common/MatDefs/Post/Overlay.j3md”));

fsQuad.getMaterial().setTexture(“Texture”, sceneTexture);

fsQuad.getMaterial().setColor(“Color”, ColorRGBA.White);



//set the viewport to render to this framebuffer

vp.setOutputFrameBuffer(buffer);

}



public void reshape(ViewPort vp, int w, int h) {

}



public boolean isInitialized() {

return vp != null;

}



public void preFrame(float tpf) {

}



public void postQueue(RenderQueue rq) {

}



public void postFrame(FrameBuffer out) {



//displayShadowMap(renderManager.getRenderer());

fsQuad.setWidth(renderWidth);

fsQuad.setHeight(renderHeight);

filterCam.resize(renderWidth, renderHeight, true);

fsQuad.setPosition(0, 0);

fsQuad.updateGeometricState();



renderManager.setCamera(filterCam, true);

//render to screen setting framebuffer to null

renderManager.getRenderer().setFrameBuffer(null);

renderManager.getRenderer().clearBuffers(true, true, true);

renderManager.renderGeometry(fsQuad);





renderer.setFrameBuffer(buffer);

renderManager.setCamera(vp.getCamera(), false);



}



private void displayShadowMap(Renderer r) {

Camera cam = viewPort.getCamera();

renderManager.setCamera(cam, true);

renderManager.getRenderer().setFrameBuffer(null);

int h = cam.getHeight();

fsQuad.setPosition(64 + 128, h / 20f);

fsQuad.setWidth(128);

fsQuad.setHeight(128);

fsQuad.updateGeometricState();

renderManager.renderGeometry(fsQuad);



renderManager.setCamera(cam, false);

renderer.setFrameBuffer(buffer);

}



public void cleanup() {

}

}

}



[/java]



I render the scene at 320x240 and display it at 1024x768.



http://i.imgur.com/WsNYb.png

1 Like