# Problem beim Anzeigen von Bildern



## Kingkook (25. Jan 2011)

Hallo liebe Com,

ich probiere mich gerade ein wenig an dem Tutorial für Spiele Programmierung in Java von Quaxli.
Dabei wende ich aber seine Hilfen nur an und schreibe dementsprechend nicht genau an dem Spiel, welches er beschreibt.Momentan hänge ich jedoch daran,das ich versuche den Hintergrund mit vielen kleinen Bildplatten zu füllen.Dafür habe ich eine neue Klasse erstellt:

```
import java.awt.Graphics;
import java.awt.geom.Rectangle2D;
import java.awt.image.BufferedImage;

public abstract class Graphicelements  extends Rectangle2D.Double implements Drawable
    {

        protected double dx,dy;

        GamePanel parent;
        BufferedImage pictures;

        public Graphicelements (BufferedImage i,double x, double y, GamePanel p,boolean openField)
            {
                pictures = i;
                this.x = x;
                this.y = y;
                this.width = pictures.getWidth();
                this.height = pictures.getHeight();
                parent = p;
            }

        public void doLogic(long delta)
            {

            }


	public void drawObjects(Graphics g)
            {

                    g.drawImage(pictures, (int) x, (int) y, null);
            }

        private void computeAnimation()
            {

            }

        public double getDx()
            {
                return dx;
            }

        public double getDy()
            {
                return dy;
            }

        public void setDx(double d)
            {
                dx = d;
            }

        public void setDy(double d)
            {
                dy = d;
            }

    }
```
Ausserdem gibt es eine Klasse Background 

```
import java.awt.image.BufferedImage;



public class Background extends Graphicelements
    {
         public Background(BufferedImage i, double x, double y, GamePanel p,boolean openField)
            {
                super(i, x, y, p,openField);
            }
    }
```
An und für sich bekomme ich keine Fehlermeldungen oder ähnliches.mein Problem ist nur,das ich beim Ausführen keine Bilder angezeigt bekomme.Irgendetwas muss er aber laden, da je nachdem an welcher Position(Ebene) ich etwas zeichnen lasse nichts zu sehen ist, oder wenigstens die Spielfigur.
Hier noch das Game Panel:

```
import java.awt.*;
import java.awt.event.*;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.net.URL;
import java.util.Random;
import java.util.Vector;
import javax.imageio.ImageIO;
import javax.swing.*;

public class GamePanel extends JPanel implements KeyListener,Runnable
    {
        private static final long serialVersionUID = 1L;

        boolean gameRunning = true;

        long delta =0;
        long last  =0;
        long fps   =0;

        boolean up    =false;
        boolean down  =false;
        boolean left  =false;
        boolean right =false;

        int speed = 50;

        Creeps creep;
        BackgroundAnimated bgAnim;
        Background bgNorm;
        Vector<GraphicelementsAnimated> groundAnimated;
        Vector<Sprite> actors;
        Vector<Graphicelements> ground;
        BufferedImage background;
        BufferedImage path;

        Random randStart = new Random();
        public int wayPoints=(randStart.nextInt(11)+1);
        Random randPoints = new Random();
        int oldWayKoord = 0;




        public GamePanel(int w,int h)
            {
                this.setPreferredSize(new Dimension(w,h));
                JFrame frame = new JFrame("TowerDefense");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.setLocation(100,100);
                frame.addKeyListener(this);
                frame.add(this);
                frame.pack();
                frame.setVisible(true);
                doInitialisations();
            }
        public static void main(String[] args)
            {
                new GamePanel(800,600);
            }
        public void doInitialisations()
            {
                last = System.nanoTime();
                actors = new Vector<Sprite>();
                ground = new Vector<Graphicelements>();
                groundAnimated = new Vector<GraphicelementsAnimated>();
                BufferedImage[] heli = loadPics("pics/heli.gif", 4);
                BufferedImage [] bgAnimated = loadPics("pics/grasanimated.gif",3);
                BufferedImage bgNormal = loadPic("pics/heli.gif");
                path = loadPic("pics/path.gif");
                creep = new Creeps(heli,400,300,100,this);
                bgAnim = new BackgroundAnimated(bgAnimated,400,300,100,this);
                bgNorm = new Background(bgNormal,200,100,this,false);
                for (int i = 0;i < 16; i++)
                {
                    for (int l = 0;l < 12; l++)
                    {
                        createBackground(i,l);
                    }
                }
                createPath(oldWayKoord,wayPoints);
                do
                    {
                        int drawWay = (randPoints.nextInt(2)+1);

                        if (drawWay == 1)
                            {
                                createPath(oldWayKoord,wayPoints-1);
                                wayPoints =wayPoints-1;
                            }
                        if (drawWay == 2)
                            {
                                 createPath(oldWayKoord+1,wayPoints);
                                 oldWayKoord = oldWayKoord + 1;
                            }
                        if (drawWay == 3)
                            {
                                createPath(oldWayKoord,wayPoints+1);
                                wayPoints =wayPoints+1;
                            }
                    }while(((oldWayKoord*50)>=0) && ((oldWayKoord*50)<=750) && ((wayPoints*50)>=0) && ((wayPoints*50)<=550));
                actors.add(creep);
                groundAnimated.add(bgAnim);




                Thread t = new Thread(this);
                t.start();
            }

    public void keyTyped(KeyEvent e)
        {
            throw new UnsupportedOperationException("Not supported yet.");
        }
    private void createBackground(int xx,int yy)
        {
            int x = xx;
            int y = yy;

//            Background backgroundGras = new Background(bgNorm,(x*50),(y*50),this,false);

            ground.add(/*backgroundGras*/bgNorm);
	}
    private void createPath(int xx,int yy)
        {
            int x = xx;
            int y = yy;

            Path backgroundPath = new Path(path,(x*50),(y*50),this,true);

            ground.add(backgroundPath);
	}
    public void keyPressed(KeyEvent e)
        {
            if(e.getKeyCode()==KeyEvent.VK_UP)
                {
                        up = true;
                }

            if(e.getKeyCode()==KeyEvent.VK_DOWN)
                {
                        down = true;
                }

            if(e.getKeyCode()==KeyEvent.VK_LEFT)
                {
                        left = true;
                }

            if(e.getKeyCode()==KeyEvent.VK_RIGHT)
                {
                        right = true;
                }
        }

    public void keyReleased(KeyEvent e)
        {
            if(e.getKeyCode()==KeyEvent.VK_UP)
                {
                        up = false;
                }

            if(e.getKeyCode()==KeyEvent.VK_DOWN)
                {
                        down = false;
                }

            if(e.getKeyCode()==KeyEvent.VK_LEFT)
                {
                        left = false;
                }

            if(e.getKeyCode()==KeyEvent.VK_RIGHT)
                {
                        right = false;
                }
        }

    public void run()
        {
            while (gameRunning)
                {
                    computeDelta();
                    checkKeys();
                    doLogic();
                    moveObjects();
                    repaint();

                    try
                    {
                        Thread.sleep(10);
                    }
                    catch(InterruptedException ie)
                    {

                    }

                }

        }

    @Override
    public void paintComponent(Graphics g)
        {
            super.paintComponent(g);


            g.setColor(Color.red);
            g.drawString("FPS: "+Long.toString(fps), 30, 20);

            if (ground !=null)
                {
                    for (Drawable draw:ground)
                        {
                            g = path.getGraphics();
                            draw.drawObjects(g);
                        }
                }

            if (groundAnimated !=null)
                {
                    for (Drawable draw2:groundAnimated)
                        {
                            draw2.drawObjects(g);
                        }
                }
            if (actors !=null)
                {
                    for (Drawable draw3:actors)
                        {
                            draw3.drawObjects(g);
                        }
                }


        }

    public void computeDelta()
        {
            delta = System.nanoTime() - last;
            last = System.nanoTime();
            fps = ((long) 1e9) / delta;
        }

    private BufferedImage[] loadPics(String path, int pics)
        {
            BufferedImage[] anim = new BufferedImage[pics];
            BufferedImage source = null;

            URL pic_url = getClass().getClassLoader().getResource(path);

            try {
                    source = ImageIO.read(pic_url);
            } catch (IOException e) {}

            for(int x=0;x<pics;x++){
                    anim[x] = source.getSubimage(x*source.getWidth()/pics, 0,
                                    source.getWidth()/pics, source.getHeight());
            }

            return anim;
        }

    private BufferedImage loadPic(String path)
        {
            BufferedImage animm = new BufferedImage(50,50,BufferedImage.TYPE_INT_ARGB);
            BufferedImage source = null;

            URL pic_url = getClass().getClassLoader().getResource(path);


            try
            {
                    source = ImageIO.read(pic_url);
//                    animm.setRGB(source.getWidth(), source.getWidth(),BufferedImage.TYPE_INT_ARGB);
            }
            catch (IOException e)
            {
                System.out.println("Fail by loadPic");
            }
            return animm;
        }
    private void doLogic()
        {
            for(Moveable mov:actors)
                {
                        mov.doLogic(delta);
                }
        }
    private void moveObjects()
        {
            for(Moveable mov:actors)
                {
                        mov.move(delta);
                }
        }
    private void checkKeys()
        {

            if(up)
                {
                    creep.setDy(-speed);
                }

            if(down)
                {
                    creep.setDy(speed);
                }

            if(right)
                {
                    creep.setDx(speed);
                }

            if(left)
                {
                    creep.setDx(-speed);
                }

            if(!up&&!down)
                {
                    creep.setDy(0);
                }

            if(!left&&!right)
                {
                    creep.setDx(0);
                }
        }
}
```

Vielen Dank schonmal für eure Hilfe und Liebe Grüße Kooki


----------



## Quaxli (25. Jan 2011)

Kingkook hat gesagt.:


> .... schreibe dementsprechend nicht genau an dem Spiel, welches er beschreibt.....



Wieso das denn? Du kaufst Dir doch auch keinen vanGogh und malst noch dran rum? 

So mal im Ernst: Vielleicht solltest Du aber doch erst mal das Tutorial durcharbeiten, bevor Du dran rum schraubst? Da sind schon ein paar Schnitzer drin. Ich weiß gar nicht ob ich alles gefunden habe. Ich habe viel Code rausgeschmissen, um überhaupt mal durchzublicken.  

Üblicherweise postet man bei sowas ein KSKB (kleines selbständig kompilierbares Beispiel). Wer soll sich den durch den ganze Code wühlen? ;( 

1. Dein grundsätzliches Problem liegt hier:


```
private BufferedImage loadPic(String path) {
		BufferedImage animm = new BufferedImage(50, 50, BufferedImage.TYPE_INT_ARGB);
		BufferedImage source = null;

		URL pic_url = getClass().getClassLoader().getResource(path);

		try {
			source = ImageIO.read(pic_url);
		} catch (IOException e) {
			System.out.println("Fail by loadPic");
		}
		return animm;
	}
```

Du lädst das Bild nach source und gibst das leere animm zurück. Dementsprechend bekommst Du auch nichts angezeigt.

Ansonsten noch ein paar Dinge, die mir so aufgefallen sind:

Diesen Konstruktor von GraphicElements (zumindest heißt das Ding bei mir so): 

```
public Graphicelements (BufferedImage i,double x, double y, GamePanel p,boolean openField)
            {
                pictures = i;
                this.x = x;
                this.y = y;
                this.width = pictures.getWidth();
                this.height = pictures.getHeight();
                parent = p;
            }
```

kann man erheblich kürzer schreiben:


```
public GraphicElements(BufferedImage i, double x, double y, GamePanel p, boolean openField) {
		super(x,y,i.getWidth(),i.getHeight());
		pictures = i;
		parent = p;
	}
```


Und der folgende Code ist auch nur drin, um hilfswillige Forenmitglieder zu nerven? ;(


```
public void keyTyped(KeyEvent e)
        {
            throw new UnsupportedOperationException("Not supported yet.");
        }
```


Und dann habe ich noch das int paintComponent gefunden:


```
....
            g.setColor(Color.red);
            g.drawString("FPS: "+Long.toString(fps), 30, 20);
 
            if (ground !=null)
                {
                    for (Drawable draw:ground)
                        {
                            g = path.getGraphics();
                            draw.drawObjects(g);
                        }
                }
           ....
```

Warum überschreibst Du das GraphicsObject mit dem eines BufferedImage und malst da alles weitere rein? Mal davon abgesehen, daß das auch noch innerhalb einer Schleife gemacht wird, macht das nicht wirklich Sinn - zumindest von meiner Warte aus...


So, soweit das was mich beim Durchsehen ins Auge gebissen hat. Gibt noch ein paar Kleinigkeiten, aber biege erst mal das gerade.


----------



## Kingkook (25. Jan 2011)

Quaxli hat gesagt.:


> Wieso das denn? Du kaufst Dir doch auch keinen vanGogh und malst noch dran rum?
> 
> Stimmt wohl...
> 
> ...



Aber alles in allem habe ich mein erstes Problem schonmal gelöst und danke dir ganz herzlich für die Hilfe...woe geht hier im Forum eigentlich der offizielle Bedanken Button oder eher wo ist der??^^


----------



## Kingkook (26. Jan 2011)

Also da komme ich einfach mal mit der nächsten frage und hoffe das ist ok das gleiche Thema zu benutzen.

ich schmeiße all meine Grafikelemente ja so wie du in einen Vector rein.
mit der vector.get(int) Methode kann man sich ja den Inhalt des Vecors an der Position von int angeben lassen.Bei mir liegen da also viele Bilder ( z.B. package.Class[x=0.0,y=100.0,w=50.0,h=50.0] ) kann mir jemand sagen wie ich auf die einzelnen Werte also z.B. x und y zugreifen kann?


----------



## ARadauer (26. Jan 2011)

auf deine Klasse casten

((Graphicelements)vector.get(5)).getDx();

bzw besser:
1. ArrayList verwenden, ist neuer
2. Generics verwenden, ist sauberer


```
ArrayList<Graphicelements> list = new ArrayList<Graphicelements>();
...
list.get(3).getDx();
```


----------



## Kingkook (28. Jan 2011)

So ein neuer tag ein neues Problem :lol: ...
Dabei geht es sich um folgendes:

Die Spielfigur soll sich nur auf Wegen (Vector path ) bewegen dürfen nicht aber auf dem gras (Vector ground ).Dabei wollte ich jetzt mithilfeeiner Kollisionsabfrage dafür sorgen, das er auf Gras ersteinmal autimatisch ( wie bei einer Wand ) nicht mehr weiterkommt.Leider ist es so, dass er zwar auf dem Gras stehen bleibt, aber nur wenn das komplette Element über dem Gras ist.Ich hab also irgendwie das gefühl das meine Kollisionsabfrage nur auf den Pixel 0,0 (x,y) reagiert und die eigentliche Größe der Grafik völlig ignoriert.

Hier die Kollisionsabfrage:

```
@Override
        public boolean colliedWith(Graphicelements g)
            {
                if (this.intersects(g))
                {
                    System.out.println("Kollision in Creep");
                    return true;
                }
                return false;
            }
```


```
private void moveObjects()
        {
            for(Moveable mov:actors)
                {
                        for (int i = 0; i < path.size(); i++)
                        {

                            if (actors.elementAt(0).colliedWith(path.elementAt(i)) == true)
                            {

                                mov.move(delta);

                            }
                            if (actors.elementAt(0).colliedWith(path.elementAt(i)) != true )
                            {


                            }
                        }
//                        mov.move(delta);
                        
                }
        }
```

Hoffe ich konnte mein Problem irgendwie etwas verständlich machen...

Danke mal wieder im vorraus und LG von Kooki


----------

