Skip to content
/ zmesh Public
forked from zig-gamedev/zmesh

Zig library for loading, generating, processing and optimising triangle meshes.

License

Notifications You must be signed in to change notification settings

ppatt/zmesh

 
 

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

10 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

image

Zig library for loading, generating, processing and optimising triangle meshes.

Under the hood this library uses below C/C++ libraries:

All memory allocations go through user-supplied, Zig allocator.

As an example program please see procedural mesh (wgpu).

Getting started

Example build.zig:

pub fn build(b: *std.Build) void {
    const exe = b.addExecutable(.{ ... });

    const zmesh = b.dependency("zmesh", .{});
    exe.root_module.addImport("zmesh", zmesh.module("root"));
    exe.linkLibrary(zmesh.artifact("zmesh"));
}

Zemscripten build.zig example:

pub fn build(b: *std.Build) void {
    const target = b.resolveTargetQuery(.{
        .cpu_arch = .wasm32,
        .os_tag = .emscripten,
    });

    const wasm = b.addLibrary(.{ .name = "zemscripten-build", .linkage = .static, .root_module = b.createModule(.{
        .root_source_file = b.path("main.zig"),
        .target = target,
        .optimize = optimize,
    }) });

    // Add Emscripten include paths for @cImport
    const emsdk_path = b.dependency("emsdk", .{}).path("").getPath(b);
    const emscripten_include_path = b.pathJoin(&.{ emsdk_path, "upstream", "emscripten", "cache", "sysroot", "include" });
    wasm.root_module.addSystemIncludePath(.{ .cwd_relative = emscripten_include_path });

    const zemscripten = b.dependency("zemscripten", .{});
    const zmesh = b.dependency("zmesh", .{
        .target = target,
        .optimize = optimize,
        .emscripten_include_path = emscripten_include_path,
    });

    wasm.root_module.addImport("zmesh", zmesh.module("root"));
    wasm.linkLibrary(zmesh.artifact("zmesh"));

    ...
}

Now in your code you may import and use zmesh:

const zmesh = @import("zmesh");

pub fn main() !void {
    ...
    zmesh.init(allocator);
    defer zmesh.deinit();

    var custom = zmesh.Shape.init(indices, positions, normals, texcoords);
    defer custom.deinit();

    var disk = zmesh.Shape.initParametricDisk(10, 2);
    defer disk.deinit();
    disk.invert(0, 0);

    var cylinder = zmesh.Shape.initCylinder(10, 4);
    defer cylinder.deinit();

    cylinder.merge(disk);
    cylinder.translate(0, 0, -1);
    disk.invert(0, 0);
    cylinder.merge(disk);

    cylinder.scale(0.5, 0.5, 2);
    cylinder.rotate(math.pi * 0.5, 1.0, 0.0, 0.0);

    cylinder.unweld();
    cylinder.computeNormals();
    ...
}
const zmesh = @import("zmesh");

pub fn main() !void {
    zmesh.init(allocator);
    defer zmesh.deinit();

    //
    // Load mesh
    //
    const data = try zmesh.io.zcgltf.parseAndLoadFile(content_dir ++ "cube.gltf");
    defer zmesh.io.zcgltf.freeData(data);

    var mesh_indices = std.ArrayListUnmanaged(u32){};
    var mesh_positions = std.ArrayListUnmanaged([3]f32){};
    var mesh_normals = std.ArrayListUnmanaged([3]f32){};

    try zmesh.io.zcgltf.appendMeshPrimitive(
        allocator,
        data,
        0, // mesh index
        0, // gltf primitive index (submesh index)
        &mesh_indices,
        &mesh_positions,
        &mesh_normals, // normals (optional)
        null, // texcoords (optional)
        null, // tangents (optional)
    );
    ...

    //
    // Optimize mesh
    //
    const Vertex = struct {
        position: [3]f32,
        normal: [3]f32,
    };

    var remap = std.ArrayListUnmanaged(u32){};
    try remap.resize(allocator, src_indices.items.len);

    const num_unique_vertices = zmesh.opt.generateVertexRemap(
        remap.items, // 'vertex remap' (destination)
        src_indices.items, // non-optimized indices
        Vertex, // Zig type describing your vertex
        src_vertices.items, // non-optimized vertices
    );

    var optimized_vertices = std.ArrayListUnmanaged(Vertex){};
    try optimized_vertices.resize(allocator, num_unique_vertices);

    zmesh.opt.remapVertexBuffer(
        Vertex, // Zig type describing your vertex
        optimized_vertices.items, // optimized vertices (destination)
        src_vertices.items, // non-optimized vertices (source)
        remap.items, // 'vertex remap' generated by generateVertexRemap()
    );

    // More optimization steps are available - see `zmeshoptimizer.zig` file.
}

About

Zig library for loading, generating, processing and optimising triangle meshes.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages

  • C 47.8%
  • C++ 43.3%
  • Zig 8.9%