Slick Forums

Discuss the Slick 2D Library
It is currently Mon May 20, 2013 8:13 am

All times are UTC




Post new topic Reply to topic  [ 6 posts ] 
Author Message
PostPosted: Fri Jan 27, 2012 8:10 am 
Offline

Joined: Mon Jan 23, 2012 9:40 pm
Posts: 12
Hey guys I am managing a background of several images and am trying to write an image on top of the background image. The problem arises when i do a setRBA on the background image trying to reset the pixels to those of the new image im trying to draw ontop of it. Basically, i edit a square of the image and then the image randomly contains a ton of separate vertical lines and i have no clue how they ended up that way... Any ideas guys? i have no clue what is causing this error, nor do i know how to fix it... =/

The important note worthy code is this:
Code:
ImageBuffer tempImgData = img;
            //Arrays.fill(tempImgData.getRGBA(), (byte)255);
            for(int h=0; h<tempHeight; h++){
                for(int w=0; w<tempWidth; w++){
                    tempC = imgToAdd.getColor(w, h);
                    if(imgAddX+w <1000 && imgAddY+h <1000)
                        tempImgData.setRGBA(imgAddX+w, imgAddY+h, (byte)tempC.getRedByte(), (byte)tempC.getGreenByte(),
                                (byte)tempC.getBlue(), (byte)tempC.getAlpha());
                }
            }
            img = tempImgData;
            lvlImages[centerBlockX][centerBlockY] = img.getImage();

But that leaves me with the several random lines as you can see here:
Image

Have any of you guys ever noticed this problem? And do you have any suggestions that may fix this? Thanks in advance for your help.


Top
 Profile  
 
PostPosted: Fri Jan 27, 2012 10:08 pm 
Offline

Joined: Mon Jan 23, 2012 9:40 pm
Posts: 12
Ok guys, so i think i have pinpointed where the error is coming from. Basically i did a bunch of random testing to try to find work-arounds for this problem and ended up with a session where i did NOT edit the rgba values of any of the pixels in my ImageBuffer img variable but continued to call the img.getImage() method. just from calling that method alone and displaying the image returned by it i got the random lines. I dont know why this method is returning an image with random lines, but even without editing the data it returned a bad image different from the previous call to getImage()

For my purposes i do need the ability to edit the pixel data withing the imageBuffer (especially since i have no clue how to do it any other way and still be able to get an image that i can save to a .png)

now that the source of the error has been narrowed down, any ideas/suggestions as to how i could possibly fix it? or could this possibly be a bug in Slick or even LWJGL?


Top
 Profile  
 
PostPosted: Fri Jan 27, 2012 11:55 pm 
Offline

Joined: Mon Jan 23, 2012 9:40 pm
Posts: 12
My error is still there, and i still have no idea where it is coming from... Just to troll with me, the test code in ImageBufferTest.java is working perfectly, even when i try messing around with setRGBA inside the key listener method...

Im at the point where im positive there is a problem with my code but i cannot possibly find it =/ Here is the full class im using (notice a lot of the setRGBA parts of the code in the AddImage() function is commented out and still the problem persists with the img.getImage() call)
Code:
import StickGame.LevelEditor.LevelData.LevelDataManager;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.nio.ByteBuffer;
import java.util.Arrays;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.newdawn.slick.Color;
import org.lwjgl.util.Rectangle;
import org.newdawn.slick.*;
import org.newdawn.slick.imageout.ImageIOWriter;
import org.newdawn.slick.opengl.ImageDataFactory;
import org.newdawn.slick.opengl.LoadableImageData;
import org.newdawn.slick.opengl.TextureLoader;

/**
*
* @author Devin LR
*/
public class BGImageManager{
   
    private ImageBuffer img = null;
    private ImageBuffer oldImg = null;
    int numImagesWide, numImagesHigh;
    static final int imgBlockSize = 1000;
    boolean needToLoadLvl = false;
    boolean lvlLoaded = false;
   
    static int iLocX, iLocY;
   
    Image drawImg;
    Image greyOverlay;
    static Rectangle overlayRect = null;
    private Image[][] lvlImages;
    static int centerBlockX, centerBlockY;
    int drawnCenterBlockX, drawnCenterBlockY;
    boolean setCenterBlock = true;
   
    BGImageManager(int width, int height, boolean loadLevel){
        numImagesWide = (width+(imgBlockSize/2))/imgBlockSize;
        numImagesHigh = (height+(imgBlockSize/2))/imgBlockSize;
        needToLoadLvl = loadLevel;
        lvlImages = new Image[numImagesWide][numImagesHigh];
        iLocX = 0;
        iLocY = 0;
        if(loadLevel)
            LoadImagesInit();
        else
            BlankImageInit();
    }
   
    private void BlankImageInit(){
       
        img = new ImageBuffer(imgBlockSize, imgBlockSize);
        Arrays.fill(img.getRGBA(), (byte)255);
       
        ImageIOWriter writer = new ImageIOWriter();
       
        int i = 0;
        FileOutputStream fos;
        drawImg = img.getImage();
        for(int w=0; w<numImagesWide; w++){
            for(int h=0; h<numImagesHigh; h++){
                try{
                    fos = new FileOutputStream(EditorStarter.PATH + "/" + LevelDataManager.levelName + "/" + LevelDataManager.levelName + i + ".png");
                    System.out.println(i);
                    writer.saveImage(drawImg, "PNG", fos, true);
                    fos.flush();
                }catch(Exception e){
                    e.printStackTrace();
                    System.exit(1);
                }
                lvlImages[w][h] = drawImg;
                i++;
            }
        }
       
        ImageBuffer tempImgData = new ImageBuffer(imgBlockSize, imgBlockSize);
        Arrays.fill(tempImgData.getRGBA(), (byte)123);
       
        greyOverlay = tempImgData.getImage();
    }
   
    void LoadImagesInit(){
        if(img == null){
            img = new ImageBuffer(imgBlockSize, imgBlockSize);
        }
       
        centerBlockX = 0; centerBlockY = 0;
        drawnCenterBlockX = 0; drawnCenterBlockY = 0;
        String tempPath = EditorStarter.PATH
                    + "/" + LevelDataManager.levelName + "/" + LevelDataManager.levelName + 0 + ".png";
        System.out.println(tempPath);
        LoadableImageData tempImg = ImageDataFactory.getImageDataFor(tempPath);
        try{
            FileInputStream fin = new FileInputStream(tempPath);

            ByteBuffer tempBuffer = tempImg.loadImage(fin);
            int i=0;
            for(int x=0; x<imgBlockSize; x++){
                for(int y=0; y<imgBlockSize; y++){
                img.setRGBA(x, y, tempBuffer.getInt(i), tempBuffer.getInt(i+1),
                        tempBuffer.getInt(i+2), tempBuffer.getInt(i+3));
                i+=4;
                }
            }
           
            int j=0;
            for(int w=0; w<numImagesWide; w++){
                for(int h=0; h<numImagesHigh; h++){
                    tempPath = EditorStarter.PATH
                        + "/" + LevelDataManager.levelName + "/" + LevelDataManager.levelName + j + ".png";
                    fin = new FileInputStream(tempPath);
                    lvlImages[w][h] = new Image(TextureLoader.getTexture("PNG", fin));
                    j++;
                }
            }
           
            ImageBuffer tempImgData = new ImageBuffer(imgBlockSize, imgBlockSize);
            Arrays.fill(tempImgData.getRGBA(), (byte)200);
            greyOverlay = tempImgData.getImage();
           
        }catch(Exception e){
            e.printStackTrace();
        }
    }
   
    void Draw(GameContainer gc, Graphics g){
        int tempx, tempy;
            for(int w=0; w<numImagesWide; w++){
                for(int h=0; h<numImagesHigh; h++){
                    tempx = iLocX+w*1000;
                    tempy = iLocY+h*1000;
                    g.drawImage(lvlImages[w][h], tempx, tempy);//lvlImages[w][h].draw(tempx, tempy);
                    if(setCenterBlock){
                        overlayRect = new Rectangle(tempx, tempy, imgBlockSize, imgBlockSize);
                        if(overlayRect.contains(gc.getWidth()/2, gc.getHeight()/2)){
                            centerBlockX = w; centerBlockY = h;
                            setCenterBlock = false;
                        }
                    }
                }
            }
            setCenterBlock = true;

            g.drawImage(greyOverlay, iLocX+centerBlockX*1000, iLocY+centerBlockY*1000);//greyOverlay.draw(iLocX+centerBlockX*1000, iLocY+centerBlockY*1000);
    }
   
    void AddImage(Image imgToAdd, int imgx, int imgy){
        if(overlayRect.contains(imgx, imgy)){
            oldImg = img;
            int imgAddX = imgx - iLocX%imgBlockSize;
            int imgAddY = imgy - iLocY%imgBlockSize;
            int tempHeight = imgToAdd.getHeight();
            int tempWidth = imgToAdd.getWidth();
            LevelDataManager.AddBrick(imgx, imgy);
                                /*ByteBuffer bb = img.getImageBufferData();
                                try {
                                    Graphics g = img.getImage().getGraphics();
                                    g.drawImage(imgToAdd, imgAddX, imgAddY);
                                } catch (SlickException ex) {
                                    Logger.getLogger(BGImageManager.class.getName()).log(Level.SEVERE, null, ex);
                                }
                                /*ImageBuffer tempImgData = img;
                                int i=0;
                                for(int x=0; x<imgBlockSize; x++){
                                    for(int y=0; y<imgBlockSize; y++){
                                        tempImgData.setRGBA(x, y, bb.get(i), bb.get(i+1),
                                                    bb.get(i+2), bb.get(i+3));
                                    }
                                }
                                img = tempImgData;//*/
                                //Color tempC = Color.blue;
                                //Arrays.fill(img.getRGBA(), (byte)255);
                                /*for(int h=0; h<tempHeight; h++){
                                    for(int w=0; w<tempWidth; w++){
                                        //tempC = imgToAdd.getColor(w, h);
                                            img.setRGBA((imgAddX+w)<imgBlockSize ? (imgAddX+w):imgBlockSize,
                                                    (imgAddY+h)<imgBlockSize ? (imgAddY+h):imgBlockSize, tempC.getRed(),
                                                    tempC.getGreen(), tempC.getBlue(), tempC.getAlpha());
                                    }
                                }//*/
            lvlImages[centerBlockX][centerBlockY] = img.getImage();
           
                                /*try{
                                    FileOutputStream fos = new FileOutputStream(EditorStarter.PATH + "/" + LevelDataManager.levelName
                                            + "/" + LevelDataManager.levelName + centerBlockX*centerBlockY + ".png");
                                    ImageIOWriter writer = new ImageIOWriter();
                                    writer.saveImage(lvlImages[centerBlockX][centerBlockY], "PNG", fos, true);
                                    fos.flush();
                                }catch(Exception e){
                                    e.printStackTrace();
                                    System.exit(1);
                                }//*/
        }else
            System.out.println("Cannot add an image onto the non-center background block...");
       
    }
   
    void Update(int locx, int locy){
        iLocX = locx;
        iLocY = locy;
       
        if(drawnCenterBlockX != centerBlockX || drawnCenterBlockY != centerBlockY){
            drawnCenterBlockX = centerBlockX;
            drawnCenterBlockY = centerBlockY;
            String tempPath = EditorStarter.PATH
                    + "/" + LevelDataManager.levelName + "/" + LevelDataManager.levelName + drawnCenterBlockX*drawnCenterBlockY + ".png";
            LoadableImageData tempImg = ImageDataFactory.getImageDataFor(tempPath);
            try{
                FileInputStream fin = new FileInputStream(tempPath);

                ByteBuffer tempBuffer = tempImg.loadImage(fin);
                int i=0;
                for(int x=0; x<imgBlockSize; x++){
                    for(int y=0; y<imgBlockSize; y++){
                    img.setRGBA(x, y, tempBuffer.getInt(i), tempBuffer.getInt(i+1),
                            tempBuffer.getInt(i+2), tempBuffer.getInt(i+3));
                    i+=4;
                    }
                }
            }catch(Exception e){
                e.printStackTrace();
            }
        }
    }
}


Also, as a comparison to working code that is doing similar things, here is the ImageBufferTest.java file that i messed with trying to reproduce my problem...
Code:
import java.util.Arrays;
import org.newdawn.slick.AppGameContainer;
import org.newdawn.slick.BasicGame;
import org.newdawn.slick.GameContainer;
import org.newdawn.slick.Graphics;
import org.newdawn.slick.Image;
import org.newdawn.slick.ImageBuffer;
import org.newdawn.slick.Input;
import org.newdawn.slick.SlickException;

/**
* A test for image buffer maniupulation rendering
*
* @author kevin
*/
public class ImageBufferTest extends BasicGame {
   /** The image we're currently displaying */
   private Image image;
        ImageBuffer buffer;
        int colorAdd = 10;
   
   /**
    * Create a new image buffer rendering test
    */
   public ImageBufferTest() {
      super("Image Buffer Test");
   }
   
   /**
    * @see org.newdawn.slick.BasicGame#init(org.newdawn.slick.GameContainer)
    */
   public void init(GameContainer container) throws SlickException {
      buffer = new ImageBuffer(1000,1000);
      Arrays.fill(buffer.getRGBA(), (byte)255);
      image = buffer.getImage();
   }

   /**
    * @see org.newdawn.slick.BasicGame#render(org.newdawn.slick.GameContainer, org.newdawn.slick.Graphics)
    */
   public void render(GameContainer container, Graphics g) {
      image.draw(50,50);
   }

   /**
    * @see org.newdawn.slick.BasicGame#update(org.newdawn.slick.GameContainer, int)
    */
   public void update(GameContainer container, int delta) {
   }

   /**
    * @see org.newdawn.slick.BasicGame#keyPressed(int, char)
    */
   public void keyPressed(int key, char c) {
      if (key == Input.KEY_ESCAPE) {
                    System.out.println("escape pressed");
         System.exit(0);
      }else if(true){
                    System.out.println("space pressed");
                    for (int x=100;x<800;x++) {
         for (int y=50;y<350;y++) {
                                buffer.setRGBA(x, y, x+colorAdd,y+colorAdd,0+colorAdd,255);
         }
                    }
                    image = buffer.getImage();
                    colorAdd += 10;
                }
   }

   /**
    * Entry point to our test
    *
    * @param argv The arguments to pass into the test
    */
   public static void main(String[] argv) {
      try {
         AppGameContainer container = new AppGameContainer(new ImageBufferTest());
         container.setDisplayMode(800,600,false);
         container.start();
      } catch (SlickException e) {
         e.printStackTrace();
      }
   }
}


Any possible suggestions you guys can give me would be greatly appreciated! But remember that i dont just need to be able to display the image nicely when i am finished adding the image, but i must also be able to save the image to a .png file (which means that with my current knowledge i cannot use the image.getGraphics to do any of this, but if you know of a way to save an image file by using the getGraphics method PLEASE let me know =])


Top
 Profile  
 
PostPosted: Sat Jan 28, 2012 12:44 am 
Offline

Joined: Mon Jan 23, 2012 9:40 pm
Posts: 12
OK GUYS I SOLVED THE PROBLEM MYSELF!!! sadly i still have no clue why this was causing the problem, but when i was loading the pixel data into the ImageBuffer using this method:
Code:
String tempPath = EditorStarter.PATH
                    + "/" + LevelDataManager.levelName + "/" + LevelDataManager.levelName + 0 + ".png";
        System.out.println(tempPath);
        LoadableImageData tempImg = ImageDataFactory.getImageDataFor(tempPath);
        try{
            FileInputStream fin = new FileInputStream(tempPath);

            ByteBuffer tempBuffer = tempImg.loadImage(fin);
            int i=0;
            for(int x=0; x<imgBlockSize; x++){
                for(int y=0; y<imgBlockSize; y++){
                img.setRGBA(x, y, tempBuffer.getInt(i), tempBuffer.getInt(i+1),
                        tempBuffer.getInt(i+2), tempBuffer.getInt(i+3));
                i+=4;
                }
            }
(rest not needed to be shown)


it was giving the error of the random lines when ever i accessed the image via the imageBuffer.getImage() function... but after changing the method for initializing the imagebuffer's data using this method:
Code:
Color tempC;
            for(int x=0; x<imgBlockSize; x++){
                for(int y=0; y<imgBlockSize; y++){
                    tempC = lvlImages[centerBlockX][centerBlockY].getColor(x, y);
                    img.setRGBA(x, y, tempC.getRed(), tempC.getGreen(),
                            tempC.getBlue(), tempC.getAlpha());
                }
            }

where the lvlImages array has already been initialized with valid images created with the new Image(Path) constructor, and then it works PERFECTLY!!! i hope my trouble is helpful to someone else so that they do not make this same fatal mistake =]


Top
 Profile  
 
PostPosted: Sat Jan 28, 2012 8:43 am 
Offline
Slick Zombie

Joined: Sat Jan 27, 2007 7:10 pm
Posts: 1467
Why can't you use render-to-texture (image graphics) instead of copying each pixel individually?


Top
 Profile  
 
PostPosted: Sun Jan 29, 2012 10:54 pm 
Offline

Joined: Mon Jan 23, 2012 9:40 pm
Posts: 12
I need to be able to save the image which i have not been able to find a way to do using the graphics method, but ive managed to get this method to work and right now my design has no need of the plausible efficiency of the graphics method so i have not tried to find out a solution that uses that method.


Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 6 posts ] 

All times are UTC


Who is online

Users browsing this forum: Google [Bot], Yuri6037 and 3 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
Powered by phpBB® Forum Software © phpBB Group