Bagikan melalui


Model shader 3 (referensi HLSL)

Shader vertex dan shader piksel sangat disederhanakan dari versi shader sebelumnya. Jika Anda menerapkan shader dalam perangkat keras, Anda tidak boleh menggunakan vs_3_0 atau ps_3_0 dengan versi shader lainnya, dan Anda tidak boleh menggunakan jenis shader dengan alur fungsi tetap. Perubahan ini memungkinkan untuk menyederhanakan driver dan runtime. Satu-satunya pengecualian adalah bahwa shader vs_3_0 khusus perangkat lunak dapat digunakan dengan versi shader piksel apa pun. Selain itu, jika Anda menggunakan shader vs_3_0 khusus perangkat lunak dengan versi shader piksel sebelumnya, shader vertex hanya dapat menggunakan semantik output yang kompatibel dengan kode format vertex fleksibel (FVF).

Semantik yang digunakan pada output shader vertex harus digunakan pada input pemecah piksel. Semantik digunakan untuk memetakan output shader vertex ke input shader piksel, mirip dengan cara deklarasi vertex dipetakan ke daftar input vertex shader dan model shader sebelumnya. Lihat Cocokkan Semantik pada vs 3.0 dan ps 3.0 Shaders.

Status render mode pembungkus tambahan telah ditambahkan untuk menutupi kemungkinan koordinat tekstur tambahan dalam skema baru ini. Atribut dengan D3DDECLUSAGE_TEXCOORD dan indeks penggunaan dari 0 hingga 15 diinterpolasi dalam mode bungkus saat D3DRS_WRAP* yang sesuai diatur.

Fitur Vertex Shader Model 3

Jenis register output shader vertex telah diciutkan menjadi dua belas register (lihat Output Register). Setiap register yang digunakan perlu dideklarasikan menggunakan instruksi dcl dan semantik (misalnya, dcl_color0 o0.xyzw).

Model shader vertex 3_0 (vs_3_0) meluas pada fitur vs_2_0 dengan pengindeksan register yang lebih kuat, serangkaian register output yang disederhanakan, kemampuan untuk mengambil sampel tekstur dalam shader vertex, dan kemampuan untuk mengontrol laju di mana input shader diinisialisasi.

Indeks Register Apa Pun

Semua register ( Register Input dan Register Output) dapat diindeks menggunakan Loop Counter Register (hanya register konstanta yang dapat diindeks dalam versi sebelumnya.)

Anda harus mendeklarasikan register input dan output sebelum mengindeksnya. Namun, Anda tidak boleh mengindeks register output apa pun yang telah dinyatakan dengan posisi atau semantik ukuran titik. Bahkan, jika pengindeksan digunakan posisi dan semantik psize harus dideklarasikan dalam o0 dan o1 register masing-masing.

Anda hanya diizinkan untuk mengindeks rentang register berkelanjutan; artinya, Anda tidak dapat mengindeks di seluruh register yang belum dideklarasikan. Meskipun pembatasan ini mungkin tidak nyaman, pembatasan ini memungkinkan pengoptimalan perangkat keras berlangsung. Mencoba mengindeks di seluruh register yang tidak bersebelahan akan menghasilkan hasil yang tidak terdefinisi. Validasi shader tidak memberlakukan pembatasan ini.

Menyederhanakan Register Output

Semua jenis register output telah diciutkan menjadi dua belas register output: 1 untuk posisi, 2 untuk warna, 8 untuk tekstur, dan 1 untuk ukuran kabut atau titik. Register ini akan menginterpolasi data apa pun yang dikandungnya untuk shader piksel. Deklarasi register output diperlukan dan semantik ditetapkan untuk setiap register.

Register dapat dipecah sebagai berikut:

  • Setidaknya satu register harus dinyatakan sebagai register posisi empat komponen. Ini adalah satu-satunya register shader vertex yang diperlukan.
  • Sepuluh register pertama yang dikonsumsi oleh shader dapat menggunakan hingga empat komponen (xyzw) maksimum.
  • Register terakhir (atau kedua belas) hanya boleh berisi skalar (seperti ukuran titik).

Untuk daftar register, lihat Registers - vs_3_0.

Sampel Tekstur dalam Shader Vertex

Vertex shader 3_0 mendukung pencarian tekstur di shader vertex menggunakan texldl - vs.

Fitur Pixel Shader Model 3

Warna shader piksel dan register tekstur telah diciutkan ke dalam sepuluh register input (lihat Jenis Daftar Input). Face Register adalah register skalar floating point. Hanya tanda register ini yang valid. Jika tanda negatif, primitif adalah wajah belakang. Ini dapat digunakan di dalam shader piksel untuk mencapai pencahayaan dua sisi, misalnya. Daftar Posisi mereferensikan piksel saat ini (x,y).

Register konstanta shader dapat diatur menggunakan:

Cocokkan Semantik pada shader vs_3_0 dan ps_3_0

Ada beberapa batasan penggunaan semantik dengan vs_3_0 dan ps_3_0. Secara umum, Anda perlu berhati-hati saat menggunakan semantik untuk input shader yang cocok dengan semantik yang digunakan pada output shader.

Misalnya, shader piksel ini mengemas beberapa nama ke dalam satu register:

ps_3_0 
dcl_texcoord0 v0.x 
dcl_texcoord1 v0.yz // Valid to pack multiple names into one register 
dcl_texcoord2_centroid v1.w
...

Setiap register memiliki semantik yang berbeda. Perhatikan bahwa Anda juga dapat memberi nama v0.x dan v0.yz dengan semantik (beberapa) yang berbeda karena penggunaan masker tulis.

Mengingat shader piksel, shader vs_3_0 berikut tidak dapat dipasangkan dengannya:

vs_3_0 
... 
dcl_texcoord0 o5.x 
dcl_texcoord1 o6.yzw 
...

Kedua shader ini bertentangan dengan penggunaan semantik D3DDECLUSAGE_TEXCOORD0 Dan D3DDECLUSAGE_TEXCOORD1 .

Regenerasi shader puncak seperti ini untuk menghindari tabrakan semantik:

vs_3_0 
... 
dcl_texcoord2 o3 
dcl_texcoord3 o9 
...

Demikian pula, nama semantik yang dideklarasikan pada register input yang berbeda di shader piksel (v0 dan v1 dalam shader piksel) tidak dapat digunakan dalam satu register output di shader vertex ini. Misalnya, shader vertex ini tidak dapat dipasangkan dengan shader piksel karena D3DDECLUSAGE_TEXCOORD1 digunakan untuk kedua register input shader piksel (v0, v1) dan register output shader vertex o3.

vs_3_0 
... 
dcl_texcoord0 o3.x 
dcl_texcoord1 o3.yz 

dcl_texcoord2 o3.w // BAD! Would be valid if this were not o3 
dcl_texcoord3 o9 ... 

Di sisi lain, shader vertex ini tidak dapat dipasangkan dengan shader piksel karena masker output untuk parameter dengan semantik tertentu tidak menyediakan data yang diminta oleh shader piksel:

vs_3_0 
... 
dcl_texcoord0 o5.x 
dcl_texcoord1 o5.yzw 
dcl_texcoord2 o7.yz // BAD! Would be valid if w were included 
dcl_texcoord3 o9 
... 

Shader vertex ini tidak menyediakan output dengan salah satu nama semantik yang diminta oleh shader piksel, sehingga pemasangan shader tidak valid:

vs_3_0 
... 
dcl_texcoord0 o5.x 
dcl_texcoord1 o5.yzw 
dcl_texcoord3 o9 
// The pixel shader wants texcoord2, with a w component, 
// but it isn't output by this vertex shader at all! 
... 

Perubahan Mode Kabut, Kedalaman, dan Bayangan

Saat D3DRS_SHADEMODE diatur untuk bayangan datar selama kliping dan rasterisasi segitiga, atribut dengan D3DDECLUSAGE_COLOR diinterpolasi sebagai berbayang datar. Jika ada komponen register yang dideklarasikan dengan semantik warna tetapi komponen lain dari register yang sama diberi semantik yang berbeda, interpolasi bayangan datar (linear vs. flat) akan tidak terdefinisi pada komponen dalam register itu tanpa semantik warna.

Jika penyajian kabut diinginkan, vs_3_0 dan ps_3_0 shader harus menerapkan kabut. Tidak ada perhitungan kabut yang dilakukan di luar shader. Tidak ada kabut yang terdaftar di vs_3_0, dan semantik tambahan D3DDECLUSAGE_FOG (untuk faktor campuran kabut yang dihitung per puncak) dan D3DDECLUSAGE_DEPTH (untuk meneruskan nilai kedalaman ke shader piksel untuk menghitung faktor campuran kabut) telah ditambahkan.

Status tahap tekstur D3DTSS_TEXCOORDINDEX diabaikan saat menggunakan pixel shader 3.0.

Nilai berikut telah ditambahkan untuk mengakomodasi perubahan ini:

// Fog and Depth usages
D3DDECLUSAGE_FOG 
D3DDECLUSAGE_DEPTH 

// Additional wrap states for vs_3_0 attributes with D3DDECLUSAGE_TEXCOORD 
D3DRS_WRAP8 
D3DRS_WRAP9 
D3DRS_WRAP10 
D3DRS_WRAP11 
D3DRS_WRAP12 
D3DRS_WRAP13 
D3DRS_WRAP14 
D3DRS_WRAP15

Konversi Titik Mengambang dan Bilangan Bulat

Matematika floating point terjadi pada presisi dan rentang yang berbeda (16-bit, 24-bit, dan 32-bit) di berbagai bagian alur. Nilai yang lebih besar dari rentang dinamis alur yang memasuki alur tersebut (misalnya, peta tekstur float 32-bit diambil sampelnya ke dalam alur float 24-bit di ps_2_0) membuat hasil yang tidak ditentukan. Untuk perilaku yang dapat diprediksi, Anda harus menjepit nilai tersebut ke rentang dinamis maksimum.

Konversi dari nilai titik mengambang ke bilangan bulat terjadi di beberapa tempat seperti:

  • Saat menemukan mova - vs instruksi.
  • Selama alamat tekstur.
  • Saat menulis ke target render titik non-floating.

Menentukan Presisi Penuh atau Parsial

Baik ps_3_0 maupun ps_2_x memberikan dukungan untuk dua tingkat presisi:

ps_3_0 ps_2_0 Presisi Nilai
x Data fp32 atau lebih tinggi
x Presisi parsial fp16=s10e5
x x Data fp24=s16e7 atau lebih tinggi
x x Presisi parsial fp16=s10e5

 

ps_3_0 mendukung lebih banyak presisi daripada ps_2_0. Secara default, semua operasi terjadi pada tingkat presisi penuh.

Presisi parsial (lihat Pixel Shader Register Modifiers) diminta dengan menambahkan pengubah _pp ke kode shader (asalkan implementasi yang mendasarinya mendukungnya). Implementasi selalu bebas untuk mengabaikan pengubah dan melakukan operasi yang terpengaruh dengan presisi penuh.

Pengubah _pp dapat terjadi dalam dua konteks:

  • Pada deklarasi koordinat tekstur untuk meneruskan koordinat tekstur presisi parsial ke shader piksel. Ini dapat digunakan ketika tekstur mengoordinasikan data warna relai ke shader piksel, yang mungkin lebih cepat dengan presisi parsial daripada dengan presisi penuh dalam beberapa implementasi.
  • Pada instruksi apa pun untuk meminta penggunaan presisi parsial, termasuk instruksi beban tekstur. Ini menunjukkan bahwa implementasi diizinkan untuk menjalankan instruksi dengan presisi parsial dan menyimpan hasil presisi parsial. Dengan tidak adanya pengubah eksplisit, instruksi harus dilakukan dengan presisi penuh (terlepas dari presisi operan input).

Aplikasi mungkin sengaja memilih untuk menukar presisi untuk performa. Ada beberapa jenis data input shader yang merupakan kandidat alami untuk pemrosesan presisi parsial:

  • Iterator warna diwakili dengan baik oleh nilai presisi parsial.
  • Nilai tekstur dari sebagian besar format dapat diwakili secara akurat oleh nilai presisi parsial (nilai yang diambil sampelnya dari tekstur format 32-bit dan floating-point adalah pengecualian yang jelas).
  • Konstanta dapat diwakili oleh representasi presisi parsial yang sesuai dengan shader.

Dalam semua kasus ini, pengembang dapat memilih untuk menentukan presisi parsial untuk memproses data, mengetahui bahwa tidak ada presisi data input yang hilang. Dalam beberapa kasus, shader mungkin mengharuskan langkah internal perhitungan dilakukan dengan presisi penuh bahkan ketika nilai input dan output akhir tidak memiliki lebih dari presisi parsial.

Vertex Perangkat Lunak dan Pixel Shaders

Implementasi perangkat lunak (run-time dan referensi untuk shader vertex dan referensi untuk shader piksel) shader versi 2_0 ke atas memiliki beberapa validasi yang dilonggarkan. Ini berguna untuk tujuan penelusuran kesalahan dan pembuatan prototipe. Aplikasi menunjukkan kepada runtime/assembler bahwa aplikasi memerlukan beberapa validasi yang dilonggarkan menggunakan bendera _sw di perakitan (misalnya, vs_2_sw). Shader perangkat lunak tidak akan bekerja dengan perangkat keras.

vs_2_sw adalah relaksasi hingga batas maksimum vs_2_x; demikian pula, ps_2_sw adalah relaksasi hingga batas maksimum ps_2_x. Secara khusus, validasi berikut dilonggarkan:

Model shader Sumber daya Batas
vs_2_sw, vs_3_sw, ps_2_sw, ps_3_sw Jumlah Instruksi Tak Terbatas
vs_2_sw, vs_3_sw, ps_2_sw, ps_3_sw Daftar Konstanta Float 8192
vs_2_sw, vs_3_sw, ps_2_sw, ps_3_sw Daftar Konstanta Bilangan Bulat 2048
vs_2_sw, vs_3_sw, ps_2_sw, ps_3_sw Daftar Konstanta Boolean 2048
ps_2_sw Kedalaman baca dependen Tak Terbatas
vs_2_sw instruksi dan label kontrol alur Tak Terbatas
vs_2_sw, vs_3_sw, ps_2_sw, ps_3_sw Perulangan mulai/langkah/hitungan Ukuran langkah perulangan dan perulangan untuk instruksi rep dan loop adalah bilangan bulat bertanda tangan 32-bit. Hitungan bisa hingga MAX_INT/64.
vs_2_sw, vs_3_sw, ps_2_sw, ps_3_sw Batas port Batas port untuk semua file register dilonggarkan.
vs_3_sw Jumlah interpolator 16 output mendaftar di vs_3_sw.
ps_3_sw Jumlah interpolator 14(16-2) daftar input untuk ps_3_sw.

 

Shader Model 3 (DirectX HLSL)