Ich habe Probleme, das Sichtfeld der Perspektive Kamera in libGDX zu verstehen (oder vielleicht sind meine Berechnungen falsch).libGDX - Perspektive Kamera und Sichtfeld
Ich möchte eine Box (zum Beispiel 800px breit, 480px hoch und 20px tief) zeichnen. Die Box wird zwischen x- und y-Achse platziert (mit anderen Worten: die Breite auf der x-Achse und die Höhe auf der y-Achse). Jetzt möchte ich hinter der Box auf der X-Achse (Kameraposition) stehen und so in eine Richtung schauen, dass ich die Box auf meiner ganz rechten Bildschirmseite sehe. ich einige Skizzen gemacht:
Am letzten Skizze, die Box auf der rechten Seite des Sichtfeldes.
Darüber hinaus muss die Höhe der Box genau in den Bildschirm passen. Mit anderen Worten: die obere Kante der Box muss auf meinem Bildschirm oben sein und die untere Kante der Box muss auf meinem Bildschirm unten sein. Hier ist ein Code und Berechnungen dies zu erreichen:
public class Box implements ApplicationListener {
public PerspectiveCamera camera;
public float SCREEN_WIDTH;
public float SCREEN_HEIGHT;
@Override
public void create() {
SCREEN_WIDTH = Gdx.graphics.getWidth(); // 800px
SCREEN_HEIGHT = Gdx.graphics.getHeight(); // 480px
// Create camera (90°) and set position
camera = new PerspectiveCamera(90f, SCREEN_WIDTH, SCREEN_HEIGHT);
camera.position.set(SCREEN_WIDTH + SCREEN_HEIGHT/2, SCREEN_HEIGHT/2, 0f);
camera.lookAt(0f, SCREEN_HEIGHT/2, 0f);
camera.near = 1;
camera.far = 2 * SCREEN_WIDTH;
camera.update();
}
@Override
public void render() {
Gdx.gl.glClearColor(Color.WHITE.r, Color.WHITE.g, Color.WHITE.b, Color.WHITE.a);
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT | GL20.GL_DEPTH_BUFFER_BIT);
// Build the box - width is screenwidth and height is screenheight - one corner in origin
ModelBuilder modelBuilder = new ModelBuilder();
modelBuilder.begin();
MeshPartBuilder mpb = modelBuilder.part("ID", GL20.GL_TRIANGLES, Usage.Position | Usage.Normal,
new Material(ColorAttribute.createDiffuse(Color.GREEN)));
// bottom left corner of the box should be in (0,0,0)
mpb.box(SCREEN_WIDTH/2, SCREEN_HEIGHT/2, -10f, SCREEN_WIDTH, SCREEN_HEIGHT, 20f);
Model model = modelBuilder.end();
ModelInstance instance = new ModelInstance(model);
// Build some light
Environment environment = new Environment();
environment.set(new ColorAttribute(ColorAttribute.AmbientLight, 0.4f, 0.4f, 0.4f, 1f));
environment.add(new DirectionalLight().set(0.8f, 0.8f, 0.8f, -1f, -0.8f, -0.2f));
// Draw the box
ModelBatch modelBatch = new ModelBatch();
modelBatch.begin(camera);
modelBatch.render(instance, environment);
modelBatch.end();
}
}
die Kastenhöhe in dem Bildschirm zu passen I zurück SCREEN_HEIGHT/2, da x = SCREEN_HEIGHT/2/tan (45 °) = SCREEN_HEIGHT/2 Schritt muss/1 = SCREEN_HEIGHT/2, deshalb habe ich diese Länge der X-Komponente in der Positionseinstellung hinzugefügt.
Der Code stellt Skizze 2 und geben Sie mir, dass die korrekte Screenshot:
Um Skizze 3 zu erreichen, muss ich mein Sichtfeld etwa 45 ° nach links drehen. Aber in diesem Zusammenhang muss ich ein wenig zurücktreten, weil die Seiten des Sehfeldes länger sind als die Mittellinie. Ich habe zwei handgezeichnete Skizzen:
Wo h = SCREEN_HEIGHT. Zuerst muss ich x berechnen. x = h/2/sin (45 °) = h/sqrt (2). Jetzt muss ich eine Länge von x zurücktreten und in eine neue Richtung schauen (45 ° links von der Box). Um den Punkt zu berechnen, an das ich suche, I berechnen die Länge y auf dieser Skizze:
y = sin (45 °) * h/2 = h * sqrt (2)/4. Also ist der Punkt zum Beispiel (SCREEN_WIDTH + (x-y), SCREEN_HEIGHT/2, y). Jetzt wechsle ich die Position und suchen Punkt in meinem Code:
public void create() {
SCREEN_WIDTH = Gdx.graphics.getWidth(); // 800px
SCREEN_HEIGHT = Gdx.graphics.getHeight(); // 480px
// Create camera (90°) and set position
camera = new PerspectiveCamera(90f, SCREEN_WIDTH, SCREEN_HEIGHT);
float x = (float) (SCREEN_HEIGHT/Math.sqrt(2));
float y = (float) (SCREEN_HEIGHT * Math.sqrt(2)/4f);
camera.position.set(SCREEN_WIDTH + x, SCREEN_HEIGHT/2, 0f);
camera.lookAt(SCREEN_WIDTH + x - y, SCREEN_HEIGHT/2, y);
camera.near = 1;
camera.far = 2 * SCREEN_WIDTH;
camera.update();
}
Und ich diesen Bildschirm:
Aber das Feld ist nicht auf dem ganz rechts :(
So, jetzt die Frage: was ist falsch? Ist mein Denken über das Sichtfeld falsch oder meine Berechnungen?
Mit freundlichen Grüßen!