Staredit Network > Forums > Technology & Computers > Topic: Help With Java
Help With Java
Dec 6 2008, 12:25 am
By: KilaByte  

Dec 6 2008, 12:25 am KilaByte Post #1



I am having a really tough time with loading images in Java.

What I'm going for here is to be able to draw images (loaded from an external file) onto the screen. From what I've read I need to load the image using the toolkit (Java Application not Applet) like this:
Quote
Image image;
image = toolkit.getImage("imagePath.ext");

That works fine for me. The problem is I can't get the image to actually display. I want to be able to control where the image is displayed. I want to be able to set the X and Y coordinates of the image without the Layout Manager messing with it. I am trying to draw it on top of a JPanel. (I have tried using ImageIcon but I just want to draw them to the screen and not have to attach them to a JLabel) A lot of articles I have read point me to this method.

Quote
public void paint(Graphics g) {
g.drawImage(image, 0, 0, null);
}
This will not work for me and it seems that everyone uses this. What I don't understand is in their sample code they don't actually call the paint() method anywhere. So I don't really understand what it is for. I have tried passing the Image object into the paint() method but that doesn't work because it is not a Graphics object. This has been very frustrating to me and if anyone could help that would be great.

Basically I want to load a set of images using the toolkit, pass the image, xcoords, ycoords into a method that will draw the image on the specified x and y coordinates when a KeyEvent takes place.



None.

Dec 6 2008, 1:06 am DT_Battlekruser Post #2



To get an image from the file, you essentially need to do what you did, but the better way to do it is more modern, and uses better types.

Image Loading Code
BufferedImage im = ImageIO.read(file);
// There is also a reformatting option, but I don't remember it offhand and my code is not nearby


There are all sorts of ways to paint images to the screen, including active rendering and double-buffering, but ultimately it comes down to using paint(Graphics g). Hopefully you understand how inheritance works (if you don't, you should really learn OO basics before trying something like this), and paint is called by the native Swing thread when Swing deems it necessary. Your method as described should work fine. In what context do you mean it "does not work"?



None.

Dec 6 2008, 1:28 am KilaByte Post #3



Quote from DT_Battlekruser
To get an image from the file, you essentially need to do what you did, but the better way to do it is more modern, and uses better types.

Image Loading Code
BufferedImage im = ImageIO.read(file);
// There is also a reformatting option, but I don't remember it offhand and my code is not nearby


There are all sorts of ways to paint images to the screen, including active rendering and double-buffering, but ultimately it comes down to using paint(Graphics g). Hopefully you understand how inheritance works (if you don't, you should really learn OO basics before trying something like this), and paint is called by the native Swing thread when Swing deems it necessary. Your method as described should work fine. In what context do you mean it "does not work"?

I have tried BufferedImage numerous times and cannot get it to work. Throws the error BufferedImage cannot be resolved to a type. Despite importing javax.imageio. What can I use to dictate when and where the image will be displayed? My first thought was to pass an image and coordinates to the paint() method. But it seems that the paint method is automatically called by something else (Swing) and accepts a Graphics obj param and not an Image object. I have no problem loading the image I just don't understand what methods to use to decided where and when to display the image.

Also I am almost finished with my first semester of Java programming. I have a basic understanding of inheritance and Object-Oriented programing. I am just trying to learn as much more as I can because I have to take a much more advanced Java class (Server-Side Java) during my next semester.



None.

Dec 6 2008, 5:45 am DT_Battlekruser Post #4



Well, basically, you want something like this. I don't have any simple examples lying around (I use integrated threads and my self-authored class library because I hate Swing like the plague for timing issues) or a working JRE on this computer, so I can't give a 100% guarantee this works, but you should get the idea.

Code
import javax.swing.JPanel;
import java.awt.image.BufferedImage;
import javax.imageio.ImageIO;
import java.awt.Graphics;
import java.io.File;

class MyPanel extends JPanel {

   private BufferedImage im;

   public MyPanel() {
       try {
           im = ImageIO.read(new File(path));  // Where 'path' is whatever you're testing as an image
       }
       catch (IOException e) {
           e.printStackTrace();
           System.exit(1);
       }
   }

   public void paintComponent(Graphics g) {
       g.drawImage(im, 0, 0, null);
   }
}


Be sure to specifically report any errors you encounter.

Also, are you using an IDE such as Eclipse 3.4? I strongly recommend it, as it will catch spelling and import mistakes, etc.




None.

Dec 6 2008, 6:14 am KilaByte Post #5



A few things.

I had to import java.io.*; for the IOException to work.

Is paint() invoked as soon as the image is loaded? (Does the image draw directly after I load it or do I have to call the paint() method?)
Does Java draw the images over JPanels or would I have to add the image to a JPanel. (The area I am trying to draw the image is over a JPanel.)

I ask this because although I am getting no errors, the image is not appearing.

Also yes I am using Eclipse.



None.

Dec 6 2008, 7:01 am DT_Battlekruser Post #6



The Swing Environment calls paint, which dispatches paintComponent, at certain necessary instances, including but not limited to

-When the Component or its parent(s) is/are made visible
-When the Component or its parent(s) is/are maximized
-When the Component or its parent(s) is/are resized

The panel should have been added to a JFrame that is being displayed. The panel constructor should make the image, so don't worry about that. Resize the frame if you are unsure. Make sure that the size of the panel is greater than (0,0) as well with setSize.




None.

Dec 6 2008, 11:40 pm Matt Burch Post #7



Quote from KilaByte
Also yes I am using Eclipse.
I used to use Eclipse until University started, then I moved to Bluej. A lot more customizable and easier to use. Easier to understand what you are doing.

BTW, did you get the assignment done on time?



None.

Dec 7 2008, 3:43 am KilaByte Post #8



It wasn't actually an assignment. I'm just trying to learn as much as I can before my next semester of Java. And no, I never got it to work haha.



None.

Dec 7 2008, 6:13 am Matt Burch Post #9



Code
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

/**
*      This class demonstrates how to use an ImageIcon
*      and a JLabel to display an image.
*/

public class MyImage extends JFrame
{
   private JPanel imagePanel;      // To hold the label
   private JPanel buttonPanel;     // To hold a button
   private JLabel imageLabel;      // To show an image
   private JButton button;         // To get an image
   
   /**
    *      Constructor
    */
   
   public MyImage()
   {
       // Set the title.
       setTitle("My Image");
       
       // Specify an action for the close button.
       setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
       
       // Create a BorderLayout manager.
       setLayout(new BorderLayout());
       
       // Build the panels.
       buildImagePanel();
       buildButtonPanel();
       
       // Add the panels to the content pane.
       add(imagePanel, BorderLayout.CENTER);
       add(buttonPanel, BorderLayout.SOUTH);
       
       // Pack and display the window.
       pack();
       setVisible(true);
   }
   
   /**
    *      The buildImagePanel method adds a label to a panel.
    */
   
   private void buildImagePanel()
   {
       // Create a panel.
       imagePanel = new JPanel();
       
       // Create a label.
       imageLabel = new JLabel("Click the button to see an image.");
       
       // Add the label to the panel.
       imagePanel.add(imageLabel);
   }
   
   /**
    *      The buildButtonPanel method adds a button
    *      to a panel.
    */
   
   private void buildButtonPanel()
   {
       ImageIcon smileyImage;
       
       // Create a panel.
       buttonPanel = new JPanel();
       
       // Get the smiley face image.
       smileyImage = new ImageIcon("Smiley.gif");
       
       // Create a button.
       button = new JButton("Get Image");
       button.setIcon(smileyImage);
       
       // Register an action listener with the button.
       button.addActionListener(new ButtonListener());
       
       // Add the button to the panel.
       buttonPanel.add(button);
   }
   
   /**
    *      Private inner class that handles the event when
    *      the user clicks the button.
    */
   
   private class ButtonListener implements ActionListener
   {
       public void actionPerformed(ActionEvent e)
       {
           // Read the image file into an ImageIcon object.
           ImageIcon myImage = new ImageIcon("MyImage.jpg");
           
           // Display the image in the label.
           imageLabel.setIcon(myImage);
           
           // Remove the text from the label.
           imageLabel.setText(null);
           
           // Pack the frame again to accomodate the
           // new size of the label.
           pack();
       }
   }
   
   /**
    *      The main method creates an instance of the
    *      MyImage class, which causes it to display
    *      its window.
    */
   
    public static void main(String[] args)
    {
        new MyImage();
    }
}


EDIT:
I guess I should list a reference
Starting Out with Java by Tony Gaddis. Chapter 12

Post has been edited 1 time(s), last time on Dec 7 2008, 6:24 am by Matt Burch.



None.

Dec 7 2008, 6:20 am Matt Burch Post #10



Picture of it working:
http://machost.exofire.net/Files.png



None.

Dec 7 2008, 6:55 am DT_Battlekruser Post #11



It's a nice way to get started, but using Swing like that makes me cringe.



None.

Dec 7 2008, 7:12 am Matt Burch Post #12



You mean with BlueJ, and not the drag and drop objects with Eclipse? I'll use Eclipse more often when I'm done learning all of the basics and start doing big projects. Right now I like my modified version of BlueJ ^^ .



None.

Dec 7 2008, 7:42 am DT_Battlekruser Post #13



No, I mean using Swing to do anything other than component-based applications programming. I don't know what KillaByte plans, but Swing is awful for anything other than what it was intended for.

Oh, and everybody that's a serious coder just writes (unless there is very good reason not to)


listeners
button.addActionListener(new ActionListener() {
   public void actionPerformed(ActionEvent e) {
       // do stuff here
   }
});




None.

Dec 7 2008, 8:39 am cheeze Post #14



Quote from DT_Battlekruser
No, I mean using Swing to do anything other than component-based applications programming. I don't know what KillaByte plans, but Swing is awful for anything other than what it was intended for.

Oh, and everybody that's a serious coder just writes (unless there is very good reason not to)


listeners
button.addActionListener(new ActionListener() {
   public void actionPerformed(ActionEvent e) {
       // do stuff here
   }
});
No, everybody that's a serious coder would ignore you. :lol:



None.

Dec 8 2008, 5:42 am KilaByte Post #15



Quote from cheeze
Quote from DT_Battlekruser
No, I mean using Swing to do anything other than component-based applications programming. I don't know what KillaByte plans, but Swing is awful for anything other than what it was intended for.

Oh, and everybody that's a serious coder just writes (unless there is very good reason not to)


What would you use to display images then? Are you not supposed to use swing to display images?

listeners
button.addActionListener(new ActionListener() {
   public void actionPerformed(ActionEvent e) {
       // do stuff here
   }
});
No, everybody that's a serious coder would ignore you. :lol:

On the subject of ActionListeners, say I have two buttons.

Code
    private static JButton button1 = new JButton("Button One");
    private static JButton button2 = new JButton("Button Two");


How would I do actionlisteners for both of them, assuming each button did something different. My first theory is that:

Code
        button1.addActionListener(new button1Listener());
        button2.addActionListener(new button2Listener());


then...

Code
    private static class button1Listener implements ActionListener
    {
        public void actionPerformed (ActionEvent event)
        {
            System.out.println("You pressed button one");
        }
    }

    private static class button2Listener implements ActionListener
    {
        public void actionPerformed (ActionEvent event)
        {
            System.out.println("You pressed button two");
        }
    }


(These classes would be added onto the same class that the buttons were made in. Thats why I made them private static classes.)

However, this seems hardly efficient. Say you had 200 buttons. Making a new class for each button (again, assuming each button did something different) would seem like a huge task. (Idk why you would have 200 buttons just humor me)

Is there a way to make one action listener class do certain things based on which button is pressed?

Btw, I'm not coding anything serious (Like I could... lol). I'm just messing around with Java to see if I really want to keep going with it.

Also, is there anyway to use the native OS buttons/windows/menu's/pop-ups/ect.ect.
Or are you stuck using the lame Swing ones.


@Matt:

I wanted to draw an image, not using ImageIcon. I can do that easy. I thought there might be a better/faster way to do it. A way to just draw an image to the screen on specified x/ycoords without attaching it to a JLabel.

Post has been edited 1 time(s), last time on Dec 8 2008, 5:49 am by KilaByte.



None.

Dec 8 2008, 6:23 am DT_Battlekruser Post #16



Quote
Is there a way to make one action listener class do certain things based on which button is pressed?

Btw, I'm not coding anything serious (Like I could... lol). I'm just messing around with Java to see if I really want to keep going with it.

There is, but not in any meaningful way. If you have 200 buttons with 200 truly independent actions, one class for all of them would involve a switch statement with a case for each button anyway. 200 actions are 200 actions, unless they can somehow be related with a parameter.

I normally declare my button actions like I showed with an instantiated internal class, but Cheeze seems to disagree. It's less lines of code, but I suppose cheeze would say that it's easier to isolate and edit the button actions if they're in a separate class.

Quote
I thought there might be a better/faster way to do it. A way to just draw an image to the screen on specified x/ycoords without attaching it to a JLabel.

There is. Graphics.drawImage(Image, int, int, ImageObserver) should work fine in general, but I would probably need to see all of your code to isolate the errors. If there is enough interest, I suppose I could make a tutorial on active rendering and timing in a JFrame, based on my favorite Java gaming book, Killer Game Programming In Java.




None.

Dec 8 2008, 6:34 am KilaByte Post #17



Quote

There is, but not in any meaningful way. If you have 200 buttons with 200 truly independent actions, one class for all of them would involve a switch statement with a case for each button anyway. 200 actions are 200 actions, unless they can somehow be related with a parameter.

I normally declare my button actions like I showed with an instantiated internal class, but Cheeze seems to disagree. It's less lines of code, but I suppose cheeze would say that it's easier to isolate and edit the button actions if they're in a separate class.

Yeah internal class, that's what I would do.

Are you saying that cheese creates and entirely new class for each action?
or one class for all actions? (<--- Doesn't seem like a bad idea actually)

I guess if you had 200 buttons having one class to hold all the button actions in would probably be a good idea.

Quote
There is. Graphics.drawImage(Image, int, int, ImageObserver) should work fine in general, but I would probably need to see all of your code to isolate the errors. If there is enough interest, I suppose I could make a tutorial on active rendering and timing in a JFrame, based on my favorite Java gaming book, Killer Game Programming In Java.

Yeah the Graphics.drawImage() would be great if I could actually get it to work.

Question though, does Graphics.drawImage() draw the image over everything (Panels, ImageIcons, other images, ect.). Or does it just matter which order you put them in the frame. Or is there a way to specify how the image treats other components/images?


edit to clarify:
Are you saying that cheese creates and entirely new class for each action? (One entirely new class for each action)
or one class for all actions? (<--- Doesn't seem like a bad idea actually) (One new class with a lot of internal classes)

Post has been edited 1 time(s), last time on Dec 8 2008, 6:47 am by KilaByte.



None.

Dec 8 2008, 7:02 am KilaByte Post #18



Maybe this will help you help me:

Code
package imageTesting;

import javax.swing.JPanel;
import java.awt.image.BufferedImage;
import javax.imageio.ImageIO;
import java.awt.Graphics;
import java.io.File;
import java.io.*;

class ImageTest extends JPanel {

  private BufferedImage im;

  public void ImageLoad() {
      try {
          im = ImageIO.read(new File("mypic.png"));  // Where 'path' is whatever you're testing as an image
      }
      catch (IOException e) {
          e.printStackTrace();
          System.exit(1);
      }
  }

  public void paintComponent(Graphics g) {
      g.drawImage(im, 0, 0, null);
  }
}


First class I have

Code
package imageTesting;

import javax.swing.*;

public class ImageTestMain {
   
    public static void main(String args[])
    {
        JFrame frame = new JFrame("Show the damn image already");
        JPanel MyPanel = new JPanel();
        MyPanel.ImageLoad();
   
        frame.add(MyPanel);
        frame.getContentPane();
        frame.pack();
        frame.setVisible(true);
       
    }

}



Error isL
ImageLoad() is undefined for the type JPanel.

Even though it should work because ImageTest extends JPanel right? So I should be able to use the LoadImage() method with a JPanel object right?

And it doesn't work if I make ImageLoad a class (ImageTest()) instead of a method. Either way it still throws the same error.

EDIT:

Nvm I'm an idiot.

I now realize that I have to make an instance of ImageTest instead of trying to run ImageLoad() from a Panel. Now it all makes sense

Now, How do I get the image without having to also make a JPanel?
How do I just draw it to the screen using Graphics.DrawImage()?

Post has been edited 1 time(s), last time on Dec 8 2008, 7:13 am by KilaByte.



None.

Dec 8 2008, 7:08 am cheeze Post #19



Well, for one, you're not using the new class you've created. And in the extension, you haven't initialized it.

To DTBK: It's an objected oriented language! ._.



None.

Dec 8 2008, 7:14 am KilaByte Post #20



Yeah I know that now.

I figured it out just before you posted xD.

EDIT:

Nvm again. I figured out how to draw image. Thanks for all your help!

Now on to learning Events....

Post has been edited 2 time(s), last time on Dec 8 2008, 7:36 am by KilaByte.



None.

Options
  Back to forum
Please log in to reply to this topic or to report it.
Members in this topic: None.
[09:24 pm]
Moose -- denis
[05:00 pm]
lil-Inferno -- benis
[10:41 am]
v9bettel -- Nice
[01:39 am]
Ultraviolet -- no u elky skeleton guy, I'll use em better
[10:50 pm]
Vrael -- Ultraviolet
Ultraviolet shouted: How about you all send me your minerals instead of washing them into the gambling void? I'm saving up for a new name color and/or glow
hey cut it out I'm getting all the minerals
[10:11 pm]
Ultraviolet -- :P
[10:11 pm]
Ultraviolet -- How about you all send me your minerals instead of washing them into the gambling void? I'm saving up for a new name color and/or glow
[2024-4-17. : 11:50 pm]
O)FaRTy1billion[MM] -- nice, now i have more than enough
[2024-4-17. : 11:49 pm]
O)FaRTy1billion[MM] -- if i don't gamble them away first
[2024-4-17. : 11:49 pm]
O)FaRTy1billion[MM] -- o, due to a donation i now have enough minerals to send you minerals
Please log in to shout.


Members Online: Moose