feat(tabs): Add 3D bevel effect (Z-Design V3)
- Add bevel: bool option to TabsConfig (default false) - Active tabs: raised effect (light top/left, dark bottom/right) - Inactive tabs: subtle inset for depth contrast - Respects tab_bg color for bevel calculations 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
parent
16fc528415
commit
49cd2e25b3
1 changed files with 21 additions and 0 deletions
|
|
@ -103,6 +103,8 @@ pub const TabsConfig = struct {
|
||||||
minimal: bool = false,
|
minimal: bool = false,
|
||||||
/// Underline indicator height (for minimal mode)
|
/// Underline indicator height (for minimal mode)
|
||||||
indicator_height: u32 = 2,
|
indicator_height: u32 = 2,
|
||||||
|
/// Z-Design V3: 3D bevel effect on tabs (raised for active, flat for inactive)
|
||||||
|
bevel: bool = false,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Tabs colors
|
/// Tabs colors
|
||||||
|
|
@ -281,6 +283,25 @@ pub fn tabsRect(
|
||||||
} else {
|
} else {
|
||||||
ctx.pushCommand(Command.rect(tab_rect.x, tab_rect.y, tab_rect.w, tab_rect.h, tab_bg));
|
ctx.pushCommand(Command.rect(tab_rect.x, tab_rect.y, tab_rect.w, tab_rect.h, tab_bg));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Z-Design V3: 3D bevel effect
|
||||||
|
if (config.bevel and tab_rect.h >= 4 and tab_rect.w >= 4 and !tab.disabled) {
|
||||||
|
const bevel_light = tab_bg.lighten(15);
|
||||||
|
const bevel_dark = tab_bg.darken(15);
|
||||||
|
const inner_h = tab_rect.h -| 2;
|
||||||
|
|
||||||
|
if (is_selected) {
|
||||||
|
// Active tab: raised effect (light on top/left)
|
||||||
|
ctx.pushCommand(Command.rect(tab_rect.x + 1, tab_rect.y + 1, tab_rect.w - 2, 1, bevel_light)); // Top
|
||||||
|
ctx.pushCommand(Command.rect(tab_rect.x + 1, tab_rect.y + 1, 1, inner_h, bevel_light)); // Left
|
||||||
|
ctx.pushCommand(Command.rect(tab_rect.x + 1, tab_rect.y + @as(i32, @intCast(tab_rect.h)) - 2, tab_rect.w - 2, 1, bevel_dark)); // Bottom
|
||||||
|
ctx.pushCommand(Command.rect(tab_rect.x + @as(i32, @intCast(tab_rect.w)) - 2, tab_rect.y + 1, 1, inner_h, bevel_dark)); // Right
|
||||||
|
} else {
|
||||||
|
// Inactive tab: flat or subtle inset (dark on top/left for "recessed" look)
|
||||||
|
ctx.pushCommand(Command.rect(tab_rect.x + 1, tab_rect.y + 1, tab_rect.w - 2, 1, bevel_dark.darken(5))); // Top (darker)
|
||||||
|
ctx.pushCommand(Command.rect(tab_rect.x + 1, tab_rect.y + 1, 1, inner_h, bevel_dark.darken(5))); // Left (darker)
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Draw active indicator (underline)
|
// Draw active indicator (underline)
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue