Sprawdzenie czy gracz kliknął na obiekt.

Sprawdzenie czy gracz kliknął na obiekt.
Losiu22
  • Rejestracja:ponad 13 lat
  • Ostatnio:prawie 10 lat
  • Postów:98
0

Witam,
próbuję teraz zrobić grę w OpenGL, w której trzeba będzie znajdywać przedmioty porozrzucane w świecie 3d :) Poruszanie się mam, wyświetlanie, wszystko jest. Niestety za bardzo nie wiem jak odczytać, czy gracz kliknął myszką na przedmiocie który miał znaleźć. Czy ktoś zna jakiś sposób żeby odgadnąć czy gracz kliknął na przedmiot?
Z góry dziękuję za odpowiedzi!

Shalom
  • Rejestracja:około 21 lat
  • Ostatnio:prawie 3 lata
  • Lokalizacja:Space: the final frontier
  • Postów:26433
0

Pobierasz informacje o tym gdzie kliknięto a potem sprawdzasz czy jest tam obiekt ;]


"Nie brookliński most, ale przemienić w jasny, nowy dzień najsmutniejszą noc - to jest dopiero coś!"
KR
tylko w 3d nie ma punktu kliknięcia tylko prosta kliknięcia :P
Losiu22
  • Rejestracja:ponad 13 lat
  • Ostatnio:prawie 10 lat
  • Postów:98
0

Hmmm. Właśnie w tym jest problem :/ Nie wiem jak to zrobić. W grze 2d nie było by najmniejszego problemu, natomiast w grze FPS nie wiem jak to zrobić bo dochodzi jeszcze oś Z.

xeo545x39
Właściwie to Y przeważnie jest głównym pionem.
xeo545x39
  • Rejestracja:ponad 14 lat
  • Ostatnio:ponad 5 lat
  • Lokalizacja:Kosmos
  • Postów:1571
0

Hmm, w 2D to wiadomo, ale w 3D ja bym zrobił promieniem. I sprawdzić czy przecina się z siatką obiektu. W chwili kliknięcia go wypuścić.

Edit:
Ehh pomyślałem trochę o czym innym, to się raczej nie sprawdzi. Hm..


Co kurła debuguj ten kod i streszczaj się klientowi chce się fixa, a jak nie kurła to odpale visuala i ci pomoge a tego byś nie chciał
edytowany 1x, ostatnio: xeo545x39
byku_guzio
  • Rejestracja:prawie 15 lat
  • Ostatnio:około 7 lat
1

Kodu Ci nie podam, bo z opengl bawiłem się parę lat temu, ale osobiście widzę 2 rozwiązania.

  1. Bierzesz rzut sceny na płaszczyznę ekranu i sprawdzasz kolor w współrzędnych kliknięcia - dużą wadą jest to, że każdy obiekt musi mieć inny kolor co się wiąże ze specjalnym wyrenderowaniem klatki na potrzeby testu

  2. Liczysz równanie prostej przechodzącą przez punkt położenia kamery i punkt kliknięcia(tu za z można przyjąć współrzędną Z bliższej płaszczyznę obcinania), sprawdzasz punkty przecięcia tej prostej z obiektami na scenie. Kliknięty obiekt to ten, którego miejsce przecięcia z prostą jest najbliżej płaszczyzny ekranu.

Mam nadzieję, że nie napisałem bzdur ;)


edytowany 1x, ostatnio: byku_guzio
mychal
  • Rejestracja:ponad 15 lat
  • Ostatnio:ponad 8 lat
  • Lokalizacja:Przedmonitorze Górne
1

Ja takie coś realizowałem przez GL_SELECT: http://glprogramming.com/red/chapter13.html z tym że ograniczałem obszar renderowania do tego naokoło klikniętego miejsca.


I fart u die.
Azarien
  • Rejestracja:ponad 21 lat
  • Ostatnio:około 4 godziny
1

przydatne mogą być funkcje gluProject(), gluUnProject()

Losiu22
  • Rejestracja:ponad 13 lat
  • Ostatnio:prawie 10 lat
  • Postów:98
0
byku_guzio napisał(a)

Kodu Ci nie podam, bo z opengl bawiłem się parę lat temu, ale osobiście widzę 2 rozwiązania.

  1. Bierzesz rzut sceny na płaszczyznę ekranu i sprawdzasz kolor w współrzędnych kliknięcia - dużą wadą jest to, że każdy obiekt musi mieć inny kolor co się wiąże ze specjalnym wyrenderowaniem klatki na potrzeby testu

  2. Liczysz równanie prostej przechodzącą przez punkt położenia kamery i punkt kliknięcia(tu za z można przyjąć współrzędną Z bliższej płaszczyznę obcinania), sprawdzasz punkty przecięcia tej prostej z obiektami na scenie. Kliknięty obiekt to ten, którego miejsce przecięcia z prostą jest najbliżej płaszczyzny ekranu.

Mam nadzieję, że nie napisałem bzdur ;)

punkt 1 dało by się zrobić, tylko zajęło by mi to dużo czasu. Obiektów będzie duuużo na jednej mapie i prawdopodobnie będzie problem z pomieszczeniem ich w kolorach RGB ^^
punkt 2 niestety jak dla mnie niewykonalny. Nie wiem jak zrobić.
Jeśli chodzi o GL_SELECT to słyszałem że jest to bardzo nieefektowne i klatkożerne. Być może się mylę.
Co do gluProject to przeraziło mnie to: http://www.opengl.org/wiki/GluProject_and_gluUnProject_code . Dla pewności: gluProject to jedna funkcja pobierająca współrzędne obiektu?

Wibowit
  • Rejestracja:prawie 20 lat
  • Ostatnio:około 19 godzin
0

punkt 1 dało by się zrobić, tylko zajęło by mi to dużo czasu. Obiektów będzie duuużo na jednej mapie i prawdopodobnie będzie problem z pomieszczeniem ich w kolorach RGB ^^

Ale obiekty nieaktywne lub w danym momencie nieinteresujące mogą mieć jeden kolor. Poza tym możesz użyć 32 bitów, a nie 24. Chociaż wiadomo, że im mniej bitów tym szybciej będzie działać renderowanie.


"Programs must be written for people to read, and only incidentally for machines to execute." - Abelson & Sussman, SICP, preface to the first edition
"Ci, co najbardziej pragną planować życie społeczne, gdyby im na to pozwolić, staliby się w najwyższym stopniu niebezpieczni i nietolerancyjni wobec planów życiowych innych ludzi. Często, tchnącego dobrocią i oddanego jakiejś sprawie idealistę, dzieli od fanatyka tylko mały krok."
Demokracja jest fajna, dopóki wygrywa twoja ulubiona partia.
0

pkt 2 jest jak najbardziej wykonalny
sam koniec artykułu: http://warsztat.gd/articles.php?x=view&id=279

satirev
  • Rejestracja:prawie 14 lat
  • Ostatnio:około 4 lata
0

Poszukaj hasełka: "OpenGL + picking"

KR
  • Rejestracja:prawie 16 lat
  • Ostatnio:5 miesięcy
  • Postów:2514
0

możesz jeszcze użyć jakiejś biblioteki w której masz możliwość sprawdzania kolizji, następnie wystrzelić niewidzialny pocisk z miejsca położenia myszy prostopadle do ekranu wgłąb i sprawdzić z czym ten pocisk się zderzył. Aczkolwiek, jeśli znasz położenia wszystkich obiektów to możesz po prostu sprawdzić punkty przecięcia prostej z kulą.

Jak wyznaczyć prostą?
Pobierasz macierz położenia kamery. Wydaje mi się, że jest to macierz jednorodna, nie jestem tylko pewien czy dostaniesz macierz opisującą współrzędne lewego górnego rogu ekranu czy środka ekranu względem globalnego układu współrzędnych.

Macierz jednorodna jest zbudowana tak:
[wx,wy,wz, T; p,s]

i teraz tak:
wx,wy,wz są to wektory 3x1 opisujące kierunki osi układu współrzędnych kamery względem globalnego układu współrzędnych (wersory, ich długości powinny być równe 1):

Kopiuj
    gx
w = gy
    gz

T jest to wektor 3x1 opisujący po prostu położenie układu współrzędnych we współrzędnych globalnych [x;y;z]

p jest to wektor 1x3 związany z perspektywą (nawet nie wiem do końca jak działa), niezbyt Cię powinna interesować, s jest to skalar (1x1) opisujący skalę (prawdopodobnie będzie równy 1)

z macierzy rotacji [wx,wy,wz] możesz wyciągnąć kierunek w który się patrzysz patrząc na monitor i tym samym wystrzelić w odpowiednią stronę niewidzialny pocisk.


░█░█░█░█░█░█░█░█░█░█░█░
edytowany 1x, ostatnio: krwq
Losiu22
  • Rejestracja:ponad 13 lat
  • Ostatnio:prawie 10 lat
  • Postów:98
0
oldman napisał(a)

pkt 2 jest jak najbardziej wykonalny
sam koniec artykułu: http://warsztat.gd/articles.php?x=view&id=279

Przykład tam zamieszczony odnosi się bardziej do DirectX'a, a z nim niestety nie miałem styczności. Mimo wszystko dziękuję za wskazanie mi tego poradnika.
krwq, dzięki z radę, postaram się coś zrobić jak ty mówisz :)

edytowany 1x, ostatnio: Losiu22
0
St4rKiller070 napisał(a)
oldman napisał(a)

pkt 2 jest jak najbardziej wykonalny
sam koniec artykułu: http://warsztat.gd/articles.php?x=view&id=279

Przykład tam zamieszczony odnosi się bardziej do DirectX'a, a z nim niestety nie miałem styczności. Mimo wszystko dziękuję za wskazanie mi tego poradnika.
krwq, dzięki z radę, postaram się coś zrobić jak ty mówisz :)

Nieprawda artykuł dotyczy

  1. działania kamery - czyli jak przejść z macierzy widoku i projekcji, które są także w opengl jak mniemam, chociaż któraś jest tam pod inną nazwą, mylę się? do obiektu jakim jest kamera - a artykuł obejmuje po prostu potrzebne algorytmy na macierzach i to wszystko, a to, że są tam wywołania D3DX*(przykład implementacji na dx) to po prostu funkcje do operacji na macierzach, które z samą funkcjonalnością d3d9 nie mają nic wspólnego.
    Potem masz efekt cząsteczkowy, ale tylko w kontekście współpracy z kamerą, czyli znowu chodzi o same operacje na macierzach - które nie są zależne od api (jedynie po prostu przykład masz w dx).
    Następnie liczenie kolizji brył otaczających (bounding box) z bryłą kamery - znowu wszystko to algorytmy geometryczne...
    I ostatnia rzecz czyli to co cię interesuje - ray casting, czyli test kolizji bryły otaczającej z "promieniem wysokości" "bryły kamery" - znów algorytm na test geometryczny
    ...i teraz gdzie tu direct3d?

Jeszcze dla ułatwienia typy które tam widzisz:
D3DXVECTOR to nic innego jak struct { float x, y, z; }; + parę metod i konstruktory dla ułatwienia. D3DXMATRIX to tak samo w uproszczeniu struct { float [4][4]; }; + metody i konstruktory, oraz widzisz tam parę funkcji D3DXMatrix*, które robią coś z macierzą - np. D3DXMatrixInverse to chyba wiadomo :>
Pisząc własną grę w końcu przyjdzie Ci podłączyć jakąś

  1. biblioteczkę do operacji matematycznych na macierzach, wektorach, itd. - np. D3DX - która jest oddzielnym komponentem od Direct3D
  2. napisać własną libkę do tego - dobra rzecz jeśli zależy Ci na nauce tego
    Nawet nic nie stoi na przeszkodzi (no chyba, że przenośność), aby dołączyć do projektu d3dx9.h i podlinkować d3dx9.lib i sobie tego używać z opengl-em :>
xeo545x39
  • Rejestracja:ponad 14 lat
  • Ostatnio:ponad 5 lat
  • Lokalizacja:Kosmos
  • Postów:1571
0

Jeżeli jeszcze aktualny ten temat to przypadkiem znalazłem coś takiego (dokumentacja XNA):

Demonstrates how to check whether the mouse is positioned over a 3D object by creating a ray starting at the camera's near clipping plane and ending at its far clipping plane. Note
This example applies only to Windows development. The Mouse and MouseState objects are not supported on Xbox 360.

The Complete Sample
The code in this topic shows you the technique. You can download a complete code sample for this topic, including full source code and any additional supporting files required by the sample.

Download Sample.

Detecting Whether a User Clicked a 3D Object
To check whether the mouse is positioned over a 3D object
Get the current state of the mouse by using GetState.

C#

Kopiuj
MouseState mouseState = Mouse.GetState();

Get the current screen coordinates of the mouse from X and Y.

C#

Kopiuj
int mouseX = mouseState.X;
int mouseY = mouseState.Y;

Using Viewport.Unproject, determine points in world space on the near and far clipping planes. For the point on the near plane, pass a source vector with x and y set to the mouse position, and z set to 0.

For the point on the far plane, pass a source vector with x and y set to the mouse position, and z set to 1.

Create a translation matrix for a point that is the origin, (0,0,0).

For both points, pass Unproject the current projection matrix, the view matrix.

C#

Kopiuj
Vector3 nearsource = new Vector3((float)mouseX, (float)mouseY, 0f);
Vector3 farsource = new Vector3((float)mouseX, (float)mouseY, 1f);

Matrix world = Matrix.CreateTranslation(0, 0, 0);

Vector3 nearPoint = GraphicsDevice.Viewport.Unproject(nearsource,
    proj, view, world);

Vector3 farPoint = GraphicsDevice.Viewport.Unproject(farsource,
    proj, view, world);

Create a Ray whose origin is at the near point and whose direction points to the far point.

C#

Kopiuj
// Create a ray from the near clip plane to the far clip plane.
Vector3 direction = farPoint - nearPoint;
direction.Normalize();
Ray pickRay = new Ray(nearPoint, direction);

Loop throught each object in the scene using the Intersects method to check whether the Ray intersects each object.

If the Ray intersects an object, check whether it is the closest object intersected so far. If it is, store the object and the distance at which it was intersected, replacing any previously stored object.

When you completely loop through the objects, the last object stored will be the closest object underneath the area the user clicked.

Może ci się przyda. Co prawda C#, ale nie chodzi o kod a sposób.


Co kurła debuguj ten kod i streszczaj się klientowi chce się fixa, a jak nie kurła to odpale visuala i ci pomoge a tego byś nie chciał
edytowany 1x, ostatnio: xeo545x39
Kliknij, aby dodać treść...

Pomoc 1.18.8

Typografia

Edytor obsługuje składnie Markdown, w której pojedynczy akcent *kursywa* oraz _kursywa_ to pochylenie. Z kolei podwójny akcent **pogrubienie** oraz __pogrubienie__ to pogrubienie. Dodanie znaczników ~~strike~~ to przekreślenie.

Możesz dodać formatowanie komendami , , oraz .

Ponieważ dekoracja podkreślenia jest przeznaczona na linki, markdown nie zawiera specjalnej składni dla podkreślenia. Dlatego by dodać podkreślenie, użyj <u>underline</u>.

Komendy formatujące reagują na skróty klawiszowe: Ctrl+B, Ctrl+I, Ctrl+U oraz Ctrl+S.

Linki

By dodać link w edytorze użyj komendy lub użyj składni [title](link). URL umieszczony w linku lub nawet URL umieszczony bezpośrednio w tekście będzie aktywny i klikalny.

Jeżeli chcesz, możesz samodzielnie dodać link: <a href="link">title</a>.

Wewnętrzne odnośniki

Możesz umieścić odnośnik do wewnętrznej podstrony, używając następującej składni: [[Delphi/Kompendium]] lub [[Delphi/Kompendium|kliknij, aby przejść do kompendium]]. Odnośniki mogą prowadzić do Forum 4programmers.net lub np. do Kompendium.

Wspomnienia użytkowników

By wspomnieć użytkownika forum, wpisz w formularzu znak @. Zobaczysz okienko samouzupełniające nazwy użytkowników. Samouzupełnienie dobierze odpowiedni format wspomnienia, zależnie od tego czy w nazwie użytkownika znajduje się spacja.

Znaczniki HTML

Dozwolone jest używanie niektórych znaczników HTML: <a>, <b>, <i>, <kbd>, <del>, <strong>, <dfn>, <pre>, <blockquote>, <hr/>, <sub>, <sup> oraz <img/>.

Skróty klawiszowe

Dodaj kombinację klawiszy komendą notacji klawiszy lub skrótem klawiszowym Alt+K.

Reprezentuj kombinacje klawiszowe używając taga <kbd>. Oddziel od siebie klawisze znakiem plus, np <kbd>Alt+Tab</kbd>.

Indeks górny oraz dolny

Przykład: wpisując H<sub>2</sub>O i m<sup>2</sup> otrzymasz: H2O i m2.

Składnia Tex

By precyzyjnie wyrazić działanie matematyczne, użyj składni Tex.

<tex>arcctg(x) = argtan(\frac{1}{x}) = arcsin(\frac{1}{\sqrt{1+x^2}})</tex>

Kod źródłowy

Krótkie fragmenty kodu

Wszelkie jednolinijkowe instrukcje języka programowania powinny być zawarte pomiędzy obróconymi apostrofami: `kod instrukcji` lub ``console.log(`string`);``.

Kod wielolinijkowy

Dodaj fragment kodu komendą . Fragmenty kodu zajmujące całą lub więcej linijek powinny być umieszczone w wielolinijkowym fragmencie kodu. Znaczniki ``` lub ~~~ umożliwiają kolorowanie różnych języków programowania. Możemy nadać nazwę języka programowania używając auto-uzupełnienia, kod został pokolorowany używając konkretnych ustawień kolorowania składni:

```javascript
document.write('Hello World');
```

Możesz zaznaczyć również już wklejony kod w edytorze, i użyć komendy  by zamienić go w kod. Użyj kombinacji Ctrl+`, by dodać fragment kodu bez oznaczników języka.

Tabelki

Dodaj przykładową tabelkę używając komendy . Przykładowa tabelka składa się z dwóch kolumn, nagłówka i jednego wiersza.

Wygeneruj tabelkę na podstawie szablonu. Oddziel komórki separatorem ; lub |, a następnie zaznacz szablonu.

nazwisko;dziedzina;odkrycie
Pitagoras;mathematics;Pythagorean Theorem
Albert Einstein;physics;General Relativity
Marie Curie, Pierre Curie;chemistry;Radium, Polonium

Użyj komendy by zamienić zaznaczony szablon na tabelkę Markdown.

Lista uporządkowana i nieuporządkowana

Możliwe jest tworzenie listy numerowanych oraz wypunktowanych. Wystarczy, że pierwszym znakiem linii będzie * lub - dla listy nieuporządkowanej oraz 1. dla listy uporządkowanej.

Użyj komendy by dodać listę uporządkowaną.

1. Lista numerowana
2. Lista numerowana

Użyj komendy by dodać listę nieuporządkowaną.

* Lista wypunktowana
* Lista wypunktowana
** Lista wypunktowana (drugi poziom)

Składnia Markdown

Edytor obsługuje składnię Markdown, która składa się ze znaków specjalnych. Dostępne komendy, jak formatowanie , dodanie tabelki lub fragmentu kodu są w pewnym sensie świadome otaczającej jej składni, i postarają się unikać uszkodzenia jej.

Dla przykładu, używając tylko dostępnych komend, nie możemy dodać formatowania pogrubienia do kodu wielolinijkowego, albo dodać listy do tabelki - mogłoby to doprowadzić do uszkodzenia składni.

W pewnych odosobnionych przypadkach brak nowej linii przed elementami markdown również mógłby uszkodzić składnie, dlatego edytor dodaje brakujące nowe linie. Dla przykładu, dodanie formatowania pochylenia zaraz po tabelce, mogłoby zostać błędne zinterpretowane, więc edytor doda oddzielającą nową linię pomiędzy tabelką, a pochyleniem.

Skróty klawiszowe

Skróty formatujące, kiedy w edytorze znajduje się pojedynczy kursor, wstawiają sformatowany tekst przykładowy. Jeśli w edytorze znajduje się zaznaczenie (słowo, linijka, paragraf), wtedy zaznaczenie zostaje sformatowane.

  • Ctrl+B - dodaj pogrubienie lub pogrub zaznaczenie
  • Ctrl+I - dodaj pochylenie lub pochyl zaznaczenie
  • Ctrl+U - dodaj podkreślenie lub podkreśl zaznaczenie
  • Ctrl+S - dodaj przekreślenie lub przekreśl zaznaczenie

Notacja Klawiszy

  • Alt+K - dodaj notację klawiszy

Fragment kodu bez oznacznika

  • Alt+C - dodaj pusty fragment kodu

Skróty operujące na kodzie i linijkach:

  • Alt+L - zaznaczenie całej linii
  • Alt+, Alt+ - przeniesienie linijki w której znajduje się kursor w górę/dół.
  • Tab/⌘+] - dodaj wcięcie (wcięcie w prawo)
  • Shit+Tab/⌘+[ - usunięcie wcięcia (wycięcie w lewo)

Dodawanie postów:

  • Ctrl+Enter - dodaj post
  • ⌘+Enter - dodaj post (MacOS)