Dies ist ein Tutorial für die Engine Alpha 4.x. Diese funktioniert anders als die EDU-Version. Du findest eine Übersicht über alle Tutorials hier.

Inhalt

In diesem Tutorial:

  • Reagierst du auf Tastatureingabe des Spielers
  • Reagierst du auf Mausklicks des Spielers

Tastencounter

Der folgende Code implementiert einen einfachen Zähler, der die Anzahl an gedrückten Tasten (vollkommen egal, welche) festhält.

Der Counter im Gange
import ea.Game;
import ea.Scene;
import ea.actor.Text;
import ea.event.KeyListener;

import java.awt.event.KeyEvent;

public class TastenCounter
extends Scene {

    public TastenCounter() {
        this.add(new CounterText());
    }

    public static void main(String[] args) {
        Game.start(500, 200, new TastenCounter());
    }

    private class CounterText
    extends Text
    implements KeyListener {

        private int counter = 0;

        public CounterText() {
            super("You pressed 0 keys.", 2);
            this.setCenter(0,0);
        }

        @Override
        public void onKeyDown(KeyEvent keyEvent) {
            counter++;
            this.setContent("You pressed " + counter + " keys.");
            this.setCenter(0,0);
        }
    }
}

Das Interface KeyListener

Eine Klasse, die auf Tastatur-Input des Nutzers reagiert implementiert das Interface ea.event.KeyListener. Die Engine nutzt das Observer-Entwurfsmuster für alle Events.

Dieses Interface hat denselben Namen wie das Standard-Java Interface java.awt.KeyListener. Achte darauf, dass du die Zeile import ea.event.KeyListener einbindest.

Die Anmeldung des KeyListener-Interfaces hat automatisch stattgefunden, als der CounterText über add(...) angemeldet wurde. Ab dem Zeitpunkt wird die onKeyDown(KeyEvent)-Methode bei jedem Tastendruck aufgerufen. Zusätzlich hat das Interface eine optionale Methode zur Reaktion auf das Loslassen einer Taste. Du findest die Information in der Dokumentation.

Auf bestimmten Tastendruck reagieren: Moving Rectangle

Im folgenden Beispiel reagiert das "Character"-Objekt auf die Tasten W, A, S und D, um sich in diskreten Schritten zu Bewegen.

Das rote Rechteck bewegt sich mit WASD
import ea.Game;
import ea.Scene;
import ea.actor.Rectangle;
import ea.event.KeyListener;

import java.awt.Color;
import java.awt.event.KeyEvent;


public class MovingRectangle
extends Scene {

    public MovingRectangle() {
        this.add(new Character());
    }

    public static void main(String[] args) {
        Game.start(600, 400, new MovingRectangle());
    }

    private class Character
    extends Rectangle
    implements KeyListener {

        public Character() {
            super(2, 2);
            this.setCenter(0,0);
            setColor(Color.RED);
        }

        @Override
        public void onKeyDown(KeyEvent keyEvent) {
            switch (keyEvent.getKeyCode()) {
                case KeyEvent.VK_W:
                    this.moveBy(0, 0.5f);
                    break;
                case KeyEvent.VK_A:
                    this.moveBy(-0.5f, 0);
                    break;
                case KeyEvent.VK_S:
                    this.moveBy(0, -0.5f);
                    break;
                case KeyEvent.VK_D:
                    this.moveBy(0.5f, 0);
                    break;
            }
        }
    }
}

KeyEvent

Alle Informationen über den Tastendruck sind im java.awt.KeyEvent gespeichert. Die Engine nutzt hier dieselbe Schnittstelle wie Standard-Java, nachdem die auch hier gut funktioniert.

Dieses Mal gibt es eine switch/case-Struktur in der onKeyDown-Methode, um abhängig von der Eingabe (W/A/S/D) unterschiedlich zu reagieren:

@Override
public void onKeyDown(KeyEvent keyEvent) {
    switch (keyEvent.getKeyCode()) {
        case KeyEvent.VK_W:
            this.moveBy(0, 0.5f);
            break;
        case KeyEvent.VK_A:
            this.moveBy(-0.5f, 0);
            break;
        case KeyEvent.VK_S:
            this.moveBy(0, -0.5f);
            break;
        case KeyEvent.VK_D:
            this.moveBy(0.5f, 0);
            break;
    }
}


Auf Mausklick reagieren: Kreise malen

Das folgende Beispiel malt bei jedem Knopfdruck einen Kreis.

Das Beispiel in Aktion
import ea.Game;
import ea.Scene;
import ea.Vector;
import ea.actor.Circle;
import ea.event.MouseButton;
import ea.event.MouseClickListener;

public class PaintingCircles
extends Scene
implements MouseClickListener {

    public PaintingCircles() {
        this.addMouseClickListener(this);
    }

    private void paintCircleAt(float mX, float mY, float diameter) {
        Circle circle = new Circle(diameter);
        circle.setCenter(mX, mY);
        this.add(circle);
    }

    public static void main(String[] args) {
        Game.start(600, 400, new PaintingCircles());
    }

    @Override
    public void onMouseDown(Vector position, MouseButton mouseButton) {
        paintCircleAt(position.getX(), position.getY(), 1);
    }
}

MouseClickListener

Das Interface ea.event.MouseClickListener ermöglicht das Reagieren auf Mausklicks des Nutzers. Ebenso ermöglicht es das Reagieren auf Loslassen der Maus. Mehr dazu in der Dokumentation.

Bei einem Mausklick (egal ob linke, rechte, oder sonstige Maustaste) wird ein Kreis an der Position des Klicks erstellt:

@Override
public void onMouseDown(Vector position, MouseButton mouseButton) {
    paintCircleAt(position.getX(), position.getY(), 1);
}

Vector

Statt zwei float-Parametern für die X/Y-Koordinaten des Klicks, nutzt die Engine hier die interne Klasse ea.Vector. Diese ist einfach ein 2D-Vektor und macht den Code übersichtlicher. Die Klasse Vector wird in der Engine durchgehend verwendet und ist essentiell für die Arbeit mit der Engine.

Anregung zum Experimentieren

Ein besseres Kreismalen: Auswählbare Größe und Farbe über ein kleines Menü

Wenn du dich mit einfacher Nutzereingabe noch vertrauter machen möchtest, kannst du unter Anderem folgende Dinge probieren:

  • Ampel Cycle: Baue eine Ampel. Bei jedem Knopfdruck bewegt sie sich eine Ampelphase weiter.
  • Besseres Kreismalen: Nur eine Farbe und eine Kreisgröße ist langweilig! Am oberen Rand des Spielfensters ist ein kleines Menü mit "klickbaren" Rechtecken zur Farbwahl und "klickbaren" Texten zur Wahl des Radius. Wie kannst du dafür sorgen, dass du nicht über das Menü "drübermalst"? Wie kannst du das Menü über Tastendruck steuerbar machen? (Tipp: Die Methode contains(Vector) könnte hilfreich werden)


Das Tutorial ist beendet. Das nächste ist Game Loop . Wenn du Feedback für uns hast, melde dich gerne.