diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 84280cd..5e9b7da 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -15,6 +15,6 @@ jobs: check: uses: fizzyedit/plugin-build-action/.github/workflows/check.yml@v7 with: - zig-version: "0.16.0" + zig-version: "0.17.0" # secrets: # build_env: ${{ secrets.MY_BUILD_ENV }} # as in release.yml, if the build needs one diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 7d0b531..655448f 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -14,4 +14,4 @@ jobs: permissions: contents: write with: - zig-version: "0.16.0" + zig-version: "0.17.0" diff --git a/.github/workflows/sdk-repin.yml b/.github/workflows/sdk-repin.yml index e1a776c..28a0fd0 100644 --- a/.github/workflows/sdk-repin.yml +++ b/.github/workflows/sdk-repin.yml @@ -31,4 +31,4 @@ jobs: with: sdk-version: ${{ github.event.client_payload.version || inputs.sdk-version || '' }} force: ${{ inputs.force == true }} - zig-version: "0.16.0" + zig-version: "0.17.0" diff --git a/build.zig.zon b/build.zig.zon index 116dc03..9d11e92 100644 --- a/build.zig.zon +++ b/build.zig.zon @@ -1,7 +1,7 @@ .{ .name = .pixi, .version = "0.0.1", - .minimum_zig_version = "0.16.0", + .minimum_zig_version = "0.17.0", .paths = .{ "build.zig", "build.zig.zon", @@ -15,8 +15,8 @@ .fingerprint = 0xdef5a52dbae70684, .dependencies = .{ .assetpack = .{ - .url = "https://github.com/foxnne/assetpack/archive/ac7592f3f5988857840d0df4610e1e1fad690e2e.tar.gz", - .hash = "assetpack-0.2.0-5DA2d1ZkAADJanNVdWrUBOGMhOzUENhrUiqXcHADxY2x", + .url = "git+https://github.com/foxnne/assetpack#fbc4392910375d428735ed9852fa2aedabc6ff52", + .hash = "assetpack-0.2.0-5DA2d2hkAACLscFkiyim4xD-Fqum33ndL5V5IFvN_dAS", }, .icons = .{ .url = "https://github.com/foxnne/zig-lib-icons/archive/db034786a1286ab28dc35aba534c098aa4f1a3aa.tar.gz", @@ -27,8 +27,8 @@ // The published SDK, not a path into a checkout: a release has to build from a // clean clone, and the release asset (never the tag's git archive) is the SDK // package alone — the monorepo root zon carries the app's own dependencies. - .url = "https://github.com/fizzyedit/fizzy/releases/download/sdk-v0.2.29/fizzy-sdk-v0.2.29.tar.gz", - .hash = "fizzy-0.2.29-SGBwY2sxJgCLLSPt4HLdlMSg7WtcP4K0fdtXI5WwJl2d", + .url = "https://github.com/fizzyedit/fizzy/releases/download/sdk-v0.2.30/fizzy-sdk-v0.2.30.tar.gz", + .hash = "fizzy-0.2.30-SGBwY1QnJwDznUMVnSLATxXgH2e8_Vz7eMwLj9UQ0sVU", }, }, } diff --git a/plugin.zig.zon b/plugin.zig.zon index 2ceb9ae..cbbbb95 100644 --- a/plugin.zig.zon +++ b/plugin.zig.zon @@ -1,8 +1,8 @@ .{ .id = "pixi", .name = "Pixi", - .version = "0.1.47", - .min_sdk_version = "0.2.29", + .version = "0.1.48", + .min_sdk_version = "0.2.30", .description = "Pixel-art editor: sprite and atlas editing for fizzy.", .tags = .{ "editor", "pixel-art" }, .author = "foxnne", diff --git a/src/Brush.zig b/src/Brush.zig index 729c628..1b97888 100644 --- a/src/Brush.zig +++ b/src/Brush.zig @@ -32,7 +32,7 @@ pub fn deinit(self: *Brush, gpa: std.mem.Allocator) void { /// The shape of a brush `size` pixels across, centred at `side / 2`: every pixel of a square, or /// those of a circle, its radius trimmed a little so small circles read round. pub fn shapeOf(kind: Kind, size: u8) Shape { - var out: Shape = .initEmpty(); + var out: Shape = .empty; const s: i32 = @max(1, size); const half = @divFloor(s, 2); var i: i32 = 0; @@ -90,7 +90,7 @@ fn covers(shape: *const Shape, o: Offset) bool { const testing = std.testing; fn shapeFrom(comptime inside: fn (x: i32, y: i32) bool) Shape { - var s: Shape = .initEmpty(); + var s: Shape = .empty; var y: i32 = -side / 2; while (y < side / 2) : (y += 1) { var x: i32 = -side / 2; diff --git a/src/PackJob.zig b/src/PackJob.zig index 8c06fb3..5d30c6f 100644 --- a/src/PackJob.zig +++ b/src/PackJob.zig @@ -200,7 +200,7 @@ window: *dvui.Window, started_at_ns: i128, -phase: std.atomic.Value(u8) = .init(@intFromEnum(Phase.queued)), +phase: std.atomic.Value(u8) = .init(@backingInt(Phase.queued)), /// Worker reports `(done_inputs, total_inputs)` while in the `loading` / `appending` phases. progress_num: std.atomic.Value(u32) = .init(0), @@ -300,7 +300,7 @@ pub fn workerMain(job: *PackJob) void { // `.path`-loaded `PackFile`s, collapse carry-overs) lives in `ws` and is freed below. const work = WorkerState.init(runtime.allocator()) catch |e| { job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; var ws = work; @@ -311,21 +311,21 @@ pub fn workerMain(job: *PackJob) void { // buffers and `buildAtlas` blits straight from those pointers. `.open` inputs are owned // by `job.inputs` for the job's full lifetime; `.path`-loaded files are parked in // `ws.loaded_files` (freed with `ws.deinit`). - job.phase.store(@intFromEnum(Phase.loading), .release); + job.phase.store(@backingInt(Phase.loading), .release); job.progress_den.store(@intCast(job.inputs.len), .monotonic); for (job.inputs, 0..) |*input, idx| { if (job.cancelled.load(.monotonic)) { - job.phase.store(@intFromEnum(Phase.cancelled), .release); + job.phase.store(@backingInt(Phase.cancelled), .release); return; } switch (input.*) { .open => |*pf| { - job.phase.store(@intFromEnum(Phase.appending), .release); + job.phase.store(@backingInt(Phase.appending), .release); ws.appendPackFile(pf) catch |e| { job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; }, @@ -338,13 +338,13 @@ pub fn workerMain(job: *PackJob) void { // reachability graph. if (comptime @import("builtin").target.cpu.arch == .wasm32) { job.err = error.PathInputsNotSupportedOnWasm; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; } - job.phase.store(@intFromEnum(Phase.loading), .release); + job.phase.store(@backingInt(Phase.loading), .release); const maybe_pf = PackFile.fromPath(runtime.allocator(), path) catch |e| { job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; if (maybe_pf) |pf_val| { @@ -352,14 +352,14 @@ pub fn workerMain(job: *PackJob) void { var tmp = pf_val; tmp.deinit(); job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; - job.phase.store(@intFromEnum(Phase.appending), .release); + job.phase.store(@backingInt(Phase.appending), .release); const ref = &ws.loaded_files.items[ws.loaded_files.items.len - 1]; ws.appendPackFile(ref) catch |e| { job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; } @@ -372,33 +372,33 @@ pub fn workerMain(job: *PackJob) void { // Nothing to pack — keep `result_atlas == null`, surface as `ready`. The main thread // treats null-result the same as the old `packAndClear` early-out: leave the existing // atlas in place. - job.phase.store(@intFromEnum(Phase.ready), .release); + job.phase.store(@backingInt(Phase.ready), .release); return; } // Try increasing texture sizes until everything fits. - job.phase.store(@intFromEnum(Phase.packing), .release); + job.phase.store(@backingInt(Phase.packing), .release); const tex_size = ws.packRects() catch |e| { job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; } orelse { job.err = error.PackFailed; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; if (job.cancelled.load(.monotonic)) { - job.phase.store(@intFromEnum(Phase.cancelled), .release); + job.phase.store(@backingInt(Phase.cancelled), .release); return; } // Blit each emitted sprite into a fresh atlas pixel buffer at the location chosen by // `packRects`, then assemble the `Internal.Atlas` value that the main thread will install. - job.phase.store(@intFromEnum(Phase.blitting), .release); + job.phase.store(@backingInt(Phase.blitting), .release); const atlas = ws.buildAtlas(tex_size) catch |e| { job.err = e; - job.phase.store(@intFromEnum(Phase.failed), .release); + job.phase.store(@backingInt(Phase.failed), .release); return; }; @@ -408,12 +408,12 @@ pub fn workerMain(job: *PackJob) void { for (atlas.data.animations) |*anim| runtime.allocator().free(anim.name); runtime.allocator().free(atlas.data.animations); runtime.allocator().free(atlas.data.sprites); - job.phase.store(@intFromEnum(Phase.cancelled), .release); + job.phase.store(@backingInt(Phase.cancelled), .release); return; } job.result_atlas = atlas; - job.phase.store(@intFromEnum(Phase.ready), .release); + job.phase.store(@backingInt(Phase.ready), .release); } // ---------------------------------------------------------------------------- diff --git a/src/Tools.zig b/src/Tools.zig index 5e1d47e..1c1b8e0 100644 --- a/src/Tools.zig +++ b/src/Tools.zig @@ -89,7 +89,7 @@ settings_popover: bool = false, settings_popover_tool: Tool = .pointer, settings_popover_from: dvui.Point.Natural = .{}, -stroke: Brush.Shape = .initEmpty(), +stroke: Brush.Shape = .empty, /// `stroke` as offsets to stamp, rebuilt with it. brush: Brush = .{}, gpa: std.mem.Allocator, diff --git a/src/Transform.zig b/src/Transform.zig index 38aa095..c816ee3 100644 --- a/src/Transform.zig +++ b/src/Transform.zig @@ -26,7 +26,7 @@ ortho: bool = true, rendered_key: u64 = 0, pub fn point(self: *Transform, transform_point: TransformPoint) *dvui.Point { - return &self.data_points[@intFromEnum(transform_point)]; + return &self.data_points[@backingInt(transform_point)]; } /// Accepts the current transform and applies it to the currently selected layer diff --git a/src/algorithms/reduce.zig b/src/algorithms/reduce.zig index 69546d9..2320381 100644 --- a/src/algorithms/reduce.zig +++ b/src/algorithms/reduce.zig @@ -46,7 +46,7 @@ pub fn anyOpaque(pixels: []const [4]u8) bool { const V = @Vector(vec_len, u32); // Alpha is byte 3 of each pixel: the high byte of the u32 on little-endian // targets, the low byte on big-endian. - const alpha_mask: V = @splat(switch (builtin.cpu.arch.endian()) { + const alpha_mask: V = @splat(switch (builtin.target.cpu.arch.endian()) { .little => 0xFF00_0000, .big => 0x0000_00FF, }); diff --git a/src/deps/stbi/zstbi.zig b/src/deps/stbi/zstbi.zig index d968b70..608af2f 100644 --- a/src/deps/stbi/zstbi.zig +++ b/src/deps/stbi/zstbi.zig @@ -53,7 +53,7 @@ pub fn packRects(context: *Context, rects: []Rect) usize { } pub fn setupHeuristic(context: *Context, heuristic: Heuristic) void { - stbrp_setup_heuristic(context, @as(u32, @intCast(@intFromEnum(heuristic)))); + stbrp_setup_heuristic(context, @as(u32, @intCast(@backingInt(heuristic)))); } pub extern fn stbrp_init_target(context: [*c]Context, width: u32, height: u32, nodes: [*c]Node, num_nodes: usize) void; diff --git a/src/dialogs/Export.zig b/src/dialogs/Export.zig index c1a6d59..8e65490 100644 --- a/src/dialogs/Export.zig +++ b/src/dialogs/Export.zig @@ -84,8 +84,8 @@ pub fn dialog(id: dvui.Id) anyerror!bool { .margin = .{ .y = 2, .h = 4 }, .padding = .all(6), .expand = .horizontal, - .color_fill = .{ .color = if (mode == @as(@TypeOf(mode), @enumFromInt(i))) dvui.themeGet().color(.window, .fill).lighten(-4) else dvui.themeGet().color(.control, .fill) }, - .box_shadow = if (i != @intFromEnum(mode)) .{ + .color_fill = .{ .color = if (mode == @as(@TypeOf(mode), @fromBackingInt(@intCast(i)))) dvui.themeGet().color(.window, .fill).lighten(-4) else dvui.themeGet().color(.control, .fill) }, + .box_shadow = if (i != @backingInt(mode)) .{ .color = .black, .offset = .{ .x = 0.0, .y = 2 }, .fade = 7.0, @@ -95,7 +95,7 @@ pub fn dialog(id: dvui.Id) anyerror!bool { } else null, }); defer button.deinit(); - if (i != @intFromEnum(mode)) { + if (i != @backingInt(mode)) { button.processEvents(); } @@ -120,13 +120,13 @@ pub fn dialog(id: dvui.Id) anyerror!bool { dvui.labelNoFmt(@src(), name, .{}, .{ .gravity_x = 0.5, .gravity_y = 0.5, - .color_text = .{ .color = if (mode == @as(@TypeOf(mode), @enumFromInt(i))) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, + .color_text = .{ .color = if (mode == @as(@TypeOf(mode), @fromBackingInt(@intCast(i)))) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, .margin = .all(0), .padding = .all(0), }); if (button.clicked()) { - mode = @enumFromInt(i); + mode = @fromBackingInt(@intCast(i)); if (mode == .animation) { anim_frame_index = 0; dvui.currentWindow().timerRemove(id); diff --git a/src/dialogs/GridLayout.zig b/src/dialogs/GridLayout.zig index 44c97cd..a8e75da 100644 --- a/src/dialogs/GridLayout.zig +++ b/src/dialogs/GridLayout.zig @@ -810,8 +810,8 @@ fn gridLayoutDrawModePill(dlg_id: dvui.Id) void { .margin = .{ .y = 2, .h = 4 }, .padding = .{ .x = 12, .y = 6, .w = 12, .h = 6 }, .expand = .horizontal, - .color_fill = .{ .color = if (mode == @as(@TypeOf(mode), @enumFromInt(i))) dvui.themeGet().color(.window, .fill).lighten(-4) else dvui.themeGet().color(.control, .fill) }, - .box_shadow = if (i != @intFromEnum(mode)) .{ + .color_fill = .{ .color = if (mode == @as(@TypeOf(mode), @fromBackingInt(@intCast(i)))) dvui.themeGet().color(.window, .fill).lighten(-4) else dvui.themeGet().color(.control, .fill) }, + .box_shadow = if (i != @backingInt(mode)) .{ .color = .black, .offset = .{ .x = 0.0, .y = 2 }, .fade = 7.0, @@ -821,7 +821,7 @@ fn gridLayoutDrawModePill(dlg_id: dvui.Id) void { } else null, }); defer button.deinit(); - if (i != @intFromEnum(mode)) { + if (i != @backingInt(mode)) { button.processEvents(); } @@ -846,13 +846,13 @@ fn gridLayoutDrawModePill(dlg_id: dvui.Id) void { dvui.labelNoFmt(@src(), name, .{}, .{ .gravity_x = 0.5, .gravity_y = 0.5, - .color_text = .{ .color = if (mode == @as(@TypeOf(mode), @enumFromInt(i))) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, + .color_text = .{ .color = if (mode == @as(@TypeOf(mode), @fromBackingInt(@intCast(i)))) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, .margin = .all(0), .padding = .all(0), }); if (button.clicked()) { - const new_mode: Mode = @enumFromInt(i); + const new_mode: Mode = @fromBackingInt(@intCast(i)); if (new_mode == .slice and mode != .slice) { if (file_id_for_dialog) |fid| if (runtime.state().docs.fileById(fid)) |tf| harmonizeSliceStateWithLayer(tf); @@ -1595,10 +1595,10 @@ pub fn windowFn(id: dvui.Id) anyerror!void { defer shell.deinit(); const header_kind: pixi.core.dialogs.DialogHeaderKind = switch (dvui.dataGet(null, id, "_header_kind", u8) orelse 0) { - @intFromEnum(pixi.core.dialogs.DialogHeaderKind.none) => .none, - @intFromEnum(pixi.core.dialogs.DialogHeaderKind.info) => .info, - @intFromEnum(pixi.core.dialogs.DialogHeaderKind.warning) => .warning, - @intFromEnum(pixi.core.dialogs.DialogHeaderKind.err) => .err, + @backingInt(pixi.core.dialogs.DialogHeaderKind.none) => .none, + @backingInt(pixi.core.dialogs.DialogHeaderKind.info) => .info, + @backingInt(pixi.core.dialogs.DialogHeaderKind.warning) => .warning, + @backingInt(pixi.core.dialogs.DialogHeaderKind.err) => .err, else => .none, }; diff --git a/src/dialogs/NewFile.zig b/src/dialogs/NewFile.zig index 34a29a2..63cc4cb 100644 --- a/src/dialogs/NewFile.zig +++ b/src/dialogs/NewFile.zig @@ -58,16 +58,16 @@ pub fn dialog(id: dvui.Id) anyerror!bool { defer hbox.deinit(); for (0..2) |i| { - const color = if (i == @intFromEnum(mode)) dvui.themeGet().color(.window, .fill).lighten(-4) else dvui.themeGet().color(.control, .fill); + const color = if (i == @backingInt(mode)) dvui.themeGet().color(.window, .fill).lighten(-4) else dvui.themeGet().color(.control, .fill); const button_opts: dvui.Options = .{ .padding = .all(6), .margin = .{ .y = 2, .h = 4 }, .corners = if (i == 0) .{ .tl = .round(100000), .bl = .round(100000) } else .{ .tr = .round(100000), .br = .round(100000) }, .expand = .horizontal, .color_fill = .{ .color = color }, - .color_fill_hover = if (i == @intFromEnum(mode)) .{ .color = color } else null, + .color_fill_hover = if (i == @backingInt(mode)) .{ .color = color } else null, .id_extra = i, - .box_shadow = if (i != @intFromEnum(mode)) .{ + .box_shadow = if (i != @backingInt(mode)) .{ .color = .black, .offset = .{ .x = 0.0, .y = 2.0 }, .fade = 7.0, @@ -80,7 +80,7 @@ pub fn dialog(id: dvui.Id) anyerror!bool { button.init(@src(), .{}, button_opts); defer button.deinit(); - if (i != @intFromEnum(mode)) { + if (i != @backingInt(mode)) { button.processEvents(); } @@ -90,7 +90,7 @@ pub fn dialog(id: dvui.Id) anyerror!bool { dvui.labelNoFmt(@src(), "Single", .{}, button_opts.strip().override(button.style()).override(.{ .gravity_x = 0.5, .gravity_y = 0.5, - .color_text = .{ .color = if (i == @intFromEnum(mode)) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, + .color_text = .{ .color = if (i == @backingInt(mode)) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, })); if (button.clicked()) { mode = .single; @@ -100,7 +100,7 @@ pub fn dialog(id: dvui.Id) anyerror!bool { dvui.labelNoFmt(@src(), "Grid", .{}, button_opts.strip().override(button.style()).override(.{ .gravity_x = 0.5, .gravity_y = 0.5, - .color_text = .{ .color = if (i == @intFromEnum(mode)) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, + .color_text = .{ .color = if (i == @backingInt(mode)) dvui.themeGet().color(.window, .text) else dvui.themeGet().color(.control, .text) }, })); if (button.clicked()) { mode = .grid; diff --git a/src/explorer/tools.zig b/src/explorer/tools.zig index 255ee6b..8812176 100644 --- a/src/explorer/tools.zig +++ b/src/explorer/tools.zig @@ -155,8 +155,8 @@ pub fn drawTools() !void { .padding = .{ .h = 10.0, .w = 4.0, .x = 4.0, .y = 4.0 }, }); defer toolbox.deinit(); - for (0..std.meta.fields(pixi.Tools.Tool).len) |i| { - const tool: pixi.Tools.Tool = @enumFromInt(i); + for (0..std.meta.fieldNames(pixi.Tools.Tool).len) |i| { + const tool: pixi.Tools.Tool = @fromBackingInt(@intCast(i)); const id_extra = i; const selected = runtime.state().tools.current == tool; diff --git a/src/internal/File.zig b/src/internal/File.zig index 38d394f..0717e12 100644 --- a/src/internal/File.zig +++ b/src/internal/File.zig @@ -340,7 +340,7 @@ pub fn checkerboardTileBlurredTexture(file: *File, sigma_px: f32, screen_scale: const b: f32 = @floatFromInt(even[ch]); px[ch] = @intFromFloat(std.math.clamp(@round(a + (b - a) * f), 0, 255)); } - buf[y * w + x] = @bitCast(px); + buf[y * w + x] = std.mem.bytesToValue(dvui.Color.PMA, &px); } } @@ -492,7 +492,7 @@ fn loadFizzyZip(path: []const u8, file_bytes: ?[]const u8) !?pixi.internal.File return error.InvalidExtension; const null_terminated_path = if (file_bytes == null) - try runtime.allocator().dupeZ(u8, path) + try runtime.allocator().dupeSentinel(u8, path, 0) else ""; defer if (file_bytes == null) runtime.allocator().free(null_terminated_path); @@ -1477,7 +1477,7 @@ pub fn applyStep(file: *File, effect: []const u8, motion: []const u8, show: bool if (motion.len > 0) if (steps.decodeMotion(gpa, motion, step.indices.len)) |m| { defer m.deinit(gpa); if (gpa.alloc(Reveal.Mark, m.kinds.len)) |ms| { - for (ms, m.kinds, m.lens) |*mk, k, l| mk.* = .{ .kind = @enumFromInt(k), .len = l }; + for (ms, m.kinds, m.lens) |*mk, k, l| mk.* = .{ .kind = @fromBackingInt(@intCast(k)), .len = l }; marks = ms; for (m.positions, drawn, was) |p, *d, *w| { d.* = .{ .index = @intCast(step.indices[p]), .color = step.after[p] }; diff --git a/src/internal/History.zig b/src/internal/History.zig index 32a60f4..a4addc4 100644 --- a/src/internal/History.zig +++ b/src/internal/History.zig @@ -38,7 +38,7 @@ pub const Person = struct { edits: u32 = 0, undone: u32 = 0, redone: u32 = 0, - kinds: std.EnumSet(ChangeType) = .initEmpty(), + kinds: std.EnumSet(ChangeType) = .empty, pub fn any(p: Person) bool { return p.edits + p.undone + p.redone > 0; @@ -212,7 +212,7 @@ pub const Change = union(ChangeType) { .selected = 0, } }, .layer_name => .{ .animation_name = .{ - .name = [_:0]u8{0} ** pixi.max_name_len, + .name = &.{}, .index = 0, } }, else => error.NotSupported, @@ -1086,7 +1086,7 @@ fn motionOf(arena: std.mem.Allocator, history: *const History, indices: []const const kinds = arena.alloc(u8, marks.len) catch return ""; const lens = arena.alloc(u32, marks.len) catch return ""; for (marks, kinds, lens) |m, *k, *l| { - k.* = @intFromEnum(m.kind); + k.* = @backingInt(m.kind); l.* = m.len; } var out: std.Io.Writer.Allocating = .init(arena); diff --git a/src/internal/steps.zig b/src/internal/steps.zig index 03ec1f2..33f599a 100644 --- a/src/internal/steps.zig +++ b/src/internal/steps.zig @@ -28,7 +28,7 @@ pub fn encode(gpa: std.mem.Allocator, w: *std.Io.Writer, layer: u64, indices: [] const order = try indexOrder(gpa, indices); defer gpa.free(order); - try w.writeByte(@intFromEnum(Tag.pixels)); + try w.writeByte(@backingInt(Tag.pixels)); try w.writeUleb128(layer); try w.writeUleb128(indices.len); var last: usize = 0; diff --git a/src/panel/sprites.zig b/src/panel/sprites.zig index 6547998..fd14fb8 100644 --- a/src/panel/sprites.zig +++ b/src/panel/sprites.zig @@ -200,9 +200,9 @@ water: wsurf.WaterSurface = .{}, /// Focused slot index last frame — re-anchors the water field as the shelf scrolls. prev_center_i: i64 = 0, /// Per-slot previous fly offset for velocity estimation (indexed by `d + field_center`). -prev_fly_offset: [max_refl_ripple_slots]f32 = .{0} ** max_refl_ripple_slots, +prev_fly_offset: [max_refl_ripple_slots]f32 = @splat(0), /// Per-slot: card dipped below the waterline (fly-in inBack overshoot), awaiting a splash. -was_dipping: [max_refl_ripple_slots]bool = .{false} ** max_refl_ripple_slots, +was_dipping: [max_refl_ripple_slots]bool = @splat(false), /// Previous `scroll_pos` — the per-frame delta drives the inertial slosh. prev_scroll_pos: f32 = 0.0, /// Smoothed shelf velocity (slots/s); its per-frame change tilts the water. diff --git a/src/radial_menu.zig b/src/radial_menu.zig index c500b90..0699a1d 100644 --- a/src/radial_menu.zig +++ b/src/radial_menu.zig @@ -76,7 +76,7 @@ pub fn draw() !void { dvui.clipSet(pixi.core.screens.pixelsFor(screen)); const center = fw.data().rectScale().pointFromPhysical(runtime.state().tools.radial_menu.center); - const tool_count: usize = std.meta.fields(Tools.Tool).len; + const tool_count: usize = std.meta.fieldNames(Tools.Tool).len; const radius: f32 = 50.0; const width: f32 = radius * 2.0; const height: f32 = radius * 2.0; @@ -149,7 +149,7 @@ pub fn draw() !void { rect.x -= rect.w / 2.0; rect.y -= rect.h / 2.0; - const tool = @as(Tools.Tool, @enumFromInt(i)); + const tool = @as(Tools.Tool, @fromBackingInt(@intCast(i))); var button: dvui.ButtonWidget = undefined; button.init(@src(), .{}, .{ diff --git a/src/sprite_render.zig b/src/sprite_render.zig index 1b8f1c3..dd9ad81 100644 --- a/src/sprite_render.zig +++ b/src/sprite_render.zig @@ -41,8 +41,8 @@ pub const reflection_surface_cols = pixi.water_surface.reflection_surface_cols; /// the seam (positive = down). The card itself stays flat — only the reflection /// mesh pins its top edge and propagates ripples downward. pub const ReflectionLagSample = struct { - cols_dx: [reflection_surface_cols]f32 = .{0} ** reflection_surface_cols, - cols_dy: [reflection_surface_cols]f32 = .{0} ** reflection_surface_cols, + cols_dx: [reflection_surface_cols]f32 = @splat(0), + cols_dy: [reflection_surface_cols]f32 = @splat(0), }; pub fn sprite(src: std.builtin.SourceLocation, init_opts: SpriteInitOptions, opts: dvui.Options) dvui.WidgetData { diff --git a/src/widgets/FileWidget.zig b/src/widgets/FileWidget.zig index 65bc466..6409e9a 100644 --- a/src/widgets/FileWidget.zig +++ b/src/widgets/FileWidget.zig @@ -1178,7 +1178,7 @@ fn renderFrostDetail(acc: *const TriAcc, tex: dvui.Texture, share: f32, uv_rect: if (uv_rect) |r| v.uv = .{ (v.pos.x - r.x) / r.w, (v.pos.y - r.y) / r.h }; } var copy = acc.*; - copy.vtx = .{ .items = vtx, .capacity = vtx.len }; + copy.vtx = .fromOwnedSlice(vtx); if (dvui.Backend.support_texture_blend) dvui.currentWindow().backend.textureBlend(tex, .over) catch {}; copy.render(tex); } @@ -2081,7 +2081,7 @@ fn drawSpriteBubbleForRow( var id_extra: usize = sprite_index; if (animation_index) |ai| { - id_extra = dvui.Id.extendId(@enumFromInt(sprite_index), @src(), ai).asUsize(); + id_extra = dvui.Id.extendId(@fromBackingInt(@intCast(sprite_index)), @src(), ai).asUsize(); } { @@ -2095,16 +2095,16 @@ fn drawSpriteBubbleForRow( if (distance < max_distance and pan.peek and current_point.y - sprite_rect.y < 0.0 and current_point.y - sprite_rect.y > -sprite_rect.h) { open = false; - id_extra = dvui.Id.update(@enumFromInt(id_extra), "peek").asUsize(); + id_extra = dvui.Id.update(@fromBackingInt(@intCast(id_extra)), "peek").asUsize(); } else { - id_extra = dvui.Id.update(@enumFromInt(id_extra), "unpeek").asUsize(); + id_extra = dvui.Id.update(@fromBackingInt(@intCast(id_extra)), "unpeek").asUsize(); } } if (accs != null) { - id_extra = dvui.Id.update(@enumFromInt(id_extra), "geom").asUsize(); + id_extra = dvui.Id.update(@fromBackingInt(@intCast(id_extra)), "geom").asUsize(); } else { - id_extra = dvui.Id.update(@enumFromInt(id_extra), "ui").asUsize(); + id_extra = dvui.Id.update(@fromBackingInt(@intCast(id_extra)), "ui").asUsize(); } var t: f32 = 0.0; @@ -3723,7 +3723,7 @@ pub fn processTransform(self: *FileWidget) void { triangles.rotate(.{ .x = transform.point(.pivot).x, .y = transform.point(.pivot).y }, transform.rotation); for (transform.data_points[0..6], 0..) |*data_point, point_index| { - const transform_point = @as(pixi.Transform.TransformPoint, @enumFromInt(point_index)); + const transform_point = @as(pixi.Transform.TransformPoint, @fromBackingInt(@intCast(point_index))); const screen_point = if (point_index < 4) file.editor.canvas.screenFromDataPoint(.{ .x = triangles.vertexes[point_index].pos.x, .y = triangles.vertexes[point_index].pos.y }) else file.editor.canvas.screenFromDataPoint(data_point.*); var screen_rect = dvui.Rect.Physical.fromPoint(screen_point); @@ -3740,7 +3740,7 @@ pub fn processTransform(self: *FileWidget) void { if (screen_rect.contains(dvui.currentWindow().mouse_pt)) { dvui.cursorSet(.hand); } else if (transform.active_point) |active_point| { - if (active_point == @as(pixi.Transform.TransformPoint, @enumFromInt(point_index))) { + if (active_point == @as(pixi.Transform.TransformPoint, @fromBackingInt(@intCast(point_index)))) { dvui.cursorSet(.hand); } } @@ -3773,7 +3773,7 @@ pub fn processTransform(self: *FileWidget) void { if (me.action == .press and me.button.pointer()) { if (screen_rect.contains(me.p)) { - transform.active_point = @enumFromInt(point_index); + transform.active_point = @fromBackingInt(@intCast(point_index)); e.handle(@src(), self.init_options.file.editor.canvas.scroll_container.data()); dvui.captureMouse(self.init_options.file.editor.canvas.scroll_container.data(), e.num); dvui.dragPreStart(me.button, me.p, .{ .name = "transform_vertex_drag" }); @@ -3817,7 +3817,7 @@ pub fn processTransform(self: *FileWidget) void { if (dvui.dragging(me.p, "transform_vertex_drag")) |_| { transform.dragging = true; if (transform.active_point) |active_point| { - if (@intFromEnum(active_point) == point_index) { + if (@backingInt(active_point) == point_index) { e.handle(@src(), self.init_options.file.editor.canvas.scroll_container.data()); // Set this state in advance so we can use it for the radius calculation @@ -4079,7 +4079,7 @@ pub fn drawTransform(self: *FileWidget) void { if (file.editor.transform) |*transform| { const show_ortho_dims = transform.ortho and blk: { if (transform.active_point) |ap| { - break :blk @intFromEnum(ap) < 4; + break :blk @backingInt(ap) < 4; } break :blk transform.dragging; }; @@ -4508,7 +4508,7 @@ pub fn drawTransform(self: *FileWidget) void { var color = dvui.themeGet().color(.window, .text); if (transform.active_point) |active_point| { - if (active_point == @as(pixi.Transform.TransformPoint, @enumFromInt(point_index))) { + if (active_point == @as(pixi.Transform.TransformPoint, @fromBackingInt(@intCast(point_index)))) { color = dvui.themeGet().color(.highlight, .fill); } } else if (screen_rect.contains(dvui.currentWindow().mouse_pt)) {