chore: update dependencies
The ICU update reduces binary size by ~20 MB.
This commit is contained in:
parent
f1f7862fbc
commit
31912afaa1
11 changed files with 878 additions and 928 deletions
1582
Cargo.lock
generated
1582
Cargo.lock
generated
File diff suppressed because it is too large
Load diff
37
Cargo.toml
37
Cargo.toml
|
|
@ -8,12 +8,8 @@ vergen = { version = "8", features = ["git", "gitcl"] }
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
anyhow = "1"
|
anyhow = "1"
|
||||||
async-fn-stream = "0.2.2"
|
async-fn-stream = "0.3"
|
||||||
icu = { version = "1.5.0", features = [
|
icu = { version = "2.0.0", features = ["compiled_data"] }
|
||||||
"experimental",
|
|
||||||
"compiled_data",
|
|
||||||
"icu_datetime_experimental",
|
|
||||||
] }
|
|
||||||
chrono-tz = "0.10"
|
chrono-tz = "0.10"
|
||||||
chrono = { version = "0.4", features = ["unstable-locales"] }
|
chrono = { version = "0.4", features = ["unstable-locales"] }
|
||||||
cosmic-applets-config.workspace = true
|
cosmic-applets-config.workspace = true
|
||||||
|
|
@ -41,10 +37,10 @@ pwd.workspace = true
|
||||||
ron.workspace = true
|
ron.workspace = true
|
||||||
shlex = "1.3.0"
|
shlex = "1.3.0"
|
||||||
xkb-data = "0.2"
|
xkb-data = "0.2"
|
||||||
xdg = "2.5.2"
|
xdg = "3.0"
|
||||||
#TODO: reduce features
|
#TODO: reduce features
|
||||||
tokio = { workspace = true, features = ["full"] }
|
tokio = { workspace = true, features = ["full"] }
|
||||||
wayland-client = "0.31.8"
|
wayland-client = "0.31.11"
|
||||||
cosmic-settings-subscriptions = { git = "https://github.com/pop-os/cosmic-settings-subscriptions", default-features = false, features = [
|
cosmic-settings-subscriptions = { git = "https://github.com/pop-os/cosmic-settings-subscriptions", default-features = false, features = [
|
||||||
"accessibility",
|
"accessibility",
|
||||||
"cosmic_a11y_manager",
|
"cosmic_a11y_manager",
|
||||||
|
|
@ -52,10 +48,8 @@ cosmic-settings-subscriptions = { git = "https://github.com/pop-os/cosmic-settin
|
||||||
cosmic-settings-daemon-config = { git = "https://github.com/pop-os/cosmic-settings-daemon", default-features = false, features = [
|
cosmic-settings-daemon-config = { git = "https://github.com/pop-os/cosmic-settings-daemon", default-features = false, features = [
|
||||||
"greeter",
|
"greeter",
|
||||||
] }
|
] }
|
||||||
cctk = { git = "https://github.com/pop-os/cosmic-protocols", package = "cosmic-client-toolkit", rev = "178eb0b" }
|
cctk = { git = "https://github.com/pop-os/cosmic-protocols", package = "cosmic-client-toolkit" }
|
||||||
cosmic-protocols = { git = "https://github.com/pop-os/cosmic-protocols", default-features = false, features = [
|
cosmic-protocols = { git = "https://github.com/pop-os/cosmic-protocols", default-features = false, features = ["client"] }
|
||||||
"client",
|
|
||||||
], rev = "1425bd4" }
|
|
||||||
|
|
||||||
# For network status using networkmanager feature
|
# For network status using networkmanager feature
|
||||||
cosmic-dbus-networkmanager = { git = "https://github.com/pop-os/dbus-settings-bindings", optional = true }
|
cosmic-dbus-networkmanager = { git = "https://github.com/pop-os/dbus-settings-bindings", optional = true }
|
||||||
|
|
@ -70,13 +64,13 @@ zbus = { workspace = true, optional = true }
|
||||||
# CLI arguments
|
# CLI arguments
|
||||||
clap_lex = "0.7"
|
clap_lex = "0.7"
|
||||||
# Internationalization
|
# Internationalization
|
||||||
i18n-embed = { version = "0.14", features = [
|
i18n-embed = { version = "0.16", features = [
|
||||||
"fluent-system",
|
"fluent-system",
|
||||||
"desktop-requester",
|
"desktop-requester",
|
||||||
] }
|
] }
|
||||||
i18n-embed-fl = "0.7"
|
i18n-embed-fl = "0.10"
|
||||||
rust-embed = "8"
|
rust-embed = "8"
|
||||||
futures-util = "0.3.30"
|
futures-util = "0.3.31"
|
||||||
timedate-zbus = { git = "https://github.com/pop-os/dbus-settings-bindings" }
|
timedate-zbus = { git = "https://github.com/pop-os/dbus-settings-bindings" }
|
||||||
cosmic-randr-shell = { workspace = true }
|
cosmic-randr-shell = { workspace = true }
|
||||||
kdl.workspace = true
|
kdl.workspace = true
|
||||||
|
|
@ -118,11 +112,11 @@ tracing-subscriber = { version = "0.3", features = ["env-filter"] }
|
||||||
color-eyre = "0.6.5"
|
color-eyre = "0.6.5"
|
||||||
|
|
||||||
# Fix zbus compilation by manually adding nix with user feature
|
# Fix zbus compilation by manually adding nix with user feature
|
||||||
nix = { version = "0.29", features = ["user"] }
|
nix = { version = "0.30", features = ["user"] }
|
||||||
pwd = "1.4.0"
|
pwd = "1.4.0"
|
||||||
ron = "0.10.1"
|
ron = "0.11"
|
||||||
serde = "1"
|
serde = "1"
|
||||||
tokio = "1.39.1"
|
tokio = "1.47.1"
|
||||||
zbus = "5"
|
zbus = "5"
|
||||||
kdl = "6"
|
kdl = "6"
|
||||||
cosmic-randr-shell = { git = "https://github.com/pop-os/cosmic-randr", default-features = false, branch = "kdl-command" }
|
cosmic-randr-shell = { git = "https://github.com/pop-os/cosmic-randr", default-features = false, branch = "kdl-command" }
|
||||||
|
|
@ -155,11 +149,12 @@ default-features = false
|
||||||
git = "https://github.com/pop-os/libcosmic"
|
git = "https://github.com/pop-os/libcosmic"
|
||||||
default-features = false
|
default-features = false
|
||||||
|
|
||||||
|
|
||||||
[patch."https://github.com/smithay/client-toolkit.git"]
|
[patch."https://github.com/smithay/client-toolkit.git"]
|
||||||
sctk = { package = "smithay-client-toolkit", version = "=0.19.2" }
|
sctk = { package = "smithay-client-toolkit", version = "0.20.0" }
|
||||||
|
|
||||||
[patch."https://github.com/pop-os/cosmic-protocols"]
|
[patch."https://github.com/pop-os/cosmic-protocols"]
|
||||||
cosmic-protocols = { git = "https://github.com/pop-os/cosmic-protocols//", rev = "5035f8c" }
|
cosmic-protocols = { git = "https://github.com/pop-os/cosmic-protocols//" }
|
||||||
|
cctk = { git = "https://github.com/pop-os/cosmic-protocols//", package = "cosmic-client-toolkit" }
|
||||||
|
|
||||||
# libcosmic = { path = "../libcosmic" }
|
# libcosmic = { path = "../libcosmic" }
|
||||||
# cosmic-config = { path = "../libcosmic/cosmic-config" }
|
# cosmic-config = { path = "../libcosmic/cosmic-config" }
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
[package]
|
[package]
|
||||||
name = "cosmic-greeter-config"
|
name = "cosmic-greeter-config"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
edition = "2021"
|
edition = "2024"
|
||||||
description = "Configuration for COSMIC Greeter"
|
description = "Configuration for COSMIC Greeter"
|
||||||
repository = "https://github.com/pop-os/cosmic-greeter"
|
repository = "https://github.com/pop-os/cosmic-greeter"
|
||||||
license = "GPL-3.0-only"
|
license = "GPL-3.0-only"
|
||||||
|
|
|
||||||
|
|
@ -3,10 +3,9 @@
|
||||||
|
|
||||||
pub mod user;
|
pub mod user;
|
||||||
|
|
||||||
use std::{collections::HashMap, num::NonZeroU32};
|
use cosmic_config::{CosmicConfigEntry, cosmic_config_derive::CosmicConfigEntry};
|
||||||
|
|
||||||
use cosmic_config::{cosmic_config_derive::CosmicConfigEntry, CosmicConfigEntry};
|
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
use std::{collections::HashMap, num::NonZeroU32};
|
||||||
|
|
||||||
pub const APP_ID: &str = "com.system76.CosmicGreeter";
|
pub const APP_ID: &str = "com.system76.CosmicGreeter";
|
||||||
pub const CONFIG_VERSION: u64 = 1;
|
pub const CONFIG_VERSION: u64 = 1;
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,8 @@
|
||||||
// Copyright 2024 System76 <info@system76.com>
|
// Copyright 2024 System76 <info@system76.com>
|
||||||
// SPDX-License-Identifier: GPL-3.0-only
|
// SPDX-License-Identifier: GPL-3.0-only
|
||||||
|
|
||||||
use std::num::NonZeroU32;
|
|
||||||
|
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
use std::num::NonZeroU32;
|
||||||
|
|
||||||
/// Per user state for Greeter.
|
/// Per user state for Greeter.
|
||||||
#[derive(Debug, Clone, PartialEq, Deserialize, Serialize)]
|
#[derive(Debug, Clone, PartialEq, Deserialize, Serialize)]
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
[package]
|
[package]
|
||||||
name = "cosmic-greeter-daemon"
|
name = "cosmic-greeter-daemon"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
edition = "2021"
|
edition = "2024"
|
||||||
|
|
||||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||||
|
|
||||||
|
|
@ -26,7 +26,7 @@ kdl.workspace = true
|
||||||
|
|
||||||
#TODO: reduce features
|
#TODO: reduce features
|
||||||
tokio = { workspace = true, features = ["full"] }
|
tokio = { workspace = true, features = ["full"] }
|
||||||
xdg = "3.0.0"
|
xdg = "3.0"
|
||||||
|
|
||||||
[features]
|
[features]
|
||||||
default = ["systemd"]
|
default = ["systemd"]
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@ use std::{
|
||||||
};
|
};
|
||||||
|
|
||||||
pub use cosmic_applets_config::time::TimeAppletConfig;
|
pub use cosmic_applets_config::time::TimeAppletConfig;
|
||||||
pub use cosmic_bg_config::{state::State as BgState, Color, Source as BgSource};
|
pub use cosmic_bg_config::{Color, Source as BgSource, state::State as BgState};
|
||||||
pub use cosmic_comp_config::{CosmicCompConfig, XkbConfig, ZoomConfig};
|
pub use cosmic_comp_config::{CosmicCompConfig, XkbConfig, ZoomConfig};
|
||||||
pub use cosmic_theme::{Theme, ThemeBuilder};
|
pub use cosmic_theme::{Theme, ThemeBuilder};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,10 @@
|
||||||
use color_eyre::eyre::Context;
|
use color_eyre::eyre::Context;
|
||||||
use color_eyre::eyre::WrapErr;
|
|
||||||
use cosmic_greeter_daemon::UserData;
|
use cosmic_greeter_daemon::UserData;
|
||||||
use std::{env, error::Error, future::pending, io, path::Path};
|
use std::{env, error::Error, future::pending, io, path::Path};
|
||||||
use tracing::metadata::LevelFilter;
|
use tracing::metadata::LevelFilter;
|
||||||
use tracing::{error, warn};
|
use tracing::warn;
|
||||||
use tracing_subscriber::{fmt, prelude::*, EnvFilter};
|
use tracing_subscriber::{EnvFilter, fmt, prelude::*};
|
||||||
use zbus::{connection::Builder, DBusError};
|
use zbus::{DBusError, connection::Builder};
|
||||||
|
|
||||||
//IMPORTANT: this function is critical to the security of this proxy. It must ensure that the
|
//IMPORTANT: this function is critical to the security of this proxy. It must ensure that the
|
||||||
// callback is executed with the permissions of the specified user id. A good test is to see if
|
// callback is executed with the permissions of the specified user id. A good test is to see if
|
||||||
|
|
@ -15,7 +14,9 @@ fn run_as_user<F: FnOnce() -> T, T>(user: &pwd::Passwd, f: F) -> Result<T, io::E
|
||||||
let root_home_opt = env::var_os("HOME");
|
let root_home_opt = env::var_os("HOME");
|
||||||
|
|
||||||
// Switch to user HOME
|
// Switch to user HOME
|
||||||
env::set_var("HOME", &user.dir);
|
unsafe {
|
||||||
|
env::set_var("HOME", &user.dir);
|
||||||
|
}
|
||||||
|
|
||||||
// Switch to user UID
|
// Switch to user UID
|
||||||
if unsafe { libc::seteuid(user.uid) } != 0 {
|
if unsafe { libc::seteuid(user.uid) } != 0 {
|
||||||
|
|
@ -31,8 +32,12 @@ fn run_as_user<F: FnOnce() -> T, T>(user: &pwd::Passwd, f: F) -> Result<T, io::E
|
||||||
|
|
||||||
// Restore root HOME
|
// Restore root HOME
|
||||||
match root_home_opt {
|
match root_home_opt {
|
||||||
Some(root_home) => env::set_var("HOME", root_home),
|
Some(root_home) => unsafe {
|
||||||
None => env::remove_var("HOME"),
|
env::set_var("HOME", root_home);
|
||||||
|
},
|
||||||
|
None => unsafe {
|
||||||
|
env::remove_var("HOME");
|
||||||
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(t)
|
Ok(t)
|
||||||
|
|
|
||||||
|
|
@ -50,7 +50,7 @@ use std::{
|
||||||
error::Error,
|
error::Error,
|
||||||
fs, io,
|
fs, io,
|
||||||
num::NonZeroU32,
|
num::NonZeroU32,
|
||||||
path::{Path, PathBuf},
|
path::Path,
|
||||||
process,
|
process,
|
||||||
sync::Arc,
|
sync::Arc,
|
||||||
time::{Duration, Instant},
|
time::{Duration, Instant},
|
||||||
|
|
@ -174,17 +174,12 @@ pub fn main() -> Result<(), Box<dyn Error>> {
|
||||||
}
|
}
|
||||||
|
|
||||||
let session_dirs = xdg::BaseDirectories::with_prefix("wayland-sessions")
|
let session_dirs = xdg::BaseDirectories::with_prefix("wayland-sessions")
|
||||||
.map_or(
|
.get_data_dirs()
|
||||||
vec![PathBuf::from("/usr/share/wayland-sessions")],
|
|
||||||
|xdg_dirs| xdg_dirs.get_data_dirs(),
|
|
||||||
)
|
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|dir| (dir, SessionType::Wayland))
|
.map(|dir| (dir, SessionType::Wayland))
|
||||||
.chain(
|
.chain(
|
||||||
xdg::BaseDirectories::with_prefix("xsessions")
|
xdg::BaseDirectories::with_prefix("xsessions")
|
||||||
.map_or(vec![PathBuf::from("/usr/share/xsessions")], |xdg_dirs| {
|
.get_data_dirs()
|
||||||
xdg_dirs.get_data_dirs()
|
|
||||||
})
|
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|dir| (dir, SessionType::X11)),
|
.map(|dir| (dir, SessionType::X11)),
|
||||||
);
|
);
|
||||||
|
|
|
||||||
|
|
@ -1,12 +1,11 @@
|
||||||
// SPDX-License-Identifier: GPL-3.0-only
|
// SPDX-License-Identifier: GPL-3.0-only
|
||||||
|
|
||||||
use std::sync::OnceLock;
|
|
||||||
|
|
||||||
use i18n_embed::{
|
use i18n_embed::{
|
||||||
DefaultLocalizer, LanguageLoader, Localizer,
|
DefaultLocalizer, LanguageLoader, Localizer,
|
||||||
fluent::{FluentLanguageLoader, fluent_language_loader},
|
fluent::{FluentLanguageLoader, fluent_language_loader},
|
||||||
};
|
};
|
||||||
use rust_embed::RustEmbed;
|
use rust_embed::RustEmbed;
|
||||||
|
use std::sync::OnceLock;
|
||||||
|
|
||||||
#[derive(RustEmbed)]
|
#[derive(RustEmbed)]
|
||||||
#[folder = "i18n/"]
|
#[folder = "i18n/"]
|
||||||
|
|
|
||||||
138
src/time.rs
138
src/time.rs
|
|
@ -1,5 +1,3 @@
|
||||||
use std::{str::FromStr, time::Duration};
|
|
||||||
|
|
||||||
use anyhow::bail;
|
use anyhow::bail;
|
||||||
use async_fn_stream::StreamEmitter;
|
use async_fn_stream::StreamEmitter;
|
||||||
use chrono::{Datelike, Timelike};
|
use chrono::{Datelike, Timelike};
|
||||||
|
|
@ -7,20 +5,18 @@ use cosmic::{
|
||||||
Task,
|
Task,
|
||||||
iced_core::Element,
|
iced_core::Element,
|
||||||
style,
|
style,
|
||||||
widget::{self, column, text::title2},
|
widget::{column, text},
|
||||||
};
|
};
|
||||||
use futures_util::StreamExt;
|
use futures_util::StreamExt;
|
||||||
use icu::{
|
use icu::{
|
||||||
calendar::DateTime,
|
|
||||||
datetime::{
|
datetime::{
|
||||||
DateTimeFormatter, DateTimeFormatterOptions,
|
DateTimeFormatter, DateTimeFormatterPreferences, fieldsets,
|
||||||
options::{
|
input::{Date, DateTime, Time as IcuTime},
|
||||||
components::{self, Bag},
|
options::TimePrecision,
|
||||||
preferences,
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
locid::Locale,
|
locale::{Locale, preferences::extensions::unicode::keywords::HourCycle},
|
||||||
};
|
};
|
||||||
|
use std::time::Duration;
|
||||||
use timedate_zbus::TimeDateProxy;
|
use timedate_zbus::TimeDateProxy;
|
||||||
use tokio::time;
|
use tokio::time;
|
||||||
|
|
||||||
|
|
@ -33,24 +29,32 @@ pub struct Time {
|
||||||
|
|
||||||
impl Time {
|
impl Time {
|
||||||
pub fn new() -> Self {
|
pub fn new() -> Self {
|
||||||
fn get_local() -> Result<Locale, Box<dyn std::error::Error>> {
|
fn get_local() -> Locale {
|
||||||
let locale = std::env::var("LC_TIME").or_else(|_| std::env::var("LANG"))?;
|
for var in ["LC_TIME", "LC_ALL", "LANG"] {
|
||||||
let locale = locale
|
if let Ok(locale_str) = std::env::var(var) {
|
||||||
.split('.')
|
let cleaned_locale = locale_str
|
||||||
.next()
|
.split('.')
|
||||||
.ok_or(format!("Can't split the locale {locale}"))?;
|
.next()
|
||||||
|
.unwrap_or(&locale_str)
|
||||||
|
.replace('_', "-");
|
||||||
|
|
||||||
let locale = Locale::from_str(locale).map_err(|e| format!("{e:?}"))?;
|
if let Ok(locale) = Locale::try_from_str(&cleaned_locale) {
|
||||||
Ok(locale)
|
return locale;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try language-only fallback (e.g., "en" from "en-US")
|
||||||
|
if let Some(lang) = cleaned_locale.split('-').next() {
|
||||||
|
if let Ok(locale) = Locale::try_from_str(lang) {
|
||||||
|
return locale;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tracing::warn!("No valid locale found in environment, using fallback");
|
||||||
|
Locale::try_from_str("en-US").expect("Failed to parse fallback locale 'en-US'")
|
||||||
}
|
}
|
||||||
|
|
||||||
let locale = match get_local() {
|
let locale = get_local();
|
||||||
Ok(locale) => locale,
|
|
||||||
Err(e) => {
|
|
||||||
tracing::error!("can't get locale {e}");
|
|
||||||
Locale::default()
|
|
||||||
}
|
|
||||||
};
|
|
||||||
let now = chrono::Local::now().fixed_offset();
|
let now = chrono::Local::now().fixed_offset();
|
||||||
|
|
||||||
Self {
|
Self {
|
||||||
|
|
@ -72,59 +76,61 @@ impl Time {
|
||||||
.unwrap_or_else(|| chrono::Local::now().into());
|
.unwrap_or_else(|| chrono::Local::now().into());
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn format<D: Datelike>(&self, bag: Bag, date: &D) -> String {
|
pub fn format_date<D: Datelike>(&self, date: &D) -> String {
|
||||||
let options = DateTimeFormatterOptions::Components(bag);
|
let prefs = DateTimeFormatterPreferences::from(&self.locale);
|
||||||
|
let dtf = DateTimeFormatter::try_new(prefs, fieldsets::MDE::long()).unwrap();
|
||||||
|
|
||||||
let dtf =
|
let datetime = DateTime {
|
||||||
DateTimeFormatter::try_new_experimental(&self.locale.clone().into(), options).unwrap();
|
date: Date::try_new_gregorian(date.year(), date.month() as u8, date.day() as u8)
|
||||||
|
.unwrap(),
|
||||||
|
time: IcuTime::try_new(
|
||||||
|
self.now.hour() as u8,
|
||||||
|
self.now.minute() as u8,
|
||||||
|
self.now.second() as u8,
|
||||||
|
0,
|
||||||
|
)
|
||||||
|
.unwrap(),
|
||||||
|
};
|
||||||
|
|
||||||
let datetime = DateTime::try_new_gregorian_datetime(
|
dtf.format(&datetime).to_string()
|
||||||
date.year(),
|
}
|
||||||
date.month() as u8,
|
|
||||||
date.day() as u8,
|
pub fn format_time<D: Datelike>(&self, date: &D, military_time: bool) -> String {
|
||||||
// hack cause we know that we will only use "now"
|
let mut prefs = DateTimeFormatterPreferences::from(&self.locale);
|
||||||
// when we need hours (NaiveDate don't support this functions)
|
prefs.hour_cycle = Some(if military_time {
|
||||||
self.now.hour() as u8,
|
HourCycle::H23
|
||||||
self.now.minute() as u8,
|
} else {
|
||||||
self.now.second() as u8,
|
HourCycle::H12
|
||||||
|
});
|
||||||
|
let dtf = DateTimeFormatter::try_new(
|
||||||
|
prefs,
|
||||||
|
fieldsets::T::medium().with_time_precision(TimePrecision::Minute),
|
||||||
)
|
)
|
||||||
.unwrap()
|
.unwrap();
|
||||||
.to_iso()
|
|
||||||
.to_any();
|
|
||||||
|
|
||||||
dtf.format(&datetime)
|
let datetime = DateTime {
|
||||||
.expect("can't format value")
|
date: Date::try_new_gregorian(date.year(), date.month() as u8, date.day() as u8)
|
||||||
.to_string()
|
.unwrap(),
|
||||||
|
time: IcuTime::try_new(
|
||||||
|
self.now.hour() as u8,
|
||||||
|
self.now.minute() as u8,
|
||||||
|
self.now.second() as u8,
|
||||||
|
0,
|
||||||
|
)
|
||||||
|
.unwrap(),
|
||||||
|
};
|
||||||
|
|
||||||
|
dtf.format(&datetime).to_string()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn date_time_widget<'a, M: 'a>(&self, military_time: bool) -> cosmic::Element<'a, M> {
|
pub fn date_time_widget<'a, M: 'a>(&self, military_time: bool) -> cosmic::Element<'a, M> {
|
||||||
let mut top_bag = Bag::empty();
|
|
||||||
|
|
||||||
top_bag.weekday = Some(components::Text::Long);
|
|
||||||
|
|
||||||
top_bag.day = Some(components::Day::NumericDayOfMonth);
|
|
||||||
top_bag.month = Some(components::Month::Long);
|
|
||||||
|
|
||||||
let mut bottom_bag = Bag::empty();
|
|
||||||
|
|
||||||
bottom_bag.hour = Some(components::Numeric::Numeric);
|
|
||||||
bottom_bag.minute = Some(components::Numeric::Numeric);
|
|
||||||
|
|
||||||
let hour_cycle = if military_time {
|
|
||||||
preferences::HourCycle::H23
|
|
||||||
} else {
|
|
||||||
preferences::HourCycle::H12
|
|
||||||
};
|
|
||||||
|
|
||||||
bottom_bag.preferences = Some(preferences::Bag::from_hour_cycle(hour_cycle));
|
|
||||||
|
|
||||||
Element::from(
|
Element::from(
|
||||||
column()
|
column()
|
||||||
.padding(16.)
|
.padding(16.)
|
||||||
.spacing(12.0)
|
.spacing(12.0)
|
||||||
.push(title2(self.format(top_bag, &self.now)).class(style::Text::Accent))
|
.push(text::title2(self.format_date(&self.now)).class(style::Text::Accent))
|
||||||
.push(
|
.push(
|
||||||
widget::text(self.format(bottom_bag, &self.now))
|
text(self.format_time(&self.now, military_time))
|
||||||
.size(if military_time { 112. } else { 75. })
|
.size(if military_time { 112. } else { 75. })
|
||||||
.class(style::Text::Accent),
|
.class(style::Text::Accent),
|
||||||
),
|
),
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue