Bagaimana cara membuat mesin voxel terrain?

53

Beberapa hari yang lalu saya menemukan sesuatu yang disebut medan voxel dan saya pikir mereka cukup keren. Tapi saya tidak tahu apa-apa menghasilkan mereka. Apakah Anda memodelkannya dalam perangkat lunak pemodelan Anda atau menggunakan sesuatu seperti peta ketinggian? Saya membaca di wikipedia bahwa voxels seperti piksel 3d atau piksel volumetrik.

Setelah saya membuat medan voxel, bagaimana saya bisa mengambil voxel ini dan membuatnya bisa dihancurkan / diggable ?


Saya akan memilih jawaban terbaik berdasarkan:

  1. kode dan algoritma. lebih disukai berbasis di C #
  2. penjelasan. Saya seorang pemula dengan algoritma tetapi saya sangat akrab dengan pemrograman berorientasi objek
  3. demonstrasi langkah demi langkah. Tidak hanya konsep tetapi juga arah.
  4. diagram / ilustrasi. Tidak, bukan tangkapan layar dari mesin lain.


Saya tahu bahwa ini adalah masalah yang rumit. Tapi terima kasih atas bantuannya!

Tidak, saya tidak mencoba membuat klon minecraft.


Sunting

Terima kasih kepada semua orang atas bantuan besar Anda (terutama Nick Wiggill)! Inilah yang saya berhasil buat (Work in progress).

Daniel Pendergast
sumber
[unity] dan C ? Itu ... tidak masuk akal.
Martin Sojka
Saya mengerti C.
Daniel Pendergast
8
Anda memiliki banyak kepercayaan pada komunitas dengan permintaan yang begitu berani. Maksud saya, makalah lengkap tentang medan voxel yang sepenuhnya dinamis untuk perangkat keras saat ini dengan FPS yang bagus, seharusnya mudah, bukan? Nah, topiknya sangat luas dan sulit, saya ragu Anda akan melihat solusi generik dan bahkan kemudian, mungkin sama sekali tidak berguna untuk kasus Anda. Tapi siapa tahu, itu bisa dilakukan tergantung pada model peran Anda. Apakah Anda menginginkan medan voxel Crysis 2 atau Delta Force ? Mungkin Anda sedang melakukan klon Minecraft atau hanya perlu simulasi pasir untuk gim? Tolong tentukan lingkup.
EnoughTea
2
Lihatlah middleware ini: forum.unity3d.com/threads/… . Terutama demo
Tetrad
1
GPU Permata 3 memiliki bab tentang medan voxel: http.developer.nvidia.com/GPUGems3/gpugems3_ch01.html
Tamschi

Jawaban:

58

Untuk menghasilkan medan voxel

( A ) Metode umum adalah untuk menghasilkan peta ketinggian menggunakan Perlin noise. Heightmap pada dasarnya adalah gambar monokrom yang mewakili ketinggian berbeda oleh kegelapan atau terang pikselnya.

masukkan deskripsi gambar di sini

Anda akan melihat masing-masing piksel dalam peta tinggi ini untuk membuat "tumpukan" voxel hingga ketinggian yang berbeda (sumbu z) di lokasi yang berbeda (x, y), sesuai dengan kecerahan piksel itu pada gambar heightmap. Karena gambar derau Perlin halus (tidak ada tepi cahaya yang tajam melawan gelap), hasilnya Anda akan memiliki medan yang bergulir dengan lancar.

(B) Anda dapat membangun secara bertahap dengan menciptakan lanskap dari polyhedra yang berbeda. Buat bentuk vektor polihedral yang mendekati bentuk voxel yang Anda inginkan. Menggunakan metode 3D-point-in-polyhedron (paling sering, point-in-convex-hull), periksa titik mana dari grid dunia Anda yang termasuk dalam volume polihedral itu. Misalnya, tentukan piramida di ruang angkasa. Setelah memeriksa setiap titik di wilayah lokal ruang dunia Anda terhadap volume piramidal itu, Anda akan tahu titik mana yang termasuk di dalamnya, dan Anda dapat mengatur sel-sel itu sebagai "sekarang" yang berarti mereka menjadi voxel daripada ruang kosong. Anda sekarang memiliki piramida voxel di ruang Anda. Anda dapat terus menambahkan bentuk apa pun bersama-sama, dengan cara ini, hingga Anda membentuk medan.

(c) (Benar-benar sama dengan b ) Tulis alat pemodelan. Voxatron menunjukkan bagaimana tampilannya. Ini hanya membuat bentuk voxel di dunia pengganti (editor) dan kemudian mengimpornya ke dunia game runtime Anda yang sebenarnya. Saya percaya Voxlap memiliki editor open source pertama untuk voxels. Anda dapat menempatkan voxel individual, atau Anda dapat menggunakan "brush" voxel dengan berbagai bentuk / volume untuk menarik voxel ke dunia Anda.


Apa yang Anda perlukan untuk membangun gim berbasis voxel Anda sendiri

Saya memasukkan bagian ini karena jalan voxel tidak mudah, setidaknya tidak saat ini. Akhir-akhir ini, banyak penelitian sekali lagi dimasukkan ke dalam mesin voxel oleh para pemain besar, menuju aplikasi rendering dan fisika.

Kesederhanaan mungkin menjadi masalah, karena secara dinamis membangun dunia dari voxels mentah adalah pendekatan prosedural untuk konstruksi dunia dan ini pada dasarnya tidak sederhana . Maaf, akan ada beberapa istilah teknis di sini. Menulis mesin voxel adalah pekerjaan yang cukup serius dan membutuhkan pengetahuan di berbagai bidang pengembangan mesin game, terutama dalam hal konsep spasial, dan ini berarti memahami matematika vektor 3D, matriks dan kalkulus dasar ke tingkat yang wajar.

Karena itu, "pembuatan medan voxel" Anda memerlukan konteks untuk bekerja, karena mesin voxel tidak sepenuhnya tersebar luas. Mari kita lanjutkan ke deskripsi dasar tentang cara kerja mesin voxel.

Voxels adalah blok bangunan dasar dunia Anda. Posisi mereka ditentukan oleh grid 3D array-diindeks (array) daripada ruang floating-point terus menerus (seperti yang digunakan dalam game 3D berbasis vektor). Ini akan menjadi "atom" dari dunia Anda. Ketinggiannya bisa 3 kaki seperti pada gim seperti Minecraft, atau bisa lebih kecil dari yang bisa dilihat mata karakter virtual Anda, kecuali terkumpul bersama dalam jumlah besar - sedikit lebih mirip molekul. Ada dua macam:

  • Cubic mesh voxels ( example ) - ini adalah jenis yang lebih baru, digunakan untuk kesederhanaan dan mudah digunakan dalam hubungannya dengan teknologi grafis modern. Digunakan dalam game seperti MineCrat dan Dungeon Keeper.
  • Titik voxels ( contoh , contoh ) - voxel asli. Masing-masing adalah individu, titik yang dapat di collidable dalam ruang, meskipun mungkin dikelilingi oleh volume pembatas bola. Mereka lebih sederhana, sehingga Anda dapat memiliki lebih banyak di dunia Anda, dan dengan demikian Anda dapat membuatnya lebih kecil, yang umumnya menguntungkan. Dua game yang menggunakan ini adalah Comanche dan remake 1990-an dari Lords of Midnight.

Apa pun caranya, pendekatan Anda untuk memanipulasi voxel di dunia Anda hampir sama, sebagai berikut.

Untuk membangun dan memindahkan objek di dunia Anda, Anda membutuhkan alat matematika yang disebutkan di atas. Misalnya, untuk membuat dinding: Bangun kotak dimensi yang sesuai dalam ruang 3D, menggunakan vektor. Gunakan matematika matriks untuk mengubah kotak Anda ke rotasi dan posisi yang Anda inginkan di dunia 3d Anda (dalam ruang vektor terus menerus). Untuk mesin voxel, langkah tambahan adalah sekarang menggunakan algoritma 3D point-in-polyhedron untuk menentukan voxel mana yang termasuk dalam ruang yang diputar.

Pada dasarnya, ini adalah cara Anda membangun sebagian besar objek di dunia Anda. Di luar itu, Anda bisa menulis alat sendiri untuk "memodelkan" karakter dengan cara yang Anda katakan, Maya atau 3DS Max. Tetapi karena Anda memodelkan karakter Anda dari voxel alih-alih titik, tepi dan wajah, metode Anda akan jauh berbeda. Jika Anda memutuskan untuk memutar objek-objek ini di dunia Anda, Anda perlu menggunakan transformasi matriks untuk melakukannya.

Medan yang dapat dirusak semudah mengeluarkan satu voxel pada suatu waktu sesuai dengan beberapa metode yang Anda pilih, atau menggunakan operasi CSG (Constructive Solid Geometry) pada volume besar voxel untuk menghapusnya sesuai dengan beberapa volume yang telah ditentukan; misalnya, jika memotret sinar laser melalui batu, Anda mungkin menggunakan volume silinder untuk mengurangi voxel di sini sinar menembak melalui batu. CSG adalah proses yang relatif sederhana menggunakan kisi spasial 3D yang membentuk dunia voxel Anda, dan memeriksa setiap sel di bagian kisi dasar (dalam hal ini batu) terhadap kisi lain (dalam hal ini, sinar laser)

Untuk memiliki "aliran" material (seperti yang ditunjukkan oleh Vigil dalam komentarnya tentang pasir), Anda perlu melihat dinamika fluida dan automata seluler. Ini digunakan oleh penulis Dwarf Fortress, Tarn Adams, dalam apa yang pada dasarnya juga dunia voxel (meskipun voxel jauh lebih besar dalam kasus ini, sebanding dengan Dungeon Keeper, prinsipnya tetap sama). Ini adalah topik canggih dan bukan keharusan untuk mesin voxel sebagaimana didefinisikan, jadi saya akan meninggalkan ini sebagai "rintisan" untuk penelitian Anda sendiri.

CSG dan dinamika fluid membawa saya, terakhir, ke optimasi. Mesin Voxel yang saat ini sedang dikembangkan hampir secara eksklusif memanfaatkan sparse voxel octrees (SVOs) yang merupakan metode pengelompokan ruang voxel ke berbagai resolusi, sebagaimana dibuktikan dalam video ini yang memamerkan mesin Atomontage yang akan datang. Menggunakan octrees / SVO lebih merupakan keharusan daripada pilihan optimasi, karena overhead pemrosesan yang terlibat dalam pemrosesan satu grid seragam besar. Oktree pada dasarnya adalah pohon (grafik asiklik terarah) di mana setiap node memiliki 8 atau nol node anak tergantung pada apakah ruang yang diwakilinya berisi volume fisik. Diagram yang menunjukkan bagaimana oktri membagi ruang untuk membentuk voxel ada di sini .

Implementasi open source voxel terbaik yang saya tahu adalah Voxlap Engine milik Ken Silverman , yang digunakan untuk Voxelstein3D. Ini ditulis dalam C ++, dan mengimplementasikan operasi CSG untuk deformasi medan.

Insinyur
sumber
Perubahan wiki komunitas bersifat permanen, tidak ada cara untuk membalikkannya. Anda perlu menghapus dan membuat ulang jawaban Anda (tentu saja mengorbankan suara Anda yang sudah ada)
Jesse Dorsey
meta.stackexchange.com/questions/2974/... klaim moderator dapat menghapusnya. Namun, tidak tahu apakah semuanya telah berubah. Terima kasih telah melihatnya.
Engineer
1
Go figure, hati-hati lain kali.
Jesse Dorsey
2
Yang pertama adalah ruang diskritisasi di mana entitas hanya bisa berbaring langsung di sel. Seperti potongan-potongan yang ditempatkan dengan sempurna di papan catur, mereka tidak bisa terletak "di antara" sel atau tumpang tindih perbatasan. Sedangkan ruang kontinu adalah seperti yang ditemukan di sebagian besar mesin fisika, yaitu didasarkan pada angka floating point dan dengan demikian kontinu daripada quantised. Entitas Anda dapat duduk di posisi sewenang-wenang di ruang yang Anda pilih - seperti dalam kehidupan nyata.
Insinyur
1
Tekstur tersirat. Voxel asli, apakah berbasis mesh atau tidak, masing-masing memiliki warna murni. Pendekatan tersebut hanya menciptakan detail yang lebih realistis, dan memungkinkan pendekatan gabungan-jala (google Unity VoxelForm). Semakin halus voxel Anda, semakin halus detail tekstur yang dihasilkan. Contoh: memodelkan dasar sungai sebagai batu (abu-abu). Konversikan setiap piksel dalam jarak x permukaan, menjadi pasir, dengan mengatur voxels ini memiliki material = "pasir"; mereka kemudian dapat dianggap berwarna pasir. Selain itu, ini juga dapat mempengaruhi interaktivitas fisik mereka, sehingga pasir dapat dipindahkan oleh air, atau digali.
Insinyur
33

Cara terbaik untuk menghasilkan medan voxel yang menarik adalah dengan peta kerapatan derau Perlin. Daripada menggunakan peta kebisingan Perlin 2D yang mendefinisikan tinggi dunia 3D, gunakan peta kebisingan Perlin 3D. Bobot peta sehingga nilai-nilai yang lebih dekat ke bawah akan lebih cenderung solid, dan nilai-nilai yang lebih dekat ke atas pasti adalah udara. Ini memberikan ketinggian dunia Anda, tetapi juga memungkinkan untuk overhang dan gua, mirip dengan medan Minecraft , karena tampilan sisi ini dari sepotong medan menunjukkan:

Dunia dengan overhang

Dari sini Anda dapat menguji pulau-pulau terapung, atau menambahkan sistem gua menggunakan kebisingan fraktal:

Dunia dengan sistem gua

Gambar-gambar di atas dan ide-ide sistem gua berasal dari posting blog yang luar biasa ini . Anda dapat mempelajari semua tentang kebisingan Perlin di sini , dan ada beberapa kode sampel untuk membantu Anda memulai di sini .

dlras2
sumber
4

Jawaban lain di sini sangat bagus, tetapi saya mengambil pendekatan yang sedikit berbeda.

Saya menghasilkan lingkungan dalam alat pemodelan (3DSMAX), dan membuat oktars yang jarang darinya. Setiap simpul daun kubus, non-kosong adalah voxel. Pada waktu render, saya menggunakan raycasting (diimplementasikan dalam HLSL) untuk menemukan voxel mana yang menempati pixel mana, dan mengatur pixel ke warna yang disimpan dalam node, yang saya hitung ketika menghasilkan pohon dengan rata-rata nilai tekstur dari model sumber.

Ini memberi Anda banyak manfaat yang bagus - deteksi tabrakan secara gratis, variabel LOD, melihat ruang culling, dll - dan, selain dari raycaster - mudah diimplementasikan.

Sayangnya, hampir tidak mungkin untuk mengirim kode sampel dari telepon.

3Dave
sumber
Memberi +1 untuk alternatif. Meskipun bukan tidak mungkin untuk diterapkan dengan kinerja yang masuk akal, pro jauh lebih besar daripada yang kontra. Voxel raytracing membebani GPU. Aritmatika dan persyaratan yang diperlukan untuk ini sangat mahal, ketika siklus GPU yang sama dapat menerapkan sejumlah efek ruang layar yang mengesankan misalnya. SSAO. Masalah terbesar adalah bahwa raycasting terlihat paling baik dengan beberapa pantulan seperti yang ditemukan dalam radiositas - tidak layak untuk adegan yang terdiri dari jutaan atau miliaran voxel dan di mana setiap segmen ray membutuhkan upaya yang cukup besar untuk memantul dan komposit.
Insinyur
... Inilah sebabnya saya menyebutkan scaline raycasting hanya sebagai tambahan dalam jawaban saya (VoxLap) - bahkan sulit untuk diimplementasikan dengan baik. Jika Anda bisa mendapatkan pendekatan pemindaian vertikal bekerja, biayanya adalah urutan besarnya kurang dari raytracing per-pixel, karena Anda telah mengurangi dimensi proses rendering dari 3D ke 2D. Pendekatan ini saya masih bertahan, meskipun tidak menghalangi solusi pencahayaan yang kompleks mungkin dengan RTRT tradisional Anda.
Insinyur