Terjemahan sub bab buku Core Techniques and Algorithms in Game Programming

 

 

MOUSE

Sejak awal mereka pada akhir 1960-an sebagai perangkat input CAD, mouse telah disesuaikan untuk banyak kegunaan termasuk game komputer. Mereka sangat populer di game PC, tapi game konsol biasanya tidak mendukung mereka. Tidak seperti keyboard atau joystick, mouse tidak hanya menghasilkan tombol atau tombol yang ditekan, tapi 2D posisi juga. Ini menyediakan pilihan yang lebih banyak masukan pada biaya kurva belajar yang lebih tinggi untuk pemain.

Mouse dapat digunakan dalam berbagai skenario, dari unit pengambilan dalam judul strategi real-time untuk populer mouselook ditemukan di sebagian besar penembak orang pertama. Dalam semua kasus, pengoperasian mouse dapat dibagi menjadi transmisi informasi posisional (berkat sensor mouse internal) dan mengirim tekan tombol dan pesan rilis.

Mari kita periksa bagaimana mouse beroperasi di bawah DirectInput. Kode sumber ini sangat mirip dengan keyboard meminta karena DirectInput memperlakukan semua perangkat yang sama. Hal ini menguntungkan bagi programmer karena rincian paling dalam yang tersembunyi. Mari kita asumsikan kita memiliki objek DirectInput utama dan berjalan, dan mulai dengan penciptaan perangkat :

LPDIRECTINPUTDEVICE g_pMouse;

HRESULT             hr;

hr = g_pDI->CreateDevice(GUID_SysMouse, &g_pMouse, NULL);

Seperti yang Anda lihat, sangat mirip dengan meminta keyboard, satu-satunya perbedaan menjadi petunjuk kami untuk meminta perangkat yang diinginkan. Kemudian, format data diatur sebagai berikut:

hr = g_pMouse->SetDataFormat(&c_dfDIMouse);

Dalam hal ini, parameter c_dfDIMouse memberitahu DirectInput kita akan melewati struktur DIMOUSESTATE ke

IDirectInputDevice :: GetDeviceState. Struktur ini memiliki tanda tangan berikut:

typedef struct DIMOUSESTATE {

    LONG lX;

    LONG lY;

    LONG lZ;

    BYTE rgbButtons[4];

} DIMOUSESTATE, *LPDIMOUSESTATE;

Struktur ini mengembalikan X dan posisi Y, dan Z sumbu opsional, yang biasanya ditugaskan untuk roda.

Kemudian, tombol array bekerja seperti array Keyboard. Tombol ditekan jika bit high-order diatur. A

varian dari struktur ini adalah DIMOUSESTATE2, ditetapkan oleh c_dfDIMouse2 parameter. Satu-satunya perbedaan adalah

bahwa yang terakhir mendukung delapan tombol bukannya empat didukung oleh DIMOUSESTATE. Ini terutama

berguna dalam mouse tertentu yang digunakan untuk sistem CAD, misalnya. Setelah format data telah ditetapkan, kita perlu mengatur level kooperatif. Tidak ada kejutan di sini, karena kode tersebut

persis sama dengan versi Keyboard:

hr = g_pMouse-> SetCooperativeLevel (hWnd,

                DISCL_EXCLUSIVE | DISCL_FOREGROUND);

Selain itu, kita perlu untuk mendapatkan siap menggunakan perangkat dengan baris:

g_pMouse-> Acquire ();

Berikut adalah kode sumber penuh di review:

LPDIRECTINPUTDEVICE g_pMouse;

HRESULT hr = g_pDI-> CreateDevice (GUID_SysMouse, & g_pMouse, NULL);

hr = g_pMouse-> SetDataFormat (& c_dfDIMouse);

hr = g_pMouse-> SetCooperativeLevel (hWnd,

                DISCL_EXCLUSIVE | DISCL_FOREGROUND);

g_pMouse-> Acquire ();

Membaca dari mouse ini dicapai dengan panggilan GetDeviceState, yang akan mengembalikan LPDIMOUSESTATE

struktur. Kode sumber akan:

DIMOUSESTATE dims; / / DirectInput ketatanegaraan tikus

ZeroMemory (& meredup, sizeof (meredup));

hr = g_pMouse-> GetDeviceState (sizeof (DIMOUSESTATE), & meredup);

if (FAILED (jam))

{

            hr = g_pMouse-> Acquire ();

sementara (hr == DIERR_INPUTLOST | | hr == DIERR_OTHERAPPHASPRIO | |

hr == DIERR_NOTACQUIRED)

hr = g_pMouse-> Acquire ();

       }

Perhatikan bagaimana saya telah menambahkan kode pencegahan unacquiring untuk menghindari kehilangan jejak mouse kita karena kejadian tak terduga. Selain itu, kode ini sangat mirip dengan membaca keyboard. Untuk mengakses mouse atribut, yang harus kita lakukan adalah:

int MouseX = dims.lX;

int mousey = dims.lY;

bool lbutton = (dims.rgbButtons [0] & 0x80) = 0)!;

Biasanya, tombol 0 ditugaskan untuk tombol kiri mouse, tombol 1 ditugaskan untuk orang yang tepat, dan tombol 2 adalah ditugaskan untuk tombol tengah (jika tersedia). Mengenai posisi, ingat bahwa mouse adalah relatif perangkat penunjuk. Ketika pertama kali diperoleh, posisi mouse adalah ulang ke (0,0). Kemudian, masing-masing membaca baru akan kembali perpindahan dari yang terakhir. Jadi, jika kita menggerakkan mouse vertikal, kita akan melihat perpindahan dalam Y arah. Tetapi ketika kita menghentikan gerakan, nilai tikus membaca akan kembali ke (0,0). Ingat, mouse tidak bekerja dengan posisi melainkan bekerja dengan perpindahan. Terakhir, but not least, mouse biasanya dikonfigurasi poin X begitu negatif ke kiri, dan titik Y positif menjauh dari tubuh kita seperti kita duduk di meja.

Selain itu, ingatlah untuk melepaskan mouse segera setelah Anda selesai menggunakannya. Kode ini lagi sangat mirip dengan kode rilis Keyboard:

if (g_pMouse) g_pMouse-> Unacquire ();

SAFE_RELEASE (g_pMouse);

SAFE_RELEASE (g_pDI);

 

Mouselook

Sebuah penggunaan populer dari mouse adalah untuk menerapkan mouselook klasik yang digunakan dalam banyak penembak orang pertama. mouselook mudah untuk kode setelah Anda memahami bagaimana mouse beroperasi. Yang harus kita lakukan adalah menggunakan kunci mengubah posisi kami, dan menggunakan mouse untuk reorientasi sudut pandang kita. Saya akan menjelaskan efek sepenuhnya, sehingga kita bisa menggabungkan apa yang telah kita pelajari tentang keyboard dan mouse.

Permainan harus memiliki setidaknya empat derajat kebebasan. Kita harus memiliki posisi yang terdiri dari X dan Z nilai, dan kemudian yaw dan sudut pos. Nilai Y sering ditambahkan ke dalam campuran sehingga kita dapat mendaki berbeda ketinggian, tapi gulungan umumnya tidak diperlukan. Kami akan menggunakan pemetaan berikut:

● Tikus: Mouselook

● Panah kiri: memberondong kiri

● Panah kanan: memberondong tepat

● Panah: Maju

● Panah bawah: Mundur

Mari kita fokus pertama pada keyboard dan melupakan orientasi kedua. Dengan asumsi standar DirectInput Keyboard, kita akan membutuhkan kode berikut untuk menerapkan perilaku yang diinginkan:

int strafe = (buffer [DIK_RIGHT] & 0x80) = 0) – (buffer [DIK_LEFT] & 0x80) = 0)!;

! int fwd = (buffer [DIK_UP] & 0x80) = 0) – (buffer [DIK_DOWN] & 0x80) = 0)!;

Perhatikan bagaimana kita telah elegan dikemas kontrol kursor. Dengan mengurangi arah yang berlawanan, kita mendapatkan dua nomor, memberondong dan fwd, dalam kisaran -1 .. 1. Jumlah ini kemudian digunakan untuk menggerakkan posisi kami memperbarui rutin:

pos.x + = fwd * FWDSPEED * elapsed * cos (yaw) +

strafe * STRAFESPEED * elapsed * cos (yaw 3,1416 / 2);

pos.z + = fwd * FWDSPEED * elapsed * sin (yaw) +

strafe * STRAFESPEED * elapsed * sin (yaw 3,1416 / 2);

The fwd dan memberondong variabel mengontrol bagaimana masing-masing anggota dikalikan dengan -1-, 0, atau 1-untuk melakukan yang diinginkan

efek. Sekarang, mari kita merawat pos dan yaw melalui mouse:

yaw + = YAWSPEED * elapsed * dims.lX;

pos + = PITCHSPEED * elapsed * dims.lY;

Jadi sekarang kita memiliki pos.x baru kami, pos.z, yaw, dan struktur pemain pos diperbarui. Jelas, kita perlu menjaga dua perangkat hidup, dan kita perlu mendefinisikan semua konstanta dalam topi untuk mengatur kecepatan yang diinginkan. Perhatikan bagaimana setiap konstan dikalikan dengan faktor waktu berlalu, yang menyimpan waktu yang dibutuhkan untuk membuat frame terakhir.

Dengan cara ini kita memastikan perangkat-independen kinerja. Untuk kelengkapan, di sini adalah source code yang diperlukan untuk menghitung semua parameter kamera spesifik siap untuk dipasang ke OpenGL atau DirectX pipa:

Titik campos (pos.x, pos.y, pos.z);

Titik camlookat (pos.x + cos (yaw) * cos (pitch), pos.y + sin (pitch),

pos.z + sin (yaw) * cos (pitch));

Posisi melihat di perhitungan koordinat hanya pemetaan bola menggunakan pitch dan yaw. Tergantung pada bagaimana kapak Anda ditata, tanda mungkin berubah atau Anda mungkin perlu menambahkan sudut konstan seperti Pi ke pos nilai-nilai.

 

Sumber : Core Techniques and Algorithms in Game Programming –chapter 5 user input -mouse

 

Iklan

Tinggalkan Balasan

Isikan data di bawah atau klik salah satu ikon untuk log in:

Logo WordPress.com

You are commenting using your WordPress.com account. Logout / Ubah )

Gambar Twitter

You are commenting using your Twitter account. Logout / Ubah )

Foto Facebook

You are commenting using your Facebook account. Logout / Ubah )

Foto Google+

You are commenting using your Google+ account. Logout / Ubah )

Connecting to %s