Use castle's stbi instead of zstbi
This commit is contained in:
@@ -3,6 +3,7 @@
|
||||
const Blocks = @This();
|
||||
const std = @import("std");
|
||||
|
||||
const media = @import("media");
|
||||
const voxels = @import("../voxels.zig");
|
||||
|
||||
const Atom = @import("../engine/Atom.zig").Atom;
|
||||
@@ -134,6 +135,7 @@ pub fn getOrLoad(
|
||||
engine: *Engine,
|
||||
materials: *Materials,
|
||||
textures: *Textures,
|
||||
stbi: *media.stbi,
|
||||
filename: []const u8,
|
||||
temp_allocator: std.mem.Allocator,
|
||||
) !Id {
|
||||
@@ -152,7 +154,7 @@ pub fn getOrLoad(
|
||||
const id = Id.fromIndexSafe(self.array.items.len) catch |err| switch (err) {
|
||||
error.Overflow => return error.OutOfBlocks,
|
||||
};
|
||||
const def = try loadBlock(engine, materials, textures, filename, temp_allocator);
|
||||
const def = try loadBlock(engine, materials, textures, stbi, filename, temp_allocator);
|
||||
|
||||
self.map.putAssumeCapacityNoClobber(key, id);
|
||||
self.array.appendAssumeCapacity(def);
|
||||
@@ -166,6 +168,7 @@ pub fn getOrLoadAtom(
|
||||
engine: *Engine,
|
||||
materials: *Materials,
|
||||
textures: *Textures,
|
||||
stbi: *media.stbi,
|
||||
filename: Atom,
|
||||
temp_allocator: std.mem.Allocator,
|
||||
) !Id {
|
||||
@@ -182,7 +185,7 @@ pub fn getOrLoadAtom(
|
||||
const id = Id.fromIndexSafe(self.array.items.len) catch |err| switch (err) {
|
||||
error.Overflow => return error.OutOfBlocks,
|
||||
};
|
||||
const def = try loadBlock(engine, materials, textures, filename.toString(), temp_allocator);
|
||||
const def = try loadBlock(engine, materials, textures, stbi, filename.toString(), temp_allocator);
|
||||
|
||||
self.map.putAssumeCapacityNoClobber(key, id);
|
||||
self.array.appendAssumeCapacity(def);
|
||||
@@ -196,6 +199,7 @@ pub fn loadAll(
|
||||
engine: *Engine,
|
||||
materials: *Materials,
|
||||
textures: *Textures,
|
||||
stbi: *media.stbi,
|
||||
temp_allocator: std.mem.Allocator,
|
||||
) void {
|
||||
const cwd = std.fs.cwd();
|
||||
@@ -216,7 +220,7 @@ pub fn loadAll(
|
||||
continue;
|
||||
}
|
||||
|
||||
_ = self.getOrLoad(engine, materials, textures, entry.name, temp_allocator) catch |err| {
|
||||
_ = self.getOrLoad(engine, materials, textures, stbi, entry.name, temp_allocator) catch |err| {
|
||||
std.log.err("Error while loading block definition entry {s}: {s}", .{ entry.name, @errorName(err) });
|
||||
};
|
||||
}
|
||||
@@ -226,6 +230,7 @@ fn loadBlock(
|
||||
engine: *Engine,
|
||||
materials: *Materials,
|
||||
textures: *Textures,
|
||||
stbi: *media.stbi,
|
||||
filename: []const u8,
|
||||
temp_allocator: std.mem.Allocator,
|
||||
) !Definition {
|
||||
@@ -274,7 +279,7 @@ fn loadBlock(
|
||||
return error.ParseError;
|
||||
}
|
||||
|
||||
const material = try materials.getOrLoad(engine, textures, name, temp_allocator);
|
||||
const material = try materials.getOrLoad(engine, textures, stbi, name, temp_allocator);
|
||||
break :blk .initUniform(material);
|
||||
}
|
||||
|
||||
@@ -284,7 +289,7 @@ fn loadBlock(
|
||||
var ret: Definition.Walls = undefined;
|
||||
inline for (@typeInfo(voxels.Orientation).@"enum".fields) |field| {
|
||||
@field(ret, field.name) = .{
|
||||
.material = try materials.getOrLoad(engine, textures, @field(walls, field.name).material, temp_allocator),
|
||||
.material = try materials.getOrLoad(engine, textures, stbi, @field(walls, field.name).material, temp_allocator),
|
||||
.transform = @field(walls, field.name).transform,
|
||||
};
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
const Materials = @This();
|
||||
const std = @import("std");
|
||||
|
||||
const media = @import("media");
|
||||
const shaders = @import("../shaders.zig");
|
||||
const vk = @import("vulkan");
|
||||
|
||||
@@ -148,7 +149,7 @@ pub fn getAtom(self: *const Materials, filename: Atom) ?Id {
|
||||
/// deinitialized or reset after this function returns. Note that during loading
|
||||
/// the engine will make its own persistent allocations, so an out of memory
|
||||
/// error is not necessarily related to `temp_allocator`.
|
||||
pub fn getOrLoad(self: *Materials, engine: *Engine, textures: *Textures, maybe_filename: ?[]const u8, temp_allocator: std.mem.Allocator) !Id {
|
||||
pub fn getOrLoad(self: *Materials, engine: *Engine, textures: *Textures, stbi: *media.stbi, maybe_filename: ?[]const u8, temp_allocator: std.mem.Allocator) !Id {
|
||||
if (maybe_filename) |filename| {
|
||||
const key: Key = .{
|
||||
// If the material already exists, then the atom must exist and the
|
||||
@@ -165,7 +166,7 @@ pub fn getOrLoad(self: *Materials, engine: *Engine, textures: *Textures, maybe_f
|
||||
const id = Id.fromIndexSafe(self.material_count) catch |err| switch (err) {
|
||||
error.Overflow => return error.OutOfMaterials,
|
||||
};
|
||||
try self.loadMaterial(engine, textures, filename, id.toInt(), temp_allocator);
|
||||
try self.loadMaterial(engine, textures, stbi, filename, id.toInt(), temp_allocator);
|
||||
|
||||
self.map.putAssumeCapacityNoClobber(key, id);
|
||||
self.material_count += 1;
|
||||
@@ -188,7 +189,7 @@ pub fn getOrLoad(self: *Materials, engine: *Engine, textures: *Textures, maybe_f
|
||||
/// deinitialized or reset after this function returns. Note that during loading
|
||||
/// the engine will make its own persistent allocations, so an out of memory
|
||||
/// error is not necessarily related to `temp_allocator`.
|
||||
pub fn getOrLoadAtom(self: *Materials, engine: *Engine, textures: *Textures, filename: Atom, temp_allocator: std.mem.Allocator) !Id {
|
||||
pub fn getOrLoadAtom(self: *Materials, engine: *Engine, textures: *Textures, stbi: *media.stbi, filename: Atom, temp_allocator: std.mem.Allocator) !Id {
|
||||
if (filename != .empty) {
|
||||
const key: Key = .{
|
||||
.filename = filename,
|
||||
@@ -203,7 +204,7 @@ pub fn getOrLoadAtom(self: *Materials, engine: *Engine, textures: *Textures, fil
|
||||
const id = Id.fromIndexSafe(self.material_count) catch |err| switch (err) {
|
||||
error.Overflow => return error.OutOfMaterials,
|
||||
};
|
||||
try self.loadMaterial(engine, textures, filename.toString(), id.toInt(), temp_allocator);
|
||||
try self.loadMaterial(engine, textures, stbi, filename.toString(), id.toInt(), temp_allocator);
|
||||
|
||||
self.map.putAssumeCapacityNoClobber(key, id);
|
||||
self.material_count += 1;
|
||||
@@ -225,7 +226,7 @@ pub fn getOrLoadAtom(self: *Materials, engine: *Engine, textures: *Textures, fil
|
||||
/// deinitialized or reset after this function returns. Note that during loading
|
||||
/// the engine will make its own persistent allocations, so an out of memory
|
||||
/// error is not necessarily related to `temp_allocator`.
|
||||
pub fn loadAll(self: *Materials, engine: *Engine, textures: *Textures, temp_allocator: std.mem.Allocator) void {
|
||||
pub fn loadAll(self: *Materials, engine: *Engine, textures: *Textures, stbi: *media.stbi, temp_allocator: std.mem.Allocator) void {
|
||||
const cwd = std.fs.cwd();
|
||||
|
||||
var dir = cwd.openDir("assets/materials", .{ .iterate = true }) catch |err| {
|
||||
@@ -244,13 +245,13 @@ pub fn loadAll(self: *Materials, engine: *Engine, textures: *Textures, temp_allo
|
||||
continue;
|
||||
}
|
||||
|
||||
_ = self.getOrLoad(engine, textures, entry.name, temp_allocator) catch |err| {
|
||||
_ = self.getOrLoad(engine, textures, stbi, entry.name, temp_allocator) catch |err| {
|
||||
std.log.err("Error while loading material entry {s}: {s}", .{ entry.name, @errorName(err) });
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
fn loadMaterial(self: *Materials, engine: *Engine, textures: *Textures, filename: []const u8, index: u32, temp_allocator: std.mem.Allocator) !void {
|
||||
fn loadMaterial(self: *Materials, engine: *Engine, textures: *Textures, stbi: *media.stbi, filename: []const u8, index: u32, temp_allocator: std.mem.Allocator) !void {
|
||||
const MaterialJson = struct {
|
||||
baseColor: [3]f32 = .{ 1, 1, 1 },
|
||||
baseColorTexture: ?[]const u8 = null,
|
||||
@@ -302,10 +303,10 @@ fn loadMaterial(self: *Materials, engine: *Engine, textures: *Textures, filename
|
||||
.normal_scale = material_json.normalScale,
|
||||
.occlusion_texture_strength = material_json.occlusionTextureStrength,
|
||||
.roughness = material_json.roughness,
|
||||
.base_color_texture = try textures.getOrLoad(engine, material_json.baseColorTexture, .base_color, temp_allocator),
|
||||
.emissive_texture = try textures.getOrLoad(engine, material_json.emissiveTexture, .emissive, temp_allocator),
|
||||
.normal_texture = try textures.getOrLoad(engine, material_json.normalTexture, .normal, temp_allocator),
|
||||
.occlusion_roughness_metallic_texture = try textures.getOrLoad(engine, material_json.occlusionRoughnessMetallicTexture, .occlusion_roughness_metallic, temp_allocator),
|
||||
.base_color_texture = try textures.getOrLoad(engine, stbi, material_json.baseColorTexture, .base_color),
|
||||
.emissive_texture = try textures.getOrLoad(engine, stbi, material_json.emissiveTexture, .emissive),
|
||||
.normal_texture = try textures.getOrLoad(engine, stbi, material_json.normalTexture, .normal),
|
||||
.occlusion_roughness_metallic_texture = try textures.getOrLoad(engine, stbi, material_json.occlusionRoughnessMetallicTexture, .occlusion_roughness_metallic),
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
const Textures = @This();
|
||||
const std = @import("std");
|
||||
|
||||
const stbi = @import("zstbi");
|
||||
const media = @import("media");
|
||||
|
||||
const Atom = @import("../engine/Atom.zig").Atom;
|
||||
const Engine = @import("../engine/Engine.zig");
|
||||
@@ -172,14 +172,7 @@ pub fn getAtom(self: *const Textures, filename: Atom, usage: Texture.Usage) ?Id
|
||||
/// if necessary. Will not return any error if the texture already exists. When
|
||||
/// the filename is `null`, returns an empty texture ID appropriate for given
|
||||
/// usage.
|
||||
///
|
||||
/// When a texture is being loaded, `temp_allocator` is used for temporary
|
||||
/// allocations necessary to perform all operations. No memory allocated with
|
||||
/// `temp_allocator` is retained, so the allocator can be deinitialized or reset
|
||||
/// after this function returns. Note that during loading the engine will make
|
||||
/// its own persistent allocations, so an out of memory error is not necessarily
|
||||
/// related to `temp_allocator`.
|
||||
pub fn getOrLoad(self: *Textures, engine: *Engine, maybe_filename: ?[]const u8, usage: Texture.Usage, temp_allocator: std.mem.Allocator) !Id {
|
||||
pub fn getOrLoad(self: *Textures, engine: *Engine, stbi: *media.stbi, maybe_filename: ?[]const u8, usage: Texture.Usage) !Id {
|
||||
if (maybe_filename) |filename| {
|
||||
const key: Key = .{
|
||||
// If the texture already exists, then the atom must exist and the
|
||||
@@ -197,7 +190,7 @@ pub fn getOrLoad(self: *Textures, engine: *Engine, maybe_filename: ?[]const u8,
|
||||
const id = Id.fromIndexSafe(self.array.items.len) catch |err| switch (err) {
|
||||
error.Overflow => return error.OutOfTextures,
|
||||
};
|
||||
const texture = try loadTexture(engine, filename, usage, temp_allocator);
|
||||
const texture = try loadTexture(engine, stbi, filename, usage);
|
||||
|
||||
self.map.putAssumeCapacityNoClobber(key, id);
|
||||
self.array.appendAssumeCapacity(texture);
|
||||
@@ -214,14 +207,7 @@ pub fn getOrLoad(self: *Textures, engine: *Engine, maybe_filename: ?[]const u8,
|
||||
/// if necessary. Will not return any error if the texture already exists. When
|
||||
/// the filename is `.empty`, returns an empty texture ID appropriate for given
|
||||
/// usage.
|
||||
///
|
||||
/// When a texture is being loaded, `temp_allocator` is used for temporary
|
||||
/// allocations necessary to perform all operations. No memory allocated with
|
||||
/// `temp_allocator` is retained, so the allocator can be deinitialized or reset
|
||||
/// after this function returns. Note that during loading the engine will make
|
||||
/// its own persistent allocations, so an out of memory is not necessarily
|
||||
/// related to `temp_allocator`.
|
||||
pub fn getOrLoadAtom(self: *Textures, engine: *Engine, filename: Atom, usage: Texture.Usage, temp_allocator: std.mem.Allocator) !Id {
|
||||
pub fn getOrLoadAtom(self: *Textures, engine: *Engine, stbi: *media.stbi, filename: Atom, usage: Texture.Usage) !Id {
|
||||
if (filename != .empty) {
|
||||
const key: Key = .{
|
||||
.filename = filename,
|
||||
@@ -237,7 +223,7 @@ pub fn getOrLoadAtom(self: *Textures, engine: *Engine, filename: Atom, usage: Te
|
||||
const id = Id.fromIndexSafe(self.array.items.len) catch |err| switch (err) {
|
||||
error.Overflow => return error.OutOfTextures,
|
||||
};
|
||||
const texture = try loadTexture(engine, filename.toString(), usage, temp_allocator);
|
||||
const texture = try loadTexture(engine, stbi, filename.toString(), usage);
|
||||
|
||||
self.map.putAssumeCapacityNoClobber(key, id);
|
||||
self.array.appendAssumeCapacity(texture);
|
||||
@@ -249,7 +235,7 @@ pub fn getOrLoadAtom(self: *Textures, engine: *Engine, filename: Atom, usage: Te
|
||||
}
|
||||
}
|
||||
|
||||
fn loadTexture(engine: *Engine, filename: []const u8, usage: Texture.Usage, temp_allocator: std.mem.Allocator) !Texture {
|
||||
fn loadTexture(engine: *Engine, stbi: *media.stbi, filename: []const u8, usage: Texture.Usage) !Texture {
|
||||
std.log.debug("Loading texture \"{s}\" as {s}...", .{ filename, @tagName(usage) });
|
||||
|
||||
const cwd = std.fs.cwd();
|
||||
@@ -257,15 +243,25 @@ fn loadTexture(engine: *Engine, filename: []const u8, usage: Texture.Usage, temp
|
||||
var dir = try cwd.openDir("assets/textures", .{});
|
||||
defer dir.close();
|
||||
|
||||
const file_buf = try dir.readFileAlloc(temp_allocator, filename, std.math.maxInt(usize));
|
||||
defer temp_allocator.free(file_buf);
|
||||
var file = try dir.openFile(filename, .{});
|
||||
defer file.close();
|
||||
|
||||
// The textures are expected to be small; a standard block base color as a
|
||||
// PNG takes well below 1 kiB.
|
||||
var buf: [4096]u8 = undefined;
|
||||
var reader = file.reader(&buf);
|
||||
|
||||
const img = try stbi.loadDynamicIo(&reader.interface);
|
||||
defer stbi.freeDynamic(img);
|
||||
|
||||
const data = img.data[0 .. img.width * img.height];
|
||||
|
||||
var img = try stbi.Image.loadFromMemory(file_buf, usage.samplesPerTexel());
|
||||
defer img.deinit();
|
||||
std.debug.assert(img.num_components == usage.samplesPerTexel());
|
||||
if (usage == .normal) {
|
||||
for (img.data) |*sample| {
|
||||
sample.* = sample.* +% 128;
|
||||
for (data) |*pixel| {
|
||||
pixel.r = pixel.r +% 128;
|
||||
pixel.g = pixel.g +% 128;
|
||||
pixel.b = pixel.b +% 128;
|
||||
pixel.a = pixel.a +% 128;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -278,7 +274,7 @@ fn loadTexture(engine: *Engine, filename: []const u8, usage: Texture.Usage, temp
|
||||
});
|
||||
errdefer texture.deinit(engine);
|
||||
|
||||
try texture.writeRaw(engine, img.data);
|
||||
try texture.writeRaw(engine, @ptrCast(data));
|
||||
return texture;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user