Skip to content

Commit 7ec0488

Browse files
committed
Implement applyConfigStruct
1 parent 948d5c7 commit 7ec0488

File tree

10 files changed

+47
-49
lines changed

10 files changed

+47
-49
lines changed

examples/demo.zig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ fn drawRounded(cnv: *anyopaque, ctx: *capy.DrawContext) !void {
7474
ctx.setColor(0.7, 0.9, 0.3);
7575
ctx.setLinearGradient(.{ .x0 = 80, .y0 = 0, .x1 = 100, .y1 = 100, .stops = &.{
7676
.{ .offset = 0.1, .color = capy.Color.yellow },
77-
.{ .offset = 0.8, .color = capy.Color.white },
77+
.{ .offset = 0.8, .color = capy.Color.red },
7878
} });
7979
ctx.roundedRectangleEx(
8080
0,

examples/fade.zig

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -33,10 +33,10 @@ pub fn main() !void {
3333
capy.expanded((try capy.row(.{}, .{
3434
capy.label(.{ .text = "Hello Zig" }),
3535
capy.expanded(
36-
capy.image(.{ .url = "asset:///ziglogo.png", .scaling = .Fit }),
36+
capy.image(.{ .url = "asset:///ziglogo.png", .scaling = .Fit, .opacity = 0 })
37+
.bind("opacity", &opacity),
3738
),
38-
}))
39-
.bind("opacity", &opacity)),
39+
}))),
4040
capy.button(.{ .label = "Hide", .onclick = startAnimation }),
4141
}),
4242
);

examples/time-feed.zig

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ fn onSubmit(_: *anyopaque) !void {
5656
try list_model.add(.{
5757
.start = @as(u64, @intCast(std.time.timestamp() - 1000)),
5858
.end = @as(u64, @intCast(std.time.timestamp())),
59-
.description = submitDesc.get(),
59+
.description = try capy.internal.lasting_allocator.dupe(u8, submitDesc.get()),
6060
});
6161

6262
// clear description
@@ -72,7 +72,7 @@ pub fn InsertCard() anyerror!capy.Container {
7272

7373
return try capy.column(.{}, .{
7474
// TODO: TextArea when it supports data wrappers
75-
capy.textField(.{ .name = "description" })
75+
capy.textArea(.{ .name = "description" })
7676
.bind("text", &submitDesc), // placeholder = "Task description..."
7777
capy.label(.{ .text = "Going on since.. 00:00:20" }),
7878
capy.alignment(.{ .x = 1 }, capy.row(.{}, .{

src/components/Button.zig

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -69,12 +69,7 @@ pub const Button = struct {
6969

7070
pub fn button(config: Button.Config) Button {
7171
var btn = Button.init();
72-
btn.label.set(config.label);
73-
btn.enabled.set(config.enabled);
74-
btn.widget_data.atoms.name.set(config.name);
75-
if (config.onclick) |onclick| {
76-
btn.addClickHandler(onclick) catch unreachable; // TODO: improve
77-
}
72+
@import("../internal.zig").applyConfigStruct(&btn, config);
7873
return btn;
7974
}
8075

src/components/Canvas.zig

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -39,14 +39,7 @@ pub const Canvas = struct {
3939

4040
pub fn canvas(config: Canvas.Config) Canvas {
4141
var cnv = Canvas.init();
42-
cnv.preferredSize = Atom(?Size).of(config.preferredSize);
43-
cnv.widget_data.atoms.name.set(config.name);
44-
if (config.onclick) |onclick| {
45-
cnv.addClickHandler(onclick) catch unreachable; // TODO: improve
46-
}
47-
if (config.ondraw) |ondraw| {
48-
cnv.addDrawHandler(ondraw) catch unreachable; // TODO: improve
49-
}
42+
@import("../internal.zig").applyConfigStruct(&cnv, config);
5043
return cnv;
5144
}
5245

@@ -108,10 +101,7 @@ pub const Rect = struct {
108101
pub fn rect(config: Rect.Config) Rect {
109102
var r = Rect.init();
110103
r.addDrawHandler(&Rect.draw) catch unreachable;
111-
r.preferredSize = Atom(?Size).of(config.preferredSize);
112-
r.color = Atom(Color).of(config.color);
113-
r.cornerRadius = Atom([4]f32).of(config.cornerRadius);
114-
r.widget_data.atoms.name.set(config.name);
104+
@import("../internal.zig").applyConfigStruct(&r, config);
115105
return r;
116106
}
117107

src/components/CheckBox.zig

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -81,12 +81,6 @@ pub const CheckBox = struct {
8181

8282
pub fn checkBox(config: CheckBox.Config) CheckBox {
8383
var btn = CheckBox.init();
84-
btn.checked.set(config.checked);
85-
btn.label.set(config.label);
86-
btn.enabled.set(config.enabled);
87-
btn.widget_data.atoms.name.set(config.name);
88-
if (config.onclick) |onclick| {
89-
btn.addClickHandler(onclick) catch unreachable; // TODO: improve
90-
}
84+
@import("../internal.zig").applyConfigStruct(&btn, config);
9185
return btn;
9286
}

src/components/Image.zig

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -41,12 +41,9 @@ pub const Image = struct {
4141

4242
// TODO: just directly accept an URL or file path if there's no data
4343
pub fn init(config: Image.Config) Image {
44-
var self = Image.init_events(Image{
45-
.url = Atom([]const u8).of(config.url),
46-
.data = Atom(?ImageData).of(config.data),
47-
.scaling = Atom(Scaling).of(config.scaling),
48-
});
44+
var self = Image.init_events(Image{ .url = Atom([]const u8).of(config.url) });
4945
self.addDrawHandler(&Image.draw) catch unreachable;
46+
@import("../internal.zig").applyConfigStruct(&self, config);
5047
return self;
5148
}
5249

@@ -147,6 +144,5 @@ pub const Image = struct {
147144
};
148145

149146
pub fn image(config: Image.Config) Image {
150-
var img = Image.init(config);
151-
return img;
147+
return Image.init(config);
152148
}

src/components/Label.zig

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -12,10 +12,9 @@ pub const Label = struct {
1212
alignment: Atom(TextAlignment) = Atom(TextAlignment).of(.Left),
1313

1414
pub fn init(config: Label.Config) Label {
15-
return Label.init_events(Label{
16-
.text = Atom([]const u8).of(config.text),
17-
.alignment = Atom(TextAlignment).of(config.alignment),
18-
});
15+
var lbl = Label.init_events(Label{});
16+
@import("../internal.zig").applyConfigStruct(&lbl, config);
17+
return lbl;
1918
}
2019

2120
pub fn _pointerMoved(self: *Label) void {

src/image.zig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ pub const ImageData = struct {
4646
/// Load from a png file using a buffer (which can be provided by @embedFile)
4747
pub fn fromBuffer(allocator: std.mem.Allocator, buf: []const u8) !ImageData {
4848
// stage1 crashes with LLVM ERROR: Unable to expand fixed point multiplication.
49-
//const img = try zigimg.Image.fromMemory(allocator, buf);
49+
// const img = try zigimg.Image.fromMemory(allocator, buf);
5050

5151
var stream = std.io.StreamSource{ .const_buffer = std.io.fixedBufferStream(buf) };
5252
return readFromStream(allocator, &stream);

src/internal.zig

Lines changed: 30 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ const Widget = @import("widget.zig").Widget;
88
const Class = @import("widget.zig").Class;
99
const Size = dataStructures.Size;
1010
const Atom = dataStructures.Atom;
11-
const Container_Impl = @import("containers.zig").Container_Impl;
11+
const Container = @import("containers.zig").Container;
1212
const Layout = @import("containers.zig").Layout;
1313
const MouseButton = @import("backends/shared.zig").MouseButton;
1414

@@ -175,7 +175,7 @@ pub fn Widgeting(comptime T: type) type {
175175
} else {
176176
comptime {
177177
var compileError: []const u8 = "No such property: " ++ name;
178-
if (T == Container_Impl) {
178+
if (T == Container) {
179179
compileError = compileError ++ ", did you mean to use getChild() ?";
180180
}
181181
@compileError(compileError);
@@ -317,9 +317,32 @@ fn iterateFields(comptime config_fields: *[]const std.builtin.Type.StructField,
317317
}
318318
}
319319

320-
pub fn applyConfigStruct(target: anytype, config: anytype) void {
321-
_ = target;
322-
_ = config;
320+
/// target is a pointer to a component
321+
/// config is a config struct generated by GenerateConfigStruct(T)
322+
pub fn applyConfigStruct(target: anytype, config: GenerateConfigStruct(std.meta.Child(@TypeOf(target)))) void {
323+
std.debug.assert(std.meta.trait.isPtrTo(.Struct)(@TypeOf(target)));
324+
iterateApplyFields(std.meta.Child(@TypeOf(target)), target, config);
325+
326+
if (config.onclick) |onclick| {
327+
target.addClickHandler(onclick) catch unreachable; // TODO: improve
328+
}
329+
if (config.ondraw) |ondraw| {
330+
target.addDrawHandler(ondraw) catch unreachable; // TODO: improve
331+
}
332+
}
333+
334+
fn iterateApplyFields(comptime T: type, target: anytype, config: GenerateConfigStruct(T)) void {
335+
inline for (std.meta.fields(std.meta.Child(@TypeOf(target)))) |field| {
336+
const FieldType = field.type;
337+
if (comptime dataStructures.isAtom(FieldType)) {
338+
const name = field.name;
339+
@field(target, field.name).set(
340+
@field(config, name),
341+
);
342+
} else if (comptime std.meta.trait.is(.Struct)(FieldType)) {
343+
iterateApplyFields(T, &@field(target, field.name), config);
344+
}
345+
}
323346
}
324347

325348
/// If T is a pointer, return the type it points to, otherwise return T.
@@ -349,7 +372,7 @@ pub fn genericWidgetFrom(component: anytype) anyerror!Widget {
349372
break :blk copy;
350373
};
351374

352-
// Udate things like data wrappers, this happens once, at initialization,
375+
// Update things like data wrappers, this happens once, at initialization,
353376
// after that the component isn't moved in memory anymore
354377
cp.pointerMoved();
355378

@@ -555,6 +578,7 @@ pub fn Events(comptime T: type) type {
555578
/// When the value is changed in the opacity data wrapper
556579
fn opacityChanged(newValue: f32, userdata: usize) void {
557580
const widget = @as(*T, @ptrFromInt(userdata));
581+
std.log.info("opaccity changed to {d}", .{newValue});
558582
if (widget.peer) |*peer| {
559583
peer.setOpacity(newValue);
560584
}

0 commit comments

Comments
 (0)