Boa Tarde, pessoal to fazendo uma classe que deve carregar uma imagen porém tá ocorrendo erro, quando tenta carregar a imagen.
No método BufferedImage, na seguinte linha url = getClass().getClassLoader().getResource(image);
O objeto url não está recebendo as informação da imagen e assim ficando nulo, e ocasionando erro.
o diretorio da imagen está correto, fiz uma pesquisada e verifiquei que tem que colocar o arquivo de resource no classpath, porém não sei o que é esse é arquivo de resource, e aonde que eu devo setar no classpath, nas variaveis de ambiente do windows, ou no java build path?
alguém poderia me tirar essas duvidas por gentileza?
public class Invaders extends Canvas {
public BufferedImage bicho = null;
public static final int width = 800;
public static final int height = 600;
Invaders() {
JFrame janela = new JFrame("invaders");
setBounds(0, 0, width, height);
JPanel panel = (JPanel) janela.getContentPane();
panel.setPreferredSize(new Dimension(width, height));
panel.setLayout(null);
panel.add(this);
janela.setBounds(0, 0, width, height);
janela.setVisible(true);
janela.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
});
}
public BufferedImage loadImage(String image) {
URL url = null;
try {
//String caminho = getClass().getName().replace('.','/') + ".res";
url = getClass().getClassLoader().getResource(image);
return ImageIO.read(url);
} catch (Exception e) {
System.out.println("não foi possivel carregar a imagem");
System.out.println("O erro foi: " + image + " de " + url);
System.out.println(e);
System.exit(0);
return null;
}
}
public void paint(Graphics g) {
BufferedImage bicho = loadImage("res/bicho.jpg");
g.drawImage(bicho, 40, 40, this);
}
public static void main(String[] args) {
Invaders teste = new Invaders();
}
}
Você está comentendo um atentado contra a performance: está carregando a mesma imagem cada vez que seu Canvas é pintado. Carregue a imagem apenas uma vez no construtor e depois use a mesma imagem. Outra coisa: a forma como você vai carregar a imagem depende da sua hierarquia de diretórios no projeto. E quanto ao BufferedImage, não me parece necessário. Acho que ImageIcon basta. Veja algumas modificações:
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.net.URL;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JPanel;
/*
* Creio que estender JPanel direto é mais simples que estender Canvas e
* adicioná-la em um JFrame
*/
public class Invaders extends JPanel {
/*
* Como sua classe estende Canvas, que por sua vez estende Component, que
* implementa Serializable, é recomendado ter uma serialVersionUID na sua
* classe.
*/
private static final long serialVersionUID = 1L;
private Image bicho = null;
private JFrame janela = null;
/*
* A convenção é usar maiúsculas separadas por underscore (_) para nomear
* variáveis estáticas e finais. Ex.: TEMPO_DA_RODADA, VK_ENTER,
* QUANTIDADE_DE_BOTOES...
*/
private static final int WIDTH = 800; // a convenção é usar maiúsculas
private static final int HEIGHT = 600; // a convenção é usar maiúsculas
/*
* Defina seu construtor como público, a não ser que realmente não queira
* assim
*/
public Invaders() {
super(true);
this.setPreferredSize(new Dimension(Invaders.WIDTH, Invaders.HEIGHT));
/*
* Carrega a imagem apenas uma vez no construtor Imagens JPG, em geral,
* são pesadas. Prefira GIF ou ainda PNG
*/
this.bicho = this.loadImage("/images/icon.png");
/*
* É uma pessíma prática definir o leiaute de um Container qualquer como
* null. É preferível fazer assim:
*/
this.janela = new JFrame("Invaders");
this.janela.setContentPane(this);
this.janela.pack();
this.janela.setLocationRelativeTo(null);
this.janela.setVisible(true);
this.janela.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public static void main(final String[] args) {
new Invaders();
}
public Image loadImage(final String image) {
URL url = null;
try {
url = this.getClass().getResource(image);
return new ImageIcon(url).getImage();
} catch (final Exception e) {
System.out.println("não foi possivel carregar a imagem");
System.out.println("O erro foi: " + image + " de " + url);
System.out.println(e);
this.janela.dispose();
return null;
}
}
@Override
public void paint(final Graphics g) {
g.drawImage(this.bicho, 40, 40, this);
}
}
Só mais uma coisa: isso me parece algo relacionado a jogos. Estou certo?
obrigado pela ajuda , marcobiscaro2112 sim é relacionado a jogos, to tentando fazer um invanders.
Agora foi mais só consigo abrir a imagen se eu colocar ela dentro da pasta src. Porém queria definia um diretorio só para as imagens do jogo. Fiz uma classe de teste jogando a Image numa instância do BufferedImage e ele carrega.
Mais se eu usar a classe url eu não consigo, obter a url das imagens.
import java.awt.*;
import java.io.*;
import java.awt.image.*;
import java.awt.event.*;
import javax.swing.*;
import javax.imageio.*;
public class Estudos extends JFrame{
private BufferedImage imagem;
public Estudos(){
super("Estudos Java");
Container c = getContentPane();
c.setLayout(new FlowLayout());
JButton btn = new JButton("Carregar Imagem");
btn.addActionListener(
new ActionListener(){
public void actionPerformed(ActionEvent e){
imagem = null;
try{
imagem = ImageIO.read( new File("res/bicho.jpg"));
}
catch(IOException exc){
JOptionPane.showMessageDialog(null,
"Erro ao carregar a imagem: " +
exc.getMessage());
}
if(imagem != null){
desenhar();
}
}
}
);
c.add(btn);
setSize(400, 300);
setVisible(true);
}
public void desenhar(){
// desenha a imagem no JFrame
Graphics g = getGraphics();
g.drawImage(imagem, 0, 0, this);
}
public static void main(String args[]){
Estudos app = new Estudos();
app.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
Legal, um Invaders… já fiz um há pouco tempo atrás. Bons estudos pra você! Quanto ao diretório, pode fazer do jeito que estava: crie uma pasta images DENTRO de src e use o comando do meu post acima. Pode deixar dentro de src, porque quando você exportar seu projeto, a hierarquia muda um pouco. Por exemplo, no Eclipse, se tivermos:
certo marcobiscaro2112, obrigado pela ajuda, era assim mesmo que eu estava fazendo para carregar as imagens, só que não ia. Agora descubrir o meu problema, eu uso o eclipse, e não tinha criado a pasta pelo mesmo, ai excluir a pasta no eclipse e criei ela de novo no eclise e não é que foi!! pior que o eclipse listava as pasta com a imagen no packge explore.
bah, que coisa de loco!
vlw
talvez esteja acontecendo com vc o mesmo que aconteceu comigo um tempo atrás.
Eu estava usando várias imagens na minha interface, e tinha hora que nao eram carregadas. Eu descobri que toda vez que eu editava a imagem em outro editor com o eclipse aberto, eu precisava dar um refresh na pasta resource(onde estao as imgens) pelo eclipse pra ele enxergar as atualizações nas imagens.
Fazendo isso eu nao tive mais nenhum problema de carregamento.