Unify shell corner radius and speed up Settings page switching
This commit is contained in:
1 parent
ef912daeba
commit
e5e2b74a25
10 files changed
+164
-91
No files matched your search
@@ -421,7 +421,9 @@ struct ThemeGeometryConfig {
|
|||||||
#[serde(default = "default_window_radius")]
|
#[serde(default = "default_window_radius")]
|
||||||
window_radius: f64,
|
window_radius: f64,
|
||||||
#[serde(default)]
|
#[serde(default)]
|
||||||
top_bar_radius: f64,
|
top_bar_radius: Option<f64>,
|
||||||
|
#[serde(default)]
|
||||||
|
shell_radius: Option<f64>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for ThemeGeometryConfig {
|
impl Default for ThemeGeometryConfig {
|
||||||
@@ -430,7 +432,8 @@ impl Default for ThemeGeometryConfig {
|
|||||||
border_width: default_border_width(),
|
border_width: default_border_width(),
|
||||||
focus_ring_width: default_focus_ring_width(),
|
focus_ring_width: default_focus_ring_width(),
|
||||||
window_radius: default_window_radius(),
|
window_radius: default_window_radius(),
|
||||||
top_bar_radius: 0.0,
|
top_bar_radius: None,
|
||||||
|
shell_radius: None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1072,8 +1075,13 @@ impl Config {
|
|||||||
unit_theme_value(self.theme.shadow.soft.opacity, "shadow.soft.opacity")?;
|
unit_theme_value(self.theme.shadow.soft.opacity, "shadow.soft.opacity")?;
|
||||||
|
|
||||||
let material_radius = nonnegative_theme_value(
|
let material_radius = nonnegative_theme_value(
|
||||||
self.appearance.corner_radius.unwrap_or(14.0),
|
self.theme
|
||||||
"appearance.corner_radius",
|
.geometry
|
||||||
|
.shell_radius
|
||||||
|
.or(self.appearance.corner_radius)
|
||||||
|
.or(self.theme.geometry.top_bar_radius)
|
||||||
|
.unwrap_or(14.0),
|
||||||
|
"geometry.shell_radius",
|
||||||
)?;
|
)?;
|
||||||
Ok(ThemeSettings {
|
Ok(ThemeSettings {
|
||||||
border_width,
|
border_width,
|
||||||
@@ -1113,10 +1121,7 @@ impl Config {
|
|||||||
)?
|
)?
|
||||||
.min(32.0),
|
.min(32.0),
|
||||||
material_radius,
|
material_radius,
|
||||||
panel_radius: nonnegative_theme_value(
|
panel_radius: material_radius,
|
||||||
self.theme.geometry.top_bar_radius,
|
|
||||||
"geometry.top_bar_radius",
|
|
||||||
)?,
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1988,6 +1993,24 @@ mod tests {
|
|||||||
assert!(invalid.gap_config().is_err());
|
assert!(invalid.gap_config().is_err());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn shell_radius_is_independent_of_windows_and_overrides_legacy_keys() {
|
||||||
|
for radius in [0.0, 18.0] {
|
||||||
|
let config = parse(&format!(
|
||||||
|
"appearance {{\n corner-radius 9\n}}\ntheme {{\n geometry {{\n shell-radius {radius}\n top-bar-radius 5\n window-radius 23\n }}\n}}"
|
||||||
|
));
|
||||||
|
let theme = config.theme_settings().unwrap();
|
||||||
|
assert_eq!(theme.material_radius, radius);
|
||||||
|
assert_eq!(theme.panel_radius, radius);
|
||||||
|
assert_eq!(theme.window_radius, 23.0);
|
||||||
|
}
|
||||||
|
assert!(
|
||||||
|
parse("theme {\n geometry {\n shell-radius -1\n }\n}")
|
||||||
|
.theme_settings()
|
||||||
|
.is_err()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn parses_and_validates_theme_window_tokens() {
|
fn parses_and_validates_theme_window_tokens() {
|
||||||
let configured = parse(
|
let configured = parse(
|
||||||
@@ -2024,7 +2047,7 @@ mod tests {
|
|||||||
material_style: MaterialStyle::Translucent,
|
material_style: MaterialStyle::Translucent,
|
||||||
backdrop_blur: 12.0,
|
backdrop_blur: 12.0,
|
||||||
material_radius: 14.0,
|
material_radius: 14.0,
|
||||||
panel_radius: 0.0,
|
panel_radius: 14.0,
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
assert!(invalid_color.theme_settings().is_err());
|
assert!(invalid_color.theme_settings().is_err());
|
||||||
|
|||||||
+11
-3
@@ -126,7 +126,7 @@ these six visually distinct.
|
|||||||
|
|
||||||
| Section / key | Type | Default | Meaning |
|
| Section / key | Type | Default | Meaning |
|
||||||
| --- | --- | --- | --- |
|
| --- | --- | --- | --- |
|
||||||
| `appearance.corner_radius` | number ≥ 0 | `14` | Shell material/card radius |
|
| `appearance.corner_radius` | number ≥ 0 | unset | Legacy fallback for shell radius |
|
||||||
| `appearance.inactive_dim.enabled` | boolean | `false` | Dim unfocused windows |
|
| `appearance.inactive_dim.enabled` | boolean | `false` | Dim unfocused windows |
|
||||||
| `appearance.inactive_dim.amount` | number 0–1 | `0.15` | Darkening strength |
|
| `appearance.inactive_dim.amount` | number 0–1 | `0.15` | Darkening strength |
|
||||||
| `appearance.inactive_dim.duration_ms` | number ≥ 0 | `150` | Dimming and focus-ring transition; 0 snaps |
|
| `appearance.inactive_dim.duration_ms` | number ≥ 0 | `150` | Dimming and focus-ring transition; 0 snaps |
|
||||||
@@ -149,12 +149,13 @@ these six visually distinct.
|
|||||||
| --- | --- | --- | --- |
|
| --- | --- | --- | --- |
|
||||||
| `border_width` | number ≥ 0 | `1` | Window border thickness |
|
| `border_width` | number ≥ 0 | `1` | Window border thickness |
|
||||||
| `focus_ring_width` | number ≥ 0 | `2` | Focused border thickness |
|
| `focus_ring_width` | number ≥ 0 | `2` | Focused border thickness |
|
||||||
| `window_radius` | number ≥ 0 | `14` | Managed-window corners |
|
| `window_radius` | number ≥ 0 | `14` | Managed-window corners, independent of the shell |
|
||||||
|
| `shell_radius` | number ≥ 0 | `14` | All shell surfaces, cards, widgets and interaction backgrounds; 0 makes them square |
|
||||||
| `top_bar_height` | number > 0 | `28` | Menu-bar height |
|
| `top_bar_height` | number > 0 | `28` | Menu-bar height |
|
||||||
| `top_bar_margin_top` | integer ≥ 0 | `0` | Space above bar |
|
| `top_bar_margin_top` | integer ≥ 0 | `0` | Space above bar |
|
||||||
| `top_bar_window_gap` | integer ≥ 0 | `0` | Clearance below bar |
|
| `top_bar_window_gap` | integer ≥ 0 | `0` | Clearance below bar |
|
||||||
| `top_bar_margin_horizontal` | integer ≥ 0 | `0` | Bar side margins |
|
| `top_bar_margin_horizontal` | integer ≥ 0 | `0` | Bar side margins |
|
||||||
| `top_bar_radius` | number ≥ 0 | `0` | Bar corners |
|
| `top_bar_radius` | number ≥ 0 | unset | Legacy fallback for shell radius |
|
||||||
| `panel_padding` | number ≥ 0 | `12` | Bar inner padding |
|
| `panel_padding` | number ≥ 0 | `12` | Bar inner padding |
|
||||||
| `control_gap` | number ≥ 0 | `12` | Right-side control spacing |
|
| `control_gap` | number ≥ 0 | `12` | Right-side control spacing |
|
||||||
|
|
||||||
@@ -387,3 +388,10 @@ Settings → Notifications controls popups, Do Not Disturb, and the default time
|
|||||||
A single-output session starts with workspace 1. Numbered workspace shortcuts create
|
A single-output session starts with workspace 1. Numbered workspace shortcuts create
|
||||||
workspaces on demand; switching forward past the last workspace also creates the
|
workspaces on demand; switching forward past the last workspace also creates the
|
||||||
next one. Additional displays receive their own workspace.
|
next one. Additional displays receive their own workspace.
|
||||||
|
|
||||||
|
Shell rounding is controlled in Settings → Appearance → Shell corner radius.
|
||||||
|
Small controls cap the radius to fit their size. Window rounding remains under
|
||||||
|
Settings → Windows. `theme.geometry.shell_radius` takes precedence over the old
|
||||||
|
`appearance.corner_radius` and then `theme.geometry.top_bar_radius` keys; when
|
||||||
|
none are set, the shell uses 14 px. Legacy clock/note radius fields no longer
|
||||||
|
override shell rounding.
|
||||||
@@ -1109,10 +1109,20 @@ impl App {
|
|||||||
column([])
|
column([])
|
||||||
.spacing(6)
|
.spacing(6)
|
||||||
.push(
|
.push(
|
||||||
widget::dropdown(families, selected, move |index| {
|
cosmic::iced::widget::pick_list(
|
||||||
let family = if index == 0 { "" } else { &families[index] };
|
families,
|
||||||
Message::SelectFont(selection_path.clone(), family.to_owned())
|
selected.map(|index| families[index].clone()),
|
||||||
})
|
move |family: String| {
|
||||||
|
let value = if family == "Default font" {
|
||||||
|
String::new()
|
||||||
|
} else {
|
||||||
|
family
|
||||||
|
};
|
||||||
|
Message::SelectFont(selection_path.clone(), value)
|
||||||
|
},
|
||||||
|
)
|
||||||
|
.font(self.font)
|
||||||
|
.text_size(12)
|
||||||
.width(225),
|
.width(225),
|
||||||
)
|
)
|
||||||
.push(
|
.push(
|
||||||
|
|||||||
@@ -376,17 +376,6 @@ fn clock_fields() -> Vec<Field> {
|
|||||||
" px",
|
" px",
|
||||||
false,
|
false,
|
||||||
),
|
),
|
||||||
range(
|
|
||||||
"desktop_widgets.clock.radius",
|
|
||||||
"Background radius",
|
|
||||||
"Used only when a background is set.",
|
|
||||||
16.0,
|
|
||||||
0.0,
|
|
||||||
128.0,
|
|
||||||
1.0,
|
|
||||||
" px",
|
|
||||||
false,
|
|
||||||
),
|
|
||||||
choice(
|
choice(
|
||||||
"desktop_widgets.clock.alignment",
|
"desktop_widgets.clock.alignment",
|
||||||
"Text alignment",
|
"Text alignment",
|
||||||
@@ -541,17 +530,6 @@ pub fn note_fields(index: usize) -> Vec<Field> {
|
|||||||
" px",
|
" px",
|
||||||
false,
|
false,
|
||||||
),
|
),
|
||||||
range(
|
|
||||||
format!("{prefix}.radius"),
|
|
||||||
"Corner radius",
|
|
||||||
"Logical pixels; centered axes ignore margins.",
|
|
||||||
16.0,
|
|
||||||
0.0,
|
|
||||||
128.0,
|
|
||||||
1.0,
|
|
||||||
" px",
|
|
||||||
false,
|
|
||||||
),
|
|
||||||
Field::new(
|
Field::new(
|
||||||
format!("{prefix}.alignment"),
|
format!("{prefix}.alignment"),
|
||||||
"Text alignment",
|
"Text alignment",
|
||||||
@@ -567,6 +545,17 @@ pub fn note_fields(index: usize) -> Vec<Field> {
|
|||||||
pub fn fields(page: Page) -> Vec<Field> {
|
pub fn fields(page: Page) -> Vec<Field> {
|
||||||
match page {
|
match page {
|
||||||
Page::Appearance => vec![
|
Page::Appearance => vec![
|
||||||
|
range(
|
||||||
|
"theme.geometry.shell_radius",
|
||||||
|
"Shell corner radius",
|
||||||
|
"Rounds the bar, menus, notifications, desktop widgets and hover backgrounds. Window corners are separate.",
|
||||||
|
14.0,
|
||||||
|
0.0,
|
||||||
|
32.0,
|
||||||
|
1.0,
|
||||||
|
" px",
|
||||||
|
false,
|
||||||
|
),
|
||||||
text(
|
text(
|
||||||
"theme.colors.accent",
|
"theme.colors.accent",
|
||||||
"Accent color",
|
"Accent color",
|
||||||
@@ -690,17 +679,6 @@ pub fn fields(page: Page) -> Vec<Field> {
|
|||||||
" px",
|
" px",
|
||||||
true,
|
true,
|
||||||
),
|
),
|
||||||
range(
|
|
||||||
"theme.geometry.top_bar_radius",
|
|
||||||
"Corner radius",
|
|
||||||
"The shape of the floating bar.",
|
|
||||||
0.0,
|
|
||||||
0.0,
|
|
||||||
24.0,
|
|
||||||
1.0,
|
|
||||||
" px",
|
|
||||||
false,
|
|
||||||
),
|
|
||||||
range(
|
range(
|
||||||
"theme.surface.bar.opacity",
|
"theme.surface.bar.opacity",
|
||||||
"Opacity",
|
"Opacity",
|
||||||
|
|||||||
@@ -438,7 +438,7 @@ pub fn preview(snapshot: &Snapshot) -> Element<'static, Message> {
|
|||||||
let bar_y = snapshot.number("theme.geometry.top_bar_margin_top", 0.) * 0.5 + 12.;
|
let bar_y = snapshot.number("theme.geometry.top_bar_margin_top", 0.) * 0.5 + 12.;
|
||||||
let bar_margin = snapshot.number("theme.geometry.top_bar_margin_horizontal", 0.) * 0.5 + 14.;
|
let bar_margin = snapshot.number("theme.geometry.top_bar_margin_horizontal", 0.) * 0.5 + 14.;
|
||||||
let bar_height = snapshot.number("theme.geometry.top_bar_height", 30.) * 0.65;
|
let bar_height = snapshot.number("theme.geometry.top_bar_height", 30.) * 0.65;
|
||||||
let bar_radius = snapshot.number("theme.geometry.top_bar_radius", 0.) * 0.65;
|
let bar_radius = snapshot.number("theme.geometry.shell_radius", 14.) * 0.65;
|
||||||
let opacity = snapshot.number("theme.surface.bar.opacity", 0.78);
|
let opacity = snapshot.number("theme.surface.bar.opacity", 0.78);
|
||||||
let right = 340. + gap / 2.;
|
let right = 340. + gap / 2.;
|
||||||
let left_width = 288. - gap / 2.;
|
let left_width = 288. - gap / 2.;
|
||||||
|
|||||||
@@ -76,7 +76,7 @@ impl Default for ShellTheme {
|
|||||||
bar_margin_top: 0,
|
bar_margin_top: 0,
|
||||||
bar_window_gap: 0,
|
bar_window_gap: 0,
|
||||||
bar_margin_horizontal: 0,
|
bar_margin_horizontal: 0,
|
||||||
bar_radius: 0.0,
|
bar_radius: 14.0,
|
||||||
material_radius: 14.0,
|
material_radius: 14.0,
|
||||||
panel_padding: 12.0,
|
panel_padding: 12.0,
|
||||||
control_gap: 12.0,
|
control_gap: 12.0,
|
||||||
@@ -253,8 +253,10 @@ struct ThemeGeometryConfig {
|
|||||||
top_bar_window_gap: i32,
|
top_bar_window_gap: i32,
|
||||||
#[serde(default = "default_bar_margin_horizontal")]
|
#[serde(default = "default_bar_margin_horizontal")]
|
||||||
top_bar_margin_horizontal: i32,
|
top_bar_margin_horizontal: i32,
|
||||||
#[serde(default = "default_bar_radius")]
|
#[serde(default)]
|
||||||
top_bar_radius: f32,
|
shell_radius: Option<f32>,
|
||||||
|
#[serde(default)]
|
||||||
|
top_bar_radius: Option<f32>,
|
||||||
#[serde(default = "default_panel_padding")]
|
#[serde(default = "default_panel_padding")]
|
||||||
panel_padding: f32,
|
panel_padding: f32,
|
||||||
#[serde(default = "default_control_gap")]
|
#[serde(default = "default_control_gap")]
|
||||||
@@ -268,7 +270,8 @@ impl Default for ThemeGeometryConfig {
|
|||||||
top_bar_margin_top: default_bar_margin_top(),
|
top_bar_margin_top: default_bar_margin_top(),
|
||||||
top_bar_window_gap: default_bar_window_gap(),
|
top_bar_window_gap: default_bar_window_gap(),
|
||||||
top_bar_margin_horizontal: default_bar_margin_horizontal(),
|
top_bar_margin_horizontal: default_bar_margin_horizontal(),
|
||||||
top_bar_radius: default_bar_radius(),
|
shell_radius: None,
|
||||||
|
top_bar_radius: None,
|
||||||
panel_padding: default_panel_padding(),
|
panel_padding: default_panel_padding(),
|
||||||
control_gap: default_control_gap(),
|
control_gap: default_control_gap(),
|
||||||
}
|
}
|
||||||
@@ -330,8 +333,17 @@ pub(crate) fn parse_source(source: &str) -> Result<ShellConfig, ferese_config::E
|
|||||||
.validate()
|
.validate()
|
||||||
.map_err(ferese_config::Error::from)?;
|
.map_err(ferese_config::Error::from)?;
|
||||||
let mut theme = shell_theme(&config.theme);
|
let mut theme = shell_theme(&config.theme);
|
||||||
theme.material_radius =
|
theme.material_radius = nonnegative_or(
|
||||||
nonnegative_or(config.appearance.corner_radius.unwrap_or(14.0), 14.0);
|
config
|
||||||
|
.theme
|
||||||
|
.geometry
|
||||||
|
.shell_radius
|
||||||
|
.or(config.appearance.corner_radius)
|
||||||
|
.or(config.theme.geometry.top_bar_radius)
|
||||||
|
.unwrap_or(14.0),
|
||||||
|
14.0,
|
||||||
|
);
|
||||||
|
theme.bar_radius = theme.material_radius;
|
||||||
|
|
||||||
Ok(ShellConfig {
|
Ok(ShellConfig {
|
||||||
notifications: config.notifications,
|
notifications: config.notifications,
|
||||||
@@ -388,7 +400,14 @@ fn shell_theme(theme: &ThemeConfig) -> ShellTheme {
|
|||||||
bar_margin_top: theme.geometry.top_bar_margin_top.max(0),
|
bar_margin_top: theme.geometry.top_bar_margin_top.max(0),
|
||||||
bar_window_gap: theme.geometry.top_bar_window_gap.max(0),
|
bar_window_gap: theme.geometry.top_bar_window_gap.max(0),
|
||||||
bar_margin_horizontal: theme.geometry.top_bar_margin_horizontal.max(0),
|
bar_margin_horizontal: theme.geometry.top_bar_margin_horizontal.max(0),
|
||||||
bar_radius: nonnegative_or(theme.geometry.top_bar_radius, defaults.bar_radius),
|
bar_radius: nonnegative_or(
|
||||||
|
theme
|
||||||
|
.geometry
|
||||||
|
.shell_radius
|
||||||
|
.or(theme.geometry.top_bar_radius)
|
||||||
|
.unwrap_or(14.0),
|
||||||
|
defaults.bar_radius,
|
||||||
|
),
|
||||||
panel_padding: nonnegative_or(theme.geometry.panel_padding, defaults.panel_padding),
|
panel_padding: nonnegative_or(theme.geometry.panel_padding, defaults.panel_padding),
|
||||||
control_gap: nonnegative_or(theme.geometry.control_gap, defaults.control_gap),
|
control_gap: nonnegative_or(theme.geometry.control_gap, defaults.control_gap),
|
||||||
shadow_offset_y: finite_or(theme.shadow.soft.offset_y, defaults.shadow_offset_y),
|
shadow_offset_y: finite_or(theme.shadow.soft.offset_y, defaults.shadow_offset_y),
|
||||||
@@ -476,10 +495,6 @@ const fn default_bar_margin_horizontal() -> i32 {
|
|||||||
0
|
0
|
||||||
}
|
}
|
||||||
|
|
||||||
const fn default_bar_radius() -> f32 {
|
|
||||||
0.0
|
|
||||||
}
|
|
||||||
|
|
||||||
const fn default_panel_padding() -> f32 {
|
const fn default_panel_padding() -> f32 {
|
||||||
12.0
|
12.0
|
||||||
}
|
}
|
||||||
@@ -572,6 +587,21 @@ theme {
|
|||||||
assert_eq!(config.theme.background.mode, WallpaperMode::Fit);
|
assert_eq!(config.theme.background.mode, WallpaperMode::Fit);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn shell_radius_unifies_surfaces_and_preserves_legacy_fallbacks() {
|
||||||
|
for radius in [0.0, 18.0] {
|
||||||
|
let config = parse_source(&format!("appearance {{\n corner-radius 9\n}}\ntheme {{\n geometry {{\n shell-radius {radius}\n top-bar-radius 5\n window-radius 23\n }}\n}}")).unwrap();
|
||||||
|
assert_eq!(config.theme.material_radius, radius);
|
||||||
|
assert_eq!(config.theme.bar_radius, radius);
|
||||||
|
}
|
||||||
|
let legacy = parse_source("theme {\n geometry {\n top-bar-radius 7\n }\n}").unwrap();
|
||||||
|
assert_eq!(legacy.theme.material_radius, 7.0);
|
||||||
|
assert_eq!(legacy.theme.bar_radius, 7.0);
|
||||||
|
let legacy = parse_source("appearance {\n corner-radius 6\n}").unwrap();
|
||||||
|
assert_eq!(legacy.theme.material_radius, 6.0);
|
||||||
|
assert_eq!(legacy.theme.bar_radius, 6.0);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn defaults_to_the_ferese_visual_profile() {
|
fn defaults_to_the_ferese_visual_profile() {
|
||||||
let config: FereseConfig = ferese_config::from_str("").unwrap();
|
let config: FereseConfig = ferese_config::from_str("").unwrap();
|
||||||
@@ -586,7 +616,7 @@ theme {
|
|||||||
assert_eq!(theme.bar_margin_top, 0);
|
assert_eq!(theme.bar_margin_top, 0);
|
||||||
assert_eq!(theme.bar_height, 28.0);
|
assert_eq!(theme.bar_height, 28.0);
|
||||||
assert_eq!(theme.bar_margin_horizontal, 0);
|
assert_eq!(theme.bar_margin_horizontal, 0);
|
||||||
assert_eq!(theme.bar_radius, 0.0);
|
assert_eq!(theme.bar_radius, 14.0);
|
||||||
assert_eq!(theme.bar_background, ShellTheme::default().bar_background);
|
assert_eq!(theme.bar_background, ShellTheme::default().bar_background);
|
||||||
assert_eq!(theme.for_bar().text_primary, theme.bar_text_primary);
|
assert_eq!(theme.for_bar().text_primary, theme.bar_text_primary);
|
||||||
assert_ne!(theme.for_bar().text_primary, theme.text_primary);
|
assert_ne!(theme.for_bar().text_primary, theme.text_primary);
|
||||||
|
|||||||
@@ -154,7 +154,7 @@ fn main() -> cosmic::iced::Result {
|
|||||||
"../../../assets/fonts/Cantarell-ExtraBold.otf"
|
"../../../assets/fonts/Cantarell-ExtraBold.otf"
|
||||||
)));
|
)));
|
||||||
let mut config = config::load();
|
let mut config = config::load();
|
||||||
motion::configure(config.animations);
|
motion::configure(config.animations, config.theme.material_radius);
|
||||||
let compositor_wallpaper = std::env::var_os("FERESE_COMPOSITOR_WALLPAPER").is_some();
|
let compositor_wallpaper = std::env::var_os("FERESE_COMPOSITOR_WALLPAPER").is_some();
|
||||||
if compositor_wallpaper {
|
if compositor_wallpaper {
|
||||||
// The compositor owns one GPU image, shared across output renderers;
|
// The compositor owns one GPU image, shared across output renderers;
|
||||||
@@ -771,7 +771,7 @@ impl FereseShell {
|
|||||||
.write()
|
.write()
|
||||||
.unwrap() = configured_font(config.font_family.as_deref());
|
.unwrap() = configured_font(config.font_family.as_deref());
|
||||||
}
|
}
|
||||||
motion::configure(config.animations);
|
motion::configure(config.animations, config.theme.material_radius);
|
||||||
if self.config.animations != config.animations
|
if self.config.animations != config.animations
|
||||||
&& let Some(menu) = &mut self.menu
|
&& let Some(menu) = &mut self.menu
|
||||||
{
|
{
|
||||||
@@ -1365,15 +1365,20 @@ impl FereseShell {
|
|||||||
.note_editor
|
.note_editor
|
||||||
.as_ref()
|
.as_ref()
|
||||||
.is_some_and(|editor| editor.id == id);
|
.is_some_and(|editor| editor.id == id);
|
||||||
body = body.push(row([]).push(header).push(
|
body = body.push(
|
||||||
button::text(if editing { "Done" } else { "Edit" }).on_press(cosmic::Action::App(
|
row([]).push(header).push(motion::button(
|
||||||
if editing {
|
button::custom(text(if editing { "Done" } else { "Edit" }))
|
||||||
Message::FinishNoteEdit
|
.padding([4, 8])
|
||||||
} else {
|
.on_press(cosmic::Action::App(if editing {
|
||||||
Message::BeginNoteEdit(id.to_owned())
|
Message::FinishNoteEdit
|
||||||
},
|
} else {
|
||||||
|
Message::BeginNoteEdit(id.to_owned())
|
||||||
|
})),
|
||||||
|
foreground,
|
||||||
|
false,
|
||||||
|
1.0,
|
||||||
)),
|
)),
|
||||||
));
|
);
|
||||||
} else if !note.title.is_empty() {
|
} else if !note.title.is_empty() {
|
||||||
body = body.push(
|
body = body.push(
|
||||||
cosmic::widget::text(note.title.clone())
|
cosmic::widget::text(note.title.clone())
|
||||||
@@ -1393,6 +1398,12 @@ impl FereseShell {
|
|||||||
let id = id.to_owned();
|
let id = id.to_owned();
|
||||||
body = body.push(
|
body = body.push(
|
||||||
cosmic::widget::TextEditor::new(&editor.content)
|
cosmic::widget::TextEditor::new(&editor.content)
|
||||||
|
.style(|theme, status| {
|
||||||
|
use cosmic::iced::widget::text_editor::Catalog;
|
||||||
|
let mut style = theme.style(&<cosmic::Theme as Catalog>::default(), status);
|
||||||
|
style.border.radius = motion::radius(f32::MAX).into();
|
||||||
|
style
|
||||||
|
})
|
||||||
.height(Length::Fill)
|
.height(Length::Fill)
|
||||||
.font(font)
|
.font(font)
|
||||||
.size(note.text_size)
|
.size(note.text_size)
|
||||||
@@ -1417,7 +1428,7 @@ impl FereseShell {
|
|||||||
.class(theme::Text::Color(foreground)),
|
.class(theme::Text::Color(foreground)),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
let radius = note.radius;
|
let radius = self.config.theme.material_radius;
|
||||||
container(body)
|
container(body)
|
||||||
.padding(note.padding)
|
.padding(note.padding)
|
||||||
.width(Length::Fill)
|
.width(Length::Fill)
|
||||||
@@ -1646,7 +1657,7 @@ impl FereseShell {
|
|||||||
tint.a *= clock.opacity;
|
tint.a *= clock.opacity;
|
||||||
Background::Color(tint)
|
Background::Color(tint)
|
||||||
});
|
});
|
||||||
let radius = clock.radius;
|
let radius = self.config.theme.material_radius;
|
||||||
container(labels)
|
container(labels)
|
||||||
.padding(clock.padding)
|
.padding(clock.padding)
|
||||||
.width(Length::Fill)
|
.width(Length::Fill)
|
||||||
@@ -2249,7 +2260,7 @@ fn workspace_selector_style(
|
|||||||
border: Border {
|
border: Border {
|
||||||
color: color_with_opacity(shell_theme.accent, 0.55),
|
color: color_with_opacity(shell_theme.accent, 0.55),
|
||||||
width: if active_elsewhere { 1.0 } else { 0.0 },
|
width: if active_elsewhere { 1.0 } else { 0.0 },
|
||||||
radius: 6.0.into(),
|
radius: shell_theme.material_radius.min(14.0).into(),
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
}
|
}
|
||||||
@@ -2440,7 +2451,7 @@ fn bar_group_style(theme: ShellTheme) -> container::Style {
|
|||||||
border: Border {
|
border: Border {
|
||||||
color: color_with_opacity(theme.text_muted, 0.12),
|
color: color_with_opacity(theme.text_muted, 0.12),
|
||||||
width: 1.0,
|
width: 1.0,
|
||||||
radius: 7.0.into(),
|
radius: theme.material_radius.min(16.0).into(),
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -42,7 +42,16 @@ impl Settings {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
static SETTINGS: std::sync::OnceLock<std::sync::RwLock<Settings>> = std::sync::OnceLock::new();
|
static SETTINGS: std::sync::OnceLock<std::sync::RwLock<Settings>> = std::sync::OnceLock::new();
|
||||||
pub(crate) fn configure(settings: Settings) {
|
static SHELL_RADIUS: std::sync::atomic::AtomicU32 =
|
||||||
|
std::sync::atomic::AtomicU32::new(14.0_f32.to_bits());
|
||||||
|
|
||||||
|
/// All shell shapes share one radius, capped to fit smaller controls.
|
||||||
|
pub(crate) fn radius(limit: f32) -> f32 {
|
||||||
|
f32::from_bits(SHELL_RADIUS.load(std::sync::atomic::Ordering::Relaxed)).min(limit)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn configure(settings: Settings, radius: f32) {
|
||||||
|
SHELL_RADIUS.store(radius.to_bits(), std::sync::atomic::Ordering::Relaxed);
|
||||||
*SETTINGS
|
*SETTINGS
|
||||||
.get_or_init(|| std::sync::RwLock::new(Settings::default()))
|
.get_or_init(|| std::sync::RwLock::new(Settings::default()))
|
||||||
.write()
|
.write()
|
||||||
@@ -138,7 +147,7 @@ pub(crate) fn button<'a, M: Clone + 'a>(
|
|||||||
let paint = move |progress: f32, pressed: bool| cosmic::widget::button::Style {
|
let paint = move |progress: f32, pressed: bool| cosmic::widget::button::Style {
|
||||||
text_color: Some(foreground),
|
text_color: Some(foreground),
|
||||||
icon_color: Some(foreground),
|
icon_color: Some(foreground),
|
||||||
border_radius: 6.0.into(),
|
border_radius: radius(14.0).into(),
|
||||||
background: Some(cosmic::iced::Background::Color(cosmic::iced::Color {
|
background: Some(cosmic::iced::Background::Color(cosmic::iced::Color {
|
||||||
a: if pressed {
|
a: if pressed {
|
||||||
0.20 * opacity
|
0.20 * opacity
|
||||||
|
|||||||
@@ -98,7 +98,7 @@ fn card_button<'a>(
|
|||||||
text_color: Some(foreground),
|
text_color: Some(foreground),
|
||||||
icon_color: Some(foreground),
|
icon_color: Some(foreground),
|
||||||
background: (active || round).then_some(Background::Color(hover)),
|
background: (active || round).then_some(Background::Color(hover)),
|
||||||
border_radius: (if round { 9.0 } else { 0.0 }).into(),
|
border_radius: (if round { motion::radius(11.0) } else { 0.0 }).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
};
|
};
|
||||||
button::custom(content)
|
button::custom(content)
|
||||||
@@ -141,7 +141,7 @@ fn icon_control<'a>(
|
|||||||
.class(theme::Container::custom(move |_| container::Style {
|
.class(theme::Container::custom(move |_| container::Style {
|
||||||
background: Some(Background::Color(background)),
|
background: Some(Background::Color(background)),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 6.0.into(),
|
radius: motion::radius(12.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
text_color: Some(foreground),
|
text_color: Some(foreground),
|
||||||
@@ -380,7 +380,7 @@ impl FereseShell {
|
|||||||
.class(theme::Container::custom(move |_| container::Style {
|
.class(theme::Container::custom(move |_| container::Style {
|
||||||
background: Some(Background::Color(well)),
|
background: Some(Background::Color(well)),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 8.0.into(),
|
radius: motion::radius(15.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -397,7 +397,7 @@ impl FereseShell {
|
|||||||
.class(theme::Container::custom(move |_| container::Style {
|
.class(theme::Container::custom(move |_| container::Style {
|
||||||
background: Some(Background::Color(accent)),
|
background: Some(Background::Color(accent)),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 8.0.into(),
|
radius: motion::radius(8.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -747,7 +747,7 @@ impl FereseShell {
|
|||||||
.class(theme::Container::custom(move |_| container::Style {
|
.class(theme::Container::custom(move |_| container::Style {
|
||||||
background: Some(Background::Color(well)),
|
background: Some(Background::Color(well)),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 28.0.into(),
|
radius: motion::radius(28.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
|
|||||||
@@ -277,7 +277,7 @@ impl FereseShell {
|
|||||||
theme::Container::custom(move |_| container::Style {
|
theme::Container::custom(move |_| container::Style {
|
||||||
background: Some(Background::Color(foreground)),
|
background: Some(Background::Color(foreground)),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 2.0.into(),
|
radius: motion::radius(2.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -345,7 +345,7 @@ impl FereseShell {
|
|||||||
0.12 * p,
|
0.12 * p,
|
||||||
))),
|
))),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 10.0.into(),
|
radius: motion::radius(20.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -772,7 +772,7 @@ fn status_summary<'a>(
|
|||||||
..badge_color
|
..badge_color
|
||||||
})),
|
})),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 9.0.into(),
|
radius: motion::radius(16.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -823,7 +823,7 @@ fn level_meter(
|
|||||||
}
|
}
|
||||||
})),
|
})),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 2.5.into(),
|
radius: motion::radius(2.5).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -854,7 +854,7 @@ fn control_card<'a>(
|
|||||||
..foreground
|
..foreground
|
||||||
})),
|
})),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 11.0.into(),
|
radius: motion::radius(22.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -890,7 +890,7 @@ fn connection_control<'a>(
|
|||||||
opacity,
|
opacity,
|
||||||
)),
|
)),
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 10.0.into(),
|
radius: motion::radius(20.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
..Default::default()
|
..Default::default()
|
||||||
@@ -1006,12 +1006,16 @@ fn slider_row(
|
|||||||
),
|
),
|
||||||
width: 4.0,
|
width: 4.0,
|
||||||
border: Border {
|
border: Border {
|
||||||
radius: 2.0.into(),
|
radius: motion::radius(2.0).into(),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
handle: Handle {
|
handle: Handle {
|
||||||
shape: HandleShape::Circle { radius: 5.0 },
|
shape: HandleShape::Rectangle {
|
||||||
|
width: 10,
|
||||||
|
height: 10,
|
||||||
|
border_radius: motion::radius(5.0).into(),
|
||||||
|
},
|
||||||
background: foreground.into(),
|
background: foreground.into(),
|
||||||
border_width: 0.0,
|
border_width: 0.0,
|
||||||
border_color: Color::TRANSPARENT,
|
border_color: Color::TRANSPARENT,
|
||||||
|
|||||||
Reference in new issue
Block a user