diff --git a/.gitignore b/.gitignore index 6ba888e..c1e6587 100644 --- a/.gitignore +++ b/.gitignore @@ -18,3 +18,4 @@ pdbs/ game_web/ .venv build/ +bin/ diff --git a/builder/builder.odin b/builder/builder.odin index 2bb7c5d..b02a955 100644 --- a/builder/builder.odin +++ b/builder/builder.odin @@ -39,18 +39,22 @@ when ODIN_OS == .Windows { EXE_EXT :: ".exe" DLL_EXT :: ".dll" LIB_PREFIX :: "" + EMSCRIPTEN_SHELL_EXT :: ".bat" } else when ODIN_OS == .Linux { EXE_EXT :: ".bin" DLL_EXT :: ".so" LIB_PREFIX :: "lib" + EMSCRIPTEN_SHELL_EXT :: "" } else when ODIN_OS == .Darwin { EXE_EXT :: ".bin" DLL_EXT :: ".dylib" LIB_PREFIX :: "lib" + EMSCRIPTEN_SHELL_EXT :: "" } else { EXE_EXT :: "" DLL_EXT :: "" LIB_PREFIX :: "" + EMSCRIPTEN_SHELL_EXT :: "" } // Returns a list of shared dependencies that have to be copied to out dir @@ -113,8 +117,8 @@ build_deps :: proc(opts: Options) -> []string { build_cmd := []string{"cmake", "--build", "build", "--config", "MinSizeRel"} if !is_built || force { if opts.variant == .Web { - run_cmd(temp_concat({"emcmake.bat"}, prepare_cmd), cwd) - run_cmd(temp_concat({"emmake.bat"}, build_cmd), cwd) + run_cmd(temp_concat({"emcmake" + EMSCRIPTEN_SHELL_EXT}, prepare_cmd), cwd) + run_cmd(temp_concat({"emmake" + EMSCRIPTEN_SHELL_EXT}, build_cmd), cwd) } else { run_cmd(prepare_cmd, cwd) run_cmd(build_cmd, cwd) @@ -199,11 +203,7 @@ setup_emsdk_env :: proc() { PATH_ENV_DELIMITER :: ":" } - PATHS :: [3]string { - "./libs/emsdk/upstream/bin", - "./libs/emsdk/upstream/emscripten", - "./libs/emsdk/ninja/git-release_64bit/bin", - } + PATHS :: [2]string{"./libs/emsdk/upstream/bin", "./libs/emsdk/upstream/emscripten"} paths: [len(PATHS)]string for path, i in PATHS { @@ -213,7 +213,7 @@ setup_emsdk_env :: proc() { set_env( "PATH", strings.join( - {paths[0], paths[1], paths[2], os.get_env("PATH", context.temp_allocator)}, + {paths[0], paths[1], os.get_env("PATH", context.temp_allocator)}, PATH_ENV_DELIMITER, context.temp_allocator, ), @@ -258,7 +258,7 @@ main :: proc() { switch opts.variant { case .Hot_Reload: - setup_bin_dir(opts, "./build/hotreload", shared_dep_paths) + setup_bin_dir(opts, "./bin/hotreload", shared_dep_paths) is_running := process_exists("game" + EXE_EXT) if !is_running { @@ -268,7 +268,7 @@ main :: proc() { "odin", "build", "main_hot_reload", - "-out:./build/hotreload/game" + EXE_EXT, + "-out:./bin/hotreload/game" + EXE_EXT, }, debug_flag, tracy_flag, @@ -286,7 +286,7 @@ main :: proc() { "-define:RAYLIB_SHARED=true", "-define:PHYSFS_SHARED=true", "-build-mode:dll", - "-out:./build/hotreload/game_tmp" + DLL_EXT, + "-out:./bin/hotreload/game_tmp" + DLL_EXT, }, tracy_flag, debug_flag, @@ -295,17 +295,17 @@ main :: proc() { ), "", ) - rename("./build/hotreload/game_tmp" + DLL_EXT, "./build/hotreload/game" + DLL_EXT) + rename("./bin/hotreload/game_tmp" + DLL_EXT, "./bin/hotreload/game" + DLL_EXT) if !is_running && opts.run { - run_cmd({"./build/hotreload/game" + EXE_EXT}, "") + run_cmd({"./bin/hotreload/game" + EXE_EXT}, "") } case .Desktop: - setup_bin_dir(opts, "./build/desktop", shared_dep_paths) + setup_bin_dir(opts, "./bin/desktop", shared_dep_paths) cmd := slice.concatenate( [][]string { - []string{"odin", "build", "main_release", "-out:./build/desktop/game" + EXE_EXT}, + []string{"odin", "build", "main_release", "-out:./bin/desktop/game" + EXE_EXT}, tracy_flag, debug_flag, optimize_flag, @@ -315,8 +315,8 @@ main :: proc() { ) run_cmd(cmd, "") case .Web: - remove_all("./build/web") - mkdir_all("./build/web") + remove_all("./bin/web") + mkdir_all("./bin/web") odin_root := run_cmd({"odin", "root"}, "") @@ -328,7 +328,7 @@ main :: proc() { "main_web", "-target:js_wasm32", "-build-mode:obj", - "-out:build/web/game", + "-out:bin/web/game", }, COMMON_FLAGS, debug_flag, @@ -339,11 +339,11 @@ main :: proc() { run_cmd( { - "emcc.bat", + "emcc" + EMSCRIPTEN_SHELL_EXT, "-g", "-o", - "build/web/index.html", - "build/web/game.wasm.o", + "bin/web/index.html", + "bin/web/game.wasm.o", "libs/raylib/zig-out-static/lib/libraylib.a", "libs/physfs/build/libphysfs.a", "-sUSE_GLFW=3", @@ -358,14 +358,14 @@ main :: proc() { }, "", ) - remove_file("./build/web/game.wasm.o") + remove_file("./bin/web/game.wasm.o") copy_file( filepath.join( {odin_root, "core", "sys", "wasm", "js", "odin.js"}, context.temp_allocator, ), - "./build/web/odin.js", + "./bin/web/odin.js", ) } } diff --git a/game/fs.odin b/game/fs.odin index d401170..f011d84 100644 --- a/game/fs.odin +++ b/game/fs.odin @@ -3,7 +3,6 @@ package game import "base:runtime" import "core:c" import "core:log" -import "core:path/filepath" import "core:strings" import "libs:physfs" import rl "libs:raylib" @@ -11,6 +10,26 @@ import rl "libs:raylib" @(private = "file") _ctx: runtime.Context +path_dir :: proc(path: string, num_dirs: int = 1) -> string { + when ODIN_OS == .Windows { + SEPARATOR :: rune('\\') + } else { + SEPARATOR :: rune('/') + } + count := 0 + #reverse for rune, i in path { + if rune == SEPARATOR { + count += 1 + + if count == num_dirs { + return path[0:i] + } + } + } + + return path +} + init_physfs :: proc(args: []string) { _ctx = context @@ -18,20 +37,17 @@ init_physfs :: proc(args: []string) { physfs.setSaneConfig("serega", "gutter-runner", "zip", 0, 1) // For non web builds, binary will live 2 subdirs below main content dir, so add it to search path - if args[0] != "." { - base_dir := filepath.dir( - filepath.dir(filepath.dir(args[0], context.temp_allocator), context.temp_allocator), - context.temp_allocator, - ) - abs_base_dir, ok := filepath.abs(base_dir, context.temp_allocator) - assert(ok) - err := physfs.mount(strings.clone_to_cstring(abs_base_dir, context.temp_allocator), "/", 1) + when ODIN_OS != .JS { + abs_path, ok := path_abs(args[0], context.temp_allocator) + assert(ok) + base_dir := path_dir(abs_path, 3) + err := physfs.mount(strings.clone_to_cstring(base_dir, context.temp_allocator), "/", 1) if err == 0 { log.panicf("physfs: failed to set base dir {0}", physfs.getLastError()) } - log.infof("physfs: added {0} to search path", abs_base_dir) + log.infof("physfs: added {0} to search path", base_dir) } } diff --git a/game/fs_desktop.odin b/game/fs_desktop.odin new file mode 100644 index 0000000..99b0b90 --- /dev/null +++ b/game/fs_desktop.odin @@ -0,0 +1,8 @@ +#+build !js +package game + +import "core:path/filepath" + +path_abs :: proc(path: string, allocator := context.allocator) -> (string, bool) { + return filepath.abs(path, allocator) +} diff --git a/game/fs_web.odin b/game/fs_web.odin new file mode 100644 index 0000000..42b9374 --- /dev/null +++ b/game/fs_web.odin @@ -0,0 +1,6 @@ +#+build js +package game + +path_abs :: proc(path: string, allocator := context.allocator) -> (string, bool) { + return path, true +}