UPDATE Kesalahan di sini sangat sederhana. Saya telah melewatkan konversi radian ke derajat. Tidak perlu membaca semuanya jika Anda memiliki masalah lain.
Saya melihat beberapa tutorial tentang ini dan ketika saya pikir saya mengerti saya mencoba menerapkan kamera berbasis angka empat. Masalahnya adalah itu tidak berfungsi dengan benar, setelah berputar kira-kira. 10 derajat melompat kembali ke -10 derajat. Saya tidak tahu apa yang salah. Saya menggunakan openTK dan sudah memiliki kelas angka empat. Saya seorang noob di OpenGL, saya melakukan ini hanya untuk bersenang-senang, dan tidak benar-benar mengerti angka empat, jadi mungkin saya melakukan sesuatu yang bodoh di sini. Berikut ini beberapa kode: (Sebenarnya hampir semua kode kecuali metode yang memuat dan menggambar vbo (diambil dari sampel OpenTK yang menunjukkan vbo-s))
Saya memuat kubus ke vbo dan menginisialisasi angka empat untuk kamera
protected override void OnLoad(EventArgs e) {
base.OnLoad(e);
cameraPos = new Vector3(0, 0, 7);
cameraRot = Quaternion.FromAxisAngle(new Vector3(0,0,-1), 0);
GL.ClearColor(System.Drawing.Color.MidnightBlue);
GL.Enable(EnableCap.DepthTest);
vbo = LoadVBO(CubeVertices, CubeElements);
}
Saya memuat proyeksi perspektif di sini. Ini dimuat di awal dan setiap kali saya mengubah ukuran jendela.
protected override void OnResize(EventArgs e) {
base.OnResize(e);
GL.Viewport(0, 0, Width, Height);
float aspect_ratio = Width / (float)Height;
Matrix4 perpective = Matrix4.CreatePerspectiveFieldOfView(MathHelper.PiOver4, aspect_ratio, 1, 64);
GL.MatrixMode(MatrixMode.Projection);
GL.LoadMatrix(ref perpective);
}
Di sini saya mendapatkan nilai rotasi terakhir dan membuat angka empat baru yang hanya mewakili rotasi terakhir dan melipatgandakannya dengan angka empat kamera. Setelah ini saya mengubah ini menjadi sumbu-sudut sehingga opengl dapat menggunakannya. (Ini adalah bagaimana saya memahaminya dari beberapa tutorial angka empat online)
protected override void OnRenderFrame(FrameEventArgs e) {
base.OnRenderFrame(e);
GL.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit);
double speed = 1;
double rx = 0, ry = 0;
if (Keyboard[Key.A]) {
ry = -speed * e.Time;
}
if (Keyboard[Key.D]) {
ry = +speed * e.Time;
}
if (Keyboard[Key.W]) {
rx = +speed * e.Time;
}
if (Keyboard[Key.S]) {
rx = -speed * e.Time;
}
Quaternion tmpQuat = Quaternion.FromAxisAngle(new Vector3(0,1,0), (float)ry);
cameraRot = tmpQuat * cameraRot;
cameraRot.Normalize();
GL.MatrixMode(MatrixMode.Modelview);
GL.LoadIdentity();
Vector3 axis;
float angle;
cameraRot.ToAxisAngle(out axis, out angle);
//////////////////////////////////////////////////////////////////////
// THIS IS WHAT I DID WRONG: I NEED TO CONVERT FROM RADIANS TO DEGREES
//////////////////////////////////////////////////////////////////////
//BEFORE
//GL.Rotate(angle, axis);
//AFTER
GL.Rotate(angle * (float)180.0/(float)Math.PI, axis);
GL.Translate(-cameraPos);
Draw(vbo);
SwapBuffers();
}
Berikut adalah 2 gambar untuk menjelaskan lebih baik: Saya memutar beberapa saat dan dari ini:
itu melompat ke ini
Bantuan apa pun dihargai.
Update1 : Saya menambahkan ini ke penulis aliran yang menulis ke file:
sw.WriteLine("camerarot: X:{0} Y:{1} Z:{2} W:{3} L:{4}", cameraRot.X, cameraRot.Y, cameraRot.Z, cameraRot.W, cameraRot.Length);
sw.WriteLine("ry: {0}", ry);
Log tersedia di sini: http://www.pasteall.org/26133/text . Pada baris 770 kubus melompat dari kanan ke kiri, ketika camerarot.Y mengubah tanda. Saya tidak tahu apakah ini normal.
Update2 Ini adalah proyek lengkap.
Jawaban:
Meskipun Anda belum menunjukkan kode yang diperlukan untuk memverifikasi asumsi saya di sini, saya hampir dapat menjamin bahwa masalah Anda sebenarnya adalah baris ini:
mengembalikan sudut nilai dinyatakan dalam radian , sementara
inginkan sudut disediakan dalam derajat .
Untuk memperbaikinya, Anda perlu mengonversi nilai sudut saat meneruskannya ke GL.Rotate (), seperti ini:
sumber
Math.Pi
konstanta yang tersedia, yang harus digunakan sebagai preferensi terhadap nilai 3.141593 literal yang saya gunakan dalam perhitungan akhir itu.Jangan. Mungkin kelihatannya lebih sulit memiliki kamera yang dapat dimanipulasi seperti objek pemandangan lainnya, tetapi dalam jangka panjang lebih baik memiliki kamera di mana Anda dapat menentukan posisi, arah mata, dan vektor ke atas. Terutama ketika Anda mulai pemrograman model gerak itu benar-benar menyebalkan untuk bekerja dengan angka empat.
sumber
Tidak tahu banyak tentang internal OpenTK. Dalam pengalaman saya, saya tidak melihat perpustakaan matematika dengan implementasi quat yang tepat yang menjaga presisi (mesin) yang dibutuhkan, karena semuanya mempengaruhi kesalahan e ^ 2-e ^ 3. Jadi efek yang Anda lihat: presisi (dan nilai epsilon) adalah sekitar 10 ^ -5, dan 'melompat' mendekati nol. Ini tebakan saya :)
sumber