# gerade für schussbahn berechnen



## RoliMG (14. Feb 2008)

hallo!
ich versuche zur zeit ein tower defence spiel in java zu programmieren.
da sich das "projekt" noch relativ am anfang der programmierung befindet, versuche ich die grundlegenden funktionen, wie das automatische zielen eines turms, zu implementieren.
das grundgerüst ist genauso aufgebaut, wie Quaxli es in seinem tutorial vorzeigt. nebenbei muss ich ein großes lob zur qualität aussprechen!
nun zu meinem problem:
ich verwende die geradengleichung der form
ax+by+c=0 (im post von benni gefunden)
zur berechnung des weges vom turm zum ziel.
jedoch erhalte ich lauter falsche y-werte, wenn ich mir diese mit x ausrechne. der neue punkt befindet sich einfach nicht auf der gerade zwischen turm und ziel.

hier der code:

```
Point p1 = new Point(300, 200);
Point p2 = new Point(150, 50);
//45° zueinander
//Point p1 = new Point(300, 300);
//Point p2 = new Point(150, 150);
double dx = p2.getX() - p1.getY();
double dy = p2.getY() - p1.getY();
double a = dy;
double b = -dx;
// müsste egal sein von welchem punkt ich die koordinaten verwende?!
double c = -(a * p1.getX() + b * p1.getY());

double x = p1.getX();
double y = 0;

if (!checkCollisions(p2))
{
	/*
	 * den y-wert ausrechnen durch umformen der gleichung
	 * a*x + b*y + c = 0
	 * auf
	 * y = -(a*x - c)/b
	 */
	y = -(a * p1.getX() - c) / b;
	x--;
	p1.setLocation(x, y); // die neue position setzen
	System.out.println(p1);
}
```
jedoch:
wenn sich die punkte in einem winkel von 45° zueinander befinden, liegt der neue punkt genau auf der gerade.
habe leider keine ahnung mehr wo der fehler liegen könnte.
bitte um hilfe
mfg
rolimg


----------



## Marco13 (15. Feb 2008)

Was du da mit der Geradengleichung ax+by+c=0 anstellst, ist mir nicht ganz klar (bzw. hab ich jetzt nicht nachvollzogen(!)). Eigentlich sollte ax+b=0 für ein 2D-Spiel reichen....


----------



## manuche (15. Feb 2008)

m*x + b = y bzw a*x + b = y
nicht gleich null schliesslich wollen wir ja das y zu dem x ausrechnen und nicht bei welchem x die gleichung null wird...


----------



## RoliMG (15. Feb 2008)

zugegeben: ich habe diese darstellung nur von diesem post http://www.java-forum.org/de/topic7220_einiges-zur-geometrie-punkte-vektoren-geraden.html, und dort wird sie unter "geraden in 2d" in der form ax+by+c=0 angeführt. werde aber die form ax+by=0 ausprobieren.


----------



## manuche (15. Feb 2008)

Also ich würde immer die Fromel nehmen, die ich auch selbst verstehe ^^ und mx + b = y hat man iwann in der mittelstufe ^^


```
double dx = p2.getX() - p1.getY(); 
double dy = p2.getY() - p1.getY();
```
müsste es nicht

```
double dx = p2.getX() - p1.getX(); 
double dy = p2.getY() - p1.getY();
```
heissen?


----------



## Marco13 (15. Feb 2008)

Aber mal nebenbei: Mit dieser Geradengleichung wirst du spätestens bei (fast) senkrechten Schüssen Probleme bekommen (da wäre die Punkt-Richtungs-Form besser). Aber sowas wie richtige flugbahnen (Parabeln) wird man mit diesem Ansatz grundsätzlich nicht hinbekommen.........


----------



## RoliMG (15. Feb 2008)

manuche hat gesagt.:
			
		

> ```
> double dx = p2.getX() - p1.getY();
> double dy = p2.getY() - p1.getY();
> ```
> ...



da habe ich tatsächlich die variablen vertauscht!
wenn man die form ax+by+c=0 auf y umformt kommt die "normale" geradengleichung y= kx+d zustande.
diese darstellung eignet sich jedoch nicht wenn das ziel sich genau über dem turm befindet, da die gerade dann parallel zur y-achse verläuft.


----------



## RoliMG (15. Feb 2008)

hallo!
habe die optimale lösung für mein problem gefunden: vektoren!
man berechnet den einheitsvektor und subtrahiert diesen vom startpunkt, dabei gibt es keine probleme bezüglich einer zu hohen steigung oder eines parallel zur y-achse verlaufenden vektors.

```
public static void main(String[] args)
{
	/*
	 * koordinaten des punktes auf der gerade bzw. dem vektor
	 */
	double xneu = 0;
	double yneu = 0;

	/*
	 * faktor für den einheitsvektor
	 */
	double i = 0;

	// punkt von dem der ball aus richtung ziel fliegt(ortsvektor)
	double OA[] = { 20, 25 };
	// ziel des balls
	double OB[] = { 15, 5 };

	// vektor von A nach B (spitze - schaft)
	double vab[] = { OB[0] - OA[0], OB[1] - OA[1] };
	// betrag des vektors ab (satz von pythagoras)
	double btr = Math.sqrt(Math.pow(vab[0], 2) + Math.pow(vab[1], 2));
	// einheitsvektor von ab (vektor/betrag
	double evab[] = { vab[0] / btr, vab[1] / btr };

	/*
	 * solange der ball nicht kollidiert oder der faktor kleiner als der
	 * betrag ist, berechnen den neuen punkt auf dem vektor ab
	 */
	while (!checkCollisions(OB[0], OB[1]) && (i <= btr))
	{
		xneu = OA[0] + evab[0] * i;
		yneu = OA[1] + evab[1] * i;
		i++;
	}
}

private static boolean checkCollisions(double x, double y)
{
	return false;
}
```


----------



## Marco13 (15. Feb 2008)

Also... Punkt-Richtungs-Form :wink: Was ganu deine CheckCollisions-Methode macht, weiß ich zwar nicht, aber du kannst vermutlich auch die Schleife weglassen, und _direkt_ den Auftreff-Punkt berechnen......


----------



## RoliMG (16. Feb 2008)

tja ...
habe ich leider nicht sofort verstanden, dass du dich dabei auf vektoren beziehst...
die checkCollisions methode ist in dem beispiel nur eine dummy methode.
dieses kleine programm soll eine hilfe für forumbesucher sein, die das selbe problem haben.


----------

