Zeichnen von Linien mit dem Bresenham-Line-Algorithmus
Mein computer graphics Hausaufgaben ist die Implementierung von OpenGL-algorithmen verwenden nur die Fähigkeit zu zeichnen Punkte.
So offensichtlich ich brauche, um drawLine()
zu arbeiten, bevor ich zeichnen kann, sonst nichts. drawLine()
hat zu tun mit ganzen zahlen nur. Keine floating point.
Dies ist, was ich gelehrt wurde. Grundsätzlich können Zeilen aufgeteilt werden in 4 verschiedene Kategorien, positive steilen, positiv, flach, negativ steilen und negativen flachen. Dies ist das Bild, das ich ziehen soll:
- und dies ist das Bild, mein Programm ist Zeichnung:
Die Farben sind für uns getan. Wir sind Eckpunkte gegeben und wir müssen Sie nutzen Bresenham-Line-Algorithmus zum zeichnen der Linien auf der Grundlage der start-und end-Punkte.
Dies ist, was ich habe, so weit:
int dx = end.x - start.x;
int dy = end.y - start.y;
//initialize varibales
int d;
int dL;
int dU;
if (dy > 0){
if (dy > dx){
//+steep
d = dy - 2*dx;
dL = -2*dx;
dU = 2*dy - 2*dx;
for (int x = start.x, y = start.y; y <= end.y; y++){
Vertex v(x,y);
drawPoint(v);
if (d >= 1){
d += dL;
}else{
x++;
d += dU;
}
}
} else {
//+shallow
d = 2*dy - dx;
dL = 2*dy;
dU = 2*dy - 2*dx;
for (int x = start.x, y = start.y; x <= end.x; x++) {
Vertex v(x,y);
drawPoint(v);
//if choosing L, next y will stay the same, we only need
//to update d by dL
if (d <= 0) {
d += dL;
//otherwise choose U, y moves up 1
} else {
y++;
d += dU;
}
}
}
} else {
if (-dy > dx){
cout << "-steep\n";
//-steep
d = dy - 2*dx;
//south
dL = 2*dx;
//southeast
dU = 2*dy - 2*dx;
for (int x = start.x, y = start.y; y >= end.y; --y){
Vertex v(x,y);
drawPoint(v);
//if choosing L, next x will stay the same, we only need
//to update d
if (d >= 1){
d -= dL;
} else {
x++;
d -= dU;
}
}
} else {
cout << "-shallow\n";
//-shallow
d = 2*dy - dx;
dL = 2*dy;
dU = 2*dy - 2*dx;
for (int x = start.x, y = start.y; x <= end.x; x++){
Vertex v(x,y);
drawPoint(v);
if (d >= 0){
d += dL;
} else {
--y;
d -= dU;
}
}
}
}
Ich weiß, dass meine Fehler dich etwas albern, aber ehrlich, ich kann nicht herausfinden, was ich falsch mache. Warum sind einige Linien falsch gezeichnet wie oben gezeigt?
- was nicht funktioniert?
- Wenn man sich die zwei Bilder in dem Absatz oben mein code, der "2. quadrant" und die "4. quadrant" sind nicht die Zeichnung rechts. Ich habe diese in Anführungszeichen, weil der Punkt (0,0) in der linken unteren Ecke des Bildes. Im Grunde, die ersten else-Anweisung, die den code enthält, der nicht ordnungsgemäß funktioniert, -flach und steil.
- führen Sie den code auf 2 einfache Beispiele, die eine, die funktioniert, und man gar nicht. Sagen (0,0), (5, 5) und (0,5), (5,0), trace durch beide und sehen, wurden Sie auseinander. Dies wird eine viel bessere übung, als jemand, der auf SO es für Sie tun.
- Ich Tat dies, und ich kann immer noch nicht scheinen, um herauszufinden, wie das problem zu lösen. Was passiert, ist die if-Anweisung, die in all der Schleifen, if - (d >= 0), ist nicht ein-so wie es soll. Für die Linie von (0,5) zu (5,0), es sollte immer subtrahieren y jedes mal, so dass es eine Linie genau bei 45 Grad aber es funktioniert nicht.
Du musst angemeldet sein, um einen Kommentar abzugeben.
Finden Sie den kompletten code in C++ eine Linie ziehen mit Bresenham-Algorithmus an http://www.etechplanet.com/codesnippets/computer-graphics-draw-a-line-using-bresenham-algorithm.aspx:
Falls sich jemand wunderte, was das problem war, ich weiß noch nicht, was es war. Was ich am Ende tun war das neu ausgearbeitete mein code, so dass die flach und steiler verwendet den gleichen Algorithmus wie +flach und +steil, beziehungsweise. Nach Einstellung der x -, y-Koordinaten (negieren der x-oder y-Koordinate), wenn ich ging um zu zeichnen Sie ich negiert meine ursprüngliche negation, so dass es dargestellt in der richtigen Stelle.
Implementiert habe ich den originalen Bresenham-Algorithmus in C++ und versucht zu optimieren, so viel wie ich konnte (vor allem in Bezug auf das entfernen der, WENN aus der inneren Schleife).
Zieht es in einen linearen Puffer anstelle von einer Oberfläche, und für diese Sache, diese Umsetzung war fast so schnell wie EFLA (Extrem Schnell-Line-Algorithmus) (vielleicht 5% langsamer).
Des EFLA-Implementierung, die ich verwende, ist: