2011-08-31 55 views
3

如何在OpenGL中繪製2D月牙形或月球形狀?我嘗試過使用罪與cos,就像我爲繪畫圈所做的一樣,但由於新月有一個「切」,罪和cos看起來不夠。我無法弄清楚我怎樣才能做兩個多邊形之間的交集。所以我在想如果有繪製新月的數學公式?在OpenGL中繪製月牙形狀

+1

新月是兩個非同心圓之間的差異。 –

+0

但我需要一種「相交」圓的方式,以便其中一個圓圈清除另一個圓的相交區域。我怎樣才能做到這一點? – Carven

回答

2

這不是數學上正確,但它可能是足夠接近滿足您的需求:

void drawCrescentLine(float step,float scale,float fullness) { 
    float angle=0.0f; 
    while (angle<M_PI) { 
     glVertex2f(scale*sinf(angle),scale*cosf(angle)); 
     angle+=step; 
    } 
    while (angle<(2.0f*M_PI)) { 
     glVertex2f(fullness*scale*sinf(angle),scale*cosf(angle)); 
     angle+=step; 
    } 
    glVertex2f(0.0f,scale); 
} 

void drawCrescentTriStrip(float step,float scale,float fullness) { 
    glVertex2f(0.0f,scale); 
    float angle=step; 
    while (angle<M_PI) { 
     float sinAngle=sinf(angle); 
     float cosAngle=cosf(angle); 
     glVertex2f(scale*sinAngle,scale*cosAngle); 
     glVertex2f(-fullness*scale*sinAngle,scale*cosAngle); 
     angle+=step; 
    } 
    glVertex2f(0.0f,-scale); 
} 

fullness=1,它會畫大小scale同時在一個圓fullness=-0.99f,它會畫出一個非常薄的cresent。您可以使用兩個不同的豐滿度值rightFullnessleftFullness,並且始終將其中的一個設置爲1.0f,以便您可以更改新月的方向。

+0

我用多邊形繪製了這個代碼,但多邊形的末端與切割整個形狀的直線相連。當顏色填滿時,整個形狀都已經消失。 – Carven

+0

@xEnOn原始版本生成頂點以便適合使用GL_LINE_STRIP。我已經更新了答案,以包含一個可以使用'GL_TRIANGLE_STRIP'的版本。 – IronMensan

+0

非常感謝!這真是一個繪製新月的聰明方法!謝謝! :) – Carven

1

您可以繪製兩個相互交叉的垂直橢圓。一個新月形成了從日食中切出的空間。繪圖時,可以通過使用按位與非邏輯運算符來移除交點。

glEnable(GL_COLOR_LOGIC_OP); 
drawEllipse1(); 
glLogicOp(GL_NAND); 
drawEllipse2(); 

這樣做的一個很長的方法是指定一堆形成所需形狀骨架的頂點。然後你可以用GL_LINES'連接點'來繪製你的形狀。如果想要更平滑的形狀,可以將頂點用作Bezier/Catmull-Rom樣條線的控制點,以便繪製連接所有頂點的平滑曲線。

+0

如何在OpenGL中指定邏輯運算符來刪除交叉點? glBegin或glVertex2f不允許我添加按位運算符參數。 – Carven

+0

我編輯了答案來回答你的問題。 – windson

+0

謝謝!我嘗試使用邏輯操作,但它看起來像素混合到背景中的任何顏色或成爲許多虛線像素。爲什麼它不能消除交叉點?我通常用多邊形的正弦和餘弦方法畫出我的橢圓。 – Carven

0

你可以試試這個:

Vertex outside [N+1]; // Fill in N with the precision you want 
Vertex inside [N+1]; // Fill in N with the precision you want 

double neg_size = sqrt (1 + NEG_DIST); // Size of intescting circle. 
             // NEG_DIST is the distance between their centers 
             // Greater NEG_DIST => wider crecent 

double start_angle = atan (1/NEG_DIST); // Start angle for the inside edge 
double arc = M_PI - (2 * start_angle); // Arc of the inside edge 

for (int i = 0; i <= N; i++) 
{ 
    // Outside edge 
    outside [i].x = cos ((M_PI/N) * i) * SIZE; 
    outside [i].y = sin ((M_PI/N) * i) * SIZE; 

    // Inside edge 
    inside [i].x = (cos (start_angle + ((arc/N) * i)) * neg_size) * SIZE; 
    inside [i].y = (sin (start_angle + ((arc/N) * i)) * neg_size - NEG_DIST) * SIZE; 
} 

這將產生一個月牙形的相交多邊形版本。它會給你一個新月形內外弧的座標陣列。然後你可以通過你最喜歡的繪製方法來提供這些。

注意:內部和外部重疊的端點(我這樣做,以便我不會有+/- 1的所有地方)。我很確定一個GL程序可以,但是如果你有一個圍欄錯誤,這可能是它來自的地方