diff --git a/Cargo.lock b/Cargo.lock index 5ca8bed1..ed9d9b43 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -192,6 +192,22 @@ dependencies = [ "libc", ] +[[package]] +name = "annotate-snippets" +version = "0.11.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "710e8eae58854cdc1790fcb56cca04d712a17be849eeb81da2a724bf4bae2bc4" +dependencies = [ + "anstyle", + "unicode-width", +] + +[[package]] +name = "anstyle" +version = "1.0.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "940b3a0ca603d1eade50a4846a2afffd5ef57a9feac2c0e2ec2e14f9ead76000" + [[package]] name = "anyhow" version = "1.0.102" @@ -490,9 +506,9 @@ dependencies = [ [[package]] name = "autocfg" -version = "1.5.0" +version = "1.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8" +checksum = "f2032f911046de80f0a198e0901378627c33f59ea0ac00e363d481118bd70a53" [[package]] name = "base64" @@ -509,6 +525,25 @@ dependencies = [ "serde", ] +[[package]] +name = "bindgen" +version = "0.72.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "993776b509cfb49c750f11b8f07a46fa23e0a1386ffc01fb1e7d343efc387895" +dependencies = [ + "annotate-snippets", + "bitflags 2.11.1", + "cexpr", + "clang-sys", + "itertools 0.13.0", + "proc-macro2", + "quote", + "regex", + "rustc-hash 2.1.2", + "shlex", + "syn", +] + [[package]] name = "bit-set" version = "0.8.0" @@ -611,7 +646,7 @@ dependencies = [ "libc", "log", "macaddr", - "nix", + "nix 0.29.0", "num-derive", "num-traits", "pin-project", @@ -664,9 +699,9 @@ dependencies = [ [[package]] name = "bumpalo" -version = "3.20.2" +version = "3.20.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5d20789868f4b01b2f2caec9f5c4e0213b41e3e5702a50157d699ae31ced2fcb" +checksum = "72f5acc6cb2ba439de613abc23857ec3d78374d8ed5ac84e9d11336e87da8649" [[package]] name = "by_address" @@ -762,6 +797,25 @@ dependencies = [ "shlex", ] +[[package]] +name = "cexpr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" +dependencies = [ + "nom 7.1.3", +] + +[[package]] +name = "cfg-expr" +version = "0.20.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c6b04e07d8080154ed4ac03546d9a2b303cc2fe1901ba0b35b301516e289368" +dependencies = [ + "smallvec", + "target-lexicon", +] + [[package]] name = "cfg-if" version = "1.0.4" @@ -796,6 +850,17 @@ dependencies = [ "inout", ] +[[package]] +name = "clang-sys" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b023947811758c97c59bf9d1c188fd619ad4718dcaa767947df1cadb14f39f4" +dependencies = [ + "glob", + "libc", + "libloading", +] + [[package]] name = "clipboard-win" version = "5.4.1" @@ -895,6 +960,21 @@ version = "3.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e57e3272f0190c3f1584272d613719ba5fc7df7f4942fe542e63d949cf3a649b" +[[package]] +name = "convert_case" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baaaa0ecca5b51987b9423ccdc971514dd8b0bb7b4060b983d3664dad3f1f89f" +dependencies = [ + "unicode-segmentation", +] + +[[package]] +name = "cookie-factory" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9885fa71e26b8ab7855e2ec7cae6e9b380edff76cd052e07c683a0319d51b3a2" + [[package]] name = "core-foundation" version = "0.9.4" @@ -967,7 +1047,7 @@ dependencies = [ [[package]] name = "cosmic-app-list" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "cosmic-app-list-config", @@ -994,7 +1074,7 @@ dependencies = [ [[package]] name = "cosmic-app-list-config" -version = "1.0.15" +version = "1.0.2" dependencies = [ "libcosmic-yoda", "serde", @@ -1002,7 +1082,7 @@ dependencies = [ [[package]] name = "cosmic-applet-a11y" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "cosmic-client-toolkit", @@ -1021,13 +1101,11 @@ dependencies = [ [[package]] name = "cosmic-applet-audio" -version = "1.0.15" +version = "1.0.2" dependencies = [ - "cosmic-settings-audio-client", - "futures", + "cosmic-settings-sound-subscription", "i18n-embed", "i18n-embed-fl", - "intmap", "libcosmic-yoda", "mpris2-zbus", "rust-embed", @@ -1039,12 +1117,11 @@ dependencies = [ "url", "urlencoding", "zbus", - "zlink", ] [[package]] name = "cosmic-applet-battery" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "cosmic-applets-config", @@ -1069,7 +1146,7 @@ dependencies = [ [[package]] name = "cosmic-applet-bluetooth" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "bluer", @@ -1088,7 +1165,7 @@ dependencies = [ [[package]] name = "cosmic-applet-input-sources" -version = "1.0.15" +version = "1.0.2" dependencies = [ "cosmic-comp-config", "i18n-embed", @@ -1104,7 +1181,7 @@ dependencies = [ [[package]] name = "cosmic-applet-minimize" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "i18n-embed", @@ -1122,7 +1199,7 @@ dependencies = [ [[package]] name = "cosmic-applet-network" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "async-fn-stream", @@ -1148,7 +1225,7 @@ dependencies = [ [[package]] name = "cosmic-applet-notifications" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "cosmic-notifications-config", @@ -1168,7 +1245,7 @@ dependencies = [ [[package]] name = "cosmic-applet-power" -version = "1.0.15" +version = "1.0.2" dependencies = [ "i18n-embed", "i18n-embed-fl", @@ -1185,7 +1262,7 @@ dependencies = [ [[package]] name = "cosmic-applet-status-area" -version = "1.0.15" +version = "1.0.2" dependencies = [ "futures", "libcosmic-yoda", @@ -1200,7 +1277,7 @@ dependencies = [ [[package]] name = "cosmic-applet-tiling" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "cosmic-client-toolkit", @@ -1219,7 +1296,7 @@ dependencies = [ [[package]] name = "cosmic-applet-time" -version = "1.0.15" +version = "1.0.2" dependencies = [ "cosmic-applets-config", "i18n-embed", @@ -1239,7 +1316,7 @@ dependencies = [ [[package]] name = "cosmic-applet-workspaces" -version = "1.0.15" +version = "1.0.2" dependencies = [ "anyhow", "cosmic-client-toolkit", @@ -1256,7 +1333,7 @@ dependencies = [ [[package]] name = "cosmic-applets" -version = "1.0.15" +version = "1.0.2" dependencies = [ "cosmic-app-list", "cosmic-applet-a11y", @@ -1282,7 +1359,7 @@ dependencies = [ [[package]] name = "cosmic-applets-config" -version = "1.0.15" +version = "1.0.2" dependencies = [ "cosmic-config", "serde", @@ -1392,7 +1469,7 @@ dependencies = [ [[package]] name = "cosmic-panel-button" -version = "1.0.15" +version = "1.0.2" dependencies = [ "cosmic-config", "libcosmic-yoda", @@ -1416,6 +1493,19 @@ dependencies = [ "xdg-shell-wrapper-config", ] +[[package]] +name = "cosmic-pipewire" +version = "1.0.7" +dependencies = [ + "intmap", + "libspa", + "libspa-sys", + "pipewire", + "serde", + "serde_json", + "tracing", +] + [[package]] name = "cosmic-protocols" version = "0.2.0" @@ -1454,31 +1544,6 @@ dependencies = [ "zbus", ] -[[package]] -name = "cosmic-settings-audio-client" -version = "1.0.0" -dependencies = [ - "cosmic-settings-audio-core", - "dirs", - "futures-util", - "ron 0.12.1", - "serde", - "tokio", - "tokio-util", - "tracing", - "zlink", -] - -[[package]] -name = "cosmic-settings-audio-core" -version = "1.0.0" -dependencies = [ - "dirs", - "ron 0.12.1", - "serde", - "zlink", -] - [[package]] name = "cosmic-settings-config" version = "0.1.0" @@ -1518,7 +1583,7 @@ dependencies = [ "cosmic-dbus-networkmanager", "futures", "iced_futures", - "itertools", + "itertools 0.14.0", "nm-secret-agent-manager", "secret-service", "secure-string", @@ -1528,6 +1593,20 @@ dependencies = [ "zbus", ] +[[package]] +name = "cosmic-settings-sound-subscription" +version = "1.0.7" +dependencies = [ + "cosmic-pipewire", + "futures", + "intmap", + "libcosmic-yoda", + "numtoa", + "rustix 1.1.4", + "tokio", + "tracing", +] + [[package]] name = "cosmic-settings-upower-subscription" version = "1.0.7" @@ -1931,9 +2010,9 @@ dependencies = [ [[package]] name = "displaydoc" -version = "0.2.5" +version = "0.2.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" +checksum = "1ac70aa55017e108007fbaf5aa0f54b021c98f92ff8af59d42eda9da96e3dd4f" dependencies = [ "proc-macro2", "quote", @@ -2027,9 +2106,9 @@ checksum = "d0881ea181b1df73ff77ffaaf9c7544ecc11e82fba9b5f27b262a3c73a332555" [[package]] name = "either" -version = "1.15.0" +version = "1.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "48c757948c5ede0e46177b7add2e67155f70e33c07fea8284df6576da70b3719" +checksum = "91622ff5e7162018101f2fea40d6ebf4a78bbe5a49736a2020649edf9693679e" [[package]] name = "endi" @@ -2159,7 +2238,7 @@ version = "0.6.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "59a98bbaacea1c0eb6a0876280051b892eb73594fd90cf3b20e9c817029c57d2" dependencies = [ - "toml", + "toml 0.5.11", ] [[package]] @@ -2363,7 +2442,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc6d3a3635983a889f065aa9ce760384713f23a9b4a04f696f86c39a5d7a6a5a" dependencies = [ "indexmap 2.14.0", - "nom", + "nom 8.0.0", ] [[package]] @@ -2461,9 +2540,9 @@ checksum = "037711b3d59c33004d3856fbdc83b99d4ff37a24768fa1be9ce3538a1cde4393" [[package]] name = "futures-timer" -version = "3.0.3" +version = "3.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f288b0a4f20f9a56b5d1da57e2227c661b7b16168e2f72365f57b63326e29b24" +checksum = "af43fadb8a98512d547e37b4e92e0ced13e205c061b87b4623eff01d918d6968" [[package]] name = "futures-util" @@ -2575,6 +2654,12 @@ version = "0.25.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "151665d9be52f9bb40fc7966565d39666f2d1e69233571b71b87791c7e0528b3" +[[package]] +name = "glob" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0cc23270f6e1808e30a928bdc84dea0b9b4136a8bc82338574f23baf47bbd280" + [[package]] name = "glow" version = "0.16.0" @@ -2607,7 +2692,7 @@ dependencies = [ "log", "presser", "thiserror 2.0.18", - "windows 0.62.2", + "windows 0.61.3", ] [[package]] @@ -3657,6 +3742,15 @@ dependencies = [ "windows-sys 0.48.0", ] +[[package]] +name = "itertools" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "413ee7dfc52ee1a4949ceeb7dbc8a33f2d6c088194d9f922fb8318faf1f01186" +dependencies = [ + "either", +] + [[package]] name = "itertools" version = "0.14.0" @@ -3680,9 +3774,9 @@ checksum = "2ceaf4c6c48465bead8cb6a0b7c4ee0c86ecbb31239032b9c66ab9a08d2f3ee1" [[package]] name = "jiff" -version = "0.2.24" +version = "0.2.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f00b5dbd620d61dfdcb6007c9c1f6054ebd75319f163d886a9055cec1155073d" +checksum = "6835eea34fb6321b9b3aa7b685c2b433948c09447e389dc017fdf687d5d11e65" dependencies = [ "jiff-static", "jiff-tzdb-platform", @@ -3695,9 +3789,9 @@ dependencies = [ [[package]] name = "jiff-static" -version = "0.2.24" +version = "0.2.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e000de030ff8022ea1da3f466fbb0f3a809f5e51ed31f6dd931c35181ad8e6d7" +checksum = "3c22e04db9c58f5136eb1757f3d5c49a7b187f49e52185228cbd2f5acdfcc08c" dependencies = [ "proc-macro2", "quote", @@ -3789,9 +3883,9 @@ dependencies = [ [[package]] name = "js-sys" -version = "0.3.98" +version = "0.3.99" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "67df7112613f8bfd9150013a0314e196f4800d3201ae742489d999db2f979f08" +checksum = "142bc4740e452c1e57ade0cbc129f139c9093e354346f0872ef985f4f5cf5f11" dependencies = [ "cfg-if", "futures-util", @@ -3992,7 +4086,35 @@ dependencies = [ "bitflags 2.11.1", "libc", "plain", - "redox_syscall 0.8.1", + "redox_syscall 0.8.0", +] + +[[package]] +name = "libspa" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6b8cfa2a7656627b4c92c6b9ef929433acd673d5ab3708cda1b18478ac00df4" +dependencies = [ + "bitflags 2.11.1", + "cc", + "convert_case", + "cookie-factory", + "libc", + "libspa-sys", + "nix 0.30.1", + "nom 8.0.0", + "system-deps", +] + +[[package]] +name = "libspa-sys" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "901049455d2eb6decf9058235d745237952f4804bc584c5fcb41412e6adcc6e0" +dependencies = [ + "bindgen", + "cc", + "system-deps", ] [[package]] @@ -4074,9 +4196,9 @@ dependencies = [ [[package]] name = "log" -version = "0.4.29" +version = "0.4.30" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e5032e24019045c762d3c0f28f5b6b8bbf38563a65908389bf7978758920897" +checksum = "616ec5685824bcc94416c6d4a7a446eea774a31efd7062c8480ba6fd06d7a6e5" [[package]] name = "logind-zbus" @@ -4172,9 +4294,9 @@ dependencies = [ [[package]] name = "memchr" -version = "2.8.0" +version = "2.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f8ca58f447f06ed17d5fc4043ce1b10dd205e060fb3ce5b979b8ed8e59ff3f79" +checksum = "6b947ae49db0d222b1dbc6b113ce7248a3fc3a6ca21b696717bfc000ba4484d8" [[package]] name = "memmap2" @@ -4231,6 +4353,12 @@ version = "0.3.17" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" +[[package]] +name = "minimal-lexical" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" + [[package]] name = "miniz_oxide" version = "0.8.9" @@ -4243,9 +4371,9 @@ dependencies = [ [[package]] name = "mio" -version = "1.2.0" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50b7e5b27aa02a74bac8c3f23f448f8d87ff11f92d3aac1a6ed369ee08cc56c1" +checksum = "02bd0af71c67b473010cbbc60715ee815645a4dc942899111f494b4b737d6fda" dependencies = [ "libc", "log", @@ -4349,6 +4477,18 @@ dependencies = [ "libc", ] +[[package]] +name = "nix" +version = "0.30.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74523f3a35e05aba87a1d978330aef40f67b0304ac79c1c00b294c9830543db6" +dependencies = [ + "bitflags 2.11.1", + "cfg-if", + "cfg_aliases", + "libc", +] + [[package]] name = "nm-secret-agent-manager" version = "0.1.0" @@ -4358,9 +4498,9 @@ dependencies = [ [[package]] name = "nmrs" -version = "3.1.4" +version = "3.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f9493a0dfbe50783b53ef52ec8ddb8d1f85fd45098be8210205236ff0f43bb7b" +checksum = "d907d6da103106d84189d3fd229d9aac921f9131b8ba38b40341c53d24409077" dependencies = [ "async-trait", "base64", @@ -4376,6 +4516,16 @@ dependencies = [ "zvariant", ] +[[package]] +name = "nom" +version = "7.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a" +dependencies = [ + "memchr", + "minimal-lexical", +] + [[package]] name = "nom" version = "8.0.0" @@ -4534,6 +4684,12 @@ dependencies = [ "syn", ] +[[package]] +name = "numtoa" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e4d8a81ede501fad07191e746a299f4d79f6dcd053bab1b97af4ff5a90099f2" + [[package]] name = "objc" version = "0.2.7" @@ -4756,9 +4912,9 @@ checksum = "04744f49eae99ab78e0d5c0b603ab218f515ea8cfe5a456d7629ad883a3b6e7d" [[package]] name = "orbclient" -version = "0.3.54" +version = "0.3.55" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a570f6bca41d29acb2139229a7c873ec99bc9a313bd10804081d89bfac8ff329" +checksum = "5df339f526ea9a60e371768d50efc2f2508c7203290731565d1f7a6f71d21747" dependencies = [ "libc", "libredox", @@ -5018,6 +5174,34 @@ dependencies = [ "futures-io", ] +[[package]] +name = "pipewire" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9688b89abf11d756499f7c6190711d6dbe5a3acdb30c8fbf001d6596d06a8d44" +dependencies = [ + "anyhow", + "bitflags 2.11.1", + "libc", + "libspa", + "libspa-sys", + "nix 0.30.1", + "once_cell", + "pipewire-sys", + "thiserror 2.0.18", +] + +[[package]] +name = "pipewire-sys" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb028afee0d6ca17020b090e3b8fa2d7de23305aef975c7e5192a5050246ea36" +dependencies = [ + "bindgen", + "libspa-sys", + "system-deps", +] + [[package]] name = "pkg-config" version = "0.3.33" @@ -5365,9 +5549,9 @@ dependencies = [ [[package]] name = "redox_syscall" -version = "0.8.1" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b44b894f2a6e36457d665d1e08c3866add6ed5e70050c1b4ba8a8ddedb02ce7" +checksum = "7c7591fa2c6b601dfcfe5f043f65a1c39fcdf50efefcd7f1572e538c1f4b398d" dependencies = [ "bitflags 2.11.1", ] @@ -5626,12 +5810,6 @@ dependencies = [ "unicode-script", ] -[[package]] -name = "ryu" -version = "1.0.23" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9774ba4a74de5f7b1c1451ed6cd5285a32eddb5cccb8cc655a4e50009e06477f" - [[package]] name = "same-file" version = "1.0.6" @@ -5775,9 +5953,9 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.149" +version = "1.0.150" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "83fc039473c5595ace860d8c4fafa220ff474b3fc6bfdb4293327f1a37e94d86" +checksum = "e8014e44b4736ed0538adeecded0fce2a272f22dc9578a7eb6b2d9993c74cfb9" dependencies = [ "indexmap 2.14.0", "itoa", @@ -5798,6 +5976,15 @@ dependencies = [ "syn", ] +[[package]] +name = "serde_spanned" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6662b5879511e06e8999a8a235d848113e942c9124f211511b16466ee2995f26" +dependencies = [ + "serde_core", +] + [[package]] name = "serde_with" version = "3.20.0" @@ -5992,9 +6179,9 @@ dependencies = [ [[package]] name = "socket2" -version = "0.6.3" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3a766e1110788c36f4fa1c2b71b387a7815aa65f88ce0229841826633d93723e" +checksum = "52d1cfed4120b4d927bf7c0f86d2087a4a7d6027c906d9f9d525a80573b9be51" dependencies = [ "libc", "windows-sys 0.61.2", @@ -6154,6 +6341,19 @@ dependencies = [ "libc", ] +[[package]] +name = "system-deps" +version = "7.0.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "396a35feb67335377e0251fcbc1092fc85c484bd4e3a7a54319399da127796e7" +dependencies = [ + "cfg-expr", + "heck 0.5.0", + "pkg-config", + "toml 1.1.2+spec-1.1.0", + "version-compare", +] + [[package]] name = "taffy" version = "0.9.2" @@ -6166,6 +6366,12 @@ dependencies = [ "slotmap", ] +[[package]] +name = "target-lexicon" +version = "0.13.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df7f62577c25e07834649fc3b39fafdc597c0a3527dc1c60129201ccfcbaa50c" + [[package]] name = "temp-dir" version = "0.1.16" @@ -6377,20 +6583,6 @@ dependencies = [ "futures-core", "pin-project-lite", "tokio", - "tokio-util", -] - -[[package]] -name = "tokio-util" -version = "0.7.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ae9cec805b01e8fc3fd2fe289f89149a9b66dd16786abd8b19cfa7b48cb0098" -dependencies = [ - "bytes", - "futures-core", - "futures-sink", - "pin-project-lite", - "tokio", ] [[package]] @@ -6402,6 +6594,21 @@ dependencies = [ "serde", ] +[[package]] +name = "toml" +version = "1.1.2+spec-1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "81f3d15e84cbcd896376e6730314d59fb5a87f31e4b038454184435cd57defee" +dependencies = [ + "indexmap 2.14.0", + "serde_core", + "serde_spanned", + "toml_datetime", + "toml_parser", + "toml_writer", + "winnow", +] + [[package]] name = "toml_datetime" version = "1.1.1+spec-1.1.0" @@ -6413,9 +6620,9 @@ dependencies = [ [[package]] name = "toml_edit" -version = "0.25.11+spec-1.1.0" +version = "0.25.12+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b59c4d22ed448339746c59b905d24568fcbb3ab65a500494f7b8c3e97739f2b" +checksum = "d2153edc6955a6c354fad8f5efd38b6a8769bdccf9fe50f8e1329f81b0baa5d7" dependencies = [ "indexmap 2.14.0", "toml_datetime", @@ -6432,6 +6639,12 @@ dependencies = [ "winnow", ] +[[package]] +name = "toml_writer" +version = "1.1.1+spec-1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "756daf9b1013ebe47a8776667b466417e2d4c5679d441c26230efd9ef78692db" + [[package]] name = "tracing" version = "0.1.44" @@ -6733,6 +6946,12 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ba73ea9cf16a25df0c8caa16c51acb937d5712a8429db78a3ee29d5dcacd3a65" +[[package]] +name = "version-compare" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "03c2856837ef78f57382f06b2b8563a2f512f7185d732608fd9176cb3b8edf0e" + [[package]] name = "version_check" version = "0.9.5" @@ -6775,9 +6994,9 @@ dependencies = [ [[package]] name = "wasm-bindgen" -version = "0.2.121" +version = "0.2.122" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49ace1d07c165b0864824eee619580c4689389afa9dc9ed3a4c75040d82e6790" +checksum = "3ed04576f974d2b2fba0f38c51dbc5518011e38c36bf1143164be765528fd409" dependencies = [ "cfg-if", "once_cell", @@ -6788,9 +7007,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-futures" -version = "0.4.71" +version = "0.4.72" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "96492d0d3ffba25305a7dc88720d250b1401d7edca02cc3bcd50633b424673b8" +checksum = "9473dbd2991ae90b6291c3c32c30c6187ac49aa32f9905d1cce280ec1e110b0f" dependencies = [ "js-sys", "wasm-bindgen", @@ -6798,9 +7017,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro" -version = "0.2.121" +version = "0.2.122" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e68e6f4afd367a562002c05637acb8578ff2dea1943df76afb9e83d177c8578" +checksum = "916151b09da36bd82f6615cbf3a419e2f0ba23a03c6160e8e92eb6bd4aa1dec6" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -6808,9 +7027,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.121" +version = "0.2.122" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d95a9ec35c64b2a7cb35d3fead40c4238d0940c86d107136999567a4703259f2" +checksum = "299047362ccbfce148b67ab7e73349f77748e00c8296f9542adfad2ad82c5c5e" dependencies = [ "bumpalo", "proc-macro2", @@ -6821,9 +7040,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-shared" -version = "0.2.121" +version = "0.2.122" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c4e0100b01e9f0d03189a92b96772a1fb998639d981193d7dbab487302513441" +checksum = "9a929b2c61f11ba3e9bc35b50c1f25cb38e0e892c0c231ae2b8cf78d5dad4437" dependencies = [ "unicode-ident", ] @@ -7028,9 +7247,9 @@ dependencies = [ [[package]] name = "web-sys" -version = "0.3.98" +version = "0.3.99" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4b572dff8bcf38bad0fa19729c89bb5748b2b9b1d8be70cf90df697e3a8f32aa" +checksum = "6d621441cfc37b84979402712047321980c178f299193a3589d05b99e8763436" dependencies = [ "js-sys", "wasm-bindgen", @@ -8239,18 +8458,18 @@ checksum = "6df3dc4292935e51816d896edcd52aa30bc297907c26167fec31e2b0c6a32524" [[package]] name = "zerocopy" -version = "0.8.48" +version = "0.8.49" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eed437bf9d6692032087e337407a86f04cd8d6a16a37199ed57949d415bd68e9" +checksum = "bce33a6288fa3f072a8c2c7d0f2fdbb90e28298f0135c1f99b96c3db2efcc60b" dependencies = [ "zerocopy-derive", ] [[package]] name = "zerocopy-derive" -version = "0.8.48" +version = "0.8.49" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "70e3cd084b1788766f53af483dd21f93881ff30d7320490ec3ef7526d203bad4" +checksum = "8fd425244944f4ab65ccff928e7323354c5a018c75838362fdce749dfad2ee1e" dependencies = [ "proc-macro2", "quote", @@ -8319,73 +8538,6 @@ dependencies = [ "syn", ] -[[package]] -name = "zlink" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9b895b99588dceb73f4d349b8323eabad9a97d48ce83698d475c7223727c6148" -dependencies = [ - "zlink-smol", - "zlink-tokio", -] - -[[package]] -name = "zlink-core" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd12701bd1d42a982b931f0159cf5054bf13d90e7828a8377dfc02ed4b00342d" -dependencies = [ - "futures-util", - "itoa", - "libc", - "pin-project-lite", - "rustix 1.1.4", - "ryu", - "serde", - "serde_json", - "tracing", - "zlink-macros", -] - -[[package]] -name = "zlink-macros" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e6f2416a5f504dfd7e04fee49f31abafe3314a3f62b4ddaa8e9a5fd496d4dd50" -dependencies = [ - "proc-macro2", - "quote", - "syn", -] - -[[package]] -name = "zlink-smol" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4bc53cd0d636ad753f759aab0abb1f456e985c3938a279d11ebda92340ae37b1" -dependencies = [ - "async-broadcast", - "async-channel", - "async-io", - "futures-lite", - "futures-util", - "pin-project-lite", - "zlink-core", -] - -[[package]] -name = "zlink-tokio" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28cbf366ac77ab41bf9a8d43535d3d620a072f7957813e03355d3d010c16cc4f" -dependencies = [ - "futures-util", - "pin-project-lite", - "tokio", - "tokio-stream", - "zlink-core", -] - [[package]] name = "zmij" version = "1.0.21" @@ -8463,14 +8615,10 @@ dependencies = [ "winnow", ] -[[patch.unused]] -name = "cosmic-settings-airplane-mode-subscription" -version = "1.0.7" - -[[patch.unused]] -name = "cosmic-settings-sound-subscription" -version = "1.0.7" - [[patch.unused]] name = "winit-x11" version = "0.31.0-beta.2" + +[[patch.unused]] +name = "cosmic-settings-airplane-mode-subscription" +version = "1.0.7" diff --git a/Cargo.toml b/Cargo.toml index 6f673cc2..098b9507 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -61,7 +61,6 @@ tokio = { version = "1.49.0", features = ["full"] } # cosmic-config = { path = "../libcosmic/cosmic-config" } cosmic-config = { path = "../libcosmic/cosmic-config" } serde = { version = "1.0.228", features = ["derive"] } -zlink = "0.5.0" [profile.release] opt-level = 3 diff --git a/cosmic-app-list/Cargo.toml b/cosmic-app-list/Cargo.toml index b3171a2c..4fb3e699 100644 --- a/cosmic-app-list/Cargo.toml +++ b/cosmic-app-list/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-app-list" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-app-list/cosmic-app-list-config/Cargo.toml b/cosmic-app-list/cosmic-app-list-config/Cargo.toml index 0d5a21d7..49e940c5 100644 --- a/cosmic-app-list/cosmic-app-list-config/Cargo.toml +++ b/cosmic-app-list/cosmic-app-list-config/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-app-list-config" -version = "1.0.15" +version = "1.0.2" edition = "2024" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/cosmic-app-list/i18n/kmr/cosmic_app_list.ftl b/cosmic-app-list/i18n/kmr/cosmic_app_list.ftl index 793d1880..e69de29b 100644 --- a/cosmic-app-list/i18n/kmr/cosmic_app_list.ftl +++ b/cosmic-app-list/i18n/kmr/cosmic_app_list.ftl @@ -1,8 +0,0 @@ -run = Bixebitîne -run-on = Li ser { $gpu } bixebitîne -run-on-default = (Berdest) -pin = Bo destgeha sepanan bi dar bixe -quit = Biqedîne -quit-all = Hemûyan biqedîne -new-window = Çarçoveya nû -cosmic-app-list = Destgeha sepanan diff --git a/cosmic-applet-a11y/Cargo.toml b/cosmic-applet-a11y/Cargo.toml index 711b4ec6..d3550f60 100644 --- a/cosmic-applet-a11y/Cargo.toml +++ b/cosmic-applet-a11y/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-a11y" -version = "1.0.15" +version = "1.0.2" edition = "2024" [dependencies] diff --git a/cosmic-applet-a11y/i18n/ja/cosmic_applet_a11y.ftl b/cosmic-applet-a11y/i18n/ja/cosmic_applet_a11y.ftl index 564e0d4f..75249579 100644 --- a/cosmic-applet-a11y/i18n/ja/cosmic_applet_a11y.ftl +++ b/cosmic-applet-a11y/i18n/ja/cosmic_applet_a11y.ftl @@ -2,5 +2,5 @@ screen-reader = スクリーンリーダー magnifier = 拡大鏡 settings = アクセシビリティ設定… invert-colors = 色を反転 -filter-colors = カラーフィルター +filter-colors = 色のフィルター high-contrast = ハイコントラスト diff --git a/cosmic-applet-a11y/i18n/kmr/cosmic_applet_a11y.ftl b/cosmic-applet-a11y/i18n/kmr/cosmic_applet_a11y.ftl index 4c772791..e69de29b 100644 --- a/cosmic-applet-a11y/i18n/kmr/cosmic_applet_a11y.ftl +++ b/cosmic-applet-a11y/i18n/kmr/cosmic_applet_a11y.ftl @@ -1,6 +0,0 @@ -screen-reader = Xwînerê dîmenderê -magnifier = Mezinker -invert-colors = Rengan berevajî bike -settings = Sazkariyên gihîştinê... -filter-colors = Rengan parzûn bike -high-contrast = Dijbiriya bilind diff --git a/cosmic-applet-audio/Cargo.toml b/cosmic-applet-audio/Cargo.toml index 3e67d3f5..c0554ebe 100644 --- a/cosmic-applet-audio/Cargo.toml +++ b/cosmic-applet-audio/Cargo.toml @@ -1,11 +1,10 @@ [package] name = "cosmic-applet-audio" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" [dependencies] -futures.workspace = true i18n-embed-fl.workspace = true i18n-embed.workspace = true cosmic.workspace = true @@ -19,9 +18,6 @@ tracing.workspace = true url = "2" urlencoding = "2.1.3" zbus.workspace = true -zlink.workspace = true -intmap = "3.1.3" -[dependencies.cosmic-settings-audio-client] -path = "../../cosmic-settings-daemon/audio-client" -features = ["codec"] +[dependencies.cosmic-settings-sound-subscription] +path = "../../cosmic-settings/subscriptions/sound" diff --git a/cosmic-applet-audio/i18n/kmr/cosmic_applet_audio.ftl b/cosmic-applet-audio/i18n/kmr/cosmic_applet_audio.ftl index 373ab157..e69de29b 100644 --- a/cosmic-applet-audio/i18n/kmr/cosmic_applet_audio.ftl +++ b/cosmic-applet-audio/i18n/kmr/cosmic_applet_audio.ftl @@ -1,7 +0,0 @@ -output = Deran -input = Ketan -unknown-artist = Nenas -sound-settings = Sazkariyên dengê... -disconnected = Girêdana PulseAudio qut bû -no-device = Tu amûr nehatine hilbijartin -show-media-controls = Kontrolên mediyayê li ser destgehê nîşan bide diff --git a/cosmic-applet-audio/src/lib.rs b/cosmic-applet-audio/src/lib.rs index bd62dfbd..78667f5f 100644 --- a/cosmic-applet-audio/src/lib.rs +++ b/cosmic-applet-audio/src/lib.rs @@ -2,13 +2,12 @@ // SPDX-License-Identifier: GPL-3.0-only mod localize; -mod model; mod mouse_area; use crate::localize::localize; use config::{AudioAppletConfig, amplification_sink, amplification_source}; use cosmic::{ - Apply, Element, Renderer, Task, Theme, app, + Element, Renderer, Task, Theme, app, applet::{ column as applet_column, cosmic_panel_config::PanelAnchor, @@ -19,24 +18,18 @@ use cosmic::{ cosmic_config::CosmicConfigEntry, cosmic_theme::Spacing, iced::{ - self, Alignment, Length, Rectangle, Subscription, + self, Alignment, Length, Subscription, futures::StreamExt, widget::{self, column, row, slider}, window, }, surface, theme, - widget::{ - Row, button, container, divider, icon, - rectangle_tracker::{RectangleTracker, RectangleUpdate, rectangle_tracker_subscription}, - space, text, toggler, - }, + widget::{Row, button, container, divider, icon, space, text, toggler}, }; -use cosmic_settings_audio_client::{self as audio_client, CosmicAudioProxy}; -use futures::SinkExt; +use cosmic_settings_sound_subscription as css; use iced::platform_specific::shell::wayland::commands::popup::{destroy_popup, get_popup}; use mpris_subscription::{MprisRequest, MprisUpdate}; use mpris2_zbus::player::PlaybackStatus; -use std::{cell::RefCell, rc::Rc, sync::Arc}; mod config; mod mpris_subscription; @@ -57,10 +50,8 @@ pub struct Audio { core: cosmic::app::Core, /// Track the applet's popup window. popup: Option, - /// Varlink connection to `com.system76.CosmicSettings.Audio`. - audio_client: Option>>, - /// Known audio device state - model: model::Model, + /// The model from cosmic-settings for managing pipewire devices. + model: css::Model, /// Whether to expand the revealer of a source or sink device. is_open: IsOpen, /// Max slider volume for the sink device, as determined by the amplification property. @@ -77,14 +68,12 @@ pub struct Audio { player_status: Option, /// Used to request an activation token for opening cosmic-settings. token_tx: Option>, - rectangle_tracker: Option>, - rectangle: Option, } impl Audio { fn output_icon_name(&self) -> &'static str { - let volume = self.model.active_sink.volume; - let mute = self.model.active_sink.mute; + let volume = self.model.sink_volume; + let mute = self.model.sink_mute; if mute || volume == 0 { "audio-volume-muted-symbolic" } else if volume < 33 { @@ -99,8 +88,8 @@ impl Audio { } fn input_icon_name(&self) -> &'static str { - let volume = self.model.active_source.volume; - let mute = self.model.active_source.mute; + let volume = self.model.source_volume; + let mute = self.model.source_mute; if mute || volume == 0 { "microphone-sensitivity-muted-symbolic" } else if volume < 33 { @@ -121,10 +110,8 @@ enum IsOpen { Input, } -#[derive(Clone, Debug)] +#[derive(Debug, Clone)] pub enum Message { - /// Connection to `com.system76.CosmicSettings`. - Client(Arc), Ignore, SetSinkVolume(u32), SetSourceVolume(u32), @@ -142,9 +129,8 @@ pub enum Message { MprisRequest(MprisRequest), Token(TokenUpdate), OpenSettings, - Subscription(audio_client::Event), + Subscription(css::Message), Surface(surface::Action), - Rectangle(RectangleUpdate), } // TODO @@ -256,9 +242,15 @@ impl cosmic::Application for Audio { const APP_ID: &'static str = "com.system76.CosmicAppletAudio"; fn init(core: cosmic::app::Core, _flags: ()) -> (Self, app::Task) { + let mut model = css::Model::default(); + model.unplugged_text = "Unplugged".into(); + model.hd_audio_text = "HD Audio".into(); + model.usb_audio_text = "USB Audio".into(); + ( Self { core, + model, ..Default::default() }, Task::none(), @@ -279,14 +271,6 @@ impl cosmic::Application for Audio { fn update(&mut self, message: Message) -> app::Task { match message { - Message::Rectangle(u) => match u { - RectangleUpdate::Rectangle(r) => { - self.rectangle = Some(r.1); - } - RectangleUpdate::Init(tracker) => { - self.rectangle_tracker.replace(tracker); - } - }, Message::Ignore => {} Message::TogglePopup => { if let Some(p) = self.popup.take() { @@ -307,21 +291,14 @@ impl cosmic::Application for Audio { (100, &[][..]) }; - let mut popup_settings = self.core.applet.get_popup_settings( + let popup_settings = self.core.applet.get_popup_settings( self.core.main_window_id().unwrap(), new_id, None, None, None, ); - if let Some(r) = self.rectangle { - popup_settings.positioner.anchor_rect = Rectangle { - x: r.x as i32, - y: r.y as i32, - width: r.width as i32, - height: r.height as i32, - }; - } + return get_popup(popup_settings); } } @@ -341,74 +318,52 @@ impl cosmic::Application for Audio { } } Message::Subscription(message) => { - self.model.update(message); + return self + .model + .update(message) + .map(|message| Message::Subscription(message).into()); } Message::SetDefaultSink(pos) => { - if let Some(&pos) = self.model.sinks.sorted_index.get(pos) - && let Some(&node_id) = self.model.sinks.id.get(pos as usize) - && let Some(client) = self.audio_client.as_mut() - { - futures::executor::block_on(async { - _ = client.borrow_mut().conn.set_default(node_id, true).await; - }); - } + return self + .model + .set_default_sink(pos) + .map(|message| Message::Subscription(message).into()); } Message::SetDefaultSource(pos) => { - if let Some(&pos) = self.model.sources.sorted_index.get(pos) - && let Some(&node_id) = self.model.sources.id.get(pos as usize) - && let Some(client) = self.audio_client.as_mut() - { - futures::executor::block_on(async { - _ = client.borrow_mut().conn.set_default(node_id, true).await; - }); - } + return self + .model + .set_default_source(pos) + .map(|message| Message::Subscription(message).into()); } - Message::ToggleSinkMute => { - if let Some(ref mut client) = self.audio_client { - futures::executor::block_on(async { - _ = client.borrow_mut().conn.sink_mute_toggle().await; - }); - } - } + Message::ToggleSinkMute => self.model.toggle_sink_mute(), - Message::ToggleSourceMute => { - if let Some(ref mut client) = self.audio_client { - futures::executor::block_on(async { - _ = client.borrow_mut().conn.source_mute_toggle().await; - }); - } - } + Message::ToggleSourceMute => self.model.toggle_source_mute(), Message::SetSinkVolume(volume) => { - if let Some(ref mut client) = self.audio_client { - self.model.active_sink.volume = volume; - self.model.active_sink.volume_text = volume.to_string(); - futures::executor::block_on(async { - _ = client.borrow_mut().conn.set_sink_volume(volume).await; - }); - } + return self + .model + .set_sink_volume(volume) + .map(|message| Message::Subscription(message).into()); } Message::SetSourceVolume(volume) => { - if let Some(ref mut client) = self.audio_client { - self.model.active_source.volume = volume; - self.model.active_source.volume_text = volume.to_string(); - futures::executor::block_on(async { - _ = client.borrow_mut().conn.set_source_volume(volume).await; - }); - } + return self + .model + .set_source_volume(volume) + .map(|message| Message::Subscription(message).into()); } Message::ToggleMediaControlsInTopPanel(enabled) => { self.config.show_media_controls_in_top_panel = enabled; if let Ok(helper) = cosmic::cosmic_config::Config::new(Self::APP_ID, AudioAppletConfig::VERSION) - && let Err(err) = self.config.write_entry(&helper) { - tracing::error!(?err, "Error writing config"); + if let Err(err) = self.config.write_entry(&helper) { + tracing::error!(?err, "Error writing config"); + } } } Message::CloseRequested(id) => { @@ -506,12 +461,6 @@ impl cosmic::Application for Audio { cosmic::app::Action::Surface(a), )); } - Message::Client(client) => { - if let Some(client) = Arc::into_inner(client) { - self.audio_client = Some(Rc::new(RefCell::new(client))); - self.model = model::Model::default(); - } - } } Task::none() @@ -527,50 +476,7 @@ impl cosmic::Application for Audio { }), mpris_subscription::mpris_subscription(0).map(Message::Mpris), activation_token_subscription(0).map(Message::Token), - Subscription::run(|| { - iced::stream::channel( - 1, - move |mut emitter: futures::channel::mpsc::Sender<_>| async move { - loop { - let mut client = match audio_client::connect().await { - Ok(client) => client, - Err(why) => { - if let zlink::Error::Io(ref why) = why - && why.kind() == std::io::ErrorKind::NotFound - { - tracing::error!( - "cosmic-settings-daemon varlink service not found." - ); - } else { - tracing::error!( - ?why, - "failed to connect to cosmic-settings's varlink service" - ); - } - - tokio::time::sleep(std::time::Duration::from_secs(3)).await; - continue; - } - }; - - if let Ok(Ok(mut stream)) = client.recv_events().await { - _ = emitter.send(Message::Client(Arc::new(client))).await; - while let Some(message) = stream.next().await { - match message { - Ok(event) => { - _ = emitter.send(Message::Subscription(event)).await; - } - Err(why) => { - tracing::error!(?why, "event error"); - } - } - } - } - } - }, - ) - }), - rectangle_tracker_subscription(0).map(|update| Message::Rectangle(update.1)), + Subscription::run(|| css::watch().map(Message::Subscription)), ]) } @@ -611,64 +517,53 @@ impl cosmic::Application for Audio { return Message::Ignore; } - let new_volume = (self.model.active_sink.volume as f64 + (scroll_vector as f64)) + let new_volume = (self.model.sink_volume as f64 + (scroll_vector as f64)) .clamp(0.0, self.max_sink_volume as f64); Message::SetSinkVolume(new_volume.round() as u32) }); - let mut has_playback_buttons = false; let playback_buttons = (!self.core.applet.suggested_bounds.as_ref().is_some_and(|c| { // if we have a configure for width and height, we're in a overflow popup c.width > 0. && c.height > 0. })) .then(|| self.playback_buttons()); - let mut ret = if let Some(playback_buttons) = playback_buttons - && !playback_buttons.is_empty() - { - has_playback_buttons = true; - Element::from(match self.core.applet.anchor { - PanelAnchor::Left | PanelAnchor::Right => Element::from( - applet_column::Column::with_children(playback_buttons) - .push(btn) - .align_x(Alignment::Center) - .height(Length::Shrink) - // TODO configurable variable from the panel? - .spacing( - -(self.core.applet.suggested_padding(true).0 as f32) - * self.core.applet.padding_overlap, + self.core + .applet + .autosize_window( + if let Some(playback_buttons) = playback_buttons + && !playback_buttons.is_empty() + { + match self.core.applet.anchor { + PanelAnchor::Left | PanelAnchor::Right => Element::from( + applet_column::Column::with_children(playback_buttons) + .push(btn) + .align_x(Alignment::Center) + .height(Length::Shrink) + // TODO configurable variable from the panel? + .spacing( + -(self.core.applet.suggested_padding(true).0 as f32) + * self.core.applet.padding_overlap, + ), ), - ), - PanelAnchor::Top | PanelAnchor::Bottom => { - applet_row::Row::with_children(playback_buttons) - .push(btn) - .align_y(Alignment::Center) - .width(Length::Shrink) - // TODO configurable variable from the panel? - .spacing( - -(self.core.applet.suggested_padding(true).0 as f32) - * self.core.applet.padding_overlap, - ) - .into() - } - }) - } else { - btn.into() - }; - - if let Some(tracker) = self.rectangle_tracker.as_ref() - && has_playback_buttons - { - ret = tracker.container(0, ret).into() - } - - if !self.core.applet.suggested_bounds.as_ref().is_some_and(|c| { - // if we have a configure for width and height, we're in a overflow popup - c.width > 0. && c.height > 0. - }) { - ret = self.core.applet.autosize_window(ret).into(); - } - ret + PanelAnchor::Top | PanelAnchor::Bottom => { + applet_row::Row::with_children(playback_buttons) + .push(btn) + .align_y(Alignment::Center) + .width(Length::Shrink) + // TODO configurable variable from the panel? + .spacing( + -(self.core.applet.suggested_padding(true).0 as f32) + * self.core.applet.padding_overlap, + ) + .into() + } + } + } else { + btn.into() + }, + ) + .into() } fn view_window(&self, _id: window::Id) -> Element<'_, Message> { @@ -676,21 +571,19 @@ impl cosmic::Application for Audio { space_xxs, space_s, .. } = theme::active().cosmic().spacing; - let sink: Option<&str> = self + let sink = self .model - .sinks - .active() - .map(|pos| self.model.sinks.sorted_display[pos].as_ref()); - let source: Option<&str> = self + .active_sink() + .and_then(|pos| self.model.sinks().get(pos)); + let source = self .model - .sources - .active() - .map(|pos| self.model.sources.sorted_display[pos].as_ref()); + .active_source() + .and_then(|pos| self.model.sources().get(pos)); let mut audio_content = { let output_slider = slider( 0..=self.max_sink_volume, - self.model.active_sink.volume, + self.model.sink_volume, Message::SetSinkVolume, ) .width(Length::FillPortion(5)) @@ -698,7 +591,7 @@ impl cosmic::Application for Audio { let input_slider = slider( 0..=self.max_source_volume, - self.model.active_source.volume, + self.model.source_volume, Message::SetSourceVolume, ) .width(Length::FillPortion(5)) @@ -717,7 +610,7 @@ impl cosmic::Application for Audio { .line_height(24) .on_press(Message::ToggleSinkMute), output_slider, - container(text(&self.model.active_sink.volume_text).size(16)) + container(text(&self.model.sink_volume_text).size(16)) .width(Length::FillPortion(1)) .align_x(Alignment::End) ] @@ -736,7 +629,7 @@ impl cosmic::Application for Audio { .line_height(24) .on_press(Message::ToggleSourceMute), input_slider, - container(text(&self.model.active_source.volume_text).size(16)) + container(text(&self.model.source_volume_text).size(16)) .width(Length::FillPortion(1)) .align_x(Alignment::End) ] @@ -751,7 +644,7 @@ impl cosmic::Application for Audio { Some(sink) => sink.to_owned(), None => fl!("no-device"), }, - &self.model.sinks.sorted_display, + self.model.sinks(), Message::OutputToggle, Message::SetDefaultSink, ), @@ -762,7 +655,7 @@ impl cosmic::Application for Audio { Some(source) => source.to_owned(), None => fl!("no-device"), }, - &self.model.sources.sorted_display, + self.model.sources(), Message::InputToggle, Message::SetDefaultSource, ) @@ -818,15 +711,19 @@ impl cosmic::Application for Audio { } if let Some(play) = self.is_play() { control_elements.push( - button::icon(icon::from_name(if play { PLAY } else { PAUSE }).symbolic(true)) - .extra_small() - .class(cosmic::theme::Button::AppletIcon) - .on_press(if play { - Message::MprisRequest(MprisRequest::Play) - } else { - Message::MprisRequest(MprisRequest::Pause) - }) - .into(), + button::icon( + icon::from_name(if play { PLAY } else { PAUSE }) + .size(32) + .symbolic(true), + ) + .extra_small() + .class(cosmic::theme::Button::AppletIcon) + .on_press(if play { + Message::MprisRequest(MprisRequest::Play) + } else { + Message::MprisRequest(MprisRequest::Pause) + }) + .into(), ); } if let Some(go_next) = self.go_next(32) { @@ -877,21 +774,20 @@ impl cosmic::Application for Audio { } } -fn revealer<'a>( +fn revealer( open: bool, title: String, selected: String, - devices: &'a [Arc], + devices: &[String], toggle: Message, mut change: impl FnMut(usize) -> Message + 'static, -) -> widget::Column<'a, Message, crate::Theme, Renderer> { +) -> widget::Column<'static, Message, crate::Theme, Renderer> { if open { - devices.iter().enumerate().fold( + devices.iter().cloned().enumerate().fold( column![revealer_head(open, title, selected, toggle)].width(Length::Fill), - move |col, (id, name)| { + |col, (id, name)| { col.push( - text::body(name.as_ref()) - .apply(menu_button) + menu_button(text::body(name)) .on_press(change(id)) .width(Length::Fill) .padding([8, 48]), @@ -909,9 +805,9 @@ fn revealer_head( selected: String, toggle: Message, ) -> cosmic::widget::Button<'static, Message> { - cosmic::widget::column::with_capacity(2) - .push(text::body(title).width(Length::Fill)) - .push(text::caption(selected)) - .apply(menu_button) - .on_press(toggle) + menu_button(column![ + text::body(title).width(Length::Fill), + text::caption(selected), + ]) + .on_press(toggle) } diff --git a/cosmic-applet-audio/src/model.rs b/cosmic-applet-audio/src/model.rs deleted file mode 100644 index 42c76b3c..00000000 --- a/cosmic-applet-audio/src/model.rs +++ /dev/null @@ -1,393 +0,0 @@ -// Copyright 2026 System76 -// SPDX-License-Identifier: GPL-3.0-only - -use std::sync::Arc; - -use cosmic_settings_audio_client::{self as audio_client, Availability, RouteInfo}; -use intmap::IntMap; - -pub type DeviceId = u32; -pub type NodeId = u32; - -#[derive(Debug, Default)] -pub struct Model { - pub device_routes: IntMap>, - pub node_devices: IntMap>, - pub sinks: Nodes, - pub sources: Nodes, - pub active_sink: ActiveNode, - pub active_source: ActiveNode, - pub default_sink: Option, - pub default_source: Option, -} - -#[derive(Debug, Default)] -pub struct Nodes { - active: Option, - pub sorted_display: Box<[Arc]>, - pub sorted_index: Box<[u16]>, - pub balance: Vec>, - pub card_profile_device: Vec>, - pub description: Vec, - pub devices: Vec>, - pub display: Vec>, - pub mute: Vec, - pub name: Vec, - pub id: Vec, - pub volume: Vec, -} - -impl Nodes { - pub fn active(&self) -> Option { - self.active.and_then(|active| { - self.sorted_index - .iter() - .position(|idx| *idx as usize == active) - }) - } - - pub fn dropdown_sort(&mut self) { - let mut enumerated_displays = self - .display - .clone() - .into_iter() - .enumerate() - .map(|(index, display)| (index as u16, display)) - .collect::>(); - enumerated_displays.sort_by_key(|v| v.1.clone()); - let (indexes, displays): (Vec<_>, Vec<_>) = enumerated_displays.into_iter().unzip(); - self.sorted_display = displays.into_boxed_slice(); - self.sorted_index = indexes.into_boxed_slice(); - } - - pub fn remove(&mut self, node_id: u32) -> bool { - let Some(pos) = self.id.iter().position(|id| node_id == *id) else { - return false; - }; - self.balance.remove(pos); - self.card_profile_device.remove(pos); - self.description.remove(pos); - self.devices.remove(pos); - self.display.remove(pos); - self.mute.remove(pos); - self.name.remove(pos); - self.id.remove(pos); - self.volume.remove(pos); - self.dropdown_sort(); - if self.active == Some(pos) { - self.active = None; - } - true - } -} - -#[derive(Debug, Default)] -pub struct ActiveNode { - pub volume_text: String, - pub volume: u32, - pub mute: bool, -} - -impl Model { - pub fn update(&mut self, event: audio_client::Event) { - tracing::debug!(?event, "update"); - match event { - audio_client::Event::NodeMute(node_id, mute) => { - if let Some(pos) = self.sinks.id.iter().position(|id| node_id == *id) { - self.sinks.mute[pos] = mute; - if self.sinks.active == Some(pos) { - self.active_sink.mute = mute; - } - } else if let Some(pos) = self.sources.id.iter().position(|id| node_id == *id) { - self.sources.mute[pos] = mute; - if self.sources.active == Some(pos) { - self.active_source.mute = mute; - } - } - } - - audio_client::Event::NodeVolume(node_id, volume, balance) => { - if let Some(pos) = self.sinks.id.iter().position(|id| node_id == *id) { - self.sinks.volume[pos] = volume; - self.sinks.balance[pos] = balance; - if self.default_sink.as_ref().is_some_and(|&id| id == node_id) - && let Some(pos) = self.sinks.active - { - self.active_sink.mute = self.sinks.mute[pos]; - self.active_sink.volume = self.sinks.volume[pos]; - self.active_sink.volume_text = self.active_sink.volume.to_string(); - } - } else if let Some(pos) = self.sources.id.iter().position(|id| node_id == *id) { - self.sources.volume[pos] = volume; - self.sources.balance[pos] = balance; - if self - .default_source - .as_ref() - .is_some_and(|&id| id == node_id) - && let Some(pos) = self.sources.active - { - self.active_source.mute = self.sources.mute[pos]; - self.active_source.volume = self.sources.volume[pos]; - self.active_source.volume_text = self.active_source.volume.to_string(); - } - } - } - - audio_client::Event::DefaultSink(node_id) => { - self.default_sink = Some(node_id); - if let Some(pos) = self.sinks.id.iter().position(|&id| id == node_id) { - self.sinks.active = Some(pos); - self.active_sink.mute = self.sinks.mute[pos]; - self.active_sink.volume = self.sinks.volume[pos]; - self.active_sink.volume_text = self.active_sink.volume.to_string(); - } - } - - audio_client::Event::DefaultSource(node_id) => { - self.default_source = Some(node_id); - if let Some(pos) = self.sources.id.iter().position(|&id| id == node_id) { - self.sources.active = Some(pos); - self.active_source.mute = self.sources.mute[pos]; - self.active_source.volume = self.sources.volume[pos]; - self.active_source.volume_text = self.active_source.volume.to_string(); - } - } - - audio_client::Event::Node(node_id, node) => { - self.node_devices.insert(node_id, node.device_id); - if node.is_sink { - let pos = if let Some(pos) = self.sinks.id.iter().position(|&id| id == node_id) - { - self.sinks.description[pos] = self.translate(&node.description); - self.sinks.name[pos] = node.name; - self.sinks.card_profile_device[pos] = node.card_profile_device; - pos - } else { - self.sinks.display.push(Arc::default()); - self.sinks - .description - .push(self.translate(&node.description)); - self.sinks.id.push(node_id); - self.sinks.volume.push(0); - self.sinks.balance.push(None); - self.sinks.mute.push(false); - self.sinks.name.push(node.name); - self.sinks.devices.push(node.device_id); - self.sinks - .card_profile_device - .push(node.card_profile_device); - self.sinks.id.len() - 1 - }; - - self.sinks.display[pos] = node - .device_id - .zip(node.card_profile_device) - .and_then(|(device_id, node_card_profile_device)| { - let routes = self.device_routes.get(device_id)?; - for route in routes { - if matches!(route.availability, Availability::No) || !route.is_sink - { - continue; - } - - if route.devices.contains(&node_card_profile_device) { - return Some(node_name( - &self.translate(&route.description), - &self.sinks.description[pos], - )); - } - } - - None - }) - .unwrap_or_else(|| { - node_name( - &node.device_profile_description, - &self.sinks.description[pos], - ) - }); - - self.sinks.dropdown_sort(); - - if let Some(default_node_id) = self.default_sink - && default_node_id == node_id - { - self.sinks.active = Some(pos); - self.active_sink.mute = self.sinks.mute[pos]; - self.active_sink.volume = self.sinks.volume[pos]; - self.active_sink.volume_text = self.active_sink.volume.to_string(); - } - } else { - let pos = - if let Some(pos) = self.sources.id.iter().position(|&id| id == node_id) { - self.sources.description[pos] = self.translate(&node.description); - self.sources.name[pos] = node.name; - self.sources.card_profile_device[pos] = node.card_profile_device; - pos - } else { - self.sources - .description - .push(self.translate(&node.description)); - self.sources.display.push(Arc::default()); - self.sources.id.push(node_id); - self.sources.volume.push(0); - self.sources.balance.push(None); - self.sources.mute.push(false); - self.sources.name.push(node.name); - self.sources.devices.push(node.device_id); - self.sources - .card_profile_device - .push(node.card_profile_device); - self.sources.id.len() - 1 - }; - - if let Some(name) = node - .device_id - .zip(node.card_profile_device) - .map(|(device_id, node_card_profile_device)| { - let routes = self.device_routes.get(device_id)?; - for route in routes { - if route.is_sink || matches!(route.availability, Availability::No) { - continue; - } - - if route.devices.contains(&node_card_profile_device) { - return Some(node_name( - &self.translate(&route.description), - &self.sources.description[pos], - )); - } - } - - None - }) - .unwrap_or_else(|| { - Some(node_name( - &node.device_profile_description, - &self.sources.description[pos], - )) - }) - { - self.sources.display[pos] = name; - self.sources.dropdown_sort(); - } else { - // Remove sources that are unplugged. - self.sources.remove(node_id); - return; - } - - if let Some(default_node_id) = self.default_source - && default_node_id == node_id - { - self.sources.active = Some(pos); - self.active_source.mute = self.sources.mute[pos]; - self.active_source.volume = self.sources.volume[pos]; - self.active_source.volume_text = self.active_source.volume.to_string(); - } - } - } - - audio_client::Event::ActiveRoute(device_id, _index, route) => { - self.update_device_names(device_id, &route); - } - - audio_client::Event::Route(device_id, index, route) => { - let routes = self.device_routes.entry(device_id).or_default(); - if index == 0 { - *routes = vec![route]; - } else { - if routes.len() < index as usize + 1 { - let additional = (index as usize + 1) - routes.capacity(); - routes.reserve_exact(additional); - routes.extend(std::iter::repeat_n(RouteInfo::default(), additional)); - } - routes[index as usize] = route; - } - } - - audio_client::Event::RemoveNode(node_id) => { - self.node_devices.remove(node_id); - - if !self.sinks.remove(node_id) { - self.sources.remove(node_id); - } - } - - audio_client::Event::RemoveDevice(device_id) => { - self.device_routes.remove(device_id); - } - - _ => (), - } - } - - fn update_device_names(&mut self, device_id: DeviceId, route: &RouteInfo) { - if matches!(route.availability, Availability::No) { - return; - } - - let compatible_nodes = self.node_devices.iter().filter_map(|(node, &dev_id)| { - if dev_id? == device_id { - Some(node) - } else { - None - } - }); - - if route.is_sink { - for n_id in compatible_nodes { - let Some(pos) = self.sinks.id.iter().position(|&node| node == n_id) else { - continue; - }; - - let Some(card_profile_device) = self.sinks.card_profile_device[pos] else { - continue; - }; - - if route.devices.contains(&card_profile_device) { - self.sinks.display[pos] = node_name( - &self.translate(&route.description), - &self.sinks.description[pos], - ); - self.sinks.dropdown_sort(); - break; - } - } - } else { - for n_id in compatible_nodes { - let Some(pos) = self.sources.id.iter().position(|&node| node == n_id) else { - continue; - }; - - let Some(card_profile_device) = self.sources.card_profile_device[pos] else { - continue; - }; - - if route.devices.contains(&card_profile_device) { - self.sources.display[pos] = node_name( - &self.translate(&route.description), - &self.sources.description[pos], - ); - self.sources.dropdown_sort(); - break; - } - } - } - } - - pub fn translate(&self, description: &str) -> String { - description - .replace("High Definition", "HD") - .replace("DisplayPort", "DP") - .replace("Controller", "") - } -} - -fn node_name(route: &str, node: &str) -> Arc { - if route.is_empty() { - node.to_owned() - } else { - [route, " - ", node].concat() - } - .into() -} diff --git a/cosmic-applet-battery/Cargo.toml b/cosmic-applet-battery/Cargo.toml index 3310f8fa..fdee2ce1 100644 --- a/cosmic-applet-battery/Cargo.toml +++ b/cosmic-applet-battery/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-battery" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-battery/i18n/kmr/cosmic_applet_battery.ftl b/cosmic-applet-battery/i18n/kmr/cosmic_applet_battery.ftl index 8c0d92d1..e69de29b 100644 --- a/cosmic-applet-battery/i18n/kmr/cosmic_applet_battery.ftl +++ b/cosmic-applet-battery/i18n/kmr/cosmic_applet_battery.ftl @@ -1,14 +0,0 @@ -battery = Betarî -seconds = ç -minutes = x -hours = d -until-empty = Heya vala dibe -power-settings = Sazkariyên hêz û betariyê... -battery-desc = Bikaranîna hêzê kêmkirî û performans. -balanced = Hevseng -balanced-desc = Performansa standard û bikaranîna betariyê. -performance = Performansa bilind -performance-desc = Performansa bilind û bikaranîna hêzê. -max-charge = Jiyana betariyê xwe dirêj bike bi riya danîna sînorê herî mezin yê tijîkrinê %80 -dgpu-running = YKG a veqetandî çalak e û dikare jiyana betariyê kêm bike -dgpu-applications = Sepanên ku YKG a veqetandî ya { $gpu_name } bi kar tînin diff --git a/cosmic-applet-battery/src/app.rs b/cosmic-applet-battery/src/app.rs index 22d9e6cc..f927bde3 100644 --- a/cosmic-applet-battery/src/app.rs +++ b/cosmic-applet-battery/src/app.rs @@ -169,20 +169,6 @@ impl CosmicBatteryApplet { self.charging_limit = Some(limit); self.update_battery(self.battery_percent, self.on_battery); } - - fn panel_icon_name(&self) -> &str { - if self.no_battery { - if self.screen_brightness.is_some() { - self.display_icon_name.as_str() - } else if self.kbd_brightness.is_some() { - "keyboard-brightness-symbolic" - } else { - "plugged-into-power-symbolic" - } - } else { - self.icon_name.as_str() - } - } } #[derive(Debug, Clone)] @@ -536,9 +522,19 @@ impl cosmic::Application for CosmicBatteryApplet { let applet_padding = self.core.applet.suggested_padding(true); let mut children = vec![ - icon::from_name(self.panel_icon_name()) - .size(suggested_size.0) - .into(), + icon::from_name(if self.no_battery { + if self.screen_brightness.is_some() { + self.display_icon_name.as_str() + } else if self.kbd_brightness.is_some() { + "keyboard-brightness-symbolic" + } else { + self.icon_name.as_str() + } + } else { + self.icon_name.as_str() + }) + .size(suggested_size.0) + .into(), ]; if self.config.show_percentage && !self.no_battery { diff --git a/cosmic-applet-bluetooth/Cargo.toml b/cosmic-applet-bluetooth/Cargo.toml index 1ee209ee..f3a8c179 100644 --- a/cosmic-applet-bluetooth/Cargo.toml +++ b/cosmic-applet-bluetooth/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-bluetooth" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-bluetooth/i18n/kmr/cosmic_applet_bluetooth.ftl b/cosmic-applet-bluetooth/i18n/kmr/cosmic_applet_bluetooth.ftl index 988f00ca..e69de29b 100644 --- a/cosmic-applet-bluetooth/i18n/kmr/cosmic_applet_bluetooth.ftl +++ b/cosmic-applet-bluetooth/i18n/kmr/cosmic_applet_bluetooth.ftl @@ -1,12 +0,0 @@ -cancel = Têk bibe -bluetooth = Bluetooth -connected = Hat girêdan -other-devices = Amûrên Bluetooth ên din -settings = Sazkariyên Bluetooth... -confirm-pin = Tika ye piştrast bike ku PIN a jêrîn bi ya ku li ser { $deviceName } tê xuyakirin re li hev tê -confirm = Bipejirîne -check-device = Piştrast bike ku { $deviceName } çalak e, di hundir rêjeyê de ye, û amade ye ji bo cotkirinê. -try-again = Dîsa hewl bide -discoverable = Dîtbar -pairable = Cotbar -unsuccessful = Cotkirin têkçûyî ye diff --git a/cosmic-applet-bluetooth/src/app.rs b/cosmic-applet-bluetooth/src/app.rs index 484b8bf3..d1d31022 100644 --- a/cosmic-applet-bluetooth/src/app.rs +++ b/cosmic-applet-bluetooth/src/app.rs @@ -21,7 +21,7 @@ use cosmic::{ widget::{Column, column, container, row}, }, theme, - widget::{button, divider, icon, indeterminate_circular, scrollable, text}, + widget::{button, divider, icon, scrollable, text}, }; use futures::FutureExt; use std::{collections::HashMap, time::Duration}; @@ -368,12 +368,14 @@ impl cosmic::Application for CosmicBluetoothApplet { ); } BluerDeviceStatus::Paired => {} - BluerDeviceStatus::Connecting - | BluerDeviceStatus::Disconnecting - | BluerDeviceStatus::Pairing => { - row = row.push(indeterminate_circular().size(24.0)); + BluerDeviceStatus::Connecting | BluerDeviceStatus::Disconnecting => { + row = row.push( + icon::from_name("process-working-symbolic") + .size(24) + .symbolic(true), + ); } - BluerDeviceStatus::Disconnected => continue, + BluerDeviceStatus::Disconnected | BluerDeviceStatus::Pairing => continue, } known_bluetooth.push( diff --git a/cosmic-applet-bluetooth/src/bluetooth.rs b/cosmic-applet-bluetooth/src/bluetooth.rs index 3a859932..0083568f 100644 --- a/cosmic-applet-bluetooth/src/bluetooth.rs +++ b/cosmic-applet-bluetooth/src/bluetooth.rs @@ -567,21 +567,22 @@ impl BluerSessionState { tick(&mut interval).await; let new_status = adapter_clone.is_powered().await.unwrap_or_default(); devices = build_device_list(devices, &adapter_clone).await; - let power_changed = new_status != status; - status = new_status; - let state = BluerState { - devices: devices.clone(), - bluetooth_enabled: status, - }; - if power_changed && state.bluetooth_enabled { - for d in &state.devices { - if d.paired_and_trusted() { - _ = req_tx.send(BluerRequest::ConnectDevice(d.address)).await; + if new_status != status { + status = new_status; + let state = BluerState { + devices: devices.clone(), + bluetooth_enabled: status, + }; + if state.bluetooth_enabled { + for d in &state.devices { + if d.paired_and_trusted() { + _ = req_tx.send(BluerRequest::ConnectDevice(d.address)).await; + } } } _ = wake_up_discover_tx.send(()).await; + let _ = tx.send(BluerSessionEvent::ChangesProcessed(state)).await; } - let _ = tx.send(BluerSessionEvent::ChangesProcessed(state)).await; } }); } @@ -672,9 +673,6 @@ impl BluerSessionState { } } - // Always refresh power state from the adapter - // to avoid stale cached is_powered values - is_powered = adapter_clone.is_powered().await.unwrap_or_default(); let _ = tx .send(BluerSessionEvent::ChangesProcessed(BluerState { devices: devices.clone(), @@ -854,7 +852,13 @@ async fn bluer_state(adapter: &Adapter) -> BluerState { #[inline(never)] async fn build_device_list(mut devices: Vec, adapter: &Adapter) -> Vec { - let addrs = adapter.device_addresses().await.unwrap_or_default(); + let addrs: Vec
= adapter + .device_addresses() + .await + .unwrap_or_default() + .into_iter() + .filter(|addr| !devices.iter().any(|d| d.address == *addr)) + .collect(); devices.clear(); if addrs.len() > devices.capacity() { diff --git a/cosmic-applet-input-sources/Cargo.toml b/cosmic-applet-input-sources/Cargo.toml index 45b54857..046a3bfb 100644 --- a/cosmic-applet-input-sources/Cargo.toml +++ b/cosmic-applet-input-sources/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-input-sources" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-input-sources/i18n/kmr/cosmic_applet_input_sources.ftl b/cosmic-applet-input-sources/i18n/kmr/cosmic_applet_input_sources.ftl index 737324c5..e69de29b 100644 --- a/cosmic-applet-input-sources/i18n/kmr/cosmic_applet_input_sources.ftl +++ b/cosmic-applet-input-sources/i18n/kmr/cosmic_applet_input_sources.ftl @@ -1,2 +0,0 @@ -show-keyboard-layout = Awaya kilîtdankê nîşan bide... -keyboard-settings = Sazkariyên kilîtdankê... diff --git a/cosmic-applet-minimize/Cargo.toml b/cosmic-applet-minimize/Cargo.toml index 29ee2c8e..5fd35bd2 100644 --- a/cosmic-applet-minimize/Cargo.toml +++ b/cosmic-applet-minimize/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-minimize" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-minimize/src/wayland_handler.rs b/cosmic-applet-minimize/src/wayland_handler.rs index 562693e2..bf2eae30 100644 --- a/cosmic-applet-minimize/src/wayland_handler.rs +++ b/cosmic-applet-minimize/src/wayland_handler.rs @@ -121,7 +121,6 @@ struct AppData { toplevel_info_state: ToplevelInfoState, toplevel_manager_state: ToplevelManagerState, seat_state: SeatState, - captured_toplevels: std::collections::HashSet, } struct CaptureData { @@ -352,36 +351,6 @@ impl AppData { } }); } - - fn handle_toplevel(&mut self, toplevel: &ExtForeignToplevelHandleV1, is_new: bool) { - let Some(info) = self.toplevel_info_state.info(toplevel) else { - return; - }; - if info - .state - .contains(&zcosmic_toplevel_handle_v1::State::Minimized) - { - // Capture a thumbnail once, on the transition into minimized. - if self.captured_toplevels.insert(toplevel.clone()) { - self.send_image(toplevel.clone()); - } - let update = if is_new { - ToplevelUpdate::Add(info.clone()) - } else { - ToplevelUpdate::Update(info.clone()) - }; - let _ = futures::executor::block_on(self.tx.send(WaylandUpdate::Toplevel(update))); - } else { - self.remove_toplevel(toplevel); - } - } - - fn remove_toplevel(&mut self, toplevel: &ExtForeignToplevelHandleV1) { - self.captured_toplevels.remove(toplevel); - let _ = futures::executor::block_on(self.tx.send(WaylandUpdate::Toplevel( - ToplevelUpdate::Remove(toplevel.clone()), - ))); - } } impl ToplevelInfoHandler for AppData { @@ -395,7 +364,23 @@ impl ToplevelInfoHandler for AppData { _qh: &QueueHandle, toplevel: &ExtForeignToplevelHandleV1, ) { - self.handle_toplevel(toplevel, true); + if let Some(info) = self.toplevel_info_state.info(toplevel) { + if info + .state + .contains(&zcosmic_toplevel_handle_v1::State::Minimized) + { + // spawn thread for sending the image + self.send_image(toplevel.clone()); + let _ = futures::executor::block_on( + self.tx + .send(WaylandUpdate::Toplevel(ToplevelUpdate::Add(info.clone()))), + ); + } else { + let _ = futures::executor::block_on(self.tx.send(WaylandUpdate::Toplevel( + ToplevelUpdate::Remove(toplevel.clone()), + ))); + } + } } fn update_toplevel( @@ -404,7 +389,21 @@ impl ToplevelInfoHandler for AppData { _qh: &QueueHandle, toplevel: &ExtForeignToplevelHandleV1, ) { - self.handle_toplevel(toplevel, false); + if let Some(info) = self.toplevel_info_state.info(toplevel) { + if info + .state + .contains(&zcosmic_toplevel_handle_v1::State::Minimized) + { + self.send_image(toplevel.clone()); + let _ = futures::executor::block_on(self.tx.send(WaylandUpdate::Toplevel( + ToplevelUpdate::Update(info.clone()), + ))); + } else { + let _ = futures::executor::block_on(self.tx.send(WaylandUpdate::Toplevel( + ToplevelUpdate::Remove(toplevel.clone()), + ))); + } + } } fn toplevel_closed( @@ -413,7 +412,9 @@ impl ToplevelInfoHandler for AppData { _qh: &QueueHandle, toplevel: &ExtForeignToplevelHandleV1, ) { - self.remove_toplevel(toplevel); + let _ = futures::executor::block_on(self.tx.send(WaylandUpdate::Toplevel( + ToplevelUpdate::Remove(toplevel.clone()), + ))); } } @@ -481,7 +482,6 @@ pub(crate) fn wayland_handler( toplevel_manager_state: ToplevelManagerState::new(®istry_state, &qh), queue_handle: qh, registry_state, - captured_toplevels: std::collections::HashSet::new(), }; loop { diff --git a/cosmic-applet-network/Cargo.toml b/cosmic-applet-network/Cargo.toml index 62efbaf9..ea265d4e 100644 --- a/cosmic-applet-network/Cargo.toml +++ b/cosmic-applet-network/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-network" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-or-later" diff --git a/cosmic-applet-network/data/dbus-1/system.d/com.system76.CosmicSettings.Applet.NetworkManager.SecretAgent.conf b/cosmic-applet-network/data/dbus-1/system.d/com.system76.CosmicSettings.Applet.NetworkManager.SecretAgent.conf deleted file mode 100644 index 8e98cedb..00000000 --- a/cosmic-applet-network/data/dbus-1/system.d/com.system76.CosmicSettings.Applet.NetworkManager.SecretAgent.conf +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - diff --git a/cosmic-applet-network/i18n/kmr/cosmic_applet_network.ftl b/cosmic-applet-network/i18n/kmr/cosmic_applet_network.ftl index 3dbb0266..e69de29b 100644 --- a/cosmic-applet-network/i18n/kmr/cosmic_applet_network.ftl +++ b/cosmic-applet-network/i18n/kmr/cosmic_applet_network.ftl @@ -1,24 +0,0 @@ -cancel = Têk bibe -connect = Girê bide -connected = Hat girêdan -network = Tor -airplane-mode = Awaya balafirê -airplane-mode-on = Awaya balafirê vekirî ye -turn-off-airplane-mode = Ji bo çalakirina Wi-Fi, Bluetooth û torên mobayîl, awaya balafirê bigire. -wifi = Wi-Fi -identity = Nasname -ipv4 = IPv4 -ipv6 = IPv6 -mac = MAC -megabits-per-second = Mbps -gigabits-per-second = Gbps -terabits-per-second = Tbps -connecting = Tê girêdan -settings = Sazkariyên torê... -visible-wireless-networks = Torên bêtêl ên xuya -vpn-connections = Girêdanên VPN -enter-password = Borînpeyvê yan jî kilîtê şîfrekirinê têxîne -router-wps-button = Tu dikarî bi pêlkirina bişkoka "WPS" ya li ser routerê jî girê bidî -unable-to-connect = Nikare bi torê ve were girêdan -check-wifi-connection = Piştrast bike ku Wi-Fi bi înternetê ve girêdayî ye û borînpeyv rast e -reset = Ji nû ve saz bike diff --git a/cosmic-applet-network/src/app.rs b/cosmic-applet-network/src/app.rs index 0b6dbe24..6939f5e3 100644 --- a/cosmic-applet-network/src/app.rs +++ b/cosmic-applet-network/src/app.rs @@ -35,7 +35,7 @@ use cosmic::{ widget::{ Id, button, column, container, divider, icon::{self, from_name}, - indeterminate_circular, row, scrollable, secure_input, text, text_input, toggler, + row, scrollable, secure_input, text, text_input, toggler, }, }; use cosmic_dbus_networkmanager::interface::enums::{ @@ -405,7 +405,6 @@ fn secret_agent_task(identifier: String) -> Task { cosmic::Task::stream(async_fn_stream::fn_stream(move |emitter| async move { let registration = SecretAgent::builder() .with_identifier(identifier) - .with_object_path("/org/freedesktop/NetworkManager/SecretAgent") .with_capabilities(SecretAgentCapabilities::VPN_HINTS) .register() .await; @@ -665,13 +664,6 @@ fn load_vpns(_conn: zbus::Connection) -> Task { let mut map: IndexMap = IndexMap::new(); for c in saved { - // Skip in-memory-only NM connections — assumed connections that NM - // auto-generated from externally-managed interfaces (e.g. one - // brought up by wg-quick@wg0.service) report unsaved=true and - // evaporate on deactivate, leaving the applet's toggle dead. - if c.unsaved { - continue; - } let uuid: UUID = Arc::from(c.uuid.as_str()); let entry = match c.summary { SettingsSummary::WireGuard { .. } => ConnectionSettings::Wireguard { id: c.id }, @@ -734,10 +726,9 @@ impl cosmic::Application for CosmicNetworkApplet { tasks.push(update_state(conn.clone())); tasks.push(update_devices(conn.clone())); tasks.push(load_vpns(conn)); - let uuid = uuid::Uuid::new_v4().to_string().replace("-", "_"); - let my_id = format!( - "com.system76.CosmicSettings.Applet._{uuid}.NetworkManager.SecretAgent", + "com.system76.CosmicSettings.Applet.{}.NetworkManager.SecretAgent", + uuid::Uuid::new_v4() ); tasks.push(secret_agent_task(my_id).map(Message::SecretAgent)); } @@ -1516,7 +1507,12 @@ impl cosmic::Application for CosmicNetworkApplet { ]; match state { ActiveConnectionState::Activating | ActiveConnectionState::Deactivating => { - btn_content.push(indeterminate_circular().size(24.0).into()); + btn_content.push( + icon::from_name("process-working-symbolic") + .size(24) + .symbolic(true) + .into(), + ); } ActiveConnectionState::Activated => btn_content.push( text::body(fl!("connected")) @@ -1724,7 +1720,12 @@ impl cosmic::Application for CosmicNetworkApplet { .into(), ); btn_content.push(ssid.into()); - btn_content.push(indeterminate_circular().size(24.0).into()); + btn_content.push( + icon::from_name("process-working-symbolic") + .size(24) + .symbolic(true) + .into(), + ); } else if matches!(known.state, DeviceState::Unavailable) { btn_content.push( icon::from_name("network-wireless-disconnected-symbolic") @@ -1896,7 +1897,10 @@ impl cosmic::Application for CosmicNetworkApplet { let connecting = padded_control( row::with_children([ Element::from(id), - indeterminate_circular().size(24.0).into(), + icon::from_name("process-working-symbolic") + .size(24) + .symbolic(true) + .into(), ]) .spacing(8), ); diff --git a/cosmic-applet-notifications/Cargo.toml b/cosmic-applet-notifications/Cargo.toml index 91752579..fbfc8ad5 100644 --- a/cosmic-applet-notifications/Cargo.toml +++ b/cosmic-applet-notifications/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-notifications" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-notifications/i18n/kmr/cosmic_applet_notifications.ftl b/cosmic-applet-notifications/i18n/kmr/cosmic_applet_notifications.ftl index b7a7578a..e69de29b 100644 --- a/cosmic-applet-notifications/i18n/kmr/cosmic_applet_notifications.ftl +++ b/cosmic-applet-notifications/i18n/kmr/cosmic_applet_notifications.ftl @@ -1,19 +0,0 @@ -hours-ago = - { $duration -> - [0] Niha - [one] 1 demjimêr berê - *[other] { $duration } demjimêr berê - } -minutes-ago = - { $duration -> - [0] Niha - [one] 1 xulek berê - *[other] { $duration } xulek berê - } -show-less = Kêmtir nîşan bide -show-more = Bêtir { $more } nîşan bide -clear-group = Komê pak bike -clear-all = Hemû agahdariyan pak bike -do-not-disturb = Rawestandina balkêşiyê -notification-settings = Sazkariyên agahdariyê.... -no-notifications = Agahdarî tune ne diff --git a/cosmic-applet-power/Cargo.toml b/cosmic-applet-power/Cargo.toml index 85f520f9..d6fae301 100644 --- a/cosmic-applet-power/Cargo.toml +++ b/cosmic-applet-power/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-power" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-power/i18n/kmr/cosmic_applet_power.ftl b/cosmic-applet-power/i18n/kmr/cosmic_applet_power.ftl index 003f4a23..e69de29b 100644 --- a/cosmic-applet-power/i18n/kmr/cosmic_applet_power.ftl +++ b/cosmic-applet-power/i18n/kmr/cosmic_applet_power.ftl @@ -1,36 +0,0 @@ -cancel = Têk bibe -confirm = Bipejirîne -power = Hêz -restart = Ji nû ve bide destpêkirin -settings = Sazkarî... -shutdown = Vemrîne -suspend = Rawestîne -log-out = Derkeve -lock-screen = Dîmenderê kilît bike -lock-screen-shortcut = Super + Escape -log-out-shortcut = Super + Shift + Escape -confirm-button = - { $action -> - [restart] { restart } - [suspend] { suspend } - [shutdown] Vemrîne - [log-out] { log-out } - *[other] { confirm } - } -confirm-title = - { $action -> - [restart] { restart } - [suspend] { suspend } - [shutdown] { shutdown } - [log-out] Hemû sepanan bigire û derkeve - *[other] Çalakiyê hilbijartî bisepîne - } niha? -confirm-body = - Pergal wê xweber were { $action -> - [restart] jinûvedestpêkkirin - [suspend] rawestandin - [shutdown] vemirandin - [lock-screen] kilîtkirin - [log-out] derketin - *[other] çalakiyê hilbijartî bisepîne - }di { $countdown } çirke de. diff --git a/cosmic-applet-status-area/Cargo.toml b/cosmic-applet-status-area/Cargo.toml index d96913ab..b222166a 100644 --- a/cosmic-applet-status-area/Cargo.toml +++ b/cosmic-applet-status-area/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-status-area" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-status-area/src/components/app.rs b/cosmic-applet-status-area/src/components/app.rs index 7bedc653..c9d1acd4 100644 --- a/cosmic-applet-status-area/src/components/app.rs +++ b/cosmic-applet-status-area/src/components/app.rs @@ -9,14 +9,10 @@ use cosmic::{ }, cctk::sctk::reexports::calloop, iced::{ - self, - Event::Mouse, - Length, Subscription, event, - mouse::{self, ScrollDelta}, + self, Length, Subscription, platform_specific::shell::commands::popup::{destroy_popup, get_popup}, window, }, - scroll::{DiscreteScrollDelta, DiscreteScrollState}, surface, widget::{container, mouse_area}, }; @@ -37,8 +33,7 @@ pub enum Msg { StatusMenu((usize, status_menu::Msg)), StatusNotifier(status_notifier_watcher::Event), TogglePopup(usize), - Hovered(Option), - WheelScrolled(ScrollDelta), + Hovered(usize), Surface(surface::Action), ToggleOverflow, HoveredOverflow, @@ -54,8 +49,6 @@ pub(crate) struct App { max_menu_id: usize, popup: Option, overflow_popup: Option, - hovered_menu: Option, - scroll_states: BTreeMap, token_tx: Option>, } @@ -110,10 +103,9 @@ impl App { let overflow_index = self.overflow_index().unwrap_or(0); let children = self.menus.iter().skip(overflow_index).map(|(id, menu)| { mouse_area( - menu_icon_button(&self.core.applet, menu).on_press_down(Msg::TogglePopup(*id)), + menu_icon_button(&self.core.applet, &menu).on_press_down(Msg::TogglePopup(*id)), ) - .on_enter(Msg::Hovered(Some(*id))) - .on_exit(Msg::Hovered(None)) + .on_enter(Msg::Hovered(*id)) .into() }); @@ -218,7 +210,6 @@ impl cosmic::Application for App { { let id = *id; self.menus.remove(&id); - self.scroll_states.remove(&id); if self.open_menu == Some(id) { self.open_menu = None; if let Some(popup_id) = self.popup { @@ -321,10 +312,6 @@ impl cosmic::Application for App { } }, Msg::Hovered(id) => { - self.hovered_menu = id; - let Some(id) = id else { - return Task::none(); - }; let mut cmds = Vec::new(); if let Some(old_id) = self.open_menu.take() { if old_id != id { @@ -374,19 +361,6 @@ impl cosmic::Application for App { cmds.push(get_popup(popup_settings)); Task::batch(cmds) } - Msg::WheelScrolled(delta) => { - let Some(id) = self.hovered_menu else { - return Task::none(); - }; - let discrete_delta = self.scroll_states.entry(id).or_default().update(delta); - let Some((delta, orientation)) = discrete_scroll_delta(discrete_delta) else { - return Task::none(); - }; - let Some(menu) = self.menus.get(&id) else { - return Task::none(); - }; - scroll(id, menu.item.item_proxy().clone(), delta, orientation) - } Msg::Surface(a) => { return cosmic::task::message(cosmic::Action::Cosmic( cosmic::app::Action::Surface(a), @@ -431,7 +405,6 @@ impl cosmic::Application for App { } } Msg::HoveredOverflow => { - self.hovered_menu = None; let mut cmds = Vec::new(); if self.overflow_popup.is_some() { // If we already have an overflow popup, do nothing @@ -487,12 +460,6 @@ impl cosmic::Application for App { subscriptions.push(menu.subscription(is_open).with(*id).map(Msg::StatusMenu)); } subscriptions.push(activation_token_subscription(0).map(Msg::Token)); - subscriptions.push(event::listen_with(|e, status, _| match (e, status) { - (Mouse(mouse::Event::WheelScrolled { delta }), event::Status::Ignored) => { - Some(Msg::WheelScrolled(delta)) - } - _ => None, - })); iced::Subscription::batch(subscriptions) } @@ -505,10 +472,9 @@ impl cosmic::Application for App { .iter() .take(overflow_index.unwrap_or(self.menus.len())) .map(|(id, menu)| { - mouse_area(menu_icon_button(&self.core.applet, menu).on_press(Msg::Activate(*id))) + mouse_area(menu_icon_button(&self.core.applet, &menu).on_press(Msg::Activate(*id))) .on_right_press(Msg::TogglePopup(*id)) - .on_enter(Msg::Hovered(Some(*id))) - .on_exit(Msg::Hovered(None)) + .on_enter(Msg::Hovered(*id)) .into() }); @@ -604,33 +570,6 @@ fn activate( }) } -fn scroll( - id: usize, - item_proxy: crate::subscriptions::status_notifier_item::StatusNotifierItemProxy<'static>, - delta: i32, - orientation: &'static str, -) -> Task> { - Task::future(async move { - match item_proxy.scroll(delta, orientation).await { - Ok(_) => cosmic::action::app(Msg::None), - Err(err) => { - tracing::error!("Scroll failed for {}: {}", id, err); - cosmic::action::app(Msg::None) - } - } - }) -} - -fn discrete_scroll_delta(delta: DiscreteScrollDelta) -> Option<(i32, &'static str)> { - if delta.y != 0 { - Some((delta.y as i32, "vertical")) - } else if delta.x != 0 { - Some((delta.x as i32, "horizontal")) - } else { - None - } -} - fn menu_icon_button<'a>( applet: &'a cosmic::applet::Context, menu: &'a status_menu::State, @@ -675,43 +614,3 @@ fn menu_icon_button<'a>( pub fn main() -> iced::Result { cosmic::applet::run::(()) } - -#[cfg(test)] -mod tests { - use super::*; - - #[test] - fn discrete_scroll_prefers_vertical_delta() { - assert_eq!( - discrete_scroll_delta(cosmic::scroll::DiscreteScrollDelta { x: 4, y: -2 }), - Some((-2, "vertical")) - ); - } - - #[test] - fn discrete_scroll_uses_horizontal_delta_when_vertical_is_zero() { - assert_eq!( - discrete_scroll_delta(cosmic::scroll::DiscreteScrollDelta { x: 3, y: 0 }), - Some((3, "horizontal")) - ); - } - - #[test] - fn discrete_scroll_ignores_zero_delta() { - assert_eq!( - discrete_scroll_delta(cosmic::scroll::DiscreteScrollDelta { x: 0, y: 0 }), - None - ); - } - - #[test] - fn pixel_scroll_accumulates_before_emitting_discrete_delta() { - let mut state = cosmic::scroll::DiscreteScrollState::default(); - - let first = state.update(ScrollDelta::Pixels { x: 0.0, y: 12.0 }); - assert_eq!(discrete_scroll_delta(first), None); - - let second = state.update(ScrollDelta::Pixels { x: 0.0, y: 12.0 }); - assert_eq!(discrete_scroll_delta(second), Some((1, "vertical"))); - } -} diff --git a/cosmic-applet-status-area/src/subscriptions/status_notifier_item.rs b/cosmic-applet-status-area/src/subscriptions/status_notifier_item.rs index 2c3d4904..c03f0f54 100644 --- a/cosmic-applet-status-area/src/subscriptions/status_notifier_item.rs +++ b/cosmic-applet-status-area/src/subscriptions/status_notifier_item.rs @@ -202,8 +202,6 @@ pub trait StatusNotifierItem { fn activate(&self, x: i32, y: i32) -> zbus::Result<()>; fn secondary_activate(&self, x: i32, y: i32) -> zbus::Result<()>; - - fn scroll(&self, delta: i32, orientation: &str) -> zbus::Result<()>; } #[derive(Clone, Debug)] diff --git a/cosmic-applet-tiling/Cargo.toml b/cosmic-applet-tiling/Cargo.toml index 7767a997..894be7d4 100644 --- a/cosmic-applet-tiling/Cargo.toml +++ b/cosmic-applet-tiling/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-tiling" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-tiling/i18n/kmr/cosmic_applet_tiling.ftl b/cosmic-applet-tiling/i18n/kmr/cosmic_applet_tiling.ftl index e3f124ff..e69de29b 100644 --- a/cosmic-applet-tiling/i18n/kmr/cosmic_applet_tiling.ftl +++ b/cosmic-applet-tiling/i18n/kmr/cosmic_applet_tiling.ftl @@ -1,20 +0,0 @@ -tile-windows = Çarçoveyan xweber berhev bike -tile-current = Qada xebatê heyî berhev bike -shortcuts = Kurterê -navigate-windows = Di nav çarçoveyan de bigere -move-window = Çarçoveyê bilivîne -toggle-floating-window = Rewşê çarçoveyê herikbar biguhêrîne -view-all-shortcuts = Hemû kurteriyan nîşan bide... -active-hint = Pêşniyara çalak -gaps = Valahî -floating-window-exceptions = Awarteyên çarçoveyê herikbar... -window-management-settings = Sazkariyên rêveberiya çarçoveyê... -all-workspaces = Hemû qadên xebatê -per-workspace = Li gorî qada xebatê -super = Super -shift = Shift -arrow-keys = tîr -tiled = Berhevkirî -floating = Herikbar -autotile-behavior = Li ser qadên xebatê çarçoveyan berhev bike -new-workspace = Tevgera qada xebatê ya nû diff --git a/cosmic-applet-time/Cargo.toml b/cosmic-applet-time/Cargo.toml index 3c85ee07..bfa73bcb 100644 --- a/cosmic-applet-time/Cargo.toml +++ b/cosmic-applet-time/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-time" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-time/i18n/kmr/cosmic_applet_time.ftl b/cosmic-applet-time/i18n/kmr/cosmic_applet_time.ftl index e6ff41f9..e69de29b 100644 --- a/cosmic-applet-time/i18n/kmr/cosmic_applet_time.ftl +++ b/cosmic-applet-time/i18n/kmr/cosmic_applet_time.ftl @@ -1 +0,0 @@ -datetime-settings = Sazkariyên dîrok, dem û salnameyê... diff --git a/cosmic-applet-workspaces/Cargo.toml b/cosmic-applet-workspaces/Cargo.toml index 103680e2..9d1b7bb9 100644 --- a/cosmic-applet-workspaces/Cargo.toml +++ b/cosmic-applet-workspaces/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applet-workspaces" -version = "1.0.15" +version = "1.0.2" authors = ["Ashley Wulber "] edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-applet-workspaces/i18n/kmr/cosmic_applet_workspaces.ftl b/cosmic-applet-workspaces/i18n/kmr/cosmic_applet_workspaces.ftl index e262ce29..e69de29b 100644 --- a/cosmic-applet-workspaces/i18n/kmr/cosmic_applet_workspaces.ftl +++ b/cosmic-applet-workspaces/i18n/kmr/cosmic_applet_workspaces.ftl @@ -1 +0,0 @@ -cosmic-applet-workspaces = Qadên xebatê yên COSMIC diff --git a/cosmic-applets-config/Cargo.toml b/cosmic-applets-config/Cargo.toml index 724da32a..b6999f16 100644 --- a/cosmic-applets-config/Cargo.toml +++ b/cosmic-applets-config/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applets-config" -version = "1.0.15" +version = "1.0.2" edition = "2024" [dependencies] diff --git a/cosmic-applets/Cargo.toml b/cosmic-applets/Cargo.toml index f204a80c..97755af8 100644 --- a/cosmic-applets/Cargo.toml +++ b/cosmic-applets/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-applets" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/cosmic-panel-button/Cargo.toml b/cosmic-panel-button/Cargo.toml index 69074433..6719e131 100644 --- a/cosmic-panel-button/Cargo.toml +++ b/cosmic-panel-button/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cosmic-panel-button" -version = "1.0.15" +version = "1.0.2" edition = "2024" license = "GPL-3.0-only" diff --git a/debian/changelog b/debian/changelog index 3d46c583..147363a2 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1,9 +1,3 @@ -cosmic-applets (1.0.15) noble; urgency=medium - - * Update changelog - - -- Michael Murphy Thu, 28 May 2026 19:33:02 +0200 - cosmic-applets (1.0.12) noble; urgency=medium * Update changelog diff --git a/i18n/ja/desktop_entries.ftl b/i18n/ja/desktop_entries.ftl index c5b41c0a..e69de29b 100644 --- a/i18n/ja/desktop_entries.ftl +++ b/i18n/ja/desktop_entries.ftl @@ -1 +0,0 @@ -cosmic-applet-a11y = アクセシビリティ diff --git a/i18n/kmr/desktop_entries.ftl b/i18n/kmr/desktop_entries.ftl index 0a42fc18..e69de29b 100644 --- a/i18n/kmr/desktop_entries.ftl +++ b/i18n/kmr/desktop_entries.ftl @@ -1,51 +0,0 @@ -cosmic-applet-audio = Deng -cosmic-app-list = Destgeha sepanan -cosmic-applet-a11y = Gihîştin -cosmic-applet-bluetooth = Bluetooth -cosmic-applet-bluetooth-comment = Amûrên Bluetooth bi rê ve bibe -cosmic-applet-bluetooth-keywords = COSMIC;Sepanok;Bluetooth; -cosmic-applet-input-sources = Çavkaniyên ketanê -cosmic-applet-input-sources-comment = Di navbera çavkaniyên ketanê de biguhêrîne -cosmic-applet-input-sources-keywords = COSMIC;Sepanok;Ketan;Çavkanî; -cosmic-app-list-comment = Sepanên darxistî veke û çarçoveyên vekirî bi rê ve bibe -cosmic-app-list-keywords = COSMIC;Sepanok;Sepan;Destgeh;Lîste;Erk;Bend; -cosmic-applet-a11y-comment = Sazkariyên gihîştinê ji destgehê saz bike -cosmic-applet-a11y-keywords = COSMIC;Sepanok;Gihîştin;Dîmender;A11y;Xwîner;Dîmender;Mezinker;Bijberî;Reng; -cosmic-applet-audio-comment = Hilbijartina amûra dengê, kontrola dengê, û kontrolên mediyaya MPRIS -cosmic-applet-audio-keywords = COSMIC;Sepanok;Deng;Deng;MPRIS; -cosmic-applet-battery = Hêz & Betarî -cosmic-applet-battery-comment = Awayên hêzê û vebijêrkên parastina hêzê -cosmic-applet-battery-keywords = COSMIC;Sepanok;Hêz;Betarî; -cosmic-applet-minimize = Çarçoveyên biçûk -cosmic-applet-minimize-comment = Çarçoveyên biçûk bi rê ve bibe -cosmic-applet-minimize-keywords = COSMIC;Sepanok;Biçûkkirin; -cosmic-applet-network = Tor -cosmic-applet-network-comment = Girêdanên torê bi rê ve bibe -cosmic-applet-network-keywords = COSMIC;Sepanok;Tor; -cosmic-applet-notifications = Navenda Agahdariyan -cosmic-applet-notifications-comment = Agahdarî û rawestandina balkişiyê bi rê ve bibe -cosmic-applet-notifications-keywords = COSMIC;Sepanok;Agahdarî; -cosmic-applet-power = Danaşîna bikarhêner -cosmic-applet-power-comment = Dîmenderê kilît bike, derkeve, rawestîne, ji nû ve bide destpêkirin, û vemrîne -cosmic-applet-power-keywords = COSMIC;Sepanok;Bikarhêner;Danaşîn;Kilîtkirin;Derketin;Destpêkirin;Vemirandin;Rawestandin; -cosmic-applet-status-area = Desgeha agahdariyan -cosmic-applet-status-area-comment = Nîşanderên sepanan ên ku dibe ku menuyan bo destgehê derxînin -cosmic-applet-status-area-keywords = COSMIC;Sepanok;Sepan;Nîşander;Agahdarî;Destgeh;Rewş; -cosmic-applet-tiling = Berhevkirin -cosmic-applet-tiling-comment = Berhevkirina xweber a çalak, ya niha û ya her qada xebatê bi rê ve bibe -cosmic-applet-tiling-keywords = COSMIC;Sepanok;Berhevkirin;Nîşander;Navenda xebatê; -cosmic-applet-time = Dîrok, dem & Salname -cosmic-applet-time-comment = Demê niha li ser destgehê bi salnameyeke vebûyî nîşan bide -cosmic-applet-time-keywords = COSMIC;Sepanok;Dîrok;Dem;Salname; -cosmic-applet-workspaces = Qada xebatê jimarkirî -cosmic-applet-workspaces-comment = Di navbera qada xebatê jimarkirî de di destgehê de biguherîne -cosmic-applet-workspaces-keywords = COSMIC;Sepanok;Qada xebatê; -cosmic-panel-app-button = Bişkoka pirtûkxaneya sepanan -cosmic-panel-app-button-comment = Pirtûkxaneya sepanan ji bo vekirina sepanên sazkirî veke -cosmic-panel-app-button-keywords = COSMIC;Sepanok;Sepan;Pirtûkxane;Destgeh; -cosmic-panel-launcher-button = Bişkoka destpêker -cosmic-panel-launcher-button-comment = Destpêkerê ji bo lêgerîna sepanan û xebitandina fermanan veke -cosmic-panel-launcher-button-keywords = COSMIC;Sepanok;Destpêker;Rêveber; -cosmic-panel-workspaces-button = Bişkoka qadên xebatê -cosmic-panel-workspaces-button-comment = Pêşdîtina qadên xebatê veke ji bo bi rê ve bibî û biguhêrînî -cosmic-panel-workspaces-button-keywords = COSMIC;Sepan;Qada xebatê;Pêşdîtin; diff --git a/i18n/ko/desktop_entries.ftl b/i18n/ko/desktop_entries.ftl index 17b758c9..7a9abf42 100644 --- a/i18n/ko/desktop_entries.ftl +++ b/i18n/ko/desktop_entries.ftl @@ -46,6 +46,3 @@ cosmic-panel-launcher-button-keywords = COSMIC;애플릿;런처;실행기; cosmic-panel-workspaces-button = 작업 공간 버튼 cosmic-panel-workspaces-button-comment = 작업 공간 관리 및 전환을 위해 작업 공간 개요 열기 cosmic-panel-workspaces-button-keywords = COSMIC;애플릿;작업 공간;개요; -cosmic-applet-workspaces-comment = 패널에서 번호가 지정된 작업 공간 간 전환 -cosmic-applet-tiling-comment = 활성 창 강조, 현재 및 작업 공간별 자동 타일링 관리 -cosmic-applet-workspaces = 번호가 지정된 작업 공간 diff --git a/i18n/pt/desktop_entries.ftl b/i18n/pt/desktop_entries.ftl index 1fe912c3..de93fad1 100644 --- a/i18n/pt/desktop_entries.ftl +++ b/i18n/pt/desktop_entries.ftl @@ -20,8 +20,3 @@ cosmic-applet-workspaces-comment = Alternar entre áreas de trabalho numeradas n cosmic-applet-workspaces-keywords = COSMIC;Miniaplicação;Applet;Área;Trabalho; cosmic-panel-workspaces-button-comment = Abrir a visão geral das áreas de trabalho para gerir e alternar entre elas cosmic-panel-workspaces-button-keywords = COSMIC;Miniaplicação;Applet;Área;Trabalho;Visão;Geral; -cosmic-applet-a11y-comment = Configurar definições de acessibilidade a partir do painel -cosmic-applet-battery = Energia e Bateria -cosmic-app-list-keywords = COSMIC;Miniaplicação;Applet;Aplicação;Bandeja;Lista;Tarefa;Barra; -cosmic-applet-a11y-keywords = COSMIC;Miniaplicação;Applet;Acessibilidade;A11y;Ecrã;Leitor;Lupa;Ampliador;Contraste;Cor; -cosmic-applet-audio-keywords = COSMIC;Miniaplicação;Applet;Som;Áudio;MPRIS; diff --git a/justfile b/justfile index 99c53104..83a9f819 100644 --- a/justfile +++ b/justfile @@ -59,16 +59,13 @@ _install_status_notifier_watcher: sed "s|@bindir@|{{ prefixdir }}|" cosmic-applet-status-area/data/com.system76.CosmicStatusNotifierWatcher.service.in > cosmic-applet-status-area/data/com.system76.CosmicStatusNotifierWatcher.service install -Dm0644 cosmic-applet-status-area/data/com.system76.CosmicStatusNotifierWatcher.service {{ libdir }}/systemd/user/com.system76.CosmicStatusNotifierWatcher.service -_install_secret_agent_policy: - install -Dm0644 cosmic-applet-network/data/dbus-1/system.d/com.system76.CosmicSettings.Applet.NetworkManager.SecretAgent.conf {{ sharedir }}/dbus-1/system.d/com.system76.CosmicSettings.Applet.NetworkManager.SecretAgent.conf - # Installs files into the system -install: (_install_bin 'cosmic-applets') (_link_applet 'cosmic-panel-button') (_install_applet 'com.system76.CosmicAppList' 'cosmic-app-list') (_install_default_schema 'cosmic-app-list') (_install_applet 'com.system76.CosmicAppletA11y' 'cosmic-applet-a11y') (_install_applet 'com.system76.CosmicAppletAudio' 'cosmic-applet-audio') (_install_applet 'com.system76.CosmicAppletInputSources' 'cosmic-applet-input-sources') (_install_applet 'com.system76.CosmicAppletBattery' 'cosmic-applet-battery') (_install_applet 'com.system76.CosmicAppletBluetooth' 'cosmic-applet-bluetooth') (_install_applet 'com.system76.CosmicAppletMinimize' 'cosmic-applet-minimize') (_install_applet 'com.system76.CosmicAppletNetwork' 'cosmic-applet-network') (_install_applet 'com.system76.CosmicAppletNotifications' 'cosmic-applet-notifications') (_install_applet 'com.system76.CosmicAppletPower' 'cosmic-applet-power') (_install_applet 'com.system76.CosmicAppletStatusArea' 'cosmic-applet-status-area') (_install_applet 'com.system76.CosmicAppletTiling' 'cosmic-applet-tiling') (_install_applet 'com.system76.CosmicAppletTime' 'cosmic-applet-time') (_install_applet 'com.system76.CosmicAppletWorkspaces' 'cosmic-applet-workspaces') (_install_button 'com.system76.CosmicPanelAppButton' 'cosmic-panel-app-button') (_install_button 'com.system76.CosmicPanelLauncherButton' 'cosmic-panel-launcher-button') (_install_button 'com.system76.CosmicPanelWorkspacesButton' 'cosmic-panel-workspaces-button') _install_metainfo _install_status_notifier_watcher _install_secret_agent_policy +install: (_install_bin 'cosmic-applets') (_link_applet 'cosmic-panel-button') (_install_applet 'com.system76.CosmicAppList' 'cosmic-app-list') (_install_default_schema 'cosmic-app-list') (_install_applet 'com.system76.CosmicAppletA11y' 'cosmic-applet-a11y') (_install_applet 'com.system76.CosmicAppletAudio' 'cosmic-applet-audio') (_install_applet 'com.system76.CosmicAppletInputSources' 'cosmic-applet-input-sources') (_install_applet 'com.system76.CosmicAppletBattery' 'cosmic-applet-battery') (_install_applet 'com.system76.CosmicAppletBluetooth' 'cosmic-applet-bluetooth') (_install_applet 'com.system76.CosmicAppletMinimize' 'cosmic-applet-minimize') (_install_applet 'com.system76.CosmicAppletNetwork' 'cosmic-applet-network') (_install_applet 'com.system76.CosmicAppletNotifications' 'cosmic-applet-notifications') (_install_applet 'com.system76.CosmicAppletPower' 'cosmic-applet-power') (_install_applet 'com.system76.CosmicAppletStatusArea' 'cosmic-applet-status-area') (_install_applet 'com.system76.CosmicAppletTiling' 'cosmic-applet-tiling') (_install_applet 'com.system76.CosmicAppletTime' 'cosmic-applet-time') (_install_applet 'com.system76.CosmicAppletWorkspaces' 'cosmic-applet-workspaces') (_install_button 'com.system76.CosmicPanelAppButton' 'cosmic-panel-app-button') (_install_button 'com.system76.CosmicPanelLauncherButton' 'cosmic-panel-launcher-button') (_install_button 'com.system76.CosmicPanelWorkspacesButton' 'cosmic-panel-workspaces-button') _install_metainfo _install_status_notifier_watcher # Vendor Cargo dependencies locally vendor: mkdir -p .cargo - cargo vendor --locked | head -n -1 > .cargo/config + cargo vendor | head -n -1 > .cargo/config echo 'directory = "vendor"' >> .cargo/config tar pcf vendor.tar vendor rm -rf vendor