ClassCastException with NiftyImage

Hello guys,
I am trying to change an image in my nifty gui.
To do so I use the following code (img is a BufferedImage):

Image jmeImg = new AWTLoader().load(img, false);
    NiftyImage niftyImg = new NiftyImage(mainApp.getNifty().getRenderEngine(), new RenderImageJme(new Texture2D(jmeImg)));
    mainApp.getNifty().getScreen("map").findElementByName("landscape").getRenderer(ImageRenderer.class).setImage(niftyImg);

I begin creating an Image with the AWTLoader, which seems to work fine.
Then I create the NiftyImage from this image (also working).
The exception occurs in the last line when I try to set the new image:

java.lang.ClassCastException: com.jme3.niftygui.RenderImageJme cannot be cast to de.lessvoid.nifty.batch.BatchRenderImage
at de.lessvoid.nifty.batch.BatchRenderDevice.renderImage(BatchRenderDevice.java:297)
at de.lessvoid.nifty.render.ScalingRenderDevice.renderImage(ScalingRenderDevice.java:103)
at de.lessvoid.nifty.render.image.renderstrategy.ResizeStrategy.render(ResizeStrategy.java:24)
at de.lessvoid.nifty.render.image.CompoundImageMode.render(CompoundImageMode.java:41)
at de.lessvoid.nifty.render.NiftyImage.render(NiftyImage.java:54)
at de.lessvoid.nifty.render.NiftyRenderEngineImpl.renderImage(NiftyRenderEngineImpl.java:242)
at de.lessvoid.nifty.elements.render.ImageRenderer.render(ImageRenderer.java:30)
at de.lessvoid.nifty.elements.Element.renderElement(Element.java:735)
at de.lessvoid.nifty.elements.Element.render(Element.java:713)
at de.lessvoid.nifty.elements.Element.renderInternalChildElements(Element.java:752)
at de.lessvoid.nifty.elements.Element.renderChildren(Element.java:745)
at de.lessvoid.nifty.elements.Element.render(Element.java:714)
at de.lessvoid.nifty.screen.Screen.renderLayers(Screen.java:316)
at de.lessvoid.nifty.Nifty.render(Nifty.java:322)
at com.jme3.niftygui.NiftyJmeDisplay.postQueue(NiftyJmeDisplay.java:246)
at com.jme3.renderer.RenderManager.renderViewPort(RenderManager.java:979)
at com.jme3.renderer.RenderManager.render(RenderManager.java:1035)
at com.jme3.app.SimpleApplication.update(SimpleApplication.java:252)
at com.jme3.system.lwjgl.LwjglAbstractDisplay.runLoop(LwjglAbstractDisplay.java:151)
at com.jme3.system.lwjgl.LwjglDisplay.runLoop(LwjglDisplay.java:185)
at com.jme3.system.lwjgl.LwjglAbstractDisplay.run(LwjglAbstractDisplay.java:228)
at java.lang.Thread.run(Thread.java:744)

I used this almost the same way in another project and I can’t find a difference that can cause the problem.
Please help me :wink:

I don’t think you’re supposed to set the image directly on the ImageRenderer?

Unfortunately I can’t remember where I got this from when I used it the first time…
Actually I can’t find another way to use BufferedImages for nifty. :frowning:

I do it this way and it works, probably not the right way, but:

// Convert the new image to a texture, and add a dummy cached entry to the asset manager
AWTLoader loader = new AWTLoader();
Texture tex = new Texture2D(loader.load(newImage, false));
((DesktopAssetManager) assetManager).addToCache(new TextureKey("HUDBackground"), tex);
NiftyImage niftyImage = nifty.createImage("HUDBackground", false);

ImageRenderer renderer = panel.getRenderer(ImageRenderer.class);
renderer.setImage(niftyImage);

Thank you, I will try it that way tomorrow :wink:

I have done it like that but now I get an exception because a loader is missing for a simple name. Just adding “.png” to the name throws an exception because the file “[name].png” was not found…

I think I might be missing something but I don’t know what…

Can’t say. I’m using exactly that and it works. JME 3.0.

I have rewritten it with almost exactly the same code as you have… And it still does not work.
Here is the code:

    BufferedImage bi = mainApp.getMainMap().getMapImage();
    
    AWTLoader loader = new AWTLoader();
    Texture tex = new Texture2D(loader.load(bi, false));
    ((DesktopAssetManager) mainApp.getAssetManager()).addToCache(new TextureKey("HUDBackground"), tex);
    NiftyImage niftyImage = mainApp.getNifty().createImage("HUDBackground", false);

    ImageRenderer renderer = mainApp.getNifty().getScreen("map").findElementByName("landscape").getRenderer(ImageRenderer.class);
    renderer.setImage(niftyImage);

And here is the exception:

java.lang.IllegalStateException: No loader registered for type ""
	at com.jme3.asset.ImplHandler.aquireLoader(ImplHandler.java:198)
	at com.jme3.asset.DesktopAssetManager.loadAsset(DesktopAssetManager.java:271)
	at com.jme3.asset.DesktopAssetManager.loadTexture(DesktopAssetManager.java:346)
	at com.jme3.niftygui.JmeBatchRenderBackend.loadImage(JmeBatchRenderBackend.java:199)
	at de.lessvoid.nifty.batch.BatchRenderDevice.createImage(BatchRenderDevice.java:207)
	at de.lessvoid.nifty.render.NiftyImageManager.addImage(NiftyImageManager.java:127)
	at de.lessvoid.nifty.render.NiftyImageManager.registerImage(NiftyImageManager.java:28)
	at de.lessvoid.nifty.render.NiftyRenderEngineImpl.createImage(NiftyRenderEngineImpl.java:172)
	at de.lessvoid.nifty.Nifty.createImage(Nifty.java:1458)
	at founder.gui.MenuController.updateMap(MenuController.java:74)
	at founder.game.Main.onAction(Main.java:127)
	at com.jme3.input.InputManager.invokeActions(InputManager.java:169)
	at com.jme3.input.InputManager.onKeyEventQueued(InputManager.java:455)
	at com.jme3.input.InputManager.processQueue(InputManager.java:831)
	at com.jme3.input.InputManager.update(InputManager.java:883)
	at com.jme3.app.Application.update(Application.java:604)
	at com.jme3.app.SimpleApplication.update(SimpleApplication.java:231)
	at com.jme3.system.lwjgl.LwjglAbstractDisplay.runLoop(LwjglAbstractDisplay.java:151)
	at com.jme3.system.lwjgl.LwjglDisplay.runLoop(LwjglDisplay.java:185)
	at com.jme3.system.lwjgl.LwjglAbstractDisplay.run(LwjglAbstractDisplay.java:228)
	at java.lang.Thread.run(Thread.java:744)

I have no idea why this happens :frowning:

Maybe it doesn’t find the image from the cache and tries to init a loader for it. But why…? There should be only one instance of AssetManager I think. Well, here is the complete code if it helps:

For everyone reading this: After weeks of despair and tears I have found a solution… I don’t know why this happens but it was the only difference between my older (working) versions and this one:
I removed the parameters for atlas width/height from my NiftyJmeDisplay constructor. Now it works as it should (using the way I originally coded it)…