Panel użytkownika
Nazwa użytkownika:
Hasło:
Nie masz jeszcze konta?

[Allegro, C++] kąt między dwoma obiektami

Ostatnio zmodyfikowano 2010-06-06 21:20
Autor Wiadomość
ison
Temat założony przez niniejszego użytkownika
[Allegro, C++] kąt między dwoma obiektami
» 2010-06-01 17:44:34
Witam

głowię się już drugą godzinę nad tym problemem i nie mogę dojść do tego co jest tutaj źle...
ten kawałek kodu powinien rysować linię wczytywaną z pliku która będzie przechodziła przez 2 punkty. Co więcej ta funkcja działa...
prawie działa bo jest jednak zauważalna różnica między tym jak powinno być a jak jest teraz.
Tutaj screen z obecnego działania programu:
http://img691.imageshack.us/img691/7506/planetyp.jpg

Linie powinny przechodzić przez środki planet

Klasa tychże linii:
C/C++
class linkST
{
public:
    int ID1, ID2;
    void display()
    {
        pivot_sprite( bufor, link_sprite, planet[ ID1 ].x + planet[ ID1 ].s / 2,
        planet[ ID1 ].y + planet[ ID1 ].s / 2,
        1, 1, itofix( angle( planet[ ID1 ].x + planet[ ID1 ].s / 2,
        planet[ ID1 ].y + planet[ ID1 ].s / 2, planet[ ID2 ].x + planet[ ID2 ].s / 2,
        planet[ ID2 ].y + planet[ ID2 ].s / 2 ) / PI * 180 ) );
    }
};

dwa argumenty w funkcji pivot_sprite o wartości 1,1 to punkt odniesienia przy obracaniu bitmap.
klasa o nazwie planet zawiera zmienną x,y i s odpowiedzialną za rozmiar planety.
Dlatego właśnie środek planety to x+s/2;y+s/2;

tutaj moja funkcja angle która zwraca kąt między dwoma obiektami względem ich położenia w przestrzeni:
C/C++
double angle( double x1, double y1, double x2, double y2 )
{
    double d = sqrt(( x2 - x1 ) *( x2 - x1 ) +( y2 - y1 ) *( y2 - y1 ) );
    return asin(( y2 - y1 ) / d );
}

bardzo proszę o pomoc gdyż nie mogę kontynuować pracy póki tego nie zrobię ;)
P-17420
DejaVu
» 2010-06-01 20:43:09
Co ma wspólnego funkcja obliczająca kąt między planetami z faktem, że linie nie są rysowane z punktu A to punktu B tylko z punktu A do punktu X?

/esit:
A tak swoją drogą to zobacz sobie dziedzinę funkcji asin/acos.
P-17430
ison
Temat założony przez niniejszego użytkownika
» 2010-06-01 20:49:50
Ma wspólnego to że sam ją pisałem i możliwe że tam tkwi błąd... Nie rozumiem zbytnio  o co panu chodzi z funkcją asin. Zwraca ona wartość w radianach i zamieniam ją na stopnie przez pomnożenie przez 180 i podzielenie przez PI. Szczerze mówiąc to liczyłem że właśnie pan będzie znał rozwiązanie mojego problemu. No niestety. Czyli błąd tkwi w funkcji obracającej obrazek z allegro? Przecież ta linia powinna z samej zasady przechodzić przez te dwa punkty...
P-17432
DejaVu
» 2010-06-01 21:17:28
Z tego co widzę w swoim kodzie to do obliczenia kąta użyłem funkcji atan... rozwiązanie tkwi w czystej matematyce i rozrysowaniu sobie przypadków w których odcinek tworzy kąt:
1) od 1 do 89 stopni
2) od 91 do 179 stopni
3) od 181 do 269 stopni
4) od 271 do 359 stopni
Dodatkowo sprawdzić:
5) 0 stopni
6) 90 stopni
7) 180 stopni
8) 270 stopni
Na podstawie tych kilku przykładów możesz wyciągnąć wnioski i napisać sobie funkcję, która w zależności od położenia wierzchołka w układzie współrzędnych zwróci prawidłowy kąt w radianach.

/edit:
Dodam, że moja funkcja przyjmuje jeden argument:
C/C++
double getRadians( const CPoint & point )
Pozbywając się klasy możesz problem rozwiązywać poprzez przekazanie dwóch argumentów.
P-17435
ison
Temat założony przez niniejszego użytkownika
» 2010-06-01 21:20:32
Moglby mi pan powiedziec dlaczego moja funkcja jest zła? Pochodzi z twierdzenia sinusów i zwraca wartość arkus sinus w radianach. Jest to zwykły stosunek jednego boku do drugiego. Dlaczego to teoretycznie działa tylko że z kilkustopniowymi błędami? Rozumiałbym jeśli to by wcale nie działało ale to działa... według mnie funkcja jest dobra i zwraca odpowiedni kąt.

/edit
Zaraz zarz... jak to możliwe że w pana funkcji w argumencie przyjmowany jest tylko jeden punkt? Czyli liczy kąt między czym a czym?...
P-17437
DejaVu
» 2010-06-01 21:27:24
Drugi punkt to (0,0).

/edit:
Czyli jeżeli chcę obliczyć kąt między obiektem A, a B to mogę zrobić:
value = getRadians( A.pos() - B.pos() );
lub
value = getRadians( B.pos() - A.pos() );
W powyższych przypadkach kąt będzie różny o 180 stopni. Pitagoras Ci się w tym wypadku nie przyda.
P-17438
ison
Temat założony przez niniejszego użytkownika
» 2010-06-01 21:35:12
ahh... chyba zrozumiałem mój błąd ;)
dziękuje za pomoc, mam nadzieje ze uda mi sie rozwiazac ten problem
P-17440
DejaVu
» 2010-06-01 21:42:07
Zakładasz, że Twój kąt jest zawsze w pierwszej ćwiartce, tj z przedziału 0..90 a to błąd.

1) Narysuj układ współrzędnych X,Y
2) Narysuj w nim punkty położone na okręgu o środku w punkcie (0,0).
3) Niech każdy punkt będzie przesunięty o 30 stopni.
4) Połącz każdy punkt z punktem (0,0) -> otrzymasz odcinki
5) Oblicz kąt dla każdego odcinka Twoją metodą z osią X (albo Y jeśli używasz osi Y jako kąt = 0 stopni)
6) Podaj wyniki (jeżeli uważasz, że są poprawne)
P-17442
« 1 » 2 3
  Strona 1 z 3 Następna strona