Double Buffering implementiert, Image weg :-(

Status
Nicht offen für weitere Antworten.

spidermobile

Bekanntes Mitglied
Hallo zusammen,

ich bin gerade dabei, das Tutorial SpaceInvaders zu verstehen und nachzubauen. Das es SWT und Canvas benutzt, habe ich gedacht, ich baue es mal auf JComponent und Double Buffering um.

Das hätte ich wohl besser bleiben lassen. Nun erscheint beim Aufruf leider die Image des Players gar nicht mehr 😳

Was habe ich falsch gemacht?

Danke für einen kleinen Tipp.

Mit Canvas und BufferStrategy (so funktioniert es):

Code:
	public void paintWorld() {
		Graphics2D g = (Graphics2D)strategy.getDrawGraphics(); 
		g.setColor(getBackground());
		g.fillRect(0, 0, this.getSize().width, this.getSize().height);
		g.setColor(getForeground());
		paint(g);

		playGround.paint(g);
		player.paint(g);
		
		strategy.show();
	}

So funktioniert es leider nicht !

Code:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.awt.image.BufferedImage;
import java.util.ArrayList;

import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JPanel;

import project.Player;
import project.SpriteCache;
import project.Stage;

public class MainCloneInvaders extends JComponent implements Stage, KeyListener  {

	private static final long serialVersionUID = 3258131375281680691L;

	public int posX,posY,vX;
	public BufferedImage buffer;
	public long usedTime;
	
	private Image img;
	private Graphics g;
	
	private SpriteCache spriteCache;
	private ArrayList actors;
	
	private Player player;
	
	public MainCloneInvaders() {
		super();

		spriteCache = new SpriteCache();
		
		JFrame frame = new JFrame("CloneInvaders");
		JPanel panel = (JPanel)frame.getContentPane(); 
		setBounds(0,0,Stage.WIDTH,Stage.HEIGHT);
		panel.setPreferredSize(new Dimension(Stage.WIDTH,Stage.HEIGHT));		
		panel.setLayout(null); 
		panel.setBackground(Color.black);
		panel.add(this);

        frame.setBounds(0,0,Stage.WIDTH,Stage.HEIGHT);
		frame.setVisible(true);
		frame.addWindowListener( new WindowAdapter() {
			public void windowClosing(WindowEvent e) {
				System.exit(0);
			}
			});
		
		 addKeyListener(this);
	}

	public SpriteCache getSpriteCache() {
		return spriteCache;
	}
		
	public Player getPlayer() {
		return player;
	}

	public void keyPressed(KeyEvent e) { 
		player.keyPressed(e); 
	} 
	
	public void keyReleased(KeyEvent e) { 
		player.keyReleased(e);
	}
	
	public void keyTyped(KeyEvent e) {
		
	}

	public void initWorld(){
		
	    player = new Player(this);
	    player.setX(Stage.WIDTH/2);
	    player.setY(Stage.PLAY_HEIGHT - 2*player.getHeight());
	}
	
	public void updateWorld(){

		player.act();

	}
	
	public void paintWorld() {
		img = createImage(this.getSize().width, this.getSize().height);
		g = img.getGraphics();
		g.setColor(getBackground());
		g.fillRect(0, 0, this.getSize().width, this.getSize().height);
	        paint(g);
		
		player.paint(g);
	}
	
	public void game() {
		initWorld();
		updateWorld();
		paintWorld();
	}
	
	public static void main(String[] args) {

		MainCloneInvaders inv = new MainCloneInvaders();
		inv.game();

	}

}

Code:
package project;

import java.awt.event.KeyEvent;

public class Player extends Actor {
	protected static final int PLAYER_SPEED = 4;
	private boolean up,down,left,right;
	
	protected int vx;
	protected int vy;
	      
	public Player(Stage stage) {
		super(stage);
		setSpriteName("spaceShipPlayer.gif");
	}
	      
	public void act() {
		super.act();
	    x+=vx;
	    y+=vy;
	    if (x < 0 || x > Stage.WIDTH)
			vx = -vx;
			if (y < 0 || y > Stage.HEIGHT)
				vy = -vy;
			}
	    
		public int getVx() { return vx; }
	    public void setVx(int i) {vx = i; }
	    public int getVy() { return vy; }
	    public void setVy(int i) {vy = i; }
		
		protected void updateSpeed() {
			vx=0;vy=0;
			if (down) vy = PLAYER_SPEED;
			if (up) vy = -PLAYER_SPEED;
			if (left) vx = -PLAYER_SPEED;
			if (right) vx = PLAYER_SPEED;
		}
			      
		public void keyReleased(KeyEvent e) {
			switch (e.getKeyCode()) {
			case KeyEvent.VK_DOWN : down = false;break;
			case KeyEvent.VK_UP : up = false; break;
			case KeyEvent.VK_LEFT : left = false; break; 
			case KeyEvent.VK_RIGHT : right = false;break;
			}
			updateSpeed();
		}
			      
		public void keyPressed(KeyEvent e) {
			switch (e.getKeyCode()) {
			case KeyEvent.VK_UP : up = true; break;
			case KeyEvent.VK_LEFT : left = true; break;
			case KeyEvent.VK_RIGHT : right = true; break;
			case KeyEvent.VK_DOWN : down = true;break;
			}
			updateSpeed();
		}
	 }

Code:
package project;

import java.awt.Graphics;
import java.awt.image.BufferedImage;

public class Actor {
	protected int x,y;
	protected int width, height;
	protected String spriteName;
	protected Stage stage;
	protected SpriteCache spriteCache;
	
	public Actor(Stage stage) {
		this.stage = stage;
		spriteCache = stage.getSpriteCache();
	}
    
	public void paint(Graphics g){
		g.drawImage( spriteCache.getSprite(spriteName), x,y, stage );
	}
      
	public int getX()  { return x; }
	public void setX(int i) { x = i; }
  
	public int getY() { return y; }
	public void setY(int i) { y = i; }
    
    public String getSpriteName() { return spriteName; }

	public void setSpriteName(String string) { 
      spriteName = string;
      BufferedImage image = spriteCache.getSprite(spriteName);
      height = image.getHeight();
      width = image.getWidth();
    }     
      
    public int getHeight() { return height; }
    public int getWidth() { return width; }
    public void setHeight(int i) {height = i; }
    public void setWidth(int i) { width = i;  }
   
    public void act() { }
}
[/code]
 
In der Klasse MainCloneInvaders zeichest du zwar alles schön in 'img' aber musst du nicht die paint der Klasse MainCloneInvaders überschreiben und dort 'img' zeichnen? So hast du's ja bisher nur aufs Bild gezeichnet aber noch nicht auf die Komponente.
 
ja, irgendwie kommt mir das auch spanisch vor. Ich gebe zu, mit dem überschreiben von paint hab ich es noch nicht so.
Im ersten Beispiel wird das überschreiben wohl mit:

Code:
Graphics2D g = (Graphics2D)strategy.getDrawGraphics();

aufgerufen. Aber was muss ich bei meinem Ansatz noch hinzufügen?
 
Überschreibt mal paint oder paintComponent und zeichne dort das Bild und ich weiß nicht wie das in Swing läuft aber ich würde nicht von JComponent erben sondern von JLabel.
Und notfalls gib mal noch die Stage, die SpriteCache und was man sonst noch benötigt (Bilder und so) dann hau ich das mal in mein Eclipse.
 
Danke für das Angebot, aber ich denke die Mühe ist es nicht wert, da es ja mit der BufferStrategy und Canvas funktioniert. Dann lass ich es eben so.
Ist ja nur zum Lernen gedacht.

Trotzdem vielen Dank!!
 
Hm, nagut. Aber wenn du's so läßt lernst du erst recht nix. Und wieso nur lernen ?
 
Bin eigentlich kein Programmierer, hab nur mit vielen von diesen (lieben) Kollegen zu tun :wink: , und ich lasse mir halt nicht gerne ein x für ein u vormachen.
Deshalb lerne ich jetzt mal ein wenig Java. Ist dann auch leichter, mal im Code der Entwickler rumzuschnüffeln und ein paar gute Tipps zu geben :lol:
 
Status
Nicht offen für weitere Antworten.

Neue Themen


Zurück
Oben