Implementasi tekstur gambar terganggu dari bahasa renderman

8

Saya mencoba menerapkan (dalam C #) algoritma perturbasi gambar yang disajikan dalam buku "Texturing and modelling - K. Perlin et al" (halaman 91 jika ada yang memilikinya), yang mengubah gambar. Kode berikut dalam bahasa Renderman: Akses tekstur

Ct = texture("example.tx", s, t);

diganti oleh

point Psh;
float ss, tt;
Psh = transform("shader", P);
ss = s + 0.2 * snoise(Psh);
tt = t + 0.2 * snoise(Psh+(l.5,6.7,3.4));
Ct = texture("example.tx", ss, tt);

mengubah gambar di sebelah kiri menjadi di sebelah kanan. masukkan deskripsi gambar di sini

Dari apa yang saya undestood, alih-alih mengakses koordinat kita mengakses sedikit koordinat yang terganggu dan menampilkannya di tempat , sehingga menciptakan gambar yang terlihat sedikit terganggu .(s,t)[0,1](ss,tt)(s,t)

snoise(x) didefinisikan sebagai , memetakan noise dari ke , dan dalam dokumentasi RenderMan mana P adalah sebuah titik, mengembalikan nilai berdasarkan pada beberapa noise (kemungkinan besar perlin atau kisi). ( http://renderman.pixar.com/resources/current/RenderMan/noiseFunctions.html )(noise(x)2)1[0,1][1,1]noise(P)

Apa yang saya tidak mengerti adalah apa fungsi transformasi tidak, yang seharusnya memetakan titik 3d P ke dalam ruang "shader", dan bagaimana hal itu bisa dilaksanakan. Juga, saya tidak yakin apakah noise (x) mengembalikan titik 3d, float (akan lebih masuk akal) dan jika saya dapat menggunakan implementasi 2d sederhana dari noise Perlin untuk mencapai efek yang diinginkan yang sama.

simog
sumber

Jawaban:

6

Seperti yang Anda duga, transform()fungsi mengubah titik dari satu ruang koordinat ke ruang koordinasi lainnya. (Ada juga vtransform()dan ntransform()untuk mentransformasikan vektor arah dan vektor normal, masing-masing.) Argumen string menamai ruang koordinat untuk diubah menjadi.

The Pedoman Shading RenderMan telah mengatakan ini tentang hal itu:

Pada awal eksekusi shader, semua variabel titik, vektor, normal, dan matriks diekspresikan dalam sistem koordinat "saat ini". Sistem koordinat mana yang "saat ini" bergantung pada implementasi. Kebetulan "saat ini" adalah "kamera" untuk PRMan *, tetapi Anda tidak boleh mengandalkan perilaku ini - sangat mungkin bahwa penyaji yang mematuhi RenderMan lainnya (termasuk penyaji masa depan dari Pixar) dapat menggunakan ruang lain (seperti "world") sebagai ruang "saat ini".

Selanjutnya memberikan kasus seperti ini sebagai contoh. Sebagian besar perhitungan pencahayaan harus dilakukan dalam ruang kamera, tetapi mengevaluasi fungsi noise harus ada dalam sistem koordinat objek, karena Anda ingin noise tetap sama dengan objek bergerak melalui ruang dunia.

Dalam implementasi C # Anda, Anda juga perlu mengubah titik yang diarsir dari ruang kamera ke sistem koordinat objek. Mungkin Anda sudah melakukan ini sebelum menghitung koordinat tekstur. Jika tidak, Anda harus mengalikannya dengan matriks transformasi objek. Ingatlah bahwa satu-satunya penggunaan titik transformasi ini adalah sebagai input (seperti seed) ke generator derau Perlin. Ini menetapkan domain yang kebisingannya bervariasi: koordinat ruang dunia.

Di RSL, noise()fungsi dapat mengembalikan tipe apa pun yang Anda suka: a float, a color, a point, atau a vector. Saat Anda menambahkannya ke yang lain float( uatau v), Anda akan mendapatkan floatkode ini. Sungguh, dua noise()panggilan, ditambahkan ke sdan t, bertindak untuk menghasilkan vektor noise 2D tunggal. Dalam kode Anda sendiri, jika Anda menggunakan vektor 2D untuk menyimpan koordinat tekstur Anda, Anda dapat menggunakan fungsi derau tunggal yang mengembalikan vektor 2D, untuk mendapatkan efek yang sama dalam satu baris kode.


Jika Anda tertarik untuk membuat generator noise yang bagus, Shadertoy memiliki banyak noise shaders yang menampilkan varian kebisingan Perlin yang berbeda dengan properti yang berbeda (isotropik atau tidak, kelancaran dan bandwidth yang dapat dikonfigurasi) dan layak untuk mencari inspirasi serta petunjuk implementasi .

Dan Hulme
sumber