258 lines
7.8 KiB
Zig
258 lines
7.8 KiB
Zig
pub const AddProgramOptions = struct {
|
|
name: []const u8,
|
|
opt: bh.Options,
|
|
root_source_file: std.Build.LazyPath,
|
|
};
|
|
|
|
// all other modules are disabled by default
|
|
pub const defaultEnabledModules: []const []const u8 = &.{
|
|
"core",
|
|
"assets",
|
|
"platform",
|
|
"rend",
|
|
};
|
|
|
|
pub const moduleOrder: []const []const u8 = &.{
|
|
"core",
|
|
"sys",
|
|
"assets",
|
|
"platform",
|
|
"net",
|
|
"physics",
|
|
"audio",
|
|
"rend",
|
|
"ui",
|
|
"imgui",
|
|
"papyrus",
|
|
};
|
|
|
|
pub const GameModule = struct {
|
|
name: []const u8,
|
|
enabled: bool = true,
|
|
};
|
|
|
|
pub const Program = struct {
|
|
name: []const u8,
|
|
opts: bh.Options,
|
|
|
|
// root_path: not used yet, we will create a second module that dynamically loads in to that root_path
|
|
|
|
gameModules: std.ArrayListUnmanaged(GameModule) = .{},
|
|
gameModulesMap: std.StringHashMapUnmanaged(bool) = .{},
|
|
buildSystem: *backlog.BuildSystem,
|
|
iconPath: ?std.Build.LazyPath = null,
|
|
allocator: std.mem.Allocator, // just set this to the build allocator
|
|
|
|
pub fn setModuleEnabled(self: *@This(), name: []const u8, enabled: bool) void {
|
|
const r = self.gameModulesMap.getOrPut(self.allocator, name);
|
|
r.value_ptr.* = enabled;
|
|
}
|
|
|
|
fn finalizeModules(self: *@This()) void {
|
|
self.gameModules.clearRetainingCapacity();
|
|
|
|
for (moduleOrder) |mod| {
|
|
var enabled: bool = false;
|
|
for (defaultEnabledModules) |default| {
|
|
if (std.mem.eql(u8, default, mod)) {
|
|
enabled = true;
|
|
}
|
|
}
|
|
|
|
if (self.gameModulesMap.get(mod)) |value| {
|
|
enabled = value;
|
|
}
|
|
|
|
if (enabled) {
|
|
self.gameModules.append(self.allocator, .{ .name = mod, .enabled = enabled }) catch unreachable;
|
|
}
|
|
}
|
|
}
|
|
|
|
pub fn setIconPath(self: *@This(), path: []const u8) void {
|
|
if (self.iconPath != null) {
|
|
return;
|
|
}
|
|
|
|
self.iconPath = self.buildSystem.generateRc(self.name, path) catch return;
|
|
}
|
|
|
|
pub fn makeSpec(self: *@This()) *std.Build.Module {
|
|
const b = self.buildSystem.b;
|
|
const run = b.addRunArtifact(self.buildSystem.specGen);
|
|
const pfile = run.addOutputFileArg(b.fmt("{s}-spec.zig", .{self.name}));
|
|
run.addArg(self.name);
|
|
for (self.gameModules.items) |mod| {
|
|
if (mod.enabled)
|
|
run.addArg(mod.name);
|
|
}
|
|
|
|
const mod = b.createModule(.{
|
|
.target = self.opts.target,
|
|
.optimize = self.opts.optimize,
|
|
.root_source_file = pfile,
|
|
});
|
|
|
|
const core = self.buildSystem.nwdep.module("core");
|
|
mod.addImport("core", core);
|
|
|
|
return mod;
|
|
}
|
|
|
|
pub fn makeGameApi(self: *@This()) *std.Build.Module {
|
|
const b = self.buildSystem.b;
|
|
const apigen = self.buildSystem.nwdep.artifact("backlog-generate-modapi");
|
|
const run = b.addRunArtifact(apigen);
|
|
const pfile = run.addOutputFileArg(b.fmt("{s}-api.zig", .{self.name}));
|
|
|
|
run.addArg(self.name);
|
|
|
|
for (self.gameModules.items) |mod| {
|
|
if (mod.enabled) {
|
|
run.addArg(mod.name);
|
|
}
|
|
}
|
|
|
|
const api = b.createModule(.{
|
|
.target = self.opts.target,
|
|
.optimize = self.opts.optimize,
|
|
.root_source_file = pfile,
|
|
});
|
|
|
|
for (self.gameModules.items) |mod| {
|
|
if (mod.enabled) {
|
|
api.addImport(mod.name, self.buildSystem.nwdep.module(mod.name));
|
|
}
|
|
}
|
|
|
|
return api;
|
|
}
|
|
|
|
pub fn makeGameModule(self: *@This()) *std.Build.Step.Compile {
|
|
const b = self.buildSystem.b;
|
|
const bEngine = self.buildSystem.bEngine;
|
|
|
|
const opts = self.opts;
|
|
|
|
// 1. generate the main launch codeset.
|
|
const lib = b.addLibrary(.{
|
|
.name = self.name,
|
|
.linkage = if (opts.static_build) .static else .dynamic,
|
|
.root_module = b.createModule(.{
|
|
.target = opts.target,
|
|
.optimize = opts.optimize,
|
|
.root_source_file = bEngine.path("engine/modulelaunch.zig"),
|
|
}),
|
|
});
|
|
|
|
lib.root_module.addImport("core", self.buildSystem.nwdep.module("core"));
|
|
|
|
if (opts.static_build) {
|
|
// b.installArtifact(lib);
|
|
} else {
|
|
const installExtern = b.addInstallArtifact(lib, .{
|
|
.dest_dir = .{ .override = .{ .custom = "modules" } },
|
|
});
|
|
b.getInstallStep().dependOn(&installExtern.step);
|
|
}
|
|
|
|
return lib;
|
|
}
|
|
|
|
// spec is linked in both the base trampoline
|
|
pub fn compileInstall(self: *@This()) *std.Build.Step.Compile {
|
|
const bEngine = self.buildSystem.bEngine;
|
|
const b = self.buildSystem.b;
|
|
const core = self.buildSystem.nwdep.module("core");
|
|
self.finalizeModules();
|
|
|
|
// 1. create the loader
|
|
const exe = bEngine.addExecutable(.{
|
|
.name = self.name,
|
|
.root_module = bEngine.createModule(.{
|
|
.target = self.opts.target,
|
|
.optimize = self.opts.optimize,
|
|
.root_source_file = bEngine.path("engine/main2.zig"),
|
|
}),
|
|
});
|
|
|
|
// link core
|
|
const spec = self.makeSpec();
|
|
exe.root_module.addImport("gamespec", spec);
|
|
exe.root_module.addImport("core", core);
|
|
exe.root_module.addOptions("BacklogOptions", self.buildSystem.options);
|
|
|
|
const gameModule = self.makeGameModule();
|
|
const gameApi = self.makeGameApi();
|
|
gameModule.root_module.addImport("backlog", gameApi);
|
|
|
|
{
|
|
const runArtifact = b.addRunArtifact(exe);
|
|
if (b.args) |args| {
|
|
runArtifact.addArgs(args);
|
|
}
|
|
|
|
const run_exe = b.step(b.fmt("run-{s}", .{self.name}), "runs the program");
|
|
run_exe.dependOn(&runArtifact.step);
|
|
}
|
|
|
|
// 2. create the actual library that the loader will try to load
|
|
|
|
// 3. set up linking, if static then we will link against the loader
|
|
|
|
self.buildSystem.b.installArtifact(exe);
|
|
|
|
// return the actual library not the loader
|
|
return exe;
|
|
}
|
|
|
|
// const b = self.b;
|
|
|
|
// const exe = self.nw_builder.addExecutable(.{
|
|
// .name = opts.name,
|
|
// .target = self.target,
|
|
// .optimize = self.optimize,
|
|
// .root_source_file = self.nw_builder.path("engine/main.zig"),
|
|
// });
|
|
|
|
// b.installArtifact(exe);
|
|
// const runArtifact = b.addRunArtifact(exe);
|
|
// if (b.args) |args| {
|
|
// runArtifact.addArgs(args);
|
|
// }
|
|
// const run_exe = b.step(self.b.fmt("run-{s}", .{opts.name}), opts.desc);
|
|
// run_exe.dependOn(&runArtifact.step);
|
|
|
|
// // main path = name/main.zig
|
|
// const mod = b.addModule(opts.name, .{
|
|
// .target = self.target,
|
|
// .optimize = self.optimize,
|
|
// .root_source_file = opts.root_source_file,
|
|
// .imports = opts.imports,
|
|
// });
|
|
|
|
// exe.root_module.addImport("main", mod);
|
|
// // todo.. remove this one and see what happens
|
|
// exe.root_module.addImport("core", self.nwdep.module("core"));
|
|
// // mod.addImport("Backlog", self.nw_mod);
|
|
// exe.root_module.addOptions("BacklogOptions", self.options);
|
|
|
|
// if (self.cookShaders) {
|
|
// const cookShadersScript = b.fmt("{s}/tools/scripts/cookShaders.py", .{self.backlogRoot});
|
|
// const cookShadersCommand = b.addSystemCommand(&[_][]const u8{"python"});
|
|
// cookShadersCommand.addArg(cookShadersScript);
|
|
|
|
// run_exe.dependOn(&cookShadersCommand.step);
|
|
// }
|
|
|
|
// b.getInstallStep().dependOn(self.nw_builder.getInstallStep());
|
|
|
|
// // run_exe.dependOn(b.getInstallStep());
|
|
|
|
// return mod;
|
|
};
|
|
|
|
const std = @import("std");
|
|
const bh = @import("bh");
|
|
const backlog = @import("../build.zig");
|