Files |  Tutorials |  Articles |  Links |  Home |  Team |  Forum |  Wiki |  Impressum

Aktuelle Zeit: Do Jul 10, 2025 10:04

Foren-Übersicht » Programmierung » OpenGL
Unbeantwortete Themen | Aktive Themen



Ein neues Thema erstellen Auf das Thema antworten  [ 22 Beiträge ]  Gehe zu Seite 1, 2  Nächste
Autor Nachricht
 Betreff des Beitrags: Selektion im Ortho-Modus anwenden?
BeitragVerfasst: Di Okt 18, 2005 20:51 
Offline
DGL Member
Benutzeravatar

Registriert: Do Feb 24, 2005 22:44
Beiträge: 29
Hallöchen,

ich habe vor, für mein Projekt das Selektionsverfahrne zu verwenden, welches auch hier auf der Seite oder im Wiki als Tutorial beschrieben wird. Dabei wird allerdings von einer 3D-Matrix ausgegangen. Ich habe für mein Projekt eine Orthogonale Matrix, diese richte ich wie folgt ein:

Code:
  1. glOrtho(0, 800, 0, 600, -30000, 15000);


Es gibt in meinem Code auch keine gluPerspective(), wie es dann im Selectionscode verwendet wird.

Bisher sieht dieser Code so aus:

Code:
  1. bool mapinfo_class::selection( int mouse_x, int mouse_y)
  2. {
  3.     unsigned int SelectBuffer[513];
  4.     int Viewport[4];
  5.     int Hits, i;
  6.     unsigned int HitZValue;
  7.     unsigned int Hit;
  8.  
  9.     glGetIntegerv(GL_VIEWPORT, Viewport);
  10.     glSelectBuffer(512, SelectBuffer);
  11.     glRenderMode(GL_SELECT);
  12.     glInitNames();
  13.     glPushName(0);
  14.     glMatrixMode(GL_PROJECTION);
  15.     glPushMatrix();
  16.     glLoadIdentity();
  17.     gluPickMatrix(mouse_x, Viewport[3]-mouse_y, 1.0, 1.0, Viewport);
  18.     gluPerspective(45.0, 800 / 600, 0.1f, 100.0f);
  19.     glLoadIdentity();
  20.     this->draw_objects();                  //hier werden die Objekte gerendert
  21.     glMatrixMode(GL_PROJECTION);
  22.     glPopMatrix();
  23.     Hits = glRenderMode(GL_RENDER);
  24.     cout<<"Treffer: "<<Hits<<endl;   //Ausgabe, wie viele Objekte getroffen wurden
  25.  
  26.     Hit = 4294967295;
  27.     HitZValue = 4294967295;
  28.    
  29.     for (i = 0; i <= Hits -1; i++)
  30.     {
  31.         if (SelectBuffer[(i*4)+1] <= HitZValue)
  32.         {
  33.             Hit = SelectBuffer[(i*4)+3];
  34.             HitZValue = SelectBuffer[(i*4)+1];
  35.         }
  36.     }
  37.  
  38.     if (Hit != -1)
  39.     {
  40.       //Wenn Objekt selektiert wurde
  41.     }
  42.     return false;
  43. }


Das Ergebnis dieser Selektion ist sehr seltsam. Sobald Objekte vorhanden sind wird als Anzahl der Treffer meist die Anzahl der Objekte ausgegeben. Als wenn sich alle Objekte in der 1 x 1 großen Selektion befanden hätten. Dabei kann ich hinklicken wo ich will, die Objekte übereinander legen, das beeinfluss das Ergebnis nicht. Jetzt hatte ich den Verdacht, das es an der Perspektive liegen könnte, die man nach glPickMatrix() anwendet. Da ich ja praktisch keine 3D-Scene habe sondern einen orthogonalen Modus. Daher wollte ich mal nachfragen, was man da denn ändern muss, damit es damit funktioniert?
Ich hoffe hier kann man mir helfen, ich sitz da schon lange dran aber ohne Ansatz ist die Sache recht kompliziert.

mfg.

Sunny


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Okt 18, 2005 21:51 
Offline
Guitar Hero
Benutzeravatar

Registriert: Do Sep 25, 2003 15:56
Beiträge: 7810
Wohnort: Sachsen - ERZ / C
Programmiersprache: Java (, Pascal)
Die Selection rendert wie gesagt die Szene nocheinmal. Allerdings nur den kleinen bereich, und nicht alles. Dabei "merkt" sich OpenGL welche Namen tatsächlich gerendert wurden, und gibt diese als Ergebnis zurück. Da du sicherlich die Objekte auswählen willst, die du siehst, musst du natürlich auch in beiden Rednerdurchläufen die selbe Projektion verwenden. Sonst isses witzlos.

Allerdings ist in 2D Selektion völlig überflüssig. Wesentlich schneller ist man, indem man vom OnMouseDown Ereignis die X,Y Koordinaten nimmt und testet, ob eins der Eigenen objekte getroffen wurde. Das is im Orthomodus ja kein Problem, wenn die Auflösungen des Rendercontexts Pixelgenau ist. (bei glOrtho wurden die Werte der Form übergeben.)

_________________
Blog: kevin-fleischer.de und fbaingermany.com


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Okt 18, 2005 21:56 
Offline
DGL Member
Benutzeravatar

Registriert: Do Feb 24, 2005 22:44
Beiträge: 29
Überflüssig ist es in sofern nicht, da ich 1. die Tiefen berücksichtigen will. Also der Z-Wert der Objekte spielt eine Rolle. Außerdem sind die Objekte leider nicht nur rechteckig sondern durchaus mal wie eine Raute, ein Parallelogramm oder sonstwie verformt. Eine Selektion soll aber nur stattfinden wenn die Maus tatsächlich einen Pixel des Objects berührt. Und da dort eben auch schiefe Kanten möglich sind will ich nicht erst berechnen, ob die Maus nun innerhalb des Objektrandes liegt oder nicht. Bei Rechtecken wär' das in der Tat keine große Sache, aber so...

Was die Selektion speziell nochmal betrifft, wie muss ich denn vorgehen nach dem glPickMatrix()?
Muss ich dann statt gluPerspective einfach glOrtho nehmen und die Matrix wieder so einrichten wie ich sie zum Rendern der Objekte verwende? Das hatte ich nämlich auch schonmal ausprobiert. Leider kommt dabei nichts besonderes raus.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Okt 18, 2005 22:00 
Offline
Guitar Hero
Benutzeravatar

Registriert: Do Sep 25, 2003 15:56
Beiträge: 7810
Wohnort: Sachsen - ERZ / C
Programmiersprache: Java (, Pascal)
Ja...eigentlich eifach die selben einstellungen nehmen. Die Selektion hatte noch paar kleine Tücken, musste mal im Forum suchen.

Was auch noch geht ist folgendes:

Im Mouse Down ereignis merkst du dir die Koordinaten und renderst deine komplette szene ohne Texturen und Beleuchtung. Jedem Objekt wird dabei eine eigene individuell einzigartige Farbe zugeordnet. Dann ließt du den Colorbuffer an der klickposition aus, und kannst anhand der Farbe erkenne, was getroffen wurde.

_________________
Blog: kevin-fleischer.de und fbaingermany.com


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Okt 18, 2005 22:13 
Offline
DGL Member
Benutzeravatar

Registriert: Do Feb 24, 2005 22:44
Beiträge: 29
Das mit der Farbe klingt auch nicht so unkompliziert, vor Allem weil ich dann jedem Objekt eine Farbe geben müsste. Und es kann vorkommen, dass ich bis zu mehrere tausend Objekte gleichzeitig anzeigen muss.

Zitat:
Die Selektion hatte noch paar kleine Tücken, musste mal im Forum suchen.

Öhm, meine Selektion im Codefeld oben? Die ist soweit von der des Tutorials übernommen (mit Anpassungen an eigenen Viewport). Oder ist der Fehler im Tutorial selbst?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Di Okt 18, 2005 22:42 
Offline
Ernährungsberater
Benutzeravatar

Registriert: Sa Jan 01, 2005 17:11
Beiträge: 2068
Programmiersprache: C++
Sunny hat geschrieben:
Öhm, meine Selektion im Codefeld oben? Die ist soweit von der des Tutorials übernommen (mit Anpassungen an eigenen Viewport). Oder ist der Fehler im Tutorial selbst?

Teilweise auch im Tutorial selbst:
Code:
  1.     Hit = 4294967295;
  2.     HitZValue = 4294967295;
  3.    
  4.     for (i = 0; i <= Hits -1; i++)
  5.     {
  6.         if (SelectBuffer[(i*4)+1] <= HitZValue)
  7.         {
  8.             Hit = SelectBuffer[(i*4)+3];
  9.             HitZValue = SelectBuffer[(i*4)+1];
  10.         }
  11.     }
  12.  
  13.     if (Hit != -1)

Wenn du kein Objekt triffst ist Hit immer noch High(Internet).
Hatte bei mir auch mal komische Ergebnisse unter Linux mit dem Quellcode.

Hier ist mein angepasster Code der auf den Tutorials auf sulaco.co.za basiert:
Code:
  1. function glSelection(x,y: Integer) : integer;
  2. var
  3.   Puffer    : Array[0..256] of GLUInt;
  4.   Viewport  : TGLVectori4;
  5.   Treffer,i : Integer;
  6.   Z_Wert    : GLUInt;
  7.   Getroffen : GLUInt;
  8. begin
  9.   glGetIntegerv(GL_VIEWPORT, @viewport);      //Die Sicht speichern
  10.   glSelectBuffer(256, @Puffer);               //Den Puffer zuordnen
  11.  
  12.   glmatrixmode(GL_PROJECTION);                //In den Projektionsmodus
  13.   glRenderMode(GL_SELECT);                    //In den Selectionsmodus schalten
  14.   glLoadIdentity;                             //Und dieselbige wieder zurückzusetzen
  15.  
  16.   gluPickMatrix(x, Viewport[3]-y, 1.0, 1.0, Viewport);
  17.   gluPerspective(60.0, Viewport[2]/Viewport[3], 1, 256);
  18.  
  19.   glMatrixMode(GL_MODELVIEW);
  20.  
  21.   glRender;                                   //Die Szene zeichnen
  22.   Treffer := glRenderMode(GL_RENDER);         //Anzahl der Treffer auslesen
  23.  
  24.   Getroffen := High(GLUInt);                 //Höchsten möglichen Wert annehmen
  25.   Z_Wert := High(GLUInt);                    //Höchsten Z - Wert
  26.   for i := 0 to Treffer-1 do
  27.   if Puffer[(i*4)+1] < Z_Wert then
  28.     begin
  29.     getroffen := Puffer[(i*4)+3];
  30.     Z_Wert := Puffer[(i*4)+1];
  31.     end;
  32.   if getroffen=High(GLUInt) then Result:=-1
  33.   else Result := getroffen;
  34. end;


@Flash:
Könntest du vielleicht den Code anschauen und vergleichen und danach ins Wiki übernehmen?
Ich schau mir dafür nochmal die übertragenen Tutorials an.
In Ordnung?


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 09:32 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Selction: Man kann doch ganz simpel und sauberer als High(GLUInt) die Variable benutzen in der die Anzahl der getroffenen Objekte steht. Wenn dort eine 0 drin steht, dann wurde nichts getroffen. Also in etwa so.

Code:
  1. if Treffer > 0 then begin
  2.   Getroffen := High(GLUInt); //Höchsten möglichen Wert annehmen
  3.   Z_Wert := High(GLUInt); //Höchsten Z - Wert
  4.  
  5.   for i := 0 to Treffer-1 do
  6.     if Puffer[(i*4)+1] < Z_Wert then begin
  7.       getroffen := Puffer[(i*4)+3];
  8.       Z_Wert := Puffer[(i*4)+1];
  9.     end;
  10.   Result := getroffen;
  11. end
  12.   else Result := -1;

Und wusch. Fertig isses. ;-)

Das mit den Farben geht natürlich auch. Ist aber im Endeffekt nichts anderes als die Selektion bis auf den Unterschied, dass man bei einer Selektion auch noch einen Stack hat. Und somit hat man noch ein paar zusätzliche Möglichkeiten (Mehr mögliche Werte). Wobei ich gestehen muss das ich so etwas bisher noch nicht gebraucht habe und auch so ohne weiteres nicht weiß wie man das anstellen sollte. ;-) Aber es ist möglich.

Hat das nen Grund warum dein zNear und zFar so extrem große Werte sind? In 2D liegt ja eh fast alles auf auf Z = 0.


Sunny nichts gegen dich oder jeden anderen. Passt zwar nicht wirklich hier her aber da gibt es was was ich mich immer wieder frage und mir gerade nicht verkneifen kann. Warum stehen eigentlich immer alle Orthoansichten auf dem Kopf? Zu mindest deren Koordinaten? Ist es nicht einfacher die Koordinaten direkt zu übergeben als immer erst einmal Height - YWert zu rechnen? Ich für meinen Teil finde es so wesentlich praktischer. Ich weiß. Es gibt dabei weder falsch noch richtig sondern alles nur eine persönliche Einschätzung. Dem ein oder anderen mag es vielleicht auf dem Kopf besser gefallen aber ich finde es so halt einfach unnötig umständlich. Ich befürchte viele wissen gar nicht, dass es auch anders geht. Vielleicht bin ich auch einfach nur zu faul und suche ständig nach einem einfacheren Weg. :roll:

[edit] Fehler im Quellcode beseitigt.


Zuletzt geändert von Lossy eX am Mi Okt 19, 2005 13:29, insgesamt 1-mal geändert.

Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 12:29 
Offline
DGL Member
Benutzeravatar

Registriert: Do Feb 24, 2005 22:44
Beiträge: 29
Zitat:
Hat das nen Grund warum dein zNear und zFar so extrem große Werte sind? In 2D liegt ja eh fast alles auf auf Z = 0.

Weil ich eine Art 2D-Engine entwickle die mittels Z-Wert sortiert und perspektivisch korrekt sein soll. Sie sortiert Pixelgenau und bietet zusätzlich noch mehrere Layer. Daraus resultieren dann viele Abstufungen und recht große Z-Bereiche. Ich hoffe mal, dass OpenGL damit zurecht kommt. Erste Tests damit liefen schonmal, bisher macht das noch keine Probleme.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 12:49 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Ah. Okay. Ich weiß nicht genau ob es immer 100%tig funktioniert. Der Tiefentest ist bei zNear ja immer am genausten und gegen zFar hin wird er ungenauer. Zu mindest wenn man einen zu geringen zNear auswählt kann es sein, dass man arge Probleme bekommt. Wenn ich dieses komische Verhalten noch richtig in Erinnerung habe. ;-) Ich weiß nicht ob ein negativer Wert da auch solche Phänomene mit sich bringt. Aber anscheinend funktioniert es ja wunderbar. ;-)

Ich verwende speziell für 2D immer ganz gerne den Tiefentest GL_LEQUAL. Dabei werden auch Objekte gezeichnet die auf der selben Position wie andere liegen. So dürfte man dann auch mit wesentlich weniger Ebenen auskommen. Da als Letztes immer noch die Zeichenreihenfolge dafür sorgt, dass die Objekte angezeigt werden. Wobei ich keine Ahnung habe ob das überhaupt in dein Konzept passt. Bin bisher aber immer recht gut damit gefahren.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 12:55 
Offline
Ernährungsberater
Benutzeravatar

Registriert: Sa Jan 01, 2005 17:11
Beiträge: 2068
Programmiersprache: C++
Lossy eX hat geschrieben:
Und wusch. Fertig isses. ;-)

fast, es muss so heissen:
Code:
  1. Getroffen := High(GLUInt); //Höchsten möglichen Wert annehmen
  2. if Treffer> 0 then begin
  3.   Z_Wert := High(GLUInt); //Höchsten Z - Wert


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 13:27 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Stimmt. Jetzt wo du es sagst. :roll:
Habe das oben mal angepasst. ;-)


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 13:59 
Offline
Forenkatze
Benutzeravatar

Registriert: Mi Okt 22, 2003 18:30
Beiträge: 1945
Wohnort: Närnberch
Programmiersprache: Scala, Java, C*
@Lossy: Wegen dem Ortho... Ich hätte es auch lieber, wenn ich die Koordinaten direkt angeben könnte, ohne sie vorher von der Formular-Höhe subtrahieren zu müssen. OpenGL zeigt jedoch im Ortho-Modus eine merkwürdige Eigenschaft: Normalerweise ist der Koordinatenursprung ja unten links. Sobald ich im Ortho-Modus aber Texturen aktiviere, wird das Koordinaten-System plötzlich an der X-Achse gespiegelt und der Ursprung wandert nach oben links. Daher die Rechnerei. Wüsste auch gerne, warum das so ist.

Und AFAIK sind die Texturkoordinaten auch irgendwo gedreht. Ganz merkwürdige Sache.

_________________
"Für kein Tier wird so viel gearbeitet wie für die Katz'."


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 14:35 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Wenn du dann die Koordinaten einfach nur spiegels ist die Erstellungsreihenfolge (Uhrzeigersinn oder dagegen) der Punkte anders und entsprechend siehst du dann die Rückseite deiner Fläche. Was natürlich dann dazu führt, dass deine Textur auf dem Kopf steht. Das musst du dann auch entsprechend anpassen.

Gleiches lässt sich auch auf die Textur übertragen. Die Textures, glBmp und fast alle Handimplementationen laden die Texturen wie sie auf Platte gespeichert sind. Da die aber in die Datei auf dem Kopf abgespeichert sind, werden die auch auf dem Kopf geladen. Bei der glBitmap ist das anders und ich benutze das so wie ich normal auch die GDI benutzen würde und habe damit bisher noch überhaupt keine Probleme gehabt.


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 16:43 
Offline
Forenkatze
Benutzeravatar

Registriert: Mi Okt 22, 2003 18:30
Beiträge: 1945
Wohnort: Närnberch
Programmiersprache: Scala, Java, C*
Aber wieso ändert sich das Koordinatensystem, wenn ich Texturen aktiviere?

_________________
"Für kein Tier wird so viel gearbeitet wie für die Katz'."


Nach oben
 Profil  
Mit Zitat antworten  
 Betreff des Beitrags:
BeitragVerfasst: Mi Okt 19, 2005 18:02 
Offline
DGL Member
Benutzeravatar

Registriert: Do Dez 05, 2002 10:35
Beiträge: 4234
Wohnort: Dortmund
Okay. Das entzieht sich meiner Kenntnis. Bzw kann ich so jetzt nicht beurrteilen. Würde aber mal sagen, dass wir das dann in einem neuen Thread besprechen sollte. Und dann auch mit Bilder und Codeschnippsel.


Nach oben
 Profil  
Mit Zitat antworten  
Beiträge der letzten Zeit anzeigen:  Sortiere nach  
Ein neues Thema erstellen Auf das Thema antworten  [ 22 Beiträge ]  Gehe zu Seite 1, 2  Nächste
Foren-Übersicht » Programmierung » OpenGL


Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 3 Gäste


Du darfst keine neuen Themen in diesem Forum erstellen.
Du darfst keine Antworten zu Themen in diesem Forum erstellen.
Du darfst deine Beiträge in diesem Forum nicht ändern.
Du darfst deine Beiträge in diesem Forum nicht löschen.
Du darfst keine Dateianhänge in diesem Forum erstellen.

Suche nach:
Gehe zu:  
  Powered by phpBB® Forum Software © phpBB Group
Deutsche Übersetzung durch phpBB.de
[ Time : 0.011s | 15 Queries | GZIP : On ]