initial commit
This commit is contained in:
parent
777a38d916
commit
8fc2fcd007
|
@ -0,0 +1,57 @@
|
|||
# ---> C
|
||||
# Prerequisites
|
||||
*.d
|
||||
|
||||
# Object files
|
||||
*.o
|
||||
*.ko
|
||||
*.elf
|
||||
*.data
|
||||
*.js
|
||||
*.wasm
|
||||
*.html
|
||||
|
||||
# Linker output
|
||||
*.ilk
|
||||
*.map
|
||||
*.exp
|
||||
|
||||
# Precompiled Headers
|
||||
*.gch
|
||||
*.pch
|
||||
|
||||
# Libraries
|
||||
*.lib
|
||||
*.a
|
||||
*.la
|
||||
*.lo
|
||||
|
||||
# Shared objects (inc. Windows DLLs)
|
||||
*.dll
|
||||
*.so
|
||||
*.so.*
|
||||
*.dylib
|
||||
|
||||
# Executables
|
||||
*.exe
|
||||
*.out
|
||||
*.app
|
||||
*.i*86
|
||||
*.x86_64
|
||||
*.hex
|
||||
|
||||
# Debug files
|
||||
*.dSYM/
|
||||
*.su
|
||||
*.idb
|
||||
*.pdb
|
||||
|
||||
# Kernel Module Compile Results
|
||||
*.mod*
|
||||
*.cmd
|
||||
.tmp_versions/
|
||||
modules.order
|
||||
Module.symvers
|
||||
Mkfile.old
|
||||
dkms.conf
|
||||
|
|
@ -0,0 +1,481 @@
|
|||
#**************************************************************************************************
|
||||
#
|
||||
# raylib makefile for Desktop platforms, Raspberry Pi, Android and HTML5
|
||||
#
|
||||
# Copyright (c) 2013-2023 Ramon Santamaria (@raysan5)
|
||||
#
|
||||
# This software is provided "as-is", without any express or implied warranty. In no event
|
||||
# will the authors be held liable for any damages arising from the use of this software.
|
||||
#
|
||||
# Permission is granted to anyone to use this software for any purpose, including commercial
|
||||
# applications, and to alter it and redistribute it freely, subject to the following restrictions:
|
||||
#
|
||||
# 1. The origin of this software must not be misrepresented; you must not claim that you
|
||||
# wrote the original software. If you use this software in a product, an acknowledgment
|
||||
# in the product documentation would be appreciated but is not required.
|
||||
#
|
||||
# 2. Altered source versions must be plainly marked as such, and must not be misrepresented
|
||||
# as being the original software.
|
||||
#
|
||||
# 3. This notice may not be removed or altered from any source distribution.
|
||||
#
|
||||
#**************************************************************************************************
|
||||
|
||||
.PHONY: all clean run
|
||||
|
||||
# Define required environment variables
|
||||
#------------------------------------------------------------------------------------------------
|
||||
# Define target platform: PLATFORM_DESKTOP, PLATFORM_RPI, PLATFORM_DRM, PLATFORM_ANDROID, PLATFORM_WEB
|
||||
PLATFORM ?= PLATFORM_DESKTOP
|
||||
|
||||
# Define project variables
|
||||
PROJECT_NAME ?= project_verne
|
||||
PROJECT_VERSION ?= 1.0
|
||||
PROJECT_BUILD_PATH ?= .
|
||||
|
||||
RAYLIB_PATH ?= ~/lib/raylib
|
||||
|
||||
# Locations of raylib.h and libraylib.a/libraylib.so
|
||||
# NOTE: Those variables are only used for PLATFORM_OS: LINUX, BSD
|
||||
RAYLIB_INCLUDE_PATH ?= /usr/local/include
|
||||
RAYLIB_LIB_PATH ?= /usr/local/lib
|
||||
|
||||
# Library type compilation: STATIC (.a) or SHARED (.so/.dll)
|
||||
RAYLIB_LIBTYPE ?= STATIC
|
||||
|
||||
# Build mode for project: DEBUG or RELEASE
|
||||
BUILD_MODE ?= RELEASE
|
||||
|
||||
# Use Wayland display server protocol on Linux desktop (by default it uses X11 windowing system)
|
||||
# NOTE: This variable is only used for PLATFORM_OS: LINUX
|
||||
USE_WAYLAND_DISPLAY ?= FALSE
|
||||
|
||||
# PLATFORM_WEB: Default properties
|
||||
BUILD_WEB_ASYNCIFY ?= TRUE
|
||||
BUILD_WEB_SHELL ?= minshell.html
|
||||
BUILD_WEB_HEAP_SIZE ?= 134217728
|
||||
BUILD_WEB_RESOURCES ?= TRUE
|
||||
BUILD_WEB_RESOURCES_PATH ?= assets
|
||||
|
||||
# Use cross-compiler for PLATFORM_RPI
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
USE_RPI_CROSS_COMPILER ?= FALSE
|
||||
ifeq ($(USE_RPI_CROSS_COMPILER),TRUE)
|
||||
RPI_TOOLCHAIN ?= C:/SysGCC/Raspberry
|
||||
RPI_TOOLCHAIN_SYSROOT ?= $(RPI_TOOLCHAIN)/arm-linux-gnueabihf/sysroot
|
||||
endif
|
||||
endif
|
||||
|
||||
# Determine PLATFORM_OS in case PLATFORM_DESKTOP selected
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
# No uname.exe on MinGW!, but OS=Windows_NT on Windows!
|
||||
# ifeq ($(UNAME),Msys) -> Windows
|
||||
ifeq ($(OS),Windows_NT)
|
||||
PLATFORM_OS = WINDOWS
|
||||
ifndef PLATFORM_SHELL
|
||||
PLATFORM_SHELL = cmd
|
||||
endif
|
||||
else
|
||||
UNAMEOS = $(shell uname)
|
||||
ifeq ($(UNAMEOS),Linux)
|
||||
PLATFORM_OS = LINUX
|
||||
endif
|
||||
ifeq ($(UNAMEOS),FreeBSD)
|
||||
PLATFORM_OS = BSD
|
||||
endif
|
||||
ifeq ($(UNAMEOS),OpenBSD)
|
||||
PLATFORM_OS = BSD
|
||||
endif
|
||||
ifeq ($(UNAMEOS),NetBSD)
|
||||
PLATFORM_OS = BSD
|
||||
endif
|
||||
ifeq ($(UNAMEOS),DragonFly)
|
||||
PLATFORM_OS = BSD
|
||||
endif
|
||||
ifeq ($(UNAMEOS),Darwin)
|
||||
PLATFORM_OS = OSX
|
||||
endif
|
||||
ifndef PLATFORM_SHELL
|
||||
PLATFORM_SHELL = sh
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
UNAMEOS = $(shell uname)
|
||||
ifeq ($(UNAMEOS),Linux)
|
||||
PLATFORM_OS = LINUX
|
||||
endif
|
||||
ifndef PLATFORM_SHELL
|
||||
PLATFORM_SHELL = sh
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_DRM)
|
||||
UNAMEOS = $(shell uname)
|
||||
ifeq ($(UNAMEOS),Linux)
|
||||
PLATFORM_OS = LINUX
|
||||
endif
|
||||
ifndef PLATFORM_SHELL
|
||||
PLATFORM_SHELL = sh
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
ifeq ($(OS),Windows_NT)
|
||||
PLATFORM_OS = WINDOWS
|
||||
ifndef PLATFORM_SHELL
|
||||
PLATFORM_SHELL = cmd
|
||||
endif
|
||||
else
|
||||
UNAMEOS = $(shell uname)
|
||||
ifeq ($(UNAMEOS),Linux)
|
||||
PLATFORM_OS = LINUX
|
||||
endif
|
||||
ifeq ($(UNAMEOS),Darwin)
|
||||
PLATFORM_OS = OSX
|
||||
endif
|
||||
ifndef PLATFORM_SHELL
|
||||
PLATFORM_SHELL = sh
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
|
||||
# Default path for raylib on Raspberry Pi
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
RAYLIB_PATH ?= /home/pi/raylib
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_DRM)
|
||||
RAYLIB_PATH ?= /home/pi/raylib
|
||||
endif
|
||||
|
||||
# Define raylib release directory for compiled library
|
||||
RAYLIB_RELEASE_PATH ?= $(RAYLIB_PATH)/src
|
||||
|
||||
# Define default C compiler: CC
|
||||
#------------------------------------------------------------------------------------------------
|
||||
CC = gcc
|
||||
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),OSX)
|
||||
# OSX default compiler
|
||||
CC = clang
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),BSD)
|
||||
# FreeBSD, OpenBSD, NetBSD, DragonFly default compiler
|
||||
CC = clang
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
ifeq ($(USE_RPI_CROSS_COMPILER),TRUE)
|
||||
# Define RPI cross-compiler
|
||||
#CC = armv6j-hardfloat-linux-gnueabi-gcc
|
||||
CC = $(RPI_TOOLCHAIN)/bin/arm-linux-gnueabihf-gcc
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
# HTML5 emscripten compiler
|
||||
# WARNING: To compile to HTML5, code must be redesigned
|
||||
# to use emscripten.h and emscripten_set_main_loop()
|
||||
CC = emcc
|
||||
endif
|
||||
|
||||
# Define default make program: MAKE
|
||||
#------------------------------------------------------------------------------------------------
|
||||
MAKE ?= make
|
||||
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
||||
MAKE = mingw32-make
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_ANDROID)
|
||||
MAKE = mingw32-make
|
||||
endif
|
||||
|
||||
# Define compiler flags: CFLAGS
|
||||
#------------------------------------------------------------------------------------------------
|
||||
# -O1 defines optimization level
|
||||
# -g include debug information on compilation
|
||||
# -s strip unnecessary data from build
|
||||
# -Wall turns on most, but not all, compiler warnings
|
||||
# -std=c99 defines C language mode (standard C from 1999 revision)
|
||||
# -std=gnu99 defines C language mode (GNU C from 1999 revision)
|
||||
# -Wno-missing-braces ignore invalid warning (GCC bug 53119)
|
||||
# -Wno-unused-value ignore unused return values of some functions (i.e. fread())
|
||||
# -D_DEFAULT_SOURCE use with -std=c99 on Linux and PLATFORM_WEB, required for timespec
|
||||
CFLAGS = -std=c99 -Wall -Wno-missing-braces -Wunused-result -D_DEFAULT_SOURCE
|
||||
|
||||
ifeq ($(BUILD_MODE),DEBUG)
|
||||
CFLAGS += -g -D_DEBUG
|
||||
else
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
ifeq ($(BUILD_WEB_ASYNCIFY),TRUE)
|
||||
CFLAGS += -O3
|
||||
else
|
||||
CFLAGS += -Os
|
||||
endif
|
||||
else
|
||||
CFLAGS += -s -O2
|
||||
endif
|
||||
endif
|
||||
|
||||
# Additional flags for compiler (if desired)
|
||||
#CFLAGS += -Wextra -Wmissing-prototypes -Wstrict-prototypes
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
ifeq ($(RAYLIB_LIBTYPE),STATIC)
|
||||
CFLAGS += -D_DEFAULT_SOURCE
|
||||
endif
|
||||
ifeq ($(RAYLIB_LIBTYPE),SHARED)
|
||||
# Explicitly enable runtime link to libraylib.so
|
||||
CFLAGS += -Wl,-rpath,$(RAYLIB_RELEASE_PATH)
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
CFLAGS += -std=gnu99
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_DRM)
|
||||
CFLAGS += -std=gnu99 -DEGL_NO_X11
|
||||
endif
|
||||
|
||||
# Define include paths for required headers: INCLUDE_PATHS
|
||||
# NOTE: Some external/extras libraries could be required (stb, physac, easings...)
|
||||
#------------------------------------------------------------------------------------------------
|
||||
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/src -I$(RAYLIB_PATH)/src/external -I$(RAYLIB_PATH)/src/extras
|
||||
|
||||
# Define additional directories containing required header files
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),BSD)
|
||||
INCLUDE_PATHS += -I$(RAYLIB_INCLUDE_PATH)
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
INCLUDE_PATHS += -I$(RAYLIB_INCLUDE_PATH)
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
INCLUDE_PATHS += -I$(RPI_TOOLCHAIN_SYSROOT)/opt/vc/include
|
||||
INCLUDE_PATHS += -I$(RPI_TOOLCHAIN_SYSROOT)/opt/vc/include/interface/vmcs_host/linux
|
||||
INCLUDE_PATHS += -I$(RPI_TOOLCHAIN_SYSROOT)/opt/vc/include/interface/vcos/pthreads
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_DRM)
|
||||
INCLUDE_PATHS += -I/usr/include/libdrm
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
INCLUDE_PATHS += -I$(EMSCRIPTEN_PATH)/cache/sysroot/include
|
||||
endif
|
||||
|
||||
# Define library paths containing required libs: LDFLAGS
|
||||
#------------------------------------------------------------------------------------------------
|
||||
LDFLAGS = -L. -L$(RAYLIB_RELEASE_PATH) -L$(RAYLIB_PATH)/src
|
||||
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
||||
# NOTE: The resource .rc file contains windows executable icon and properties
|
||||
LDFLAGS += $(RAYLIB_PATH)/src/raylib.rc.data
|
||||
# -Wl,--subsystem,windows hides the console window
|
||||
ifeq ($(BUILD_MODE), RELEASE)
|
||||
LDFLAGS += -Wl,--subsystem,windows
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
LDFLAGS += -L$(RAYLIB_LIB_PATH)
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),BSD)
|
||||
LDFLAGS += -Lsrc -L$(RAYLIB_LIB_PATH)
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
# -Os # size optimization
|
||||
# -O2 # optimization level 2, if used, also set --memory-init-file 0
|
||||
# -s USE_GLFW=3 # Use glfw3 library (context/input management)
|
||||
# -s ALLOW_MEMORY_GROWTH=1 # to allow memory resizing -> WARNING: Audio buffers could FAIL!
|
||||
# -s TOTAL_MEMORY=16777216 # to specify heap memory size (default = 16MB) (67108864 = 64MB)
|
||||
# -s USE_PTHREADS=1 # multithreading support
|
||||
# -s WASM=0 # disable Web Assembly, emitted by default
|
||||
# -s ASYNCIFY # lets synchronous C/C++ code interact with asynchronous JS
|
||||
# -s FORCE_FILESYSTEM=1 # force filesystem to load/save files data
|
||||
# -s ASSERTIONS=1 # enable runtime checks for common memory allocation errors (-O1 and above turn it off)
|
||||
# --profiling # include information for code profiling
|
||||
# --memory-init-file 0 # to avoid an external memory initialization code file (.mem)
|
||||
# --preload-file resources # specify a resources folder for data compilation
|
||||
# --source-map-base # allow debugging in browser with source map
|
||||
LDFLAGS += -s USE_GLFW=3 -s TOTAL_MEMORY=$(BUILD_WEB_HEAP_SIZE) -s FORCE_FILESYSTEM=1 -s ALLOW_MEMORY_GROWTH=1
|
||||
|
||||
# Build using asyncify
|
||||
ifeq ($(BUILD_WEB_ASYNCIFY),TRUE)
|
||||
LDFLAGS += -s ASYNCIFY
|
||||
endif
|
||||
|
||||
# Add resources building if required
|
||||
ifeq ($(BUILD_WEB_RESOURCES),TRUE)
|
||||
LDFLAGS += --preload-file $(BUILD_WEB_RESOURCES_PATH)
|
||||
endif
|
||||
|
||||
# Add debug mode flags if required
|
||||
ifeq ($(BUILD_MODE),DEBUG)
|
||||
LDFLAGS += -s ASSERTIONS=1 --profiling
|
||||
endif
|
||||
|
||||
LDFLAGS += -lwebsocket.js
|
||||
|
||||
# Define a custom shell .html and output extension
|
||||
LDFLAGS += --shell-file $(BUILD_WEB_SHELL)
|
||||
EXT = .html
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
LDFLAGS += -L$(RPI_TOOLCHAIN_SYSROOT)/opt/vc/lib
|
||||
endif
|
||||
|
||||
# Define libraries required on linking: LDLIBS
|
||||
# NOTE: To link libraries (lib<name>.so or lib<name>.a), use -l<name>
|
||||
#------------------------------------------------------------------------------------------------
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
||||
# Libraries for Windows desktop compilation
|
||||
# NOTE: WinMM library required to set high-res timer resolution
|
||||
LDLIBS = -lraylib -lopengl32 -lgdi32 -lwinmm
|
||||
# Required for physac examples
|
||||
LDLIBS += -static -lpthread
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
# Libraries for Debian GNU/Linux desktop compiling
|
||||
# NOTE: Required packages: libegl1-mesa-dev
|
||||
LDLIBS = -lraylib -lGL -lm -lpthread -ldl -lrt
|
||||
|
||||
# On X11 requires also below libraries
|
||||
LDLIBS += -lX11
|
||||
# NOTE: It seems additional libraries are not required any more, latest GLFW just dlopen them
|
||||
#LDLIBS += -lXrandr -lXinerama -lXi -lXxf86vm -lXcursor
|
||||
|
||||
# On Wayland windowing system, additional libraries requires
|
||||
ifeq ($(USE_WAYLAND_DISPLAY),TRUE)
|
||||
LDLIBS += -lwayland-client -lwayland-cursor -lwayland-egl -lxkbcommon
|
||||
endif
|
||||
# Explicit link to libc
|
||||
ifeq ($(RAYLIB_LIBTYPE),SHARED)
|
||||
LDLIBS += -lc
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),OSX)
|
||||
# Libraries for OSX 10.9 desktop compiling
|
||||
# NOTE: Required packages: libopenal-dev libegl1-mesa-dev
|
||||
LDLIBS = -lraylib -framework OpenGL -framework Cocoa -framework IOKit -framework CoreAudio -framework CoreVideo
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),BSD)
|
||||
# Libraries for FreeBSD, OpenBSD, NetBSD, DragonFly desktop compiling
|
||||
# NOTE: Required packages: mesa-libs
|
||||
LDLIBS = -lraylib -lGL -lpthread -lm
|
||||
|
||||
# On XWindow requires also below libraries
|
||||
LDLIBS += -lX11 -lXrandr -lXinerama -lXi -lXxf86vm -lXcursor
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
# Libraries for Raspberry Pi compiling
|
||||
# NOTE: Required packages: libasound2-dev (ALSA)
|
||||
LDLIBS = -lraylib -lbrcmGLESv2 -lbrcmEGL -lpthread -lrt -lm -lbcm_host -ldl
|
||||
ifeq ($(USE_RPI_CROSS_COMPILER),TRUE)
|
||||
LDLIBS += -lvchiq_arm -lvcos
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_DRM)
|
||||
# Libraries for DRM compiling
|
||||
# NOTE: Required packages: libasound2-dev (ALSA)
|
||||
LDLIBS = -lraylib -lGLESv2 -lEGL -lpthread -lrt -lm -lgbm -ldrm -ldl
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
# Libraries for web (HTML5) compiling
|
||||
LDLIBS = $(RAYLIB_RELEASE_PATH)/libraylib.a
|
||||
endif
|
||||
|
||||
# Define source code object files required
|
||||
#------------------------------------------------------------------------------------------------
|
||||
PROJECT_SOURCE_FILES ?= \
|
||||
main.c \
|
||||
#screen_logo.c \
|
||||
#screen_title.c \
|
||||
#screen_options.c \
|
||||
#screen_gameplay.c \
|
||||
#screen_ending.c
|
||||
|
||||
# Define all object files from source files
|
||||
OBJS = $(patsubst %.c, %.o, $(PROJECT_SOURCE_FILES))
|
||||
|
||||
|
||||
# Define processes to execute
|
||||
#------------------------------------------------------------------------------------------------
|
||||
# For Android platform we call a custom Makefile.Android
|
||||
ifeq ($(PLATFORM),PLATFORM_ANDROID)
|
||||
MAKEFILE_PARAMS = -f Makefile.Android
|
||||
export PROJECT_NAME
|
||||
export PROJECT_SOURCE_FILES
|
||||
else
|
||||
MAKEFILE_PARAMS = $(PROJECT_NAME)
|
||||
endif
|
||||
|
||||
# Default target entry
|
||||
# NOTE: We call this Makefile target or Makefile.Android target
|
||||
all:
|
||||
$(MAKE) $(MAKEFILE_PARAMS)
|
||||
|
||||
# Project target defined by PROJECT_NAME
|
||||
$(PROJECT_NAME): $(OBJS)
|
||||
$(CC) -o $(PROJECT_NAME)$(EXT) $(OBJS) $(CFLAGS) $(INCLUDE_PATHS) $(LDFLAGS) $(LDLIBS) -D$(PLATFORM)
|
||||
|
||||
# Compile source files
|
||||
# NOTE: This pattern will compile every module defined on $(OBJS)
|
||||
%.o: %.c
|
||||
$(CC) -c $< -o $@ $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM)
|
||||
|
||||
run:
|
||||
$(MAKE) $(MAKEFILE_PARAMS)
|
||||
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
||||
$(PROJECT_NAME)
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
./$(PROJECT_NAME)
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),OSX)
|
||||
./$(PROJECT_NAME)
|
||||
endif
|
||||
endif
|
||||
|
||||
.PHONY: clean_shell_cmd clean_shell_sh
|
||||
|
||||
# Clean everything
|
||||
clean: clean_shell_$(PLATFORM_SHELL)
|
||||
@echo Cleaning done
|
||||
|
||||
clean_shell_sh:
|
||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
find . -type f -executable -delete
|
||||
rm -fv *.o
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),OSX)
|
||||
find . -type f -perm +ugo+x -delete
|
||||
rm -f *.o
|
||||
endif
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
||||
find . -type f -executable -delete
|
||||
rm -fv *.o
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_DRM)
|
||||
find . -type f -executable -delete
|
||||
rm -fv *.o
|
||||
endif
|
||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||
ifeq ($(PLATFORM_OS),LINUX)
|
||||
rm -fv *.o $(PROJECT_NAME).data $(PROJECT_NAME).html $(PROJECT_NAME).js $(PROJECT_NAME).wasm
|
||||
endif
|
||||
ifeq ($(PLATFORM_OS),OSX)
|
||||
rm -f *.o $(PROJECT_NAME).data $(PROJECT_NAME).html $(PROJECT_NAME).js $(PROJECT_NAME).wasm
|
||||
endif
|
||||
endif
|
||||
|
||||
# Set specific target variable
|
||||
clean_shell_cmd: SHELL=sh
|
||||
clean_shell_cmd:
|
||||
rm *.o *.exe $(PROJECT_NAME).data $(PROJECT_NAME).html $(PROJECT_NAME).js $(PROJECT_NAME).wasm /s
|
|
@ -0,0 +1,47 @@
|
|||
# Blender 3.6.2 MTL File: 'parthanon.blend'
|
||||
# www.blender.org
|
||||
|
||||
newmtl Dirt
|
||||
Ka 1.000000 1.000000 1.000000
|
||||
Ks 0.500000 0.500000 0.500000
|
||||
Ke 0.000000 0.000000 0.000000
|
||||
Ni 1.450000
|
||||
d 1.000000
|
||||
illum 2
|
||||
map_Kd -s 30 30 30 /home/zongor/Documents/Blender/ground_24_4k/Ground024_4K-PNG_Color.png
|
||||
map_Ns -s 30 30 30 /home/zongor/Documents/Blender/ground_24_4k/Ground024_4K-PNG_Roughness.png
|
||||
map_Bump -s 30 30 30 -bm 1.000000 /home/zongor/Documents/Blender/ground_24_4k/Ground024_4K-PNG_NormalGL.png
|
||||
|
||||
newmtl Stone
|
||||
Ka 1.000000 1.000000 1.000000
|
||||
Ks 0.500000 0.500000 0.500000
|
||||
Ke 0.000000 0.000000 0.000000
|
||||
Ni 1.450000
|
||||
d 1.000000
|
||||
illum 2
|
||||
map_Kd -s 30 30 30 /home/zongor/Documents/Blender/rocks_11_4k/Rocks011_4K-PNG_Color.png
|
||||
map_Ns -s 30 30 30 /home/zongor/Documents/Blender/rocks_11_4k/Rocks011_4K-PNG_Roughness.png
|
||||
map_Bump -s 30 30 30 -bm 1.000000 /home/zongor/Documents/Blender/rocks_11_4k/Rocks011_4K-PNG_NormalGL.png
|
||||
|
||||
newmtl gold_metal
|
||||
Ka 1.000000 1.000000 1.000000
|
||||
Ks 0.500000 0.500000 0.500000
|
||||
Ke 0.000000 0.000000 0.000000
|
||||
Ni 1.450000
|
||||
d 1.000000
|
||||
illum 2
|
||||
map_Kd Metal034_4K_Color.jpg
|
||||
map_Ns Metal034_4K_Roughness.jpg
|
||||
map_refl Metal034_4K_Metalness.jpg
|
||||
map_Bump -bm 1.000000 Metal034_4K_NormalGL.jpg
|
||||
|
||||
newmtl marble_12
|
||||
Ka 1.000000 1.000000 1.000000
|
||||
Ks 0.500000 0.500000 0.500000
|
||||
Ke 0.000000 0.000000 0.000000
|
||||
Ni 1.450000
|
||||
d 1.000000
|
||||
illum 2
|
||||
map_Kd -s 30 30 30 Marble012_4K_Color.jpg
|
||||
map_Ns -s 30 30 30 Marble012_4K_Roughness.jpg
|
||||
map_Bump -s 30 30 30 -bm 1.000000 Marble012_4K_NormalGL.jpg
|
Binary file not shown.
After Width: | Height: | Size: 1.3 MiB |
Binary file not shown.
After Width: | Height: | Size: 51 MiB |
|
@ -0,0 +1 @@
|
|||
PLATFORM=PLATFORM_WEB make -B && mv project_verne.* build/
|
|
@ -0,0 +1,184 @@
|
|||
#include "raylib.h"
|
||||
#include "rcamera.h"
|
||||
#include <emscripten/emscripten.h>
|
||||
#include <emscripten/websocket.h>
|
||||
#include <stdio.h>
|
||||
|
||||
const int screen_width = 800;
|
||||
const int screen_height = 450;
|
||||
|
||||
Camera camera = {0};
|
||||
Ray ray = {0};
|
||||
Model parth;
|
||||
Texture2D texture;
|
||||
Vector3 parth_pos = {0.0f, 0.0f, 0.0f};
|
||||
BoundingBox parth_bound_box;
|
||||
|
||||
void MainGameLoop(void);
|
||||
EM_BOOL onopen(int eventType,
|
||||
const EmscriptenWebSocketOpenEvent *websocketEvent,
|
||||
void *userData);
|
||||
EM_BOOL onerror(int eventType,
|
||||
const EmscriptenWebSocketErrorEvent *websocketEvent,
|
||||
void *userData);
|
||||
EM_BOOL onclose(int eventType,
|
||||
const EmscriptenWebSocketCloseEvent *websocketEvent,
|
||||
void *userData);
|
||||
EM_BOOL onmessage(int eventType,
|
||||
const EmscriptenWebSocketMessageEvent *websocketEvent,
|
||||
void *userData);
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
InitWindow(screen_width, screen_height, "Project Verne");
|
||||
|
||||
camera.position = (Vector3){-9.0f, 9.0f, 4.0f};
|
||||
camera.target = (Vector3){9.0f, 9.0f, 0.0f};
|
||||
camera.up = (Vector3){0.0f, 1.0f, 0.0f};
|
||||
camera.fovy = 60.0f;
|
||||
camera.projection = CAMERA_PERSPECTIVE;
|
||||
|
||||
parth = LoadModel("assets/parthanon.obj");
|
||||
texture = LoadTexture("assets/parthanon_8k.png");
|
||||
parth.materials[0].maps[MATERIAL_MAP_DIFFUSE].texture = texture;
|
||||
|
||||
parth_bound_box = GetMeshBoundingBox(parth.meshes[0]);
|
||||
|
||||
if (!emscripten_websocket_is_supported()) {
|
||||
return 0;
|
||||
}
|
||||
EmscriptenWebSocketCreateAttributes ws_attrs = {"wss://echo.websocket.org",
|
||||
NULL, EM_TRUE};
|
||||
|
||||
EMSCRIPTEN_WEBSOCKET_T ws = emscripten_websocket_new(&ws_attrs);
|
||||
emscripten_websocket_set_onopen_callback(ws, NULL, onopen);
|
||||
emscripten_websocket_set_onerror_callback(ws, NULL, onerror);
|
||||
emscripten_websocket_set_onclose_callback(ws, NULL, onclose);
|
||||
emscripten_websocket_set_onmessage_callback(ws, NULL, onmessage);
|
||||
|
||||
#if defined(PLATFORM_WEB)
|
||||
emscripten_set_main_loop(MainGameLoop, 0, 1);
|
||||
#else
|
||||
SetTargetFPS(60); // Set our game to run at 60 frames-per-second
|
||||
|
||||
DisableCursor();
|
||||
|
||||
while (!WindowShouldClose()) {
|
||||
MainGameLoop();
|
||||
}
|
||||
#endif
|
||||
|
||||
UnloadModel(parth);
|
||||
UnloadTexture(texture);
|
||||
|
||||
CloseWindow();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Main game loop
|
||||
*/
|
||||
void MainGameLoop(void) {
|
||||
// Lock mouse cursor if mouse click on canvas
|
||||
if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON))
|
||||
DisableCursor();
|
||||
if (IsKeyPressed(KEY_ESCAPE))
|
||||
EnableCursor();
|
||||
|
||||
UpdateCamera(&camera, CAMERA_THIRD_PERSON);
|
||||
|
||||
RayCollision collision = {0};
|
||||
collision.distance = 10000000.0f; // arbitrary reasonable distance.
|
||||
collision.hit = false;
|
||||
|
||||
// ray pointing down so we are always just above the floor.
|
||||
ray = (Ray){camera.target, (Vector3){0.0f, -1.0f, 0.0f}};
|
||||
|
||||
RayCollision bb_hit = GetRayCollisionBox(ray, parth_bound_box);
|
||||
if ((bb_hit.hit) && (bb_hit.distance < collision.distance)) {
|
||||
collision = bb_hit;
|
||||
|
||||
RayCollision mesh_collide = {0};
|
||||
for (int m = 0; m < parth.meshCount; m++) {
|
||||
mesh_collide = GetRayCollisionMesh(ray, parth.meshes[m], parth.transform);
|
||||
if (mesh_collide.hit) {
|
||||
if ((!collision.hit) || (collision.distance > mesh_collide.distance)) {
|
||||
collision = mesh_collide;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (mesh_collide.hit) {
|
||||
collision = mesh_collide;
|
||||
}
|
||||
}
|
||||
|
||||
BeginDrawing();
|
||||
|
||||
ClearBackground(RAYWHITE);
|
||||
|
||||
BeginMode3D(camera);
|
||||
|
||||
DrawModel(parth, parth_pos, 1.0f, WHITE);
|
||||
|
||||
if (collision.hit) {
|
||||
camera.target.y = collision.point.y + 0.1;
|
||||
if (camera.target.y < 0.0f) {
|
||||
camera.target.y = 0.0f;
|
||||
}
|
||||
}
|
||||
|
||||
DrawCube(camera.target, 0.1f, 0.1f, 0.1f, RED);
|
||||
|
||||
DrawGrid(10, 10.0f);
|
||||
|
||||
EndMode3D();
|
||||
|
||||
DrawFPS(10, 10);
|
||||
|
||||
EndDrawing();
|
||||
}
|
||||
|
||||
EM_BOOL onopen(int eventType,
|
||||
const EmscriptenWebSocketOpenEvent *websocketEvent,
|
||||
void *userData) {
|
||||
puts("onopen");
|
||||
|
||||
EMSCRIPTEN_RESULT result;
|
||||
result = emscripten_websocket_send_utf8_text(websocketEvent->socket, "hoge");
|
||||
if (result) {
|
||||
printf("Failed to emscripten_websocket_send_utf8_text(): %d\n", result);
|
||||
}
|
||||
return EM_TRUE;
|
||||
}
|
||||
EM_BOOL onerror(int eventType,
|
||||
const EmscriptenWebSocketErrorEvent *websocketEvent,
|
||||
void *userData) {
|
||||
puts("onerror");
|
||||
|
||||
return EM_TRUE;
|
||||
}
|
||||
EM_BOOL onclose(int eventType,
|
||||
const EmscriptenWebSocketCloseEvent *websocketEvent,
|
||||
void *userData) {
|
||||
puts("onclose");
|
||||
|
||||
return EM_TRUE;
|
||||
}
|
||||
EM_BOOL onmessage(int eventType,
|
||||
const EmscriptenWebSocketMessageEvent *websocketEvent,
|
||||
void *userData) {
|
||||
puts("onmessage");
|
||||
if (websocketEvent->isText) {
|
||||
// For only ascii chars.
|
||||
printf("message: %s\n", websocketEvent->data);
|
||||
}
|
||||
|
||||
EMSCRIPTEN_RESULT result;
|
||||
result =
|
||||
emscripten_websocket_close(websocketEvent->socket, 1000, "no reason");
|
||||
if (result) {
|
||||
printf("Failed to emscripten_websocket_close(): %d\n", result);
|
||||
}
|
||||
return EM_TRUE;
|
||||
}
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,558 @@
|
|||
/*******************************************************************************************
|
||||
*
|
||||
* rcamera - Basic camera system with support for multiple camera modes
|
||||
*
|
||||
* CONFIGURATION:
|
||||
* #define RCAMERA_IMPLEMENTATION
|
||||
* Generates the implementation of the library into the included file.
|
||||
* If not defined, the library is in header only mode and can be included in other headers
|
||||
* or source files without problems. But only ONE file should hold the implementation.
|
||||
*
|
||||
* #define RCAMERA_STANDALONE
|
||||
* If defined, the library can be used as standalone as a camera system but some
|
||||
* functions must be redefined to manage inputs accordingly.
|
||||
*
|
||||
* CONTRIBUTORS:
|
||||
* Ramon Santamaria: Supervision, review, update and maintenance
|
||||
* Christoph Wagner: Complete redesign, using raymath (2022)
|
||||
* Marc Palau: Initial implementation (2014)
|
||||
*
|
||||
*
|
||||
* LICENSE: zlib/libpng
|
||||
*
|
||||
* Copyright (c) 2022-2023 Christoph Wagner (@Crydsch) & Ramon Santamaria (@raysan5)
|
||||
*
|
||||
* This software is provided "as-is", without any express or implied warranty. In no event
|
||||
* will the authors be held liable for any damages arising from the use of this software.
|
||||
*
|
||||
* Permission is granted to anyone to use this software for any purpose, including commercial
|
||||
* applications, and to alter it and redistribute it freely, subject to the following restrictions:
|
||||
*
|
||||
* 1. The origin of this software must not be misrepresented; you must not claim that you
|
||||
* wrote the original software. If you use this software in a product, an acknowledgment
|
||||
* in the product documentation would be appreciated but is not required.
|
||||
*
|
||||
* 2. Altered source versions must be plainly marked as such, and must not be misrepresented
|
||||
* as being the original software.
|
||||
*
|
||||
* 3. This notice may not be removed or altered from any source distribution.
|
||||
*
|
||||
**********************************************************************************************/
|
||||
|
||||
#ifndef RCAMERA_H
|
||||
#define RCAMERA_H
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Defines and Macros
|
||||
//----------------------------------------------------------------------------------
|
||||
// Function specifiers definition
|
||||
|
||||
// Function specifiers in case library is build/used as a shared library (Windows)
|
||||
// NOTE: Microsoft specifiers to tell compiler that symbols are imported/exported from a .dll
|
||||
#if defined(_WIN32)
|
||||
#if defined(BUILD_LIBTYPE_SHARED)
|
||||
#if defined(__TINYC__)
|
||||
#define __declspec(x) __attribute__((x))
|
||||
#endif
|
||||
#define RLAPI __declspec(dllexport) // We are building the library as a Win32 shared library (.dll)
|
||||
#elif defined(USE_LIBTYPE_SHARED)
|
||||
#define RLAPI __declspec(dllimport) // We are using the library as a Win32 shared library (.dll)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef RLAPI
|
||||
#define RLAPI // Functions defined as 'extern' by default (implicit specifiers)
|
||||
#endif
|
||||
|
||||
#if defined(RCAMERA_STANDALONE)
|
||||
#define CAMERA_CULL_DISTANCE_NEAR 0.01
|
||||
#define CAMERA_CULL_DISTANCE_FAR 1000.0
|
||||
#else
|
||||
#define CAMERA_CULL_DISTANCE_NEAR RL_CULL_DISTANCE_NEAR
|
||||
#define CAMERA_CULL_DISTANCE_FAR RL_CULL_DISTANCE_FAR
|
||||
#endif
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Types and Structures Definition
|
||||
// NOTE: Below types are required for standalone usage
|
||||
//----------------------------------------------------------------------------------
|
||||
#if defined(RCAMERA_STANDALONE)
|
||||
// Vector2, 2 components
|
||||
typedef struct Vector2 {
|
||||
float x; // Vector x component
|
||||
float y; // Vector y component
|
||||
} Vector2;
|
||||
|
||||
// Vector3, 3 components
|
||||
typedef struct Vector3 {
|
||||
float x; // Vector x component
|
||||
float y; // Vector y component
|
||||
float z; // Vector z component
|
||||
} Vector3;
|
||||
|
||||
// Matrix, 4x4 components, column major, OpenGL style, right-handed
|
||||
typedef struct Matrix {
|
||||
float m0, m4, m8, m12; // Matrix first row (4 components)
|
||||
float m1, m5, m9, m13; // Matrix second row (4 components)
|
||||
float m2, m6, m10, m14; // Matrix third row (4 components)
|
||||
float m3, m7, m11, m15; // Matrix fourth row (4 components)
|
||||
} Matrix;
|
||||
|
||||
// Camera type, defines a camera position/orientation in 3d space
|
||||
typedef struct Camera3D {
|
||||
Vector3 position; // Camera position
|
||||
Vector3 target; // Camera target it looks-at
|
||||
Vector3 up; // Camera up vector (rotation over its axis)
|
||||
float fovy; // Camera field-of-view apperture in Y (degrees) in perspective, used as near plane width in orthographic
|
||||
int projection; // Camera projection type: CAMERA_PERSPECTIVE or CAMERA_ORTHOGRAPHIC
|
||||
} Camera3D;
|
||||
|
||||
typedef Camera3D Camera; // Camera type fallback, defaults to Camera3D
|
||||
|
||||
// Camera projection
|
||||
typedef enum {
|
||||
CAMERA_PERSPECTIVE = 0, // Perspective projection
|
||||
CAMERA_ORTHOGRAPHIC // Orthographic projection
|
||||
} CameraProjection;
|
||||
|
||||
// Camera system modes
|
||||
typedef enum {
|
||||
CAMERA_CUSTOM = 0, // Camera custom, controlled by user (UpdateCamera() does nothing)
|
||||
CAMERA_FREE, // Camera free mode
|
||||
CAMERA_ORBITAL, // Camera orbital, around target, zoom supported
|
||||
CAMERA_FIRST_PERSON, // Camera first person
|
||||
CAMERA_THIRD_PERSON // Camera third person
|
||||
} CameraMode;
|
||||
#endif
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Global Variables Definition
|
||||
//----------------------------------------------------------------------------------
|
||||
//...
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Module Functions Declaration
|
||||
//----------------------------------------------------------------------------------
|
||||
|
||||
#if defined(__cplusplus)
|
||||
extern "C" { // Prevents name mangling of functions
|
||||
#endif
|
||||
|
||||
RLAPI Vector3 GetCameraForward(Camera *camera);
|
||||
RLAPI Vector3 GetCameraUp(Camera *camera);
|
||||
RLAPI Vector3 GetCameraRight(Camera *camera);
|
||||
|
||||
// Camera movement
|
||||
RLAPI void CameraMoveForward(Camera *camera, float distance, bool moveInWorldPlane);
|
||||
RLAPI void CameraMoveUp(Camera *camera, float distance);
|
||||
RLAPI void CameraMoveRight(Camera *camera, float distance, bool moveInWorldPlane);
|
||||
RLAPI void CameraMoveToTarget(Camera *camera, float delta);
|
||||
|
||||
// Camera rotation
|
||||
RLAPI void CameraYaw(Camera *camera, float angle, bool rotateAroundTarget);
|
||||
RLAPI void CameraPitch(Camera *camera, float angle, bool lockView, bool rotateAroundTarget, bool rotateUp);
|
||||
RLAPI void CameraRoll(Camera *camera, float angle);
|
||||
|
||||
RLAPI Matrix GetCameraViewMatrix(Camera *camera);
|
||||
RLAPI Matrix GetCameraProjectionMatrix(Camera* camera, float aspect);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif // RCAMERA_H
|
||||
|
||||
|
||||
/***********************************************************************************
|
||||
*
|
||||
* CAMERA IMPLEMENTATION
|
||||
*
|
||||
************************************************************************************/
|
||||
|
||||
#if defined(RCAMERA_IMPLEMENTATION)
|
||||
|
||||
#include "raymath.h" // Required for vector maths:
|
||||
// Vector3Add()
|
||||
// Vector3Subtract()
|
||||
// Vector3Scale()
|
||||
// Vector3Normalize()
|
||||
// Vector3Distance()
|
||||
// Vector3CrossProduct()
|
||||
// Vector3RotateByAxisAngle()
|
||||
// Vector3Angle()
|
||||
// Vector3Negate()
|
||||
// MatrixLookAt()
|
||||
// MatrixPerspective()
|
||||
// MatrixOrtho()
|
||||
// MatrixIdentity()
|
||||
|
||||
// raylib required functionality:
|
||||
// GetMouseDelta()
|
||||
// GetMouseWheelMove()
|
||||
// IsKeyDown()
|
||||
// IsKeyPressed()
|
||||
// GetFrameTime()
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Defines and Macros
|
||||
//----------------------------------------------------------------------------------
|
||||
#define CAMERA_MOVE_SPEED 0.09f
|
||||
#define CAMERA_ROTATION_SPEED 0.03f
|
||||
#define CAMERA_PAN_SPEED 0.2f
|
||||
|
||||
// Camera mouse movement sensitivity
|
||||
#define CAMERA_MOUSE_MOVE_SENSITIVITY 0.003f // TODO: it should be independant of framerate
|
||||
#define CAMERA_MOUSE_SCROLL_SENSITIVITY 1.5f
|
||||
|
||||
#define CAMERA_ORBITAL_SPEED 0.5f // Radians per second
|
||||
|
||||
|
||||
#define CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER 8.0f
|
||||
#define CAMERA_FIRST_PERSON_STEP_DIVIDER 30.0f
|
||||
#define CAMERA_FIRST_PERSON_WAVING_DIVIDER 200.0f
|
||||
|
||||
// PLAYER (used by camera)
|
||||
#define PLAYER_MOVEMENT_SENSITIVITY 20.0f
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Types and Structures Definition
|
||||
//----------------------------------------------------------------------------------
|
||||
//...
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Global Variables Definition
|
||||
//----------------------------------------------------------------------------------
|
||||
//...
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Module specific Functions Declaration
|
||||
//----------------------------------------------------------------------------------
|
||||
//...
|
||||
|
||||
//----------------------------------------------------------------------------------
|
||||
// Module Functions Definition
|
||||
//----------------------------------------------------------------------------------
|
||||
// Returns the cameras forward vector (normalized)
|
||||
Vector3 GetCameraForward(Camera *camera)
|
||||
{
|
||||
return Vector3Normalize(Vector3Subtract(camera->target, camera->position));
|
||||
}
|
||||
|
||||
// Returns the cameras up vector (normalized)
|
||||
// Note: The up vector might not be perpendicular to the forward vector
|
||||
Vector3 GetCameraUp(Camera *camera)
|
||||
{
|
||||
return Vector3Normalize(camera->up);
|
||||
}
|
||||
|
||||
// Returns the cameras right vector (normalized)
|
||||
Vector3 GetCameraRight(Camera *camera)
|
||||
{
|
||||
Vector3 forward = GetCameraForward(camera);
|
||||
Vector3 up = GetCameraUp(camera);
|
||||
|
||||
return Vector3CrossProduct(forward, up);
|
||||
}
|
||||
|
||||
// Moves the camera in its forward direction
|
||||
void CameraMoveForward(Camera *camera, float distance, bool moveInWorldPlane)
|
||||
{
|
||||
Vector3 forward = GetCameraForward(camera);
|
||||
|
||||
if (moveInWorldPlane)
|
||||
{
|
||||
// Project vector onto world plane
|
||||
forward.y = 0;
|
||||
forward = Vector3Normalize(forward);
|
||||
}
|
||||
|
||||
// Scale by distance
|
||||
forward = Vector3Scale(forward, distance);
|
||||
|
||||
// Move position and target
|
||||
camera->position = Vector3Add(camera->position, forward);
|
||||
camera->target = Vector3Add(camera->target, forward);
|
||||
}
|
||||
|
||||
// Moves the camera in its up direction
|
||||
void CameraMoveUp(Camera *camera, float distance)
|
||||
{
|
||||
Vector3 up = GetCameraUp(camera);
|
||||
|
||||
// Scale by distance
|
||||
up = Vector3Scale(up, distance);
|
||||
|
||||
// Move position and target
|
||||
camera->position = Vector3Add(camera->position, up);
|
||||
camera->target = Vector3Add(camera->target, up);
|
||||
}
|
||||
|
||||
// Moves the camera target in its current right direction
|
||||
void CameraMoveRight(Camera *camera, float distance, bool moveInWorldPlane)
|
||||
{
|
||||
Vector3 right = GetCameraRight(camera);
|
||||
|
||||
if (moveInWorldPlane)
|
||||
{
|
||||
// Project vector onto world plane
|
||||
right.y = 0;
|
||||
right = Vector3Normalize(right);
|
||||
}
|
||||
|
||||
// Scale by distance
|
||||
right = Vector3Scale(right, distance);
|
||||
|
||||
// Move position and target
|
||||
camera->position = Vector3Add(camera->position, right);
|
||||
camera->target = Vector3Add(camera->target, right);
|
||||
}
|
||||
|
||||
// Moves the camera position closer/farther to/from the camera target
|
||||
void CameraMoveToTarget(Camera *camera, float delta)
|
||||
{
|
||||
float distance = Vector3Distance(camera->position, camera->target);
|
||||
|
||||
// Apply delta
|
||||
distance += delta;
|
||||
|
||||
// Distance must be greater than 0
|
||||
if (distance <= 0) distance = 0.001f;
|
||||
|
||||
// Set new distance by moving the position along the forward vector
|
||||
Vector3 forward = GetCameraForward(camera);
|
||||
camera->position = Vector3Add(camera->target, Vector3Scale(forward, -distance));
|
||||
}
|
||||
|
||||
// Rotates the camera around its up vector
|
||||
// Yaw is "looking left and right"
|
||||
// If rotateAroundTarget is false, the camera rotates around its position
|
||||
// Note: angle must be provided in radians
|
||||
void CameraYaw(Camera *camera, float angle, bool rotateAroundTarget)
|
||||
{
|
||||
// Rotation axis
|
||||
Vector3 up = GetCameraUp(camera);
|
||||
|
||||
// View vector
|
||||
Vector3 targetPosition = Vector3Subtract(camera->target, camera->position);
|
||||
|
||||
// Rotate view vector around up axis
|
||||
targetPosition = Vector3RotateByAxisAngle(targetPosition, up, angle);
|
||||
|
||||
if (rotateAroundTarget)
|
||||
{
|
||||
// Move position relative to target
|
||||
camera->position = Vector3Subtract(camera->target, targetPosition);
|
||||
}
|
||||
else // rotate around camera.position
|
||||
{
|
||||
// Move target relative to position
|
||||
camera->target = Vector3Add(camera->position, targetPosition);
|
||||
}
|
||||
}
|
||||
|
||||
// Rotates the camera around its right vector, pitch is "looking up and down"
|
||||
// - lockView prevents camera overrotation (aka "somersaults")
|
||||
// - rotateAroundTarget defines if rotation is around target or around its position
|
||||
// - rotateUp rotates the up direction as well (typically only usefull in CAMERA_FREE)
|
||||
// NOTE: angle must be provided in radians
|
||||
void CameraPitch(Camera *camera, float angle, bool lockView, bool rotateAroundTarget, bool rotateUp)
|
||||
{
|
||||
// Up direction
|
||||
Vector3 up = GetCameraUp(camera);
|
||||
|
||||
// View vector
|
||||
Vector3 targetPosition = Vector3Subtract(camera->target, camera->position);
|
||||
|
||||
if (lockView)
|
||||
{
|
||||
// In these camera modes we clamp the Pitch angle
|
||||
// to allow only viewing straight up or down.
|
||||
|
||||
// Clamp view up
|
||||
float maxAngleUp = Vector3Angle(up, targetPosition);
|
||||
maxAngleUp -= 0.001f; // avoid numerical errors
|
||||
if (angle > maxAngleUp) angle = maxAngleUp;
|
||||
|
||||
// Clamp view down
|
||||
float maxAngleDown = Vector3Angle(Vector3Negate(up), targetPosition);
|
||||
maxAngleDown *= -1.0f; // downwards angle is negative
|
||||
maxAngleDown += 0.001f; // avoid numerical errors
|
||||
if (angle < maxAngleDown) angle = maxAngleDown;
|
||||
}
|
||||
|
||||
// Rotation axis
|
||||
Vector3 right = GetCameraRight(camera);
|
||||
|
||||
// Rotate view vector around right axis
|
||||
targetPosition = Vector3RotateByAxisAngle(targetPosition, right, angle);
|
||||
|
||||
if (rotateAroundTarget)
|
||||
{
|
||||
// Move position relative to target
|
||||
camera->position = Vector3Subtract(camera->target, targetPosition);
|
||||
}
|
||||
else // rotate around camera.position
|
||||
{
|
||||
// Move target relative to position
|
||||
camera->target = Vector3Add(camera->position, targetPosition);
|
||||
}
|
||||
|
||||
if (rotateUp)
|
||||
{
|
||||
// Rotate up direction around right axis
|
||||
camera->up = Vector3RotateByAxisAngle(camera->up, right, angle);
|
||||
}
|
||||
}
|
||||
|
||||
// Rotates the camera around its forward vector
|
||||
// Roll is "turning your head sideways to the left or right"
|
||||
// Note: angle must be provided in radians
|
||||
void CameraRoll(Camera *camera, float angle)
|
||||
{
|
||||
// Rotation axis
|
||||
Vector3 forward = GetCameraForward(camera);
|
||||
|
||||
// Rotate up direction around forward axis
|
||||
camera->up = Vector3RotateByAxisAngle(camera->up, forward, angle);
|
||||
}
|
||||
|
||||
// Returns the camera view matrix
|
||||
Matrix GetCameraViewMatrix(Camera *camera)
|
||||
{
|
||||
return MatrixLookAt(camera->position, camera->target, camera->up);
|
||||
}
|
||||
|
||||
// Returns the camera projection matrix
|
||||
Matrix GetCameraProjectionMatrix(Camera *camera, float aspect)
|
||||
{
|
||||
if (camera->projection == CAMERA_PERSPECTIVE)
|
||||
{
|
||||
return MatrixPerspective(camera->fovy*DEG2RAD, aspect, CAMERA_CULL_DISTANCE_NEAR, CAMERA_CULL_DISTANCE_FAR);
|
||||
}
|
||||
else if (camera->projection == CAMERA_ORTHOGRAPHIC)
|
||||
{
|
||||
double top = camera->fovy/2.0;
|
||||
double right = top*aspect;
|
||||
|
||||
return MatrixOrtho(-right, right, -top, top, CAMERA_CULL_DISTANCE_NEAR, CAMERA_CULL_DISTANCE_FAR);
|
||||
}
|
||||
|
||||
return MatrixIdentity();
|
||||
}
|
||||
|
||||
#if !defined(RCAMERA_STANDALONE)
|
||||
// Update camera position for selected mode
|
||||
// Camera mode: CAMERA_FREE, CAMERA_FIRST_PERSON, CAMERA_THIRD_PERSON, CAMERA_ORBITAL or CUSTOM
|
||||
void UpdateCamera(Camera *camera, int mode)
|
||||
{
|
||||
Vector2 mousePositionDelta = GetMouseDelta();
|
||||
|
||||
bool moveInWorldPlane = ((mode == CAMERA_FIRST_PERSON) || (mode == CAMERA_THIRD_PERSON));
|
||||
bool rotateAroundTarget = ((mode == CAMERA_THIRD_PERSON) || (mode == CAMERA_ORBITAL));
|
||||
bool lockView = ((mode == CAMERA_FIRST_PERSON) || (mode == CAMERA_THIRD_PERSON) || (mode == CAMERA_ORBITAL));
|
||||
bool rotateUp = false;
|
||||
|
||||
if (mode == CAMERA_ORBITAL)
|
||||
{
|
||||
// Orbital can just orbit
|
||||
Matrix rotation = MatrixRotate(GetCameraUp(camera), CAMERA_ORBITAL_SPEED*GetFrameTime());
|
||||
Vector3 view = Vector3Subtract(camera->position, camera->target);
|
||||
view = Vector3Transform(view, rotation);
|
||||
camera->position = Vector3Add(camera->target, view);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Camera rotation
|
||||
if (IsKeyDown(KEY_DOWN)) CameraPitch(camera, -CAMERA_ROTATION_SPEED, lockView, rotateAroundTarget, rotateUp);
|
||||
if (IsKeyDown(KEY_UP)) CameraPitch(camera, CAMERA_ROTATION_SPEED, lockView, rotateAroundTarget, rotateUp);
|
||||
if (IsKeyDown(KEY_RIGHT)) CameraYaw(camera, -CAMERA_ROTATION_SPEED, rotateAroundTarget);
|
||||
if (IsKeyDown(KEY_LEFT)) CameraYaw(camera, CAMERA_ROTATION_SPEED, rotateAroundTarget);
|
||||
if (IsKeyDown(KEY_Q)) CameraRoll(camera, -CAMERA_ROTATION_SPEED);
|
||||
if (IsKeyDown(KEY_E)) CameraRoll(camera, CAMERA_ROTATION_SPEED);
|
||||
|
||||
// Camera movement
|
||||
if (!IsGamepadAvailable(0))
|
||||
{
|
||||
// Camera pan (for CAMERA_FREE)
|
||||
if ((mode == CAMERA_FREE) && (IsMouseButtonDown(MOUSE_BUTTON_MIDDLE)))
|
||||
{
|
||||
const Vector2 mouseDelta = GetMouseDelta();
|
||||
if (mouseDelta.x > 0.0f) CameraMoveRight(camera, CAMERA_PAN_SPEED, moveInWorldPlane);
|
||||
if (mouseDelta.x < 0.0f) CameraMoveRight(camera, -CAMERA_PAN_SPEED, moveInWorldPlane);
|
||||
if (mouseDelta.y > 0.0f) CameraMoveUp(camera, -CAMERA_PAN_SPEED);
|
||||
if (mouseDelta.y < 0.0f) CameraMoveUp(camera, CAMERA_PAN_SPEED);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Mouse support
|
||||
CameraYaw(camera, -mousePositionDelta.x*CAMERA_MOUSE_MOVE_SENSITIVITY, rotateAroundTarget);
|
||||
CameraPitch(camera, -mousePositionDelta.y*CAMERA_MOUSE_MOVE_SENSITIVITY, lockView, rotateAroundTarget, rotateUp);
|
||||
}
|
||||
|
||||
// Keyboard support
|
||||
if (IsKeyDown(KEY_W)) CameraMoveForward(camera, CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
if (IsKeyDown(KEY_A)) CameraMoveRight(camera, -CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
if (IsKeyDown(KEY_S)) CameraMoveForward(camera, -CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
if (IsKeyDown(KEY_D)) CameraMoveRight(camera, CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Gamepad controller support
|
||||
CameraYaw(camera, -(GetGamepadAxisMovement(0, GAMEPAD_AXIS_RIGHT_X) * 2)*CAMERA_MOUSE_MOVE_SENSITIVITY, rotateAroundTarget);
|
||||
CameraPitch(camera, -(GetGamepadAxisMovement(0, GAMEPAD_AXIS_RIGHT_Y) * 2)*CAMERA_MOUSE_MOVE_SENSITIVITY, lockView, rotateAroundTarget, rotateUp);
|
||||
|
||||
if (GetGamepadAxisMovement(0, GAMEPAD_AXIS_LEFT_Y) <= -0.25f) CameraMoveForward(camera, CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
if (GetGamepadAxisMovement(0, GAMEPAD_AXIS_LEFT_X) <= -0.25f) CameraMoveRight(camera, -CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
if (GetGamepadAxisMovement(0, GAMEPAD_AXIS_LEFT_Y) >= 0.25f) CameraMoveForward(camera, -CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
if (GetGamepadAxisMovement(0, GAMEPAD_AXIS_LEFT_X) >= 0.25f) CameraMoveRight(camera, CAMERA_MOVE_SPEED, moveInWorldPlane);
|
||||
}
|
||||
|
||||
if (mode == CAMERA_FREE)
|
||||
{
|
||||
if (IsKeyDown(KEY_SPACE)) CameraMoveUp(camera, CAMERA_MOVE_SPEED);
|
||||
if (IsKeyDown(KEY_LEFT_CONTROL)) CameraMoveUp(camera, -CAMERA_MOVE_SPEED);
|
||||
}
|
||||
}
|
||||
|
||||
if ((mode == CAMERA_THIRD_PERSON) || (mode == CAMERA_ORBITAL) || (mode == CAMERA_FREE))
|
||||
{
|
||||
// Zoom target distance
|
||||
CameraMoveToTarget(camera, -GetMouseWheelMove());
|
||||
if (IsKeyPressed(KEY_KP_SUBTRACT)) CameraMoveToTarget(camera, 2.0f);
|
||||
if (IsKeyPressed(KEY_KP_ADD)) CameraMoveToTarget(camera, -2.0f);
|
||||
}
|
||||
}
|
||||
#endif // !RCAMERA_STANDALONE
|
||||
|
||||
// Update camera movement, movement/rotation values should be provided by user
|
||||
void UpdateCameraPro(Camera *camera, Vector3 movement, Vector3 rotation, float zoom)
|
||||
{
|
||||
// Required values
|
||||
// movement.x - Move forward/backward
|
||||
// movement.y - Move right/left
|
||||
// movement.z - Move up/down
|
||||
// rotation.x - yaw
|
||||
// rotation.y - pitch
|
||||
// rotation.z - roll
|
||||
// zoom - Move towards target
|
||||
|
||||
bool lockView = true;
|
||||
bool rotateAroundTarget = false;
|
||||
bool rotateUp = false;
|
||||
bool moveInWorldPlane = true;
|
||||
|
||||
// Camera rotation
|
||||
CameraPitch(camera, -rotation.y*DEG2RAD, lockView, rotateAroundTarget, rotateUp);
|
||||
CameraYaw(camera, -rotation.x*DEG2RAD, rotateAroundTarget);
|
||||
CameraRoll(camera, rotation.z*DEG2RAD);
|
||||
|
||||
// Camera movement
|
||||
CameraMoveForward(camera, movement.x, moveInWorldPlane);
|
||||
CameraMoveRight(camera, movement.y, moveInWorldPlane);
|
||||
CameraMoveUp(camera, movement.z);
|
||||
|
||||
// Zoom target distance
|
||||
CameraMoveToTarget(camera, zoom);
|
||||
}
|
||||
|
||||
#endif // RCAMERA_IMPLEMENTATION
|
|
@ -0,0 +1 @@
|
|||
python3 -m http.server -d build/
|
Loading…
Reference in New Issue