OBSAH WEBU
ČTĚTE!
Zde můžete vidět rozdíly mezi vybranou verzí a aktuální verzí dané stránky.
temata:11-rasterizace:main [2011/04/15 22:37] vagabund |
temata:11-rasterizace:main [2016/05/27 11:41] (aktuální) xpavel27 [Bresenhamův algoritmus] |
||
---|---|---|---|
Řádek 1: | Řádek 1: | ||
+ | ~~ODT~~ | ||
+ | |||
====== 11 - Metody rasterizace 2D vektorových objektů ====== | ====== 11 - Metody rasterizace 2D vektorových objektů ====== | ||
Řádek 34: | Řádek 36: | ||
* Používá ”floating-point aritmetiku”, pak se zaokrouhluje | * Používá ”floating-point aritmetiku”, pak se zaokrouhluje | ||
* Nízká efektivita, náročná implementace do HW | * Nízká efektivita, náročná implementace do HW | ||
+ | * V podstate **x** sa inkrementuje a **y** sa zväčšuje o smernicu | ||
+ | * Vzorec smernice je vyssie, je to podiel prirastku y a x | ||
|<m>x_{n + 1} = x_n + 1</m>| | |<m>x_{n + 1} = x_n + 1</m>| | ||
|<m>y_{n + 1} = y_n + k, k = (y_2 − y_1)/(x_2 − x_1)</m> ... směrnice| | |<m>y_{n + 1} = y_n + k, k = (y_2 − y_1)/(x_2 − x_1)</m> ... směrnice| | ||
- | </box> | ||
+ | <code> | ||
+ | LineDDA(int x1, int y1, int x2, int y2) | ||
+ | { | ||
+ | double k = (y2-y1)/(x2-x1); | ||
+ | double y = y1; | ||
+ | for (int x = x1; x <= x2; x++) | ||
+ | { | ||
+ | draw_pixel( x, y); | ||
+ | y += k; | ||
+ | } | ||
+ | } | ||
+ | </code> | ||
+ | </box> | ||
==== Error control DDA ==== | ==== Error control DDA ==== | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
* modifikace DDA | * modifikace DDA | ||
+ | * V podstate len používame premennú **E** kde ukladame smernicu | ||
+ | * Ak je hodnota **E** aspoň **0.5** a viac inkrementujeme **X** a odpočítame **jedničku** | ||
<code> | <code> | ||
Řádek 63: | Řádek 81: | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
- | * nejpoužívanější, velmi efektivní, snadná implementace do HW | + | Nejpoužívanější, velmi efektivní, snadná implementace do HW\\ |
- | * používá celočíselnou aritmetiku, sčítání, porovnání | + | Používá celočíselnou aritmetiku, sčítání, porovnání\\ |
- | * posun v ose Y podle znaménka **prediktoru** | + | Posun v ose Y podle znaménka **prediktoru**\\ \\ |
- | + | * Pokud <m>E_i + k \ge 0.5</m>, potom <m>E_{i + 1} = E_i + k - 1</m>\\ | |
- | Pokud <m>E_i + k \ge 0.5</m>, potom <m>E_{i + 1} = E_i + k</m>\\ | + | * Pokud <m>E_i + k < 0.5</m> potom <m>E_{i + 1} = E_i + k</m>\\ |
- | Pokud <m>E_i + k < 0.5</m> potom <m>E_{i + 1} = E_i + k - 1</m>\\ | + | |
Takze po vynásobení rovnic <m>2\Delta x</m>: | Takze po vynásobení rovnic <m>2\Delta x</m>: | ||
- | |<m>P_0 = 2\Delta y - \Delta x</m>| | + | * <m>P_0 = 2\Delta y - \Delta x</m> |
- | + | * <m>P_i < 0 \doubleright P_{i + 1} = P_i + 2\Delta y</m> | |
- | |<m>P_i < 0 \doubleright P_{i + 1} = P_i + 2\Delta y</m>| | + | * <m>P_i \ge 0 \doubleright P_{i + 1} = P_i + 2 \Delta y - 2 \Delta x</m> |
- | |<m>P_i \ge 0 \doubleright P_{i + 1} = P_i + 2 \Delta y - 2 \Delta x</m>| | + | V podstate: |
+ | * nepracujeme so smernicou ale len s prírastkami | ||
+ | * vytvoríme si tri predikáty | ||
+ | * Upravovaný predikát: <m>P_0 = 2\Delta y - \Delta x</m> | ||
+ | * Menší ako nula: <m>P_1 = 2\Delta y</m> | ||
+ | * Aspoň nula: <m>P_2 = P_1 - 2\Delta x</m> | ||
+ | * následne upravovaný predikát inkrementujeme o hodnotu P1 alebo P2 | ||
+ | * v prípade, že je P aspoň 0 inkrementujeme y | ||
<code> | <code> | ||
LineBres(int x1, int y1, int x2, int y2) | LineBres(int x1, int y1, int x2, int y2) | ||
{ | { | ||
- | int dx = x2-x1, dy = y2-y1; | + | int dx = x2-x1; |
+ | int dy = y2-y1; | ||
int P = 2*dy – dx; | int P = 2*dy – dx; | ||
int P1 = 2*dy, P2 = P1 - 2*dx; | int P1 = 2*dy, P2 = P1 - 2*dx; | ||
Řádek 94: | Řádek 119: | ||
</code> | </code> | ||
</box> | </box> | ||
- | |||
===== Kružnice ===== | ===== Kružnice ===== | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 114: | Řádek 138: | ||
* Používá ”floating-point aritmetiku” | * Používá ”floating-point aritmetiku” | ||
* nízká efektivita, náročná implementace v HW | * nízká efektivita, náročná implementace v HW | ||
+ | * vykreslujeme ve smere hodinových ruciciek. | ||
* od bodu [0,R] po pixelech dokud není x=y | * od bodu [0,R] po pixelech dokud není x=y | ||
|<m>dx = 1, y = \sqrt(R^2-x^2)</m>| | |<m>dx = 1, y = \sqrt(R^2-x^2)</m>| | ||
- | </box> | ||
+ | {{ temata:11-rasterizace:obyckruh.png?500 }} | ||
+ | </box> | ||
==== Vykreslení kružnice jako N-úhelník ==== | ==== Vykreslení kružnice jako N-úhelník ==== | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
- | * varianta DDA pro kružnici-floating point, nízka efektivita, vysoká náročnost implementace v HW | ||
- | * rekurentní posun o konstaní přírůstek úhlu(sin a cos se počítají pouze jednou) | ||
- | |<m>x_{n + 1} = x_n \cos\alpha − y_n \sin\alpha</m>| | + | * **Info** |
+ | * varianta DDA pro kružnici-floating point | ||
+ | * aplikace rotacní transformace bodu. | ||
+ | * používá "floating-point aritmetiku". | ||
+ | * nízká efektivita, nárocná implementace do HW. | ||
+ | * rekurentní posun o konstaní přírůstek úhlu | ||
+ | * funkce sin a cos jsou vypocítány pouze jednou! | ||
+ | * souradnice X a Y se zaokrouhlují na nejbližší celé císlo. | ||
+ | * vypoctené souˇradnice spojujeme úseckami. | ||
- | |<m>y_{n + 1} = x_n \sin\alpha − y_n \cos\alpha</m>| | + | * **Vzorce** |
+ | * <m>x_{n + 1} = x_n \cos\alpha − y_n \sin\alpha</m> | ||
+ | * <m>y_{n + 1} = x_n \sin\alpha − y_n \cos\alpha</m> | ||
+ | |||
+ | * **V podstate** | ||
+ | * Vypočítame cos jedného uhla <m>\cos (2\pi / N)</m> | ||
+ | * Vypočítame sin jedného uhla <m>\sin (2\pi / N)</m> | ||
+ | * Začneme na súradnici R,0 | ||
+ | * Pre každý uhol vypočítame nové x a y podľa vzorca | ||
+ | |||
+ | {{ temata:11-rasterizace:kruhuholnik.png?500 }} | ||
</box> | </box> | ||
- | |||
==== Midpoint algoritmus ==== | ==== Midpoint algoritmus ==== | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
- | * variace na Bresenhamův =>celočíselná aritmetika, vysoká efektivita, snadná implementace | + | * variace na Bresenhamův |
+ | * celočíselná aritmetika | ||
+ | * vysoká efektivita | ||
+ | * snadná implementace | ||
* po pixelu od [0,R] dokud <m>x = y</m> | * po pixelu od [0,R] dokud <m>x = y</m> | ||
+ | * startovací hodnota je <m>p_i = 1 − R</m> | ||
|<m>p_i = (x_i + 1)^2 + (y_i − 1/2)^2 − R^2</m>| | |<m>p_i = (x_i + 1)^2 + (y_i − 1/2)^2 − R^2</m>| | ||
- | |||
|<m>p_i < 0 \doubleright y_{i + 1} = y_i, p_{i+1} = p_i + 2x_i + 3</m>| | |<m>p_i < 0 \doubleright y_{i + 1} = y_i, p_{i+1} = p_i + 2x_i + 3</m>| | ||
- | |||
|<m>p_i \ge 0 \doubleright y_{i + 1} = y_i - 1, p_i + 1 = p_i + 2x_i − 2y_i + 5</m>| | |<m>p_i \ge 0 \doubleright y_{i + 1} = y_i - 1, p_i + 1 = p_i + 2x_i − 2y_i + 5</m>| | ||
- | * startovací hodnota je <m>p_i = 1 − R</m> | + | {{ temata:11-rasterizace:basenkruh.png?500 }} |
- | <code> | + | |
- | CircleMid(int s1, int s2, int R) | + | |
- | { int x = 0, y = R; | + | |
- | int P = 1-R, X2 = 3, Y2 = 2*R-2; | + | |
- | while (x < y) | + | |
- | { | + | |
- | draw_pixel_circle(x, y); | + | |
- | if (P >= 0) | + | |
- | { P += -Y2; Y2 -= 2; y--; } | + | |
- | P += X2; | + | |
- | X2 += 2; | + | |
- | x++; | + | |
- | } | + | |
- | } | + | |
- | </code> | + | |
</box> | </box> | ||
- | |||
===== Elipsa ===== | ===== Elipsa ===== | ||
Řádek 168: | Řádek 196: | ||
* úhlem natočení hlavní poloosy | * úhlem natočení hlavní poloosy | ||
* rovnicí elipsy popisující geometrii: <m>F(x, y) : b^2x^2 + a^2y^2 − a^2b^2 = 0</m> | * rovnicí elipsy popisující geometrii: <m>F(x, y) : b^2x^2 + a^2y^2 − a^2b^2 = 0</m> | ||
+ | * je 4x symetrická. | ||
+ | * výpočet pre štvrtinu bodov | ||
</box> | </box> | ||
Řádek 178: | Řádek 208: | ||
* založen na určování polohy midpointu vůči elipse | * založen na určování polohy midpointu vůči elipse | ||
* V ose X/Y postupujeme o 1, v Y/X o posunu rozhoduje znaménko prediktoru. | * V ose X/Y postupujeme o 1, v Y/X o posunu rozhoduje znaménko prediktoru. | ||
- | </box> | ||
+ | {{ temata:11-rasterizace:midelipsa.png?500 }} | ||
+ | </box> | ||
===== Křivky ===== | ===== Křivky ===== | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 205: | Řádek 236: | ||
</box> | </box> | ||
- | ==== Fergusonova kubika ==== | + | ==== Interpolační ==== |
+ | |||
+ | === Fergusonova kubika === | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 216: | Řádek 249: | ||
</box> | </box> | ||
- | ==== Kochanek Bartels spline ==== | + | === Kochanek Bartels spline === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 226: | Řádek 259: | ||
</box> | </box> | ||
- | ==== Catmull-Rom spline ==== | + | === Catmull-Rom spline === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 238: | Řádek 271: | ||
</box> | </box> | ||
- | ==== Beziérovy křivky ==== | + | ==== Aproximační ==== |
+ | |||
+ | === Beziérovy křivky === | ||
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 249: | Řádek 284: | ||
</box> | </box> | ||
- | ==== Beziérovy kubiky ==== | + | === Beziérovy kubiky === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 260: | Řádek 295: | ||
</box> | </box> | ||
- | ==== Racionální beziérové křivky ==== | + | === Racionální beziérové křivky === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 270: | Řádek 305: | ||
</box> | </box> | ||
- | ==== Coonsova kubika ==== | + | === Coonsova kubika === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 278: | Řádek 313: | ||
</box> | </box> | ||
- | ==== B-spline křivky ==== | + | === B-spline křivky === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> | ||
Řádek 291: | Řádek 326: | ||
</box> | </box> | ||
- | ==== NURBS Non Uniform Rational B-Spline ==== | + | === NURBS Non Uniform Rational B-Spline === |
<box left round blue 90%|**Popis**> | <box left round blue 90%|**Popis**> |