Pertama-tama, saya tahu persis apa masalah menggambar saya, dan saya memiliki berbagai ide tentang cara pendekatan untuk menyelesaikannya. Saya di sini untuk mencari cara menyesuaikan frame mana yang digambar sehingga "ilusi" isometrik dipertahankan.
Saya sedang menulis game 2D, pandangan burung yang berlangsung di luar angkasa. Saya mencoba menggunakan grafik isometrik di dunia di mana Up adalah Utara, tidak ada putaran dunia game seperti di game isometrik tradisional (ingat, permainan berlangsung di ruang angkasa, tidak ada medan). Berikut adalah contoh sprite yang saya coba gunakan: http://cell.stat-life.com/images/stories/AsteroidOutpost/Spaceship64.png Diputar 64 kali tentang sumbu vertikalnya sendiri dengan sudut pandang 35 derajat (alias, iso). Gambar itu dihasilkan, jadi ini bisa diubah.
Demi kejelasan, saya telah menentukan bahwa Utara (Atas) adalah 0 derajat, dan Timur (Kanan) adalah 90.
Masalah saya adalah sprite saya tidak selalu terlihat seperti menghadap ke tempat permainan berpikir itu karena perbedaan dalam pesawat 3D yang digunakan. Tidak yakin apakah saya menggunakan terminologi dengan benar, tetapi pesawat ruang angkasa saya diputar pada satu pesawat, dan pesawat pandangan mengharapkan hal-hal yang akan diputar pada pesawatnya sendiri. Berikut gambaran masalah:
http://cell.stat-life.com/images/stories/AsteroidOutpost/ProjectionIssue.png Di sebelah kiri, saya memiliki tampilan samping, di sebelah kanan saya memiliki tampilan top-down. Di bagian atas, saya memiliki tampilan kapal ruang / sprite dunia. Di bagian bawah, saya memiliki apa yang tampak seperti sprite ketika ditarik ke layar.
Di kanan atas adalah versi yang disederhanakan tentang bagaimana pesawat ruang angkasa saya diputar (pemisahan derajat antara setiap frame). Di kanan bawah adalah sudut yang sprite tampak menghadap ketika sudut tertentu digambar di layar. Masalahnya paling jelas sekitar 45 derajat. Berikut adalah gambar yang dilapis dengan garis "layar pesawat" yang mengarah ke arah yang seharusnya dihadapi kapal: http://cell.stat-life.com/images/stories/AsteroidOutpost/Spaceship64RedLine.png Garis merah harus selalu menunjuk ke arah yang sama persis seperti kapal, tetapi seperti yang Anda lihat, masalah proyeksi menyebabkan masalah. Saya harap saya menggambarkan masalah ini dengan cukup baik.
EDIT: Garis merah diputar pada bidang layar, sedangkan kapal ruang diputar pada "bidang pesawat", maka perbedaan besar antara sudut kapal dan sudut layar ketika digambar. AKHIR EDIT
Terlihat agak aneh ketika kapal ini menembakkan sinar laser ke target yang mengarah ke satu sisi, padahal seharusnya menembak lurus ke depan.
Jadi ... solusi yang saya buat adalah:
- Berhentilah mencoba memalsukan tampilan isometrik, pergi besar atau pulang. Putar duniaku. (PS: ini akan memperbaiki masalah saya, kan?)
- Ubah lembar sprite saya (entah bagaimana) untuk memiliki bingkai yang mewakili "sudut layar" di mana model akan dilihat. Jadi ketika saya meminta gambar 45 derajat, itu akan benar-benar terlihat seperti menghadap 45 derajat di layar.
- Ubah sistem rendering sprite saya untuk mengambil bingkai yang berbeda dari lembar sprite (entah bagaimana), mengetahui bahwa mengambil frame "normal" akan terlihat lucu. Jadi, alih-alih meraih frame 45 derajat, ia akan mengambil ... frame 33 derajat (hanya menebak) sehingga terlihat benar bagi pengguna.
- Cukup gunakan 3D! Jauh lebih mudah
Untuk satu: Solusi mana yang akan Anda rekomendasikan? Saya condong ke arah 2, meskipun saya tahu itu salah. Ingat bahwa saya memiliki akses penuh ke alat pembangkit sprite. Metode 3 akan menjadi pilihan kedua saya. Kedua metode ini hanya mengharuskan saya menerapkan beberapa matematika ke sudut (s) untuk mendapatkan hasil yang saya inginkan. Btw, saya menambahkan # 4 di sana sebagai lelucon, saya tidak ingin pindah ke 3D.
Untuk dua: Menggunakan metode 2 atau 3, bagaimana cara menyesuaikan sudut input atau output? Saya tidak terlalu bagus dengan proyeksi 3D, dan matriks 3D (apalagi matriks 2D), dan apa pun matematika lain yang dapat digunakan untuk mencapai hasil yang saya inginkan.
Berpikir keras di sini: jika saya mengambil unit vektor menghadap ke arah yang saya ingin kapal melihat (di layar pesawat), kemudian proyeksikan itu ke pesawat kapal, lalu cari tahu apa sudut antara garis yang diproyeksikan dan garis pesawat utara adalah, saya harus memiliki sudut grafik kapal yang ingin saya tampilkan. Baik? (solusi untuk # 3?) Man ... Saya tidak bisa menyelesaikannya.
EDIT:
Saya tahu masalahnya sulit untuk divisualisasikan dengan gambar statis, jadi saya telah memenuhi Sprite Library Visual Tester saya untuk menampilkan masalah: http://cell.stat-life.com/downloads/SpriteLibVisualTest.zip Diperlukan XNA 4.0 Aplikasi ini cukup memutar sprite, dan menggambar garis dari titik pusatnya ke luar pada sudut permainan berpikir kapal harus menghadap.
EDIT 8 September
Melanjutkan paragraf "berpikir keras": Alih-alih menggunakan proyeksi (karena terlihat keras), saya berpikir saya bisa mengambil vektor satuan yang menghadap ke utara (0x, 1y, 0z), gunakan matriks untuk memutarnya ke sudut sprite sebenarnya menghadap, kemudian putar lagi dari "pesawat melihat" ke luar ke "pesawat sprite" di sekitar sumbu X, lalu ... ratakan? vektor (pada dasarnya memproyeksikannya) kembali ke bidang tampilan dengan hanya menggunakan X dan Y (mengabaikan Z). Kemudian menggunakan vektor rata yang baru, saya bisa menentukan sudutnya dan menggunakannya untuk ... sesuatu. Saya akan berpikir lebih banyak nanti.
EDIT 8 September (2)
Saya mencoba mengikuti ide saya dari atas dengan beberapa keberhasilan, yay! Jadi ... untuk mendapatkan garis merah agar terlihat seperti langsung keluar dari pesawat ruang angkasa saya (tujuan pengujian saja), saya melakukan yang berikut:
Vector3 vect = new Vector3(0, 1, 0);
vect = Vector3.Transform(vect, Matrix.CreateRotationZ(rotation));
vect = Vector3.Transform(vect, Matrix.CreateRotationY((float)((Math.PI / 2) - MathHelper.ToRadians(AngleFromHorizon))));
Vector2 flattenedVect = new Vector2(vect.X, vect.Y);
float adjustedRotation = (float)(getAngle(flattenedVect.X, flattenedVect.Y));
Di mana rotation
sudut layar dan adjustedRotation
sekarang sudut layar terlihat pada bidang sprite. Saya tidak tahu mengapa saya perlu memutar Y alih-alih X, tapi itu mungkin ada hubungannya dengan 3D yang tidak saya ketahui.
Jadi, sekarang saya memiliki informasi tambahan, tetapi bagaimana saya menggunakan ini untuk memilih kerangka yang lebih tepat? Mungkin alih-alih memutar dari bidang pandangan ke bidang sprite, lalu memproyeksikan kembali, saya harus mencoba melakukannya sebaliknya. Inilah sprite saya dengan garis merah yang disesuaikan, tetapi yang ingin saya lakukan adalah menyesuaikan modelnya, bukan garisnya: http://cell.stat-life.com/images/stories/AsteroidOutpost/Spaceship64RedLineCorrected.png
Sunting 9 September
HORAY! Sudah diperbaiki! Saya akan menjelaskan apa yang saya lakukan untuk memperbaikinya:
Saya mengikuti saran eBusiness dan "diperas" oleh sistem koordinat dunia (atau ditarik ...?). Ini pada dasarnya solusi # 1, meskipun saya mendapat kesan bahwa saya harus memutar sistem koordinat dunia saya sehubungan dengan sistem coord layar. Tidak benar! Naik masih + y, dan Kanan masih + x. Saya memodifikasi metode WorldToScreen dan ScreenToWorld saya untuk mengkonversi antara dunia dan koordinat layar dengan benar. Metode ini mungkin tidak optimal, tetapi hanya ada dua metode dalam basis kode saya yang harus diubah.
public Vector2 ScreenToWorld(float x, float y)
{
float deltaX = x - (size.Width / 2f);
float deltaY = y - (size.Height / 2f);
deltaX = deltaX * scaleFactor / (float)Math.Sqrt(3);
deltaY = deltaY * scaleFactor;
return new Vector2(focusWorldPoint.X + deltaX, focusWorldPoint.Y + deltaY);
}
public Vector2 WorldToScreen(float x, float y)
{
float deltaX = x - focusWorldPoint.X;
float deltaY = y - focusWorldPoint.Y;
deltaX = deltaX / scaleFactor * (float)Math.Sqrt(3);
deltaY = deltaY / scaleFactor;
return new Vector2(size.Width / 2f + deltaX, size.Height / 2f + deltaY);
}
Itu dia! Mengubah kedua metode tersebut memengaruhi segalanya: apa yang saya lihat, di mana objek di mana ditarik, di mana saya mengklik, semuanya. Pesawat ruang angkasa saya sekarang melihat langsung ke target yang ditembakkan, dan semuanya jatuh ke tempatnya. Saya akan bereksperimen dengan proyeksi ortografi, melihat apakah itu membuat semuanya tampak lebih 'nyata'.