mirror of
https://github.com/slint-ui/slint.git
synced 2025-08-31 07:37:24 +00:00

These are showing off use-cases for Slint, but they're not examples showing individual Slint features. Also removed the old printerdemo while at it.
128 lines
3.2 KiB
Text
128 lines
3.2 KiB
Text
// Copyright © SixtyFPS GmbH <info@slint.dev>
|
|
// SPDX-License-Identifier: MIT
|
|
|
|
import { Theme } from "../theme.slint";
|
|
|
|
component Tab {
|
|
in property <string> title;
|
|
in property <bool> selected;
|
|
in property <image> icon;
|
|
|
|
callback clicked <=> i-touch-area.clicked;
|
|
|
|
private property <angle> angle: Math.atan(self.height / 2 / self.width);
|
|
private property <bool> has-icon: root.icon.width > 0 && root.icon.height > 0;
|
|
|
|
preferred-width: 200px;
|
|
|
|
states [
|
|
selected when selected : {
|
|
i-initiator.width: root.width;
|
|
i-title.color: Theme.palette.lemon-green;
|
|
i-gradient.opacity: 1.0;
|
|
}
|
|
]
|
|
|
|
GridLayout {
|
|
padding: root.has-icon ? 7px : 25px;
|
|
|
|
VerticalLayout {
|
|
spacing: root.has-icon ? 7px : 0;
|
|
|
|
if (root.has-icon) : Image {
|
|
x: (parent.width - self.width) / 2;
|
|
width: 24px;
|
|
height: 24px;
|
|
source: root.icon;
|
|
colorize: i-title.color;
|
|
}
|
|
|
|
i-title := Text {
|
|
text: title;
|
|
horizontal-alignment: center;
|
|
vertical-alignment: center;
|
|
font-size: root.has-icon ? Theme.typo.description-light.size : Theme.typo.header-item-light.size;
|
|
font-weight: root.has-icon ? Theme.typo.header-item-light.weight : Theme.typo.description-light.weight;
|
|
color: Theme.palette.white;
|
|
|
|
animate color { duration: Theme.durations.medium; }
|
|
}
|
|
}
|
|
}
|
|
|
|
i-gradient := Rectangle {
|
|
opacity: 0;
|
|
visible: !root.has-icon;
|
|
|
|
Rectangle {
|
|
y: 0;
|
|
width: 50%;
|
|
height: 50%;
|
|
x: 0;
|
|
background: @linear-gradient(angle, rgba(222, 251, 58, 0) , rgba(222, 251, 58, 0.2));
|
|
}
|
|
|
|
Rectangle {
|
|
y: 0;
|
|
width: 50%;
|
|
height: 50%;
|
|
x: self.width;
|
|
background: @linear-gradient(-angle, rgba(222, 251, 58, 0) , rgba(222, 251, 58, 0.2));
|
|
}
|
|
|
|
animate opacity { duration: Theme.durations.medium; }
|
|
}
|
|
|
|
i-initiator := Rectangle {
|
|
width: 0;
|
|
y: 0;
|
|
height: 1px;
|
|
background: Theme.palette.lemon-green;
|
|
visible: selected;
|
|
|
|
animate width { duration: Theme.durations.medium; }
|
|
}
|
|
|
|
i-touch-area := TouchArea {}
|
|
}
|
|
|
|
export struct TabItem {
|
|
text: string,
|
|
icon: image
|
|
}
|
|
|
|
export component TabWidget {
|
|
in property <[TabItem]> tabs;
|
|
in-out property <int> selected-tab;
|
|
|
|
vertical-stretch: 1;
|
|
|
|
VerticalLayout {
|
|
Rectangle {
|
|
vertical-stretch: 1;
|
|
|
|
@children
|
|
}
|
|
|
|
Rectangle {
|
|
vertical-stretch: 0;
|
|
background: Theme.palette.tab-gradient;
|
|
|
|
HorizontalLayout {
|
|
alignment: center;
|
|
min-height: 80px;
|
|
vertical-stretch: 0;
|
|
|
|
for tab[index] in tabs : Tab {
|
|
title: tab.text;
|
|
icon: tab.icon;
|
|
selected: index == selected-tab;
|
|
|
|
clicked => {
|
|
selected-tab = index;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|