Reflection on type pub constants

I have a ui-colors.zig which just contains a rainbow (collective noun for colors?) of color constants;

...
pub const chocolate = 0xFFd2691e;
pub const coral = 0xFFff7f50;
pub const cornflowerblue = 0xFF6495ed;
...

I just wanted to put together a demo app that lists these by name and color, but I’m struggling to get the reflection right. I’ve used something like this before (but with inline for), but today I’m getting a strange error on the si. of access of union field 'struct' while field 'type' is active.

So my understanding of .zig files being structs seems wrong. Is there a way to do this please, without moving all the constants into their own struct? Thanks.

const colors = @import("ui-colors.zig");

pub fn tick() void {
    const si = @typeInfo(@TypeOf(colors));
    for (si.@"struct".fields, 0..) |fld, i| {
        _=i;
        const fval = @field(colors, fld.name);
        logS(fld.name);
        logS("=");
        logU32(fval);
    }
}

When you import it you get the struct (a type) as opposed to an instance of that struct!

Moreover - those are decls, not fields.

1 Like

Thanks :slight_smile: so that got me this far, but could use a hint for getting at the u32 value please.

    const si = @typeInfo(colors);
    for (si.@"struct".decls, 0..) |d, i| {
        _ = i;
        logS(d.name);
        logS("=");
        //logU32(fval);
    }

you should be able to use the @field builtin to get the value. From the docs:

Performs field access by a compile-time string. Works on both fields and declarations.

5 Likes

Perfect, working :slight_smile: thanks

1 Like

Hey, sorry I didn’t get back to you sooner. Glad @Calder-Ty could help you out!

1 Like

Just a quick note - if you ever use this for iterating over @cImport()you might need to use inline for with if (comptime xxx) {}wrap because the translated code/struct often includes some @compileError calls.

2 Likes