وبلاگ تخصصي برنامه نويسي با VB

مباحث پيشرفته Direct3D - درس سوم

موضوع : استفاده از Index Buffer براي ذخيره سازي اشکال سه بعدي

مقدمه : مکعبي که در درسهاي قبلي ساختيم را درنظر بگيريد . با دانشي که اکنون داريد ، دو راه براي ساخت يک مکعب داريم : ۱ - استفاده از 36 عدد vertex براي تعريف face هاي مکعب ۲ - ساخت مکعب با استفاده از يک مدلساز و ذخيره آن با فرمت X
روش اول غيرکارامد است زيرا شما بايستي از تعداد زيادي vertex براي يک شکل بسيار ساده استفاده کنيد . روش دوم مناسب است اما زمانيکه بخواهيم رنگها و بافتها را تغيير دهيم دچار مشکل خواهيم شد . روش جديدي که امروز در مورد آن صحبت مي کنم استفاده ار Index Buffer است .
Index Buffer شامل يکسري عدد integer است که اين اعداد مرجعي براي vertex هاي ذخيره شده در يک Vertex Buffer هستند . براي مثال فرض کنيد يک Vertex Buffer شامل 8 عدد vertex داريم که يک مکعب را براي ما توصيف مي کند . ما مي توانيم يک Index Buffer با ۳۶ عضو بسازيم بطوريکه ترتيب اتصال vertex ها را براي ما مشخص کنند . مثلاً Index هاي ۰ و ۱و ۳ براي مشخص کردن face شماره ۱ مکعب بکار مي روند . بنابراين بجاي استفاده از ۳۶ عدد vertex مي توانيم مکعب را با ۸ عدد vertex و يک Index Buffer بسازيم .
گرچه استفاده از Index Buffer بسيار کارامد است اما چندين محدوديت در استفاده از آن وجود دارد . مهمترين آنها اينست که تمام انديسهايي که يک vertex مشابه را share مي کنند بايستي خصوصيات مشابهي داشته باشند - موقعيت ، رنگ ، بافت و نرمال يکسان - براي مثال نمي توانيد مکعبي بسازيد که هر face آن يک رنگ داشته باشد .

ساخت Index Buffer : ابتدا به متغيرهاي زير نياز داريم :

Dim VBuffer as Direct3DVertexBuffer8
Dim IBuffer as Direct3DIndexBuffer8
Dim Vlist(0 to 7) as LITVERTEX
Dim Ilist(0 to 35) as Integer


تابع InitGeometry بصورت زير بازنويسي مي شود:
۱- توليد هشت vertex براي مکعب :

Vlist(0) = CreateLitVertex(-1, -1, -1, &HFF0000, 0, 0, 0)x
Vlist(1) = CreateLitVertex(-1, 1, -1, &HFF00&, 0, 0, 0)x
Vlist(2) = CreateLitVertex(1, -1, -1, &HFF&, 0, 0, 0)x
Vlist(3) = CreateLitVertex(1, 1, -1, &HFF00FF, 0, 0, 0)x
Vlist(4) = CreateLitVertex(-1, -1, 1, &HFFFF00, 0, 0, 0)x
Vlist(5) = CreateLitVertex(-1, 1, 1, &HFFFF, 0, 0, 0)x
Vlist(6) = CreateLitVertex(1, -1, 1, &HFFCC00, 0, 0, 0)x
Vlist(7) = CreateLitVertex(1, 1, 1, &HFFFFFF, 0, 0, 0)x


۲ - ايجاد Vertex Buffer توسط تابع CreateVertexBuffer :

Set VBuffer = D3DDevice.CreateVertexBuffer(Len(Vlist(0)) * 8, 0, Lit_FVF, D3DPOOL_DEFAULT)x
D3DVertexBuffer8SetData VBuffer, 0, Len(Vlist(0)) * 8, 0, Vlist(0)x


۳ - توليد index ها :

front '
Ilist(0) = 0: Ilist(1) = 1: Ilist(2) = 2
Ilist(3) = 1: Ilist(4) = 3: Ilist(5) = 2
Right '
Ilist(6) = 2: Ilist(7) = 3: Ilist(8) = 6
Ilist(9) = 3: Ilist(10) = 7: Ilist(11) = 6
Back '
Ilist(12) = 6: Ilist(13) = 7: Ilist(14) = 4
Ilist(15) = 7: Ilist(16) = 5: Ilist(17) = 4
Left '
Ilist(18) = 4: Ilist(19) = 5: Ilist(20) = 0
Ilist(21) = 5: Ilist(22) = 1: Ilist(23) = 0
Top '
Ilist(24) = 1: Ilist(25) = 5: Ilist(26) = 3
Ilist(27) = 5: Ilist(28) = 7: Ilist(29) = 3
Bottom '
Ilist(30) = 2: Ilist(31) = 6: Ilist(32) = 0
Ilist(33) = 6: Ilist(34) = 4: Ilist(35) = 0


۴ - ايجاد Index Buffer توسط تابع CreateIndexBuffer :

Set IBuffer = D3DDevice.CreateIndexBuffer(Len(Ilist(0)) * 36, 0, D3DFMT_INDEX16, D3DPOOL_DEFAULT)x
D3DIndexBuffer8SetData IBuffer, 0, Len(Ilist(0)) * 36, 0, Ilist(0)x


تابع Render : براي رندر کردن اين مکعب دو روش وجود دارد :
۱ - استفاده از تابع DrawIndexedPrimitive : در اين روش از VBuffer و IBUffer و آرايه vertex ها استفاده مي شود :

Public Sub Render()x
D3DDevice.Clear 0, ByVal 0, D3DCLEAR_TARGET Or D3DCLEAR_ZBUFFER, 0, 1#, 0
D3DDevice.BeginScene
D3DDevice.SetStreamSource 0, VBuffer, Len(Vlist(0))x
D3DDevice.SetIndices IBuffer, 0
D3DDevice.DrawIndexedPrimitive D3DPT_TRIANGLELIST, 0, 36, 0, 12

D3DDevice.EndScene
D3DDevice.Present ByVal 0, ByVal 0, 0, ByVal 0
End Sub


۲ - استفاده از تابع DrawIndexedPrimitiveUP : در اين روش از آرايه هاي vertex و index استفاده مي شود :

Public Sub Render()x
D3DDevice.Clear 0, ByVal 0, D3DCLEAR_TARGET Or D3DCLEAR_ZBUFFER, 0, 1#, 0
D3DDevice.BeginScene
D3DDevice.DrawIndexedPrimitiveUP D3DPT_TRIANGLELIST, 0, 8, 12, Ilist(0), D3DFMT_INDEX16, Vlist(0), Len(Vlist(0))x
D3DDevice.EndScene
D3DDevice.Present ByVal 0, ByVal 0, 0, ByVal 0
End Sub


نکته : براي دريافت برنامه نمونه و يا اطلاعات بيشتر در مورد توابعي که در اين درس استفاده شد با من تماس بگيريد .


+ حامد شیدائیان ; ۳:٤٧ ‎ب.ظ ; چهارشنبه ۱٧ مهر ،۱۳۸۱
comment نظرات ()