Jak narysować N jednostronny wielokąt regularny we współrzędnych kartezjańskich?
Próbowałem dowiedzieć się, jak napisać prosty program do obliczania punktów x,y do tworzenia regularnego wielokąta N boków. Może mi ktoś podać jakieś przykłady kodu, które nie używają wcześniej istniejących funkcji rysujących wielokąty? Chcę zrozumieć proces, który zakładam, że jest podobny do tego:
- Wybierz kąt, aby rozpocząć od promienia i punktu środkowego
- jakoś obliczyć pozycję x,y w tej odległości od centrum(jak?)
- podziel 360 przez liczba boków, przesuń tę odległość i narysuj następną linię od pierwszego punktu x, Y
- Kontynuuj do kąta = 360 podzielonego przez tę liczbę.
Zakładając, że moje założenia są poprawne, najważniejsze jest zrozumienie, jak obliczyć punkty x, y.
Preferuj odpowiedzi w visual basic (lub nawet w starym stylu Microsoft / Atari / Commodore BASIC) lub czytelny dla człowieka zestaw kroków w języku angielskim. Jeśli musisz odpowiedzieć formułą matematyczną, zrób to w języku komputerowym, żebym mógł czytać to, nawet w C lub c++ mogę to rozgryźć, ale nie wiem jak czytać notację matematyczną. Język, którego używam, jest językiem podobnym do Visual Basica, który nie ma prawie żadnych prymitywów graficznych innych niż rysowanie linii.
6 answers
Załóżmy, że chcesz narysować N-wielokąt o promieniu r , wyśrodkowany na (0,0). Następnie N wierzchołki są podane przez:
x[n] = r * cos(2*pi*n/N)
y[n] = r * sin(2*pi*n/N)
Gdzie 0 n N . Zauważ, że cos
i sin
tutaj działają w radianach, a nie stopniach (jest to dość powszechne w większości języków programowania).
Jeśli chcesz mieć inny środek, po prostu dodaj współrzędne punktu środkowego do każdego ( x [n], y [n] ). Jeśli chcesz inny orientacja, wystarczy dodać stały kąt. Tak więc ogólna forma to:
x[n] = r * cos(2*pi*n/N + theta) + x_centre
y[n] = r * sin(2*pi*n/N + theta) + y_centre
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-08-25 22:58:33
angle = start_angle
angle_increment = 360 / n_sides
for n_sides:
x = x_centre + radius * cos(angle)
y = y_centre + radius * sin(angle)
angle += angle_increment
W praktyce, podczas rysowania linii zamiast tylko obliczania punktów narożnych, należy również" połączyć " wielokąt powtarzając pierwszy punkt.
Również, Jeśli sin()
i cos()
pracują w radianach, a nie stopniach, chcesz 2 * PI
zamiast 360
.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-08-25 22:57:18
Oto pełny program c++, który wypisuje punkty regularnego wielokąta. W tym przypadku p to liczba boków, r to promień wielokąta, A d to kierunek lub kąt pierwszego punktu od środka. Może to pomoże.
//g++ ck.cpp -o ck && ./ck
#include <stdio.h>
#include <math.h>
int p=3; //number of sides
double r=1000,d=3/4.0;
int main()
{
int i=0;
double x,y,t;
while(i<p)
{
t=2*M_PI*((double)i/p+d);
x=cos(t)*r;
y=sin(t)*r;
printf("x%i:%f y%i:%f\n",i,x,i,y);
i++;
}
}
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-04-15 02:59:14
Jeśli chcesz zrobić to szybciej kosztem jakiejś nagromadzenia błędów, użyj (złożonego) prymitywnego n-tego pierwiastka jedności i przejmij jego moce (albo używając wbudowanej obsługi liczb złożonych w Twoim języku lub kodując mnożenie ręcznie). W C:
complex double omega=cexp(2*M_PI*I/n), z;
for (i=0, z=1; i<n; i++, z*=omega) {
/* do something with z */
}
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-03-08 00:02:43
Wiem, że prosiłeś o odpowiedź w Visual Basic, jednak Oto rozwiązanie w JavaScript.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-07-04 20:47:04
ODPOWIEDŹ "for n_sides:" jest najłatwiejsza. Dla faceta, który zasugerował, że można uprościć obliczenia używając liczb złożonych, prawie wszystkie biblioteki matematyczne mają procedury cos() i sin() oparte na tabelach z efektywną interpolacją, więc nie ma potrzeby zagłębiania się w stosunkowo niejasne rozwiązania. Zazwyczaj zwykły n-gon może być zainicjalizowany i sprzętowe skalowanie OpenGL używane do skalowania / przekształcania go dla dowolnej konkretnej instancji.
If you want to be hardcore about it, wstępnie Wygeneruj wszystkie potrzebne n-gony i załaduj je do buforów wierzchołków.
Na marginesie, oto powyższe rozwiązanie w Lua. Po prostu wypisuje współrzędne, ale oczywiście możesz zwrócić współrzędne w tablicy / tabeli. Zwrócone współrzędne mogą być użyte do zainicjalizowania siatki OpenGL GL_LINE_LOOP.
require 'math'
-- computes coordinates for n-sided, regular polygon of given radius and start angle
-- all values are in radians
function polypoints(sides, radius, start)
local x_center = 0.0
local y_center = 0.0
local angle = start
local angle_increment = 2 * math.pi / sides
local x=0.0
local y=0.0
print(string.format("coordinates for a %d sided regular polygon of radius %d\nVertex",sides,radius),"X"," ","Y")
for i=1,sides do
x = x_center + radius * math.cos(angle)
y = y_center + radius * math.sin(angle)
print(string.format("%d\t%f\t%f",i,x,y))
angle = angle + angle_increment
end
end
-- Generate a regular hexagon inscribed in unit circle
polypoints(6, 1.0, 0.0)
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-01-03 17:45:48