Free look camera 3d
This commit is contained in:
parent
138e946f34
commit
b7e15bf4cd
@ -14,15 +14,17 @@
|
|||||||
|
|
||||||
package game
|
package game
|
||||||
|
|
||||||
import "core:math/linalg"
|
|
||||||
import "core:fmt"
|
import "core:fmt"
|
||||||
|
import "core:math/linalg"
|
||||||
import rl "vendor:raylib"
|
import rl "vendor:raylib"
|
||||||
|
|
||||||
PIXEL_WINDOW_HEIGHT :: 180
|
PIXEL_WINDOW_HEIGHT :: 360
|
||||||
|
|
||||||
Game_Memory :: struct {
|
Game_Memory :: struct {
|
||||||
player_pos: rl.Vector2,
|
player_pos: rl.Vector3,
|
||||||
some_number: int,
|
camera_yaw_pitch: rl.Vector2,
|
||||||
|
camera_speed: f32,
|
||||||
|
mouse_captured: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
g_mem: ^Game_Memory
|
g_mem: ^Game_Memory
|
||||||
@ -31,20 +33,33 @@ game_camera :: proc() -> rl.Camera2D {
|
|||||||
w := f32(rl.GetScreenWidth())
|
w := f32(rl.GetScreenWidth())
|
||||||
h := f32(rl.GetScreenHeight())
|
h := f32(rl.GetScreenHeight())
|
||||||
|
|
||||||
|
return {zoom = h / PIXEL_WINDOW_HEIGHT, target = g_mem.player_pos.xy, offset = {w / 2, h / 2}}
|
||||||
|
}
|
||||||
|
|
||||||
|
camera_rotation_matrix :: proc() -> matrix[3, 3]f32 {
|
||||||
|
return linalg.matrix3_from_euler_angles_xy(g_mem.camera_yaw_pitch.x, g_mem.camera_yaw_pitch.y)
|
||||||
|
}
|
||||||
|
|
||||||
|
camera_forward_vec :: proc() -> rl.Vector3 {
|
||||||
|
rotation_matrix := camera_rotation_matrix()
|
||||||
|
return rotation_matrix * rl.Vector3{0, 0, 1}
|
||||||
|
}
|
||||||
|
|
||||||
|
game_camera_3d :: proc() -> rl.Camera3D {
|
||||||
return {
|
return {
|
||||||
zoom = h/PIXEL_WINDOW_HEIGHT,
|
position = g_mem.player_pos,
|
||||||
target = g_mem.player_pos,
|
up = {0, 1, 0},
|
||||||
offset = { w/2, h/2 },
|
fovy = 60,
|
||||||
|
target = g_mem.player_pos + camera_forward_vec(),
|
||||||
|
projection = .PERSPECTIVE,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ui_camera :: proc() -> rl.Camera2D {
|
ui_camera :: proc() -> rl.Camera2D {
|
||||||
return {
|
return {zoom = f32(rl.GetScreenHeight()) / PIXEL_WINDOW_HEIGHT}
|
||||||
zoom = f32(rl.GetScreenHeight())/PIXEL_WINDOW_HEIGHT,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
update :: proc() {
|
update_free_look_camera :: proc() {
|
||||||
input: rl.Vector2
|
input: rl.Vector2
|
||||||
|
|
||||||
if rl.IsKeyDown(.UP) || rl.IsKeyDown(.W) {
|
if rl.IsKeyDown(.UP) || rl.IsKeyDown(.W) {
|
||||||
@ -60,24 +75,51 @@ update :: proc() {
|
|||||||
input.x += 1
|
input.x += 1
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if rl.IsKeyPressed(.ESCAPE) {
|
||||||
|
if g_mem.mouse_captured {
|
||||||
|
g_mem.mouse_captured = false
|
||||||
|
rl.EnableCursor()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if g_mem.mouse_captured {
|
||||||
|
g_mem.camera_yaw_pitch += rl.GetMouseDelta().yx * -1 * 0.001
|
||||||
|
}
|
||||||
|
|
||||||
|
g_mem.camera_speed += rl.GetMouseWheelMove() * 0.01
|
||||||
|
g_mem.camera_speed = linalg.clamp(g_mem.camera_speed, 0.01, 10)
|
||||||
|
|
||||||
|
rotation_matrix := camera_rotation_matrix()
|
||||||
|
forward := -rotation_matrix[2]
|
||||||
|
right := linalg.cross(rl.Vector3{0, 1, 0}, forward)
|
||||||
|
|
||||||
input = linalg.normalize0(input)
|
input = linalg.normalize0(input)
|
||||||
g_mem.player_pos += input * rl.GetFrameTime() * 100
|
g_mem.player_pos += (input.x * right + input.y * forward) * g_mem.camera_speed
|
||||||
g_mem.some_number += 1
|
}
|
||||||
|
|
||||||
|
update :: proc() {
|
||||||
|
if rl.IsMouseButtonPressed(.LEFT) {
|
||||||
|
g_mem.mouse_captured = true
|
||||||
|
rl.DisableCursor()
|
||||||
|
}
|
||||||
|
|
||||||
|
update_free_look_camera()
|
||||||
}
|
}
|
||||||
|
|
||||||
draw :: proc() {
|
draw :: proc() {
|
||||||
rl.BeginDrawing()
|
rl.BeginDrawing()
|
||||||
rl.ClearBackground(rl.BLACK)
|
rl.ClearBackground(rl.BLACK)
|
||||||
|
|
||||||
rl.BeginMode2D(game_camera())
|
{
|
||||||
rl.DrawRectangleV(g_mem.player_pos, {10, 20}, rl.WHITE)
|
rl.BeginMode3D(game_camera_3d())
|
||||||
rl.DrawRectangleV({20, 20}, {10, 10}, rl.RED)
|
defer rl.EndMode3D()
|
||||||
rl.DrawRectangleV({-30, -20}, {10, 10}, rl.GREEN)
|
|
||||||
rl.EndMode2D()
|
rl.DrawBoundingBox(rl.BoundingBox{min = -1, max = 1}, {255, 0, 0, 255})
|
||||||
|
}
|
||||||
|
|
||||||
rl.BeginMode2D(ui_camera())
|
rl.BeginMode2D(ui_camera())
|
||||||
// Note: main_hot_reload.odin clears the temp allocator at end of frame.
|
// Note: main_hot_reload.odin clears the temp allocator at end of frame.
|
||||||
rl.DrawText(fmt.ctprintf("some_number: %v\nplayer_pos: %v", g_mem.some_number, g_mem.player_pos), 5, 5, 8, rl.WHITE)
|
rl.DrawText(fmt.ctprintf("player_pos: %v", g_mem.player_pos), 5, 5, 8, rl.WHITE)
|
||||||
rl.EndMode2D()
|
rl.EndMode2D()
|
||||||
|
|
||||||
rl.EndDrawing()
|
rl.EndDrawing()
|
||||||
@ -94,6 +136,7 @@ game_update :: proc() -> bool {
|
|||||||
game_init_window :: proc() {
|
game_init_window :: proc() {
|
||||||
rl.SetConfigFlags({.WINDOW_RESIZABLE, .VSYNC_HINT})
|
rl.SetConfigFlags({.WINDOW_RESIZABLE, .VSYNC_HINT})
|
||||||
rl.InitWindow(1280, 720, "Odin + Raylib + Hot Reload template!")
|
rl.InitWindow(1280, 720, "Odin + Raylib + Hot Reload template!")
|
||||||
|
rl.SetExitKey(.KEY_NULL)
|
||||||
rl.SetWindowPosition(200, 200)
|
rl.SetWindowPosition(200, 200)
|
||||||
rl.SetTargetFPS(500)
|
rl.SetTargetFPS(500)
|
||||||
}
|
}
|
||||||
@ -102,9 +145,7 @@ game_init_window :: proc() {
|
|||||||
game_init :: proc() {
|
game_init :: proc() {
|
||||||
g_mem = new(Game_Memory)
|
g_mem = new(Game_Memory)
|
||||||
|
|
||||||
g_mem^ = Game_Memory {
|
g_mem^ = Game_Memory{}
|
||||||
some_number = 100,
|
|
||||||
}
|
|
||||||
|
|
||||||
game_hot_reloaded(g_mem)
|
game_hot_reloaded(g_mem)
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user