mirror of
https://github.com/niri-wm/niri.git
synced 2026-06-24 02:01:18 +07:00
Restructure things and add tty backend
This commit is contained in:
Generated
+381
-1
@@ -2,6 +2,21 @@
|
|||||||
# It is not intended for manual editing.
|
# It is not intended for manual editing.
|
||||||
version = 3
|
version = 3
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "addr2line"
|
||||||
|
version = "0.20.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "f4fa78e18c64fce05e902adecd7a5eed15a5e0a3439f7b0e169f0252214865e3"
|
||||||
|
dependencies = [
|
||||||
|
"gimli",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "adler"
|
||||||
|
version = "1.0.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "aho-corasick"
|
name = "aho-corasick"
|
||||||
version = "1.0.2"
|
version = "1.0.2"
|
||||||
@@ -35,6 +50,64 @@ version = "0.2.2"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "fc7eb209b1518d6bb87b283c20095f5228ecda460da70b44f0802523dea6da04"
|
checksum = "fc7eb209b1518d6bb87b283c20095f5228ecda460da70b44f0802523dea6da04"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anstream"
|
||||||
|
version = "0.3.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "0ca84f3628370c59db74ee214b3263d58f9aadd9b4fe7e711fd87dc452b7f163"
|
||||||
|
dependencies = [
|
||||||
|
"anstyle",
|
||||||
|
"anstyle-parse",
|
||||||
|
"anstyle-query",
|
||||||
|
"anstyle-wincon",
|
||||||
|
"colorchoice",
|
||||||
|
"is-terminal",
|
||||||
|
"utf8parse",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anstyle"
|
||||||
|
version = "1.0.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "3a30da5c5f2d5e72842e00bcb57657162cdabef0931f40e2deb9b4140440cecd"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anstyle-parse"
|
||||||
|
version = "0.2.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "938874ff5980b03a87c5524b3ae5b59cf99b1d6bc836848df7bc5ada9643c333"
|
||||||
|
dependencies = [
|
||||||
|
"utf8parse",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anstyle-query"
|
||||||
|
version = "1.0.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b"
|
||||||
|
dependencies = [
|
||||||
|
"windows-sys 0.48.0",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anstyle-wincon"
|
||||||
|
version = "1.0.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "180abfa45703aebe0093f79badacc01b8fd4ea2e35118747e5811127f926e188"
|
||||||
|
dependencies = [
|
||||||
|
"anstyle",
|
||||||
|
"windows-sys 0.48.0",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "anyhow"
|
||||||
|
version = "1.0.72"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "3b13c32d80ecc7ab747b80c3784bce54ee8a7a0cc4fbda9bf4cda2cf6fe90854"
|
||||||
|
dependencies = [
|
||||||
|
"backtrace",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "appendlist"
|
name = "appendlist"
|
||||||
version = "1.4.0"
|
version = "1.4.0"
|
||||||
@@ -56,6 +129,21 @@ version = "1.1.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "backtrace"
|
||||||
|
version = "0.3.68"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "4319208da049c43661739c5fade2ba182f09d1dc2299b32298d3a31692b17e12"
|
||||||
|
dependencies = [
|
||||||
|
"addr2line",
|
||||||
|
"cc",
|
||||||
|
"cfg-if",
|
||||||
|
"libc",
|
||||||
|
"miniz_oxide",
|
||||||
|
"object",
|
||||||
|
"rustc-demangle",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "bitflags"
|
name = "bitflags"
|
||||||
version = "1.3.2"
|
version = "1.3.2"
|
||||||
@@ -93,6 +181,26 @@ version = "3.13.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1"
|
checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "bytemuck"
|
||||||
|
version = "1.13.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "17febce684fd15d89027105661fec94afb475cb995fbc59d2865198446ba2eea"
|
||||||
|
dependencies = [
|
||||||
|
"bytemuck_derive",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "bytemuck_derive"
|
||||||
|
version = "1.4.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "fdde5c9cd29ebd706ce1b35600920a33550e402fc998a2e53ad3b42c3c47a192"
|
||||||
|
dependencies = [
|
||||||
|
"proc-macro2",
|
||||||
|
"quote",
|
||||||
|
"syn 2.0.28",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "calloop"
|
name = "calloop"
|
||||||
version = "0.10.6"
|
version = "0.10.6"
|
||||||
@@ -139,6 +247,53 @@ dependencies = [
|
|||||||
"num-traits",
|
"num-traits",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "clap"
|
||||||
|
version = "4.3.21"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "c27cdf28c0f604ba3f512b0c9a409f8de8513e4816705deb0498b627e7c3a3fd"
|
||||||
|
dependencies = [
|
||||||
|
"clap_builder",
|
||||||
|
"clap_derive",
|
||||||
|
"once_cell",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "clap_builder"
|
||||||
|
version = "4.3.21"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "08a9f1ab5e9f01a9b81f202e8562eb9a10de70abf9eaeac1be465c28b75aa4aa"
|
||||||
|
dependencies = [
|
||||||
|
"anstream",
|
||||||
|
"anstyle",
|
||||||
|
"clap_lex",
|
||||||
|
"strsim",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "clap_derive"
|
||||||
|
version = "4.3.12"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "54a9bb5758fc5dfe728d1019941681eccaf0cf8a4189b692a0ee2f2ecf90a050"
|
||||||
|
dependencies = [
|
||||||
|
"heck",
|
||||||
|
"proc-macro2",
|
||||||
|
"quote",
|
||||||
|
"syn 2.0.28",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "clap_lex"
|
||||||
|
version = "0.5.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "2da6da31387c7e4ef160ffab6d5e7f00c42626fe39aea70a7b0f1773f7dd6c1b"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "colorchoice"
|
||||||
|
version = "1.0.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "core-foundation"
|
name = "core-foundation"
|
||||||
version = "0.9.3"
|
version = "0.9.3"
|
||||||
@@ -200,18 +355,67 @@ version = "1.2.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "9ea835d29036a4087793836fa931b08837ad5e957da9e23886b29586fb9b6650"
|
checksum = "9ea835d29036a4087793836fa931b08837ad5e957da9e23886b29586fb9b6650"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "drm"
|
||||||
|
version = "0.9.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "edf9159ef4bcecd0c5e4cbeb573b8d0037493403d542780dba5d840bbf9df56f"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 1.3.2",
|
||||||
|
"bytemuck",
|
||||||
|
"drm-ffi",
|
||||||
|
"drm-fourcc",
|
||||||
|
"nix 0.26.2",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "drm-ffi"
|
||||||
|
version = "0.5.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "1352481b7b90e27a8a1bf8ef6b33cf18b98dba7c410e75c24bb3eef2f0d8d525"
|
||||||
|
dependencies = [
|
||||||
|
"drm-sys",
|
||||||
|
"nix 0.26.2",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "drm-fourcc"
|
name = "drm-fourcc"
|
||||||
version = "2.2.0"
|
version = "2.2.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "0aafbcdb8afc29c1a7ee5fbe53b5d62f4565b35a042a662ca9fecd0b54dae6f4"
|
checksum = "0aafbcdb8afc29c1a7ee5fbe53b5d62f4565b35a042a662ca9fecd0b54dae6f4"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "drm-sys"
|
||||||
|
version = "0.4.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "1369f1679d6b706d234c4c1e0613c415c2c74b598a09ad28080ba2474b72e42d"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "edid-rs"
|
||||||
|
version = "0.1.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "2ab5fa33485cd85ac354df485819a63360fefa312fe04cffe65e6f175be1522c"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "equivalent"
|
name = "equivalent"
|
||||||
version = "1.0.1"
|
version = "1.0.1"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
|
checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "errno"
|
||||||
|
version = "0.2.8"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "f639046355ee4f37944e44f60642c6f3a7efa3cf6b78c78a0d989a8ce6c396a1"
|
||||||
|
dependencies = [
|
||||||
|
"errno-dragonfly",
|
||||||
|
"libc",
|
||||||
|
"winapi",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "errno"
|
name = "errno"
|
||||||
version = "0.3.2"
|
version = "0.3.2"
|
||||||
@@ -254,6 +458,30 @@ version = "0.1.1"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b"
|
checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "gbm"
|
||||||
|
version = "0.12.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "f2ec389cda876966cf824111bf6e533fb934c711d473498279964a990853b3c6"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 1.3.2",
|
||||||
|
"drm",
|
||||||
|
"drm-fourcc",
|
||||||
|
"gbm-sys",
|
||||||
|
"libc",
|
||||||
|
"wayland-backend",
|
||||||
|
"wayland-server",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "gbm-sys"
|
||||||
|
version = "0.2.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "b63eba9b9b7a231514482deb08759301c9f9f049ac6869403f381834ebfeaf67"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "getrandom"
|
name = "getrandom"
|
||||||
version = "0.2.10"
|
version = "0.2.10"
|
||||||
@@ -265,6 +493,12 @@ dependencies = [
|
|||||||
"wasi",
|
"wasi",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "gimli"
|
||||||
|
version = "0.27.3"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "b6c80984affa11d98d1b88b66ac8853f143217b399d3c74116778ff8fdb4ed2e"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "gl_generator"
|
name = "gl_generator"
|
||||||
version = "0.14.0"
|
version = "0.14.0"
|
||||||
@@ -288,6 +522,12 @@ version = "0.14.0"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "2c6201b9ff9fd90a5a3bac2e56a830d0caa509576f0e503818ee82c181b3437a"
|
checksum = "2c6201b9ff9fd90a5a3bac2e56a830d0caa509576f0e503818ee82c181b3437a"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "heck"
|
||||||
|
version = "0.4.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "hermit-abi"
|
name = "hermit-abi"
|
||||||
version = "0.3.2"
|
version = "0.3.2"
|
||||||
@@ -314,6 +554,28 @@ dependencies = [
|
|||||||
"hashbrown 0.14.0",
|
"hashbrown 0.14.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "input"
|
||||||
|
version = "0.8.3"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "e6e74cd82cedcd66db78742a8337bdc48f188c4d2c12742cbc5cd85113f0b059"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 1.3.2",
|
||||||
|
"input-sys",
|
||||||
|
"io-lifetimes",
|
||||||
|
"libc",
|
||||||
|
"udev",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "input-sys"
|
||||||
|
version = "1.17.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "05f6c2a17e8aba7217660e32863af87b0febad811d4b8620ef76b386603fddc2"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "instant"
|
name = "instant"
|
||||||
version = "0.1.12"
|
version = "0.1.12"
|
||||||
@@ -337,6 +599,17 @@ dependencies = [
|
|||||||
"windows-sys 0.48.0",
|
"windows-sys 0.48.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "is-terminal"
|
||||||
|
version = "0.4.9"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b"
|
||||||
|
dependencies = [
|
||||||
|
"hermit-abi",
|
||||||
|
"rustix",
|
||||||
|
"windows-sys 0.48.0",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "jni-sys"
|
name = "jni-sys"
|
||||||
version = "0.3.0"
|
version = "0.3.0"
|
||||||
@@ -389,6 +662,36 @@ dependencies = [
|
|||||||
"windows-sys 0.48.0",
|
"windows-sys 0.48.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "libseat"
|
||||||
|
version = "0.1.7"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "845e5c255462c9bc7c71c17b996766b76e3c66f2ddd5846bfbc83f18382aa648"
|
||||||
|
dependencies = [
|
||||||
|
"errno 0.2.8",
|
||||||
|
"libseat-sys",
|
||||||
|
"slog",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "libseat-sys"
|
||||||
|
version = "0.1.7"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "3671cb5e03871f1d6bf0b3b5daa9275549e348fa6359e0f9adb910ca163d4c34"
|
||||||
|
dependencies = [
|
||||||
|
"pkg-config",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "libudev-sys"
|
||||||
|
version = "0.1.4"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "3c8469b4a23b962c1396b9b451dda50ef5b283e8dd309d69033475fa9b334324"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
"pkg-config",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "linux-raw-sys"
|
name = "linux-raw-sys"
|
||||||
version = "0.4.5"
|
version = "0.4.5"
|
||||||
@@ -458,6 +761,15 @@ version = "0.2.1"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a"
|
checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "miniz_oxide"
|
||||||
|
version = "0.7.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7"
|
||||||
|
dependencies = [
|
||||||
|
"adler",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "mio"
|
name = "mio"
|
||||||
version = "0.8.8"
|
version = "0.8.8"
|
||||||
@@ -503,8 +815,12 @@ dependencies = [
|
|||||||
name = "niri"
|
name = "niri"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
|
"anyhow",
|
||||||
"bitflags 2.3.3",
|
"bitflags 2.3.3",
|
||||||
|
"clap",
|
||||||
"smithay",
|
"smithay",
|
||||||
|
"smithay-drm-extras",
|
||||||
|
"tracing",
|
||||||
"tracing-subscriber",
|
"tracing-subscriber",
|
||||||
]
|
]
|
||||||
|
|
||||||
@@ -644,6 +960,15 @@ dependencies = [
|
|||||||
"objc-sys",
|
"objc-sys",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "object"
|
||||||
|
version = "0.31.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "8bda667d9f2b5051b8833f59f3bf748b28ef54f850f4fcb389a252aa383866d1"
|
||||||
|
dependencies = [
|
||||||
|
"memchr",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "once_cell"
|
name = "once_cell"
|
||||||
version = "1.18.0"
|
version = "1.18.0"
|
||||||
@@ -840,6 +1165,12 @@ version = "0.7.4"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "e5ea92a5b6195c6ef2a0295ea818b312502c6fc94dde986c5553242e18fd4ce2"
|
checksum = "e5ea92a5b6195c6ef2a0295ea818b312502c6fc94dde986c5553242e18fd4ce2"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "rustc-demangle"
|
||||||
|
version = "0.1.23"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "rustix"
|
name = "rustix"
|
||||||
version = "0.38.7"
|
version = "0.38.7"
|
||||||
@@ -847,7 +1178,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||||||
checksum = "172891ebdceb05aa0005f533a6cbfca599ddd7d966f6f5d4d9b2e70478e70399"
|
checksum = "172891ebdceb05aa0005f533a6cbfca599ddd7d966f6f5d4d9b2e70478e70399"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bitflags 2.3.3",
|
"bitflags 2.3.3",
|
||||||
"errno",
|
"errno 0.3.2",
|
||||||
"libc",
|
"libc",
|
||||||
"linux-raw-sys",
|
"linux-raw-sys",
|
||||||
"windows-sys 0.48.0",
|
"windows-sys 0.48.0",
|
||||||
@@ -874,6 +1205,12 @@ dependencies = [
|
|||||||
"lazy_static",
|
"lazy_static",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "slog"
|
||||||
|
version = "2.7.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "8347046d4ebd943127157b94d63abb990fcf729dc4e9978927fdf4ac3c998d06"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "slotmap"
|
name = "slotmap"
|
||||||
version = "1.0.6"
|
version = "1.0.6"
|
||||||
@@ -897,27 +1234,37 @@ dependencies = [
|
|||||||
"appendlist",
|
"appendlist",
|
||||||
"bitflags 2.3.3",
|
"bitflags 2.3.3",
|
||||||
"calloop",
|
"calloop",
|
||||||
|
"cc",
|
||||||
"cgmath",
|
"cgmath",
|
||||||
"downcast-rs",
|
"downcast-rs",
|
||||||
|
"drm",
|
||||||
|
"drm-ffi",
|
||||||
"drm-fourcc",
|
"drm-fourcc",
|
||||||
|
"gbm",
|
||||||
"gl_generator",
|
"gl_generator",
|
||||||
"indexmap 1.9.3",
|
"indexmap 1.9.3",
|
||||||
|
"input",
|
||||||
"lazy_static",
|
"lazy_static",
|
||||||
"libc",
|
"libc",
|
||||||
"libloading",
|
"libloading",
|
||||||
|
"libseat",
|
||||||
"nix 0.26.2",
|
"nix 0.26.2",
|
||||||
"once_cell",
|
"once_cell",
|
||||||
|
"pkg-config",
|
||||||
"profiling",
|
"profiling",
|
||||||
"rand",
|
"rand",
|
||||||
"scan_fmt",
|
"scan_fmt",
|
||||||
"tempfile",
|
"tempfile",
|
||||||
"thiserror",
|
"thiserror",
|
||||||
"tracing",
|
"tracing",
|
||||||
|
"udev",
|
||||||
|
"wayland-backend",
|
||||||
"wayland-egl",
|
"wayland-egl",
|
||||||
"wayland-protocols 0.30.1",
|
"wayland-protocols 0.30.1",
|
||||||
"wayland-protocols-misc",
|
"wayland-protocols-misc",
|
||||||
"wayland-protocols-wlr",
|
"wayland-protocols-wlr",
|
||||||
"wayland-server",
|
"wayland-server",
|
||||||
|
"wayland-sys 0.30.1",
|
||||||
"winit",
|
"winit",
|
||||||
"xkbcommon",
|
"xkbcommon",
|
||||||
]
|
]
|
||||||
@@ -941,12 +1288,26 @@ dependencies = [
|
|||||||
"wayland-protocols 0.29.5",
|
"wayland-protocols 0.29.5",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "smithay-drm-extras"
|
||||||
|
version = "0.1.0"
|
||||||
|
dependencies = [
|
||||||
|
"drm",
|
||||||
|
"edid-rs",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "static_assertions"
|
name = "static_assertions"
|
||||||
version = "1.1.0"
|
version = "1.1.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f"
|
checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "strsim"
|
||||||
|
version = "0.10.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "syn"
|
name = "syn"
|
||||||
version = "1.0.109"
|
version = "1.0.109"
|
||||||
@@ -1091,12 +1452,29 @@ dependencies = [
|
|||||||
"tracing-log",
|
"tracing-log",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "udev"
|
||||||
|
version = "0.7.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "4ebdbbd670373442a12fe9ef7aeb53aec4147a5a27a00bbc3ab639f08f48191a"
|
||||||
|
dependencies = [
|
||||||
|
"libc",
|
||||||
|
"libudev-sys",
|
||||||
|
"pkg-config",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "unicode-ident"
|
name = "unicode-ident"
|
||||||
version = "1.0.11"
|
version = "1.0.11"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "301abaae475aa91687eb82514b328ab47a211a533026cb25fc3e519b86adfc3c"
|
checksum = "301abaae475aa91687eb82514b328ab47a211a533026cb25fc3e519b86adfc3c"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "utf8parse"
|
||||||
|
version = "0.2.1"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "valuable"
|
name = "valuable"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
@@ -1343,7 +1721,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||||||
checksum = "96b2a02ac608e07132978689a6f9bf4214949c85998c247abadd4f4129b1aa06"
|
checksum = "96b2a02ac608e07132978689a6f9bf4214949c85998c247abadd4f4129b1aa06"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"dlib",
|
"dlib",
|
||||||
|
"libc",
|
||||||
"log",
|
"log",
|
||||||
|
"memoffset 0.7.1",
|
||||||
"pkg-config",
|
"pkg-config",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|||||||
+19
-4
@@ -1,18 +1,33 @@
|
|||||||
[package]
|
[package]
|
||||||
name = "niri"
|
name = "niri"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
edition = "2021"
|
description = "A Wayland compositor"
|
||||||
|
authors = ["Ivan Molodetskikh <yalterz@gmail.com>"]
|
||||||
license = "GPL-3.0-or-later"
|
license = "GPL-3.0-or-later"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
tracing-subscriber = { version = "0.3.16", features = ["env-filter"] }
|
anyhow = { version = "1.0.72", features = ["backtrace"] }
|
||||||
bitflags = "2.2.1"
|
bitflags = "2.3.3"
|
||||||
|
clap = { version = "4.3.21", features = ["derive"] }
|
||||||
|
smithay-drm-extras = { version = "0.1.0", path = "../smithay/smithay-drm-extras" }
|
||||||
|
tracing = "0.1.37"
|
||||||
|
tracing-subscriber = { version = "0.3.17", features = ["env-filter"] }
|
||||||
|
|
||||||
[dependencies.smithay]
|
[dependencies.smithay]
|
||||||
git = "https://github.com/Smithay/smithay"
|
git = "https://github.com/Smithay/smithay"
|
||||||
default-features = false
|
default-features = false
|
||||||
features = [
|
features = [
|
||||||
|
"backend_drm",
|
||||||
|
"backend_egl",
|
||||||
|
"backend_gbm",
|
||||||
|
"backend_libinput",
|
||||||
|
"backend_session_libseat",
|
||||||
|
"backend_udev",
|
||||||
"backend_winit",
|
"backend_winit",
|
||||||
"wayland_frontend",
|
|
||||||
"desktop",
|
"desktop",
|
||||||
|
"renderer_gl",
|
||||||
|
"renderer_multi",
|
||||||
|
"use_system_lib",
|
||||||
|
"wayland_frontend",
|
||||||
]
|
]
|
||||||
|
|||||||
@@ -0,0 +1,15 @@
|
|||||||
|
use smithay::backend::renderer::element::surface::WaylandSurfaceRenderElement;
|
||||||
|
use smithay::backend::renderer::gles::GlesRenderer;
|
||||||
|
use smithay::desktop::space::SpaceRenderElements;
|
||||||
|
|
||||||
|
use crate::Niri;
|
||||||
|
|
||||||
|
pub trait Backend {
|
||||||
|
fn seat_name(&self) -> String;
|
||||||
|
fn renderer(&mut self) -> &mut GlesRenderer;
|
||||||
|
fn render(
|
||||||
|
&mut self,
|
||||||
|
niri: &mut Niri,
|
||||||
|
elements: &[SpaceRenderElements<GlesRenderer, WaylandSurfaceRenderElement<GlesRenderer>>],
|
||||||
|
);
|
||||||
|
}
|
||||||
+12
-12
@@ -6,19 +6,19 @@ use smithay::input::pointer::{
|
|||||||
use smithay::reexports::wayland_server::protocol::wl_surface::WlSurface;
|
use smithay::reexports::wayland_server::protocol::wl_surface::WlSurface;
|
||||||
use smithay::utils::{Logical, Point};
|
use smithay::utils::{Logical, Point};
|
||||||
|
|
||||||
use crate::Smallvil;
|
use crate::Niri;
|
||||||
|
|
||||||
pub struct MoveSurfaceGrab {
|
pub struct MoveSurfaceGrab {
|
||||||
pub start_data: PointerGrabStartData<Smallvil>,
|
pub start_data: PointerGrabStartData<Niri>,
|
||||||
pub window: Window,
|
pub window: Window,
|
||||||
pub initial_window_location: Point<i32, Logical>,
|
pub initial_window_location: Point<i32, Logical>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl PointerGrab<Smallvil> for MoveSurfaceGrab {
|
impl PointerGrab<Niri> for MoveSurfaceGrab {
|
||||||
fn motion(
|
fn motion(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
_focus: Option<(WlSurface, Point<i32, Logical>)>,
|
_focus: Option<(WlSurface, Point<i32, Logical>)>,
|
||||||
event: &MotionEvent,
|
event: &MotionEvent,
|
||||||
) {
|
) {
|
||||||
@@ -33,8 +33,8 @@ impl PointerGrab<Smallvil> for MoveSurfaceGrab {
|
|||||||
|
|
||||||
fn relative_motion(
|
fn relative_motion(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
focus: Option<(WlSurface, Point<i32, Logical>)>,
|
focus: Option<(WlSurface, Point<i32, Logical>)>,
|
||||||
event: &RelativeMotionEvent,
|
event: &RelativeMotionEvent,
|
||||||
) {
|
) {
|
||||||
@@ -43,8 +43,8 @@ impl PointerGrab<Smallvil> for MoveSurfaceGrab {
|
|||||||
|
|
||||||
fn button(
|
fn button(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
event: &ButtonEvent,
|
event: &ButtonEvent,
|
||||||
) {
|
) {
|
||||||
handle.button(data, event);
|
handle.button(data, event);
|
||||||
@@ -61,14 +61,14 @@ impl PointerGrab<Smallvil> for MoveSurfaceGrab {
|
|||||||
|
|
||||||
fn axis(
|
fn axis(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
details: AxisFrame,
|
details: AxisFrame,
|
||||||
) {
|
) {
|
||||||
handle.axis(data, details)
|
handle.axis(data, details)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn start_data(&self) -> &PointerGrabStartData<Smallvil> {
|
fn start_data(&self) -> &PointerGrabStartData<Niri> {
|
||||||
&self.start_data
|
&self.start_data
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+13
-13
@@ -11,7 +11,7 @@ use smithay::utils::{Logical, Point, Rectangle, Size};
|
|||||||
use smithay::wayland::compositor;
|
use smithay::wayland::compositor;
|
||||||
use smithay::wayland::shell::xdg::SurfaceCachedState;
|
use smithay::wayland::shell::xdg::SurfaceCachedState;
|
||||||
|
|
||||||
use crate::Smallvil;
|
use crate::Niri;
|
||||||
|
|
||||||
bitflags::bitflags! {
|
bitflags::bitflags! {
|
||||||
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
|
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
|
||||||
@@ -37,7 +37,7 @@ impl From<xdg_toplevel::ResizeEdge> for ResizeEdge {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub struct ResizeSurfaceGrab {
|
pub struct ResizeSurfaceGrab {
|
||||||
start_data: PointerGrabStartData<Smallvil>,
|
start_data: PointerGrabStartData<Niri>,
|
||||||
window: Window,
|
window: Window,
|
||||||
|
|
||||||
edges: ResizeEdge,
|
edges: ResizeEdge,
|
||||||
@@ -48,7 +48,7 @@ pub struct ResizeSurfaceGrab {
|
|||||||
|
|
||||||
impl ResizeSurfaceGrab {
|
impl ResizeSurfaceGrab {
|
||||||
pub fn start(
|
pub fn start(
|
||||||
start_data: PointerGrabStartData<Smallvil>,
|
start_data: PointerGrabStartData<Niri>,
|
||||||
window: Window,
|
window: Window,
|
||||||
edges: ResizeEdge,
|
edges: ResizeEdge,
|
||||||
initial_window_rect: Rectangle<i32, Logical>,
|
initial_window_rect: Rectangle<i32, Logical>,
|
||||||
@@ -72,11 +72,11 @@ impl ResizeSurfaceGrab {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl PointerGrab<Smallvil> for ResizeSurfaceGrab {
|
impl PointerGrab<Niri> for ResizeSurfaceGrab {
|
||||||
fn motion(
|
fn motion(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
_focus: Option<(WlSurface, Point<i32, Logical>)>,
|
_focus: Option<(WlSurface, Point<i32, Logical>)>,
|
||||||
event: &MotionEvent,
|
event: &MotionEvent,
|
||||||
) {
|
) {
|
||||||
@@ -132,8 +132,8 @@ impl PointerGrab<Smallvil> for ResizeSurfaceGrab {
|
|||||||
|
|
||||||
fn relative_motion(
|
fn relative_motion(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
focus: Option<(WlSurface, Point<i32, Logical>)>,
|
focus: Option<(WlSurface, Point<i32, Logical>)>,
|
||||||
event: &RelativeMotionEvent,
|
event: &RelativeMotionEvent,
|
||||||
) {
|
) {
|
||||||
@@ -142,8 +142,8 @@ impl PointerGrab<Smallvil> for ResizeSurfaceGrab {
|
|||||||
|
|
||||||
fn button(
|
fn button(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
event: &ButtonEvent,
|
event: &ButtonEvent,
|
||||||
) {
|
) {
|
||||||
handle.button(data, event);
|
handle.button(data, event);
|
||||||
@@ -175,14 +175,14 @@ impl PointerGrab<Smallvil> for ResizeSurfaceGrab {
|
|||||||
|
|
||||||
fn axis(
|
fn axis(
|
||||||
&mut self,
|
&mut self,
|
||||||
data: &mut Smallvil,
|
data: &mut Niri,
|
||||||
handle: &mut PointerInnerHandle<'_, Smallvil>,
|
handle: &mut PointerInnerHandle<'_, Niri>,
|
||||||
details: AxisFrame,
|
details: AxisFrame,
|
||||||
) {
|
) {
|
||||||
handle.axis(data, details)
|
handle.axis(data, details)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn start_data(&self) -> &PointerGrabStartData<Smallvil> {
|
fn start_data(&self) -> &PointerGrabStartData<Niri> {
|
||||||
&self.start_data
|
&self.start_data
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,10 +11,10 @@ use smithay::{delegate_compositor, delegate_shm};
|
|||||||
|
|
||||||
use super::xdg_shell;
|
use super::xdg_shell;
|
||||||
use crate::grabs::resize_grab;
|
use crate::grabs::resize_grab;
|
||||||
use crate::state::ClientState;
|
use crate::niri::ClientState;
|
||||||
use crate::Smallvil;
|
use crate::Niri;
|
||||||
|
|
||||||
impl CompositorHandler for Smallvil {
|
impl CompositorHandler for Niri {
|
||||||
fn compositor_state(&mut self) -> &mut CompositorState {
|
fn compositor_state(&mut self) -> &mut CompositorState {
|
||||||
&mut self.compositor_state
|
&mut self.compositor_state
|
||||||
}
|
}
|
||||||
@@ -44,15 +44,15 @@ impl CompositorHandler for Smallvil {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl BufferHandler for Smallvil {
|
impl BufferHandler for Niri {
|
||||||
fn buffer_destroyed(&mut self, _buffer: &wl_buffer::WlBuffer) {}
|
fn buffer_destroyed(&mut self, _buffer: &wl_buffer::WlBuffer) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ShmHandler for Smallvil {
|
impl ShmHandler for Niri {
|
||||||
fn shm_state(&self) -> &ShmState {
|
fn shm_state(&self) -> &ShmState {
|
||||||
&self.shm_state
|
&self.shm_state
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
delegate_compositor!(Smallvil);
|
delegate_compositor!(Niri);
|
||||||
delegate_shm!(Smallvil);
|
delegate_shm!(Niri);
|
||||||
|
|||||||
+9
-9
@@ -10,13 +10,13 @@ use smithay::wayland::data_device::{
|
|||||||
};
|
};
|
||||||
use smithay::{delegate_data_device, delegate_output, delegate_seat};
|
use smithay::{delegate_data_device, delegate_output, delegate_seat};
|
||||||
|
|
||||||
use crate::Smallvil;
|
use crate::Niri;
|
||||||
|
|
||||||
impl SeatHandler for Smallvil {
|
impl SeatHandler for Niri {
|
||||||
type KeyboardFocus = WlSurface;
|
type KeyboardFocus = WlSurface;
|
||||||
type PointerFocus = WlSurface;
|
type PointerFocus = WlSurface;
|
||||||
|
|
||||||
fn seat_state(&mut self) -> &mut SeatState<Smallvil> {
|
fn seat_state(&mut self) -> &mut SeatState<Niri> {
|
||||||
&mut self.seat_state
|
&mut self.seat_state
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -29,26 +29,26 @@ impl SeatHandler for Smallvil {
|
|||||||
fn focus_changed(&mut self, _seat: &smithay::input::Seat<Self>, _focused: Option<&WlSurface>) {}
|
fn focus_changed(&mut self, _seat: &smithay::input::Seat<Self>, _focused: Option<&WlSurface>) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
delegate_seat!(Smallvil);
|
delegate_seat!(Niri);
|
||||||
|
|
||||||
//
|
//
|
||||||
// Wl Data Device
|
// Wl Data Device
|
||||||
//
|
//
|
||||||
|
|
||||||
impl DataDeviceHandler for Smallvil {
|
impl DataDeviceHandler for Niri {
|
||||||
type SelectionUserData = ();
|
type SelectionUserData = ();
|
||||||
fn data_device_state(&self) -> &smithay::wayland::data_device::DataDeviceState {
|
fn data_device_state(&self) -> &smithay::wayland::data_device::DataDeviceState {
|
||||||
&self.data_device_state
|
&self.data_device_state
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ClientDndGrabHandler for Smallvil {}
|
impl ClientDndGrabHandler for Niri {}
|
||||||
impl ServerDndGrabHandler for Smallvil {}
|
impl ServerDndGrabHandler for Niri {}
|
||||||
|
|
||||||
delegate_data_device!(Smallvil);
|
delegate_data_device!(Niri);
|
||||||
|
|
||||||
//
|
//
|
||||||
// Wl Output & Xdg Output
|
// Wl Output & Xdg Output
|
||||||
//
|
//
|
||||||
|
|
||||||
delegate_output!(Smallvil);
|
delegate_output!(Niri);
|
||||||
|
|||||||
@@ -14,9 +14,9 @@ use smithay::wayland::shell::xdg::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
use crate::grabs::{MoveSurfaceGrab, ResizeSurfaceGrab};
|
use crate::grabs::{MoveSurfaceGrab, ResizeSurfaceGrab};
|
||||||
use crate::Smallvil;
|
use crate::Niri;
|
||||||
|
|
||||||
impl XdgShellHandler for Smallvil {
|
impl XdgShellHandler for Niri {
|
||||||
fn xdg_shell_state(&mut self) -> &mut XdgShellState {
|
fn xdg_shell_state(&mut self) -> &mut XdgShellState {
|
||||||
&mut self.xdg_shell_state
|
&mut self.xdg_shell_state
|
||||||
}
|
}
|
||||||
@@ -102,13 +102,13 @@ impl XdgShellHandler for Smallvil {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Xdg Shell
|
// Xdg Shell
|
||||||
delegate_xdg_shell!(Smallvil);
|
delegate_xdg_shell!(Niri);
|
||||||
|
|
||||||
fn check_grab(
|
fn check_grab(
|
||||||
seat: &Seat<Smallvil>,
|
seat: &Seat<Niri>,
|
||||||
surface: &WlSurface,
|
surface: &WlSurface,
|
||||||
serial: Serial,
|
serial: Serial,
|
||||||
) -> Option<PointerGrabStartData<Smallvil>> {
|
) -> Option<PointerGrabStartData<Niri>> {
|
||||||
let pointer = seat.get_pointer()?;
|
let pointer = seat.get_pointer()?;
|
||||||
|
|
||||||
// Check that this surface has a click grab.
|
// Check that this surface has a click grab.
|
||||||
|
|||||||
+29
-5
@@ -2,28 +2,52 @@ use smithay::backend::input::{
|
|||||||
AbsolutePositionEvent, Axis, AxisSource, ButtonState, Event, InputBackend, InputEvent,
|
AbsolutePositionEvent, Axis, AxisSource, ButtonState, Event, InputBackend, InputEvent,
|
||||||
KeyboardKeyEvent, PointerAxisEvent, PointerButtonEvent,
|
KeyboardKeyEvent, PointerAxisEvent, PointerButtonEvent,
|
||||||
};
|
};
|
||||||
use smithay::input::keyboard::FilterResult;
|
use smithay::input::keyboard::{keysyms, FilterResult};
|
||||||
use smithay::input::pointer::{AxisFrame, ButtonEvent, MotionEvent};
|
use smithay::input::pointer::{AxisFrame, ButtonEvent, MotionEvent};
|
||||||
use smithay::reexports::wayland_server::protocol::wl_surface::WlSurface;
|
use smithay::reexports::wayland_server::protocol::wl_surface::WlSurface;
|
||||||
use smithay::utils::SERIAL_COUNTER;
|
use smithay::utils::SERIAL_COUNTER;
|
||||||
|
|
||||||
use crate::state::Smallvil;
|
use crate::niri::Niri;
|
||||||
|
|
||||||
impl Smallvil {
|
enum InputAction {
|
||||||
|
Quit,
|
||||||
|
ChangeVt(i32),
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Niri {
|
||||||
pub fn process_input_event<I: InputBackend>(&mut self, event: InputEvent<I>) {
|
pub fn process_input_event<I: InputBackend>(&mut self, event: InputEvent<I>) {
|
||||||
|
trace!("process_input_event");
|
||||||
|
|
||||||
match event {
|
match event {
|
||||||
InputEvent::Keyboard { event, .. } => {
|
InputEvent::Keyboard { event, .. } => {
|
||||||
let serial = SERIAL_COUNTER.next_serial();
|
let serial = SERIAL_COUNTER.next_serial();
|
||||||
let time = Event::time_msec(&event);
|
let time = Event::time_msec(&event);
|
||||||
|
|
||||||
self.seat.get_keyboard().unwrap().input::<(), _>(
|
let action = self.seat.get_keyboard().unwrap().input(
|
||||||
self,
|
self,
|
||||||
event.key_code(),
|
event.key_code(),
|
||||||
event.state(),
|
event.state(),
|
||||||
serial,
|
serial,
|
||||||
time,
|
time,
|
||||||
|_, _, _| FilterResult::Forward,
|
|_, _, keysym| match keysym.modified_sym() {
|
||||||
|
keysyms::KEY_Escape => FilterResult::Intercept(InputAction::Quit),
|
||||||
|
keysym @ keysyms::KEY_XF86Switch_VT_1..=keysyms::KEY_XF86Switch_VT_12 => {
|
||||||
|
let vt = (keysym - keysyms::KEY_XF86Switch_VT_1 + 1) as i32;
|
||||||
|
FilterResult::Intercept(InputAction::ChangeVt(vt))
|
||||||
|
}
|
||||||
|
_ => FilterResult::Forward,
|
||||||
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
|
if let Some(action) = action {
|
||||||
|
match action {
|
||||||
|
InputAction::Quit => {
|
||||||
|
info!("quitting because Esc was pressed");
|
||||||
|
self.stop_signal.stop()
|
||||||
|
}
|
||||||
|
InputAction::ChangeVt(vt) => todo!(),
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
InputEvent::PointerMotion { .. } => {}
|
InputEvent::PointerMotion { .. } => {}
|
||||||
InputEvent::PointerMotionAbsolute { event, .. } => {
|
InputEvent::PointerMotionAbsolute { event, .. } => {
|
||||||
|
|||||||
+90
-35
@@ -1,54 +1,109 @@
|
|||||||
|
#[macro_use]
|
||||||
|
extern crate tracing;
|
||||||
|
|
||||||
mod handlers;
|
mod handlers;
|
||||||
|
|
||||||
|
mod backend;
|
||||||
mod grabs;
|
mod grabs;
|
||||||
mod input;
|
mod input;
|
||||||
mod state;
|
mod niri;
|
||||||
|
mod tty;
|
||||||
mod winit;
|
mod winit;
|
||||||
|
|
||||||
use smithay::reexports::calloop::EventLoop;
|
use std::env;
|
||||||
use smithay::reexports::wayland_server::Display;
|
use std::ffi::OsString;
|
||||||
pub use state::Smallvil;
|
|
||||||
|
|
||||||
pub struct CalloopData {
|
use backend::Backend;
|
||||||
state: Smallvil,
|
use clap::Parser;
|
||||||
display: Display<Smallvil>,
|
use niri::Niri;
|
||||||
|
use smithay::reexports::calloop::EventLoop;
|
||||||
|
use smithay::reexports::wayland_server::{Display, DisplayHandle};
|
||||||
|
use tracing_subscriber::EnvFilter;
|
||||||
|
use tty::Tty;
|
||||||
|
use winit::Winit;
|
||||||
|
|
||||||
|
#[derive(Parser)]
|
||||||
|
#[command(author, version, about, long_about = None)]
|
||||||
|
struct Cli {
|
||||||
|
#[arg(last = true)]
|
||||||
|
command: Option<OsString>,
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
pub struct LoopData {
|
||||||
if let Ok(env_filter) = tracing_subscriber::EnvFilter::try_from_default_env() {
|
niri: Niri,
|
||||||
|
display_handle: DisplayHandle,
|
||||||
|
|
||||||
|
// Last so that it's dropped after the Smithay state in Niri.
|
||||||
|
display: Display<Niri>,
|
||||||
|
|
||||||
|
tty: Option<Tty>,
|
||||||
|
winit: Option<Winit>,
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
env::set_var("RUST_BACKTRACE", "1");
|
||||||
|
|
||||||
|
let directives = env::var("RUST_LOG").unwrap_or_else(|_| "niri=debug,info".to_owned());
|
||||||
|
let env_filter = EnvFilter::builder().parse_lossy(directives);
|
||||||
tracing_subscriber::fmt()
|
tracing_subscriber::fmt()
|
||||||
.compact()
|
.compact()
|
||||||
.with_env_filter(env_filter)
|
.with_env_filter(env_filter)
|
||||||
.init();
|
.init();
|
||||||
|
|
||||||
|
let cli = Cli::parse();
|
||||||
|
|
||||||
|
let mut event_loop = EventLoop::try_new().unwrap();
|
||||||
|
|
||||||
|
let has_display = env::var_os("WAYLAND_DISPLAY").is_some() || env::var_os("DISPLAY").is_some();
|
||||||
|
|
||||||
|
let mut winit = None;
|
||||||
|
let mut tty = None;
|
||||||
|
let backend: &mut dyn Backend = if has_display {
|
||||||
|
winit = Some(Winit::new(event_loop.handle()));
|
||||||
|
winit.as_mut().unwrap()
|
||||||
} else {
|
} else {
|
||||||
tracing_subscriber::fmt().compact().init();
|
tty = Some(Tty::new(event_loop.handle()));
|
||||||
|
tty.as_mut().unwrap()
|
||||||
|
};
|
||||||
|
|
||||||
|
let mut display = Display::new().unwrap();
|
||||||
|
let display_handle = display.handle();
|
||||||
|
let niri = Niri::new(
|
||||||
|
event_loop.handle(),
|
||||||
|
event_loop.get_signal(),
|
||||||
|
&mut display,
|
||||||
|
backend.seat_name(),
|
||||||
|
);
|
||||||
|
|
||||||
|
let mut data = LoopData {
|
||||||
|
niri,
|
||||||
|
display_handle,
|
||||||
|
display,
|
||||||
|
|
||||||
|
tty,
|
||||||
|
winit,
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Some(tty) = data.tty.as_mut() {
|
||||||
|
tty.init(&mut data.niri);
|
||||||
|
}
|
||||||
|
if let Some(winit) = data.winit.as_mut() {
|
||||||
|
winit.init(&mut data.niri);
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut event_loop: EventLoop<CalloopData> = EventLoop::try_new()?;
|
let res = if let Some(command) = &cli.command {
|
||||||
|
std::process::Command::new(command).spawn()
|
||||||
let mut display: Display<Smallvil> = Display::new()?;
|
} else {
|
||||||
let state = Smallvil::new(&event_loop, &mut display);
|
std::process::Command::new("weston-terminal").spawn()
|
||||||
|
};
|
||||||
let mut data = CalloopData { state, display };
|
if let Err(err) = res {
|
||||||
|
warn!("error spawning command: {err}");
|
||||||
crate::winit::init_winit(&event_loop, &mut data)?;
|
|
||||||
|
|
||||||
let mut args = std::env::args().skip(1);
|
|
||||||
let flag = args.next();
|
|
||||||
let arg = args.next();
|
|
||||||
|
|
||||||
match (flag.as_deref(), arg) {
|
|
||||||
(Some("-c") | Some("--command"), Some(command)) => {
|
|
||||||
std::process::Command::new(command).spawn().ok();
|
|
||||||
}
|
|
||||||
_ => {
|
|
||||||
std::process::Command::new("weston-terminal").spawn().ok();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
event_loop.run(None, &mut data, move |_| {
|
event_loop
|
||||||
// Smallvil is running
|
.run(None, &mut data, move |data| {
|
||||||
})?;
|
// niri is running.
|
||||||
|
data.display.flush_clients().unwrap();
|
||||||
Ok(())
|
})
|
||||||
|
.unwrap();
|
||||||
}
|
}
|
||||||
|
|||||||
+168
@@ -0,0 +1,168 @@
|
|||||||
|
use std::os::unix::io::AsRawFd;
|
||||||
|
use std::sync::Arc;
|
||||||
|
use std::time::Duration;
|
||||||
|
|
||||||
|
use smithay::desktop::space::space_render_elements;
|
||||||
|
use smithay::desktop::{Space, Window, WindowSurfaceType};
|
||||||
|
use smithay::input::keyboard::XkbConfig;
|
||||||
|
use smithay::input::pointer::PointerHandle;
|
||||||
|
use smithay::input::{Seat, SeatState};
|
||||||
|
use smithay::output::Output;
|
||||||
|
use smithay::reexports::calloop::generic::Generic;
|
||||||
|
use smithay::reexports::calloop::{Interest, LoopHandle, LoopSignal, Mode, PostAction};
|
||||||
|
use smithay::reexports::wayland_server::backend::{ClientData, ClientId, DisconnectReason};
|
||||||
|
use smithay::reexports::wayland_server::protocol::wl_surface::WlSurface;
|
||||||
|
use smithay::reexports::wayland_server::{Display, DisplayHandle};
|
||||||
|
use smithay::utils::{Logical, Point};
|
||||||
|
use smithay::wayland::compositor::{CompositorClientState, CompositorState};
|
||||||
|
use smithay::wayland::data_device::DataDeviceState;
|
||||||
|
use smithay::wayland::output::OutputManagerState;
|
||||||
|
use smithay::wayland::shell::xdg::XdgShellState;
|
||||||
|
use smithay::wayland::shm::ShmState;
|
||||||
|
use smithay::wayland::socket::ListeningSocketSource;
|
||||||
|
|
||||||
|
use crate::backend::Backend;
|
||||||
|
use crate::LoopData;
|
||||||
|
|
||||||
|
pub struct Niri {
|
||||||
|
pub start_time: std::time::Instant,
|
||||||
|
pub event_loop: LoopHandle<'static, LoopData>,
|
||||||
|
pub stop_signal: LoopSignal,
|
||||||
|
pub display_handle: DisplayHandle,
|
||||||
|
|
||||||
|
pub space: Space<Window>,
|
||||||
|
|
||||||
|
// Smithay state.
|
||||||
|
pub compositor_state: CompositorState,
|
||||||
|
pub xdg_shell_state: XdgShellState,
|
||||||
|
pub shm_state: ShmState,
|
||||||
|
pub output_manager_state: OutputManagerState,
|
||||||
|
pub seat_state: SeatState<Self>,
|
||||||
|
pub data_device_state: DataDeviceState,
|
||||||
|
|
||||||
|
pub seat: Seat<Self>,
|
||||||
|
pub output: Option<Output>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Niri {
|
||||||
|
pub fn new(
|
||||||
|
event_loop: LoopHandle<'static, LoopData>,
|
||||||
|
stop_signal: LoopSignal,
|
||||||
|
display: &mut Display<Self>,
|
||||||
|
seat_name: String,
|
||||||
|
) -> Self {
|
||||||
|
let start_time = std::time::Instant::now();
|
||||||
|
|
||||||
|
let display_handle = display.handle();
|
||||||
|
|
||||||
|
let compositor_state = CompositorState::new::<Self>(&display_handle);
|
||||||
|
let xdg_shell_state = XdgShellState::new::<Self>(&display_handle);
|
||||||
|
let shm_state = ShmState::new::<Self>(&display_handle, vec![]);
|
||||||
|
let output_manager_state = OutputManagerState::new_with_xdg_output::<Self>(&display_handle);
|
||||||
|
let mut seat_state = SeatState::new();
|
||||||
|
let data_device_state = DataDeviceState::new::<Self>(&display_handle);
|
||||||
|
|
||||||
|
let mut seat: Seat<Self> = seat_state.new_wl_seat(&display_handle, seat_name);
|
||||||
|
// FIXME: get Xkb and repeat interval from GNOME dconf.
|
||||||
|
seat.add_keyboard(XkbConfig::default(), 400, 30).unwrap();
|
||||||
|
seat.add_pointer();
|
||||||
|
|
||||||
|
let space = Space::default();
|
||||||
|
|
||||||
|
let socket_source = ListeningSocketSource::new_auto().unwrap();
|
||||||
|
let socket_name = socket_source.socket_name().to_os_string();
|
||||||
|
event_loop
|
||||||
|
.insert_source(socket_source, move |client, _, data| {
|
||||||
|
if let Err(err) = data
|
||||||
|
.display_handle
|
||||||
|
.insert_client(client, Arc::new(ClientState::default()))
|
||||||
|
{
|
||||||
|
error!("error inserting client: {err}");
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
std::env::set_var("WAYLAND_DISPLAY", &socket_name);
|
||||||
|
info!(
|
||||||
|
"listening on Wayland socket: {}",
|
||||||
|
socket_name.to_string_lossy()
|
||||||
|
);
|
||||||
|
|
||||||
|
let display_source = Generic::new(
|
||||||
|
display.backend().poll_fd().as_raw_fd(),
|
||||||
|
Interest::READ,
|
||||||
|
Mode::Level,
|
||||||
|
);
|
||||||
|
event_loop
|
||||||
|
.insert_source(display_source, |_, _, data| {
|
||||||
|
data.display.dispatch_clients(&mut data.niri).unwrap();
|
||||||
|
Ok(PostAction::Continue)
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
Self {
|
||||||
|
start_time,
|
||||||
|
event_loop,
|
||||||
|
stop_signal,
|
||||||
|
display_handle,
|
||||||
|
|
||||||
|
space,
|
||||||
|
|
||||||
|
compositor_state,
|
||||||
|
xdg_shell_state,
|
||||||
|
shm_state,
|
||||||
|
output_manager_state,
|
||||||
|
seat_state,
|
||||||
|
data_device_state,
|
||||||
|
|
||||||
|
seat,
|
||||||
|
output: None,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn surface_under_pointer(
|
||||||
|
&self,
|
||||||
|
pointer: &PointerHandle<Self>,
|
||||||
|
) -> Option<(WlSurface, Point<i32, Logical>)> {
|
||||||
|
let pos = pointer.current_location();
|
||||||
|
self.space
|
||||||
|
.element_under(pos)
|
||||||
|
.and_then(|(window, location)| {
|
||||||
|
window
|
||||||
|
.surface_under(pos - location.to_f64(), WindowSurfaceType::ALL)
|
||||||
|
.map(|(s, p)| (s, p + location))
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn redraw(&mut self, backend: &mut dyn Backend) {
|
||||||
|
let elements = space_render_elements(
|
||||||
|
backend.renderer(),
|
||||||
|
[&self.space],
|
||||||
|
self.output.as_ref().unwrap(),
|
||||||
|
1.,
|
||||||
|
)
|
||||||
|
.unwrap();
|
||||||
|
backend.render(self, &elements);
|
||||||
|
|
||||||
|
let output = self.output.as_ref().unwrap();
|
||||||
|
self.space.elements().for_each(|window| {
|
||||||
|
window.send_frame(
|
||||||
|
output,
|
||||||
|
self.start_time.elapsed(),
|
||||||
|
Some(Duration::ZERO),
|
||||||
|
|_, _| Some(output.clone()),
|
||||||
|
)
|
||||||
|
});
|
||||||
|
|
||||||
|
self.space.refresh();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Default)]
|
||||||
|
pub struct ClientState {
|
||||||
|
pub compositor_state: CompositorClientState,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl ClientData for ClientState {
|
||||||
|
fn initialized(&self, _client_id: ClientId) {}
|
||||||
|
fn disconnected(&self, _client_id: ClientId, _reason: DisconnectReason) {}
|
||||||
|
}
|
||||||
-165
@@ -1,165 +0,0 @@
|
|||||||
use std::ffi::OsString;
|
|
||||||
use std::os::unix::io::AsRawFd;
|
|
||||||
use std::sync::Arc;
|
|
||||||
|
|
||||||
use smithay::desktop::{Space, Window, WindowSurfaceType};
|
|
||||||
use smithay::input::pointer::PointerHandle;
|
|
||||||
use smithay::input::{Seat, SeatState};
|
|
||||||
use smithay::reexports::calloop::generic::Generic;
|
|
||||||
use smithay::reexports::calloop::{EventLoop, Interest, LoopSignal, Mode, PostAction};
|
|
||||||
use smithay::reexports::wayland_server::backend::{ClientData, ClientId, DisconnectReason};
|
|
||||||
use smithay::reexports::wayland_server::protocol::wl_surface::WlSurface;
|
|
||||||
use smithay::reexports::wayland_server::Display;
|
|
||||||
use smithay::utils::{Logical, Point};
|
|
||||||
use smithay::wayland::compositor::{CompositorClientState, CompositorState};
|
|
||||||
use smithay::wayland::data_device::DataDeviceState;
|
|
||||||
use smithay::wayland::output::OutputManagerState;
|
|
||||||
use smithay::wayland::shell::xdg::XdgShellState;
|
|
||||||
use smithay::wayland::shm::ShmState;
|
|
||||||
use smithay::wayland::socket::ListeningSocketSource;
|
|
||||||
|
|
||||||
use crate::CalloopData;
|
|
||||||
|
|
||||||
pub struct Smallvil {
|
|
||||||
pub start_time: std::time::Instant,
|
|
||||||
pub socket_name: OsString,
|
|
||||||
|
|
||||||
pub space: Space<Window>,
|
|
||||||
pub loop_signal: LoopSignal,
|
|
||||||
|
|
||||||
// Smithay State
|
|
||||||
pub compositor_state: CompositorState,
|
|
||||||
pub xdg_shell_state: XdgShellState,
|
|
||||||
pub shm_state: ShmState,
|
|
||||||
pub output_manager_state: OutputManagerState,
|
|
||||||
pub seat_state: SeatState<Smallvil>,
|
|
||||||
pub data_device_state: DataDeviceState,
|
|
||||||
|
|
||||||
pub seat: Seat<Self>,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Smallvil {
|
|
||||||
pub fn new(event_loop: &EventLoop<CalloopData>, display: &mut Display<Self>) -> Self {
|
|
||||||
let start_time = std::time::Instant::now();
|
|
||||||
|
|
||||||
let dh = display.handle();
|
|
||||||
|
|
||||||
let compositor_state = CompositorState::new::<Self>(&dh);
|
|
||||||
let xdg_shell_state = XdgShellState::new::<Self>(&dh);
|
|
||||||
let shm_state = ShmState::new::<Self>(&dh, vec![]);
|
|
||||||
let output_manager_state = OutputManagerState::new_with_xdg_output::<Self>(&dh);
|
|
||||||
let mut seat_state = SeatState::new();
|
|
||||||
let data_device_state = DataDeviceState::new::<Self>(&dh);
|
|
||||||
|
|
||||||
// A seat is a group of keyboards, pointer and touch devices.
|
|
||||||
// A seat typically has a pointer and maintains a keyboard focus and a pointer focus.
|
|
||||||
let mut seat: Seat<Self> = seat_state.new_wl_seat(&dh, "winit");
|
|
||||||
|
|
||||||
// Notify clients that we have a keyboard, for the sake of the example we assume that
|
|
||||||
// keyboard is always present. You may want to track keyboard hot-plug in real
|
|
||||||
// compositor.
|
|
||||||
seat.add_keyboard(Default::default(), 200, 200).unwrap();
|
|
||||||
|
|
||||||
// Notify clients that we have a pointer (mouse)
|
|
||||||
// Here we assume that there is always pointer plugged in
|
|
||||||
seat.add_pointer();
|
|
||||||
|
|
||||||
// A space represents a two-dimensional plane. Windows and Outputs can be mapped onto it.
|
|
||||||
//
|
|
||||||
// Windows get a position and stacking order through mapping.
|
|
||||||
// Outputs become views of a part of the Space and can be rendered via Space::render_output.
|
|
||||||
let space = Space::default();
|
|
||||||
|
|
||||||
let socket_name = Self::init_wayland_listener(display, event_loop);
|
|
||||||
|
|
||||||
// Get the loop signal, used to stop the event loop
|
|
||||||
let loop_signal = event_loop.get_signal();
|
|
||||||
|
|
||||||
Self {
|
|
||||||
start_time,
|
|
||||||
|
|
||||||
space,
|
|
||||||
loop_signal,
|
|
||||||
socket_name,
|
|
||||||
|
|
||||||
compositor_state,
|
|
||||||
xdg_shell_state,
|
|
||||||
shm_state,
|
|
||||||
output_manager_state,
|
|
||||||
seat_state,
|
|
||||||
data_device_state,
|
|
||||||
seat,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn init_wayland_listener(
|
|
||||||
display: &mut Display<Smallvil>,
|
|
||||||
event_loop: &EventLoop<CalloopData>,
|
|
||||||
) -> OsString {
|
|
||||||
// Creates a new listening socket, automatically choosing the next available `wayland`
|
|
||||||
// socket name.
|
|
||||||
let listening_socket = ListeningSocketSource::new_auto().unwrap();
|
|
||||||
|
|
||||||
// Get the name of the listening socket.
|
|
||||||
// Clients will connect to this socket.
|
|
||||||
let socket_name = listening_socket.socket_name().to_os_string();
|
|
||||||
|
|
||||||
let handle = event_loop.handle();
|
|
||||||
|
|
||||||
event_loop
|
|
||||||
.handle()
|
|
||||||
.insert_source(listening_socket, move |client_stream, _, state| {
|
|
||||||
// Inside the callback, you should insert the client into the display.
|
|
||||||
//
|
|
||||||
// You may also associate some data with the client when inserting the client.
|
|
||||||
state
|
|
||||||
.display
|
|
||||||
.handle()
|
|
||||||
.insert_client(client_stream, Arc::new(ClientState::default()))
|
|
||||||
.unwrap();
|
|
||||||
})
|
|
||||||
.expect("Failed to init the wayland event source.");
|
|
||||||
|
|
||||||
// You also need to add the display itself to the event loop, so that client events will be
|
|
||||||
// processed by wayland-server.
|
|
||||||
handle
|
|
||||||
.insert_source(
|
|
||||||
Generic::new(
|
|
||||||
display.backend().poll_fd().as_raw_fd(),
|
|
||||||
Interest::READ,
|
|
||||||
Mode::Level,
|
|
||||||
),
|
|
||||||
|_, _, state| {
|
|
||||||
state.display.dispatch_clients(&mut state.state).unwrap();
|
|
||||||
Ok(PostAction::Continue)
|
|
||||||
},
|
|
||||||
)
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
socket_name
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn surface_under_pointer(
|
|
||||||
&self,
|
|
||||||
pointer: &PointerHandle<Self>,
|
|
||||||
) -> Option<(WlSurface, Point<i32, Logical>)> {
|
|
||||||
let pos = pointer.current_location();
|
|
||||||
self.space
|
|
||||||
.element_under(pos)
|
|
||||||
.and_then(|(window, location)| {
|
|
||||||
window
|
|
||||||
.surface_under(pos - location.to_f64(), WindowSurfaceType::ALL)
|
|
||||||
.map(|(s, p)| (s, p + location))
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Default)]
|
|
||||||
pub struct ClientState {
|
|
||||||
pub compositor_state: CompositorClientState,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ClientData for ClientState {
|
|
||||||
fn initialized(&self, _client_id: ClientId) {}
|
|
||||||
fn disconnected(&self, _client_id: ClientId, _reason: DisconnectReason) {}
|
|
||||||
}
|
|
||||||
+423
@@ -0,0 +1,423 @@
|
|||||||
|
use std::os::fd::FromRawFd;
|
||||||
|
use std::path::PathBuf;
|
||||||
|
use std::time::Duration;
|
||||||
|
|
||||||
|
use anyhow::anyhow;
|
||||||
|
use smithay::backend::allocator::dmabuf::Dmabuf;
|
||||||
|
use smithay::backend::allocator::gbm::{GbmAllocator, GbmBufferFlags, GbmDevice};
|
||||||
|
use smithay::backend::allocator::Fourcc;
|
||||||
|
use smithay::backend::drm::compositor::DrmCompositor;
|
||||||
|
use smithay::backend::drm::{DrmDevice, DrmDeviceFd, DrmEvent};
|
||||||
|
use smithay::backend::egl::{EGLContext, EGLDisplay};
|
||||||
|
use smithay::backend::libinput::{LibinputInputBackend, LibinputSessionInterface};
|
||||||
|
use smithay::backend::renderer::element::surface::WaylandSurfaceRenderElement;
|
||||||
|
use smithay::backend::renderer::gles::{GlesRenderbuffer, GlesRenderer};
|
||||||
|
use smithay::backend::renderer::{Bind, ImportEgl};
|
||||||
|
use smithay::backend::session::libseat::LibSeatSession;
|
||||||
|
use smithay::backend::session::{Event as SessionEvent, Session};
|
||||||
|
use smithay::backend::udev::{self, UdevBackend, UdevEvent};
|
||||||
|
use smithay::desktop::space::SpaceRenderElements;
|
||||||
|
use smithay::output::{Mode, Output, OutputModeSource, PhysicalProperties, Subpixel};
|
||||||
|
use smithay::reexports::calloop::timer::{TimeoutAction, Timer};
|
||||||
|
use smithay::reexports::calloop::{LoopHandle, RegistrationToken};
|
||||||
|
use smithay::reexports::drm::control::connector::{
|
||||||
|
Interface as ConnectorInterface, State as ConnectorState,
|
||||||
|
};
|
||||||
|
use smithay::reexports::drm::control::{Device, ModeTypeFlags};
|
||||||
|
use smithay::reexports::input::Libinput;
|
||||||
|
use smithay::reexports::nix::fcntl::OFlag;
|
||||||
|
use smithay::reexports::nix::libc::dev_t;
|
||||||
|
use smithay::utils::DeviceFd;
|
||||||
|
use smithay_drm_extras::edid::EdidInfo;
|
||||||
|
|
||||||
|
use crate::backend::Backend;
|
||||||
|
use crate::{LoopData, Niri};
|
||||||
|
|
||||||
|
const SUPPORTED_COLOR_FORMATS: &[Fourcc] = &[Fourcc::Argb8888, Fourcc::Abgr8888];
|
||||||
|
|
||||||
|
pub struct Tty {
|
||||||
|
session: LibSeatSession,
|
||||||
|
primary_gpu_path: PathBuf,
|
||||||
|
output_device: Option<OutputDevice>,
|
||||||
|
}
|
||||||
|
|
||||||
|
type GbmDrmCompositor =
|
||||||
|
DrmCompositor<GbmAllocator<DrmDeviceFd>, GbmDevice<DrmDeviceFd>, (), DrmDeviceFd>;
|
||||||
|
|
||||||
|
struct OutputDevice {
|
||||||
|
id: dev_t,
|
||||||
|
path: PathBuf,
|
||||||
|
token: RegistrationToken,
|
||||||
|
drm: DrmDevice,
|
||||||
|
gles: GlesRenderer,
|
||||||
|
drm_compositor: GbmDrmCompositor,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Backend for Tty {
|
||||||
|
fn seat_name(&self) -> String {
|
||||||
|
self.session.seat()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn renderer(&mut self) -> &mut GlesRenderer {
|
||||||
|
&mut self.output_device.as_mut().unwrap().gles
|
||||||
|
}
|
||||||
|
|
||||||
|
fn render(
|
||||||
|
&mut self,
|
||||||
|
niri: &mut Niri,
|
||||||
|
elements: &[SpaceRenderElements<GlesRenderer, WaylandSurfaceRenderElement<GlesRenderer>>],
|
||||||
|
) {
|
||||||
|
let output_device = self.output_device.as_mut().unwrap();
|
||||||
|
let res = output_device
|
||||||
|
.drm_compositor
|
||||||
|
.render_frame::<_, _, GlesRenderbuffer>(
|
||||||
|
&mut output_device.gles,
|
||||||
|
elements,
|
||||||
|
[0.1, 0.1, 0.1, 1.],
|
||||||
|
)
|
||||||
|
.unwrap();
|
||||||
|
assert!(!res.needs_sync());
|
||||||
|
if res.damage.is_some() {
|
||||||
|
output_device.drm_compositor.queue_frame(()).unwrap();
|
||||||
|
} else {
|
||||||
|
niri.event_loop
|
||||||
|
.insert_source(
|
||||||
|
Timer::from_duration(Duration::from_millis(6)),
|
||||||
|
|_, _, data| {
|
||||||
|
data.niri.redraw(data.tty.as_mut().unwrap());
|
||||||
|
TimeoutAction::Drop
|
||||||
|
},
|
||||||
|
)
|
||||||
|
.unwrap();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Tty {
|
||||||
|
pub fn new(event_loop: LoopHandle<LoopData>) -> Self {
|
||||||
|
let (session, notifier) = LibSeatSession::new().unwrap();
|
||||||
|
let seat_name = session.seat();
|
||||||
|
|
||||||
|
let mut libinput = Libinput::new_with_udev(LibinputSessionInterface::from(session.clone()));
|
||||||
|
libinput.udev_assign_seat(&seat_name).unwrap();
|
||||||
|
|
||||||
|
let input_backend = LibinputInputBackend::new(libinput.clone());
|
||||||
|
event_loop
|
||||||
|
.insert_source(input_backend, |event, _, data| {
|
||||||
|
data.niri.process_input_event(event)
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
event_loop
|
||||||
|
.insert_source(notifier, move |event, _, data| {
|
||||||
|
let tty = data.tty.as_mut().unwrap();
|
||||||
|
let niri = &mut data.niri;
|
||||||
|
|
||||||
|
match event {
|
||||||
|
SessionEvent::PauseSession => {
|
||||||
|
libinput.suspend();
|
||||||
|
|
||||||
|
if let Some(output_device) = &tty.output_device {
|
||||||
|
output_device.drm.pause();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
SessionEvent::ActivateSession => {
|
||||||
|
if libinput.resume().is_err() {
|
||||||
|
error!("error resuming libinput");
|
||||||
|
}
|
||||||
|
|
||||||
|
if let Some(output_device) = &tty.output_device {
|
||||||
|
// FIXME: according to Catacomb, resetting DRM+Compositor is preferrable
|
||||||
|
// here, but currently not possible due to a bug somewhere.
|
||||||
|
tty.device_changed(output_device.id, niri);
|
||||||
|
}
|
||||||
|
|
||||||
|
niri.redraw(tty);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let primary_gpu_path = udev::primary_gpu(&seat_name).unwrap().unwrap();
|
||||||
|
|
||||||
|
Self {
|
||||||
|
session,
|
||||||
|
primary_gpu_path,
|
||||||
|
output_device: None,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn init(&mut self, niri: &mut Niri) {
|
||||||
|
let backend = UdevBackend::new(&self.session.seat()).unwrap();
|
||||||
|
for (device_id, path) in backend.device_list() {
|
||||||
|
if let Err(err) = self.device_added(device_id, path.to_owned(), niri) {
|
||||||
|
warn!("error adding device: {err:?}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
niri.event_loop
|
||||||
|
.insert_source(backend, move |event, _, data| {
|
||||||
|
let tty = data.tty.as_mut().unwrap();
|
||||||
|
let niri = &mut data.niri;
|
||||||
|
|
||||||
|
match event {
|
||||||
|
UdevEvent::Added { device_id, path } => {
|
||||||
|
if let Err(err) = tty.device_added(device_id, path, niri) {
|
||||||
|
warn!("error adding device: {err:?}");
|
||||||
|
}
|
||||||
|
niri.redraw(tty);
|
||||||
|
}
|
||||||
|
UdevEvent::Changed { device_id } => tty.device_changed(device_id, niri),
|
||||||
|
UdevEvent::Removed { device_id } => tty.device_removed(device_id, niri),
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
niri.redraw(self);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn device_added(
|
||||||
|
&mut self,
|
||||||
|
device_id: dev_t,
|
||||||
|
path: PathBuf,
|
||||||
|
niri: &mut Niri,
|
||||||
|
) -> anyhow::Result<()> {
|
||||||
|
if path != self.primary_gpu_path {
|
||||||
|
debug!("skipping non-primary device {path:?}");
|
||||||
|
return Ok(());
|
||||||
|
}
|
||||||
|
|
||||||
|
debug!("adding device {path:?}");
|
||||||
|
assert!(self.output_device.is_none());
|
||||||
|
|
||||||
|
let open_flags = OFlag::O_RDWR | OFlag::O_CLOEXEC | OFlag::O_NOCTTY | OFlag::O_NONBLOCK;
|
||||||
|
let fd = self.session.open(&path, open_flags)?;
|
||||||
|
let device_fd = unsafe { DrmDeviceFd::new(DeviceFd::from_raw_fd(fd)) };
|
||||||
|
|
||||||
|
let (drm, drm_notifier) = DrmDevice::new(device_fd.clone(), true)?;
|
||||||
|
let gbm = GbmDevice::new(device_fd)?;
|
||||||
|
|
||||||
|
let display = EGLDisplay::new(gbm.clone())?;
|
||||||
|
let egl_context = EGLContext::new(&display)?;
|
||||||
|
|
||||||
|
let mut gles = unsafe { GlesRenderer::new(egl_context)? };
|
||||||
|
gles.bind_wl_display(&niri.display_handle)?;
|
||||||
|
|
||||||
|
let drm_compositor = self.create_drm_compositor(&drm, &gbm, &gles, niri)?;
|
||||||
|
|
||||||
|
let token = niri
|
||||||
|
.event_loop
|
||||||
|
.insert_source(drm_notifier, move |event, metadata, data| {
|
||||||
|
let tty = data.tty.as_mut().unwrap();
|
||||||
|
match event {
|
||||||
|
DrmEvent::VBlank(_crtc) => {
|
||||||
|
info!("vblank {metadata:?}");
|
||||||
|
|
||||||
|
let output_device = tty.output_device.as_mut().unwrap();
|
||||||
|
|
||||||
|
// Mark the last frame as submitted.
|
||||||
|
if let Err(err) = output_device.drm_compositor.frame_submitted() {
|
||||||
|
error!("error marking frame as submitted: {err}");
|
||||||
|
}
|
||||||
|
|
||||||
|
// Send presentation time feedback.
|
||||||
|
// catacomb
|
||||||
|
// .windows
|
||||||
|
// .mark_presented(&output_device.last_render_states, metadata);
|
||||||
|
|
||||||
|
// Request redraw before the next VBlank.
|
||||||
|
// let frame_interval = catacomb.windows.output().frame_interval();
|
||||||
|
// let duration = frame_interval - RENDER_TIME_OFFSET;
|
||||||
|
// catacomb.backend.schedule_redraw(duration);
|
||||||
|
data.niri.redraw(tty);
|
||||||
|
}
|
||||||
|
DrmEvent::Error(error) => error!("DRM error: {error}"),
|
||||||
|
};
|
||||||
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
self.output_device = Some(OutputDevice {
|
||||||
|
id: device_id,
|
||||||
|
path,
|
||||||
|
token,
|
||||||
|
drm,
|
||||||
|
gles,
|
||||||
|
drm_compositor,
|
||||||
|
});
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn device_changed(&mut self, device_id: dev_t, niri: &mut Niri) {
|
||||||
|
if let Some(output_device) = &self.output_device {
|
||||||
|
if output_device.id == device_id {
|
||||||
|
debug!("output device changed");
|
||||||
|
|
||||||
|
let path = output_device.path.clone();
|
||||||
|
self.device_removed(device_id, niri);
|
||||||
|
if let Err(err) = self.device_added(device_id, path, niri) {
|
||||||
|
warn!("error adding device: {err:?}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn device_removed(&mut self, device_id: dev_t, niri: &mut Niri) {
|
||||||
|
if let Some(mut output_device) = self.output_device.take() {
|
||||||
|
if output_device.id != device_id {
|
||||||
|
self.output_device = Some(output_device);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// FIXME: remove wl_output.
|
||||||
|
niri.event_loop.remove(output_device.token);
|
||||||
|
niri.output = None;
|
||||||
|
output_device.gles.unbind_wl_display();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn create_drm_compositor(
|
||||||
|
&mut self,
|
||||||
|
drm: &DrmDevice,
|
||||||
|
gbm: &GbmDevice<DrmDeviceFd>,
|
||||||
|
gles: &GlesRenderer,
|
||||||
|
niri: &mut Niri,
|
||||||
|
) -> anyhow::Result<GbmDrmCompositor> {
|
||||||
|
let formats = Bind::<Dmabuf>::supported_formats(gles)
|
||||||
|
.ok_or_else(|| anyhow!("no supported formats"))?;
|
||||||
|
let resources = drm.resource_handles()?;
|
||||||
|
|
||||||
|
let mut connector = None;
|
||||||
|
resources
|
||||||
|
.connectors()
|
||||||
|
.iter()
|
||||||
|
.filter_map(|conn| match drm.get_connector(*conn, true) {
|
||||||
|
Ok(info) => Some(info),
|
||||||
|
Err(err) => {
|
||||||
|
warn!("error probing connector: {err}");
|
||||||
|
None
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.inspect(|conn| {
|
||||||
|
debug!(
|
||||||
|
"connector: {}-{}, {:?}, {} modes",
|
||||||
|
conn.interface().as_str(),
|
||||||
|
conn.interface_id(),
|
||||||
|
conn.state(),
|
||||||
|
conn.modes().len(),
|
||||||
|
);
|
||||||
|
})
|
||||||
|
.filter(|conn| conn.state() == ConnectorState::Connected)
|
||||||
|
// FIXME: don't hardcode eDP.
|
||||||
|
.filter(|conn| conn.interface() == ConnectorInterface::EmbeddedDisplayPort)
|
||||||
|
.for_each(|conn| connector = Some(conn));
|
||||||
|
let connector = connector.ok_or_else(|| anyhow!("no compatible connector"))?;
|
||||||
|
info!(
|
||||||
|
"picking connector: {}-{}",
|
||||||
|
connector.interface().as_str(),
|
||||||
|
connector.interface_id(),
|
||||||
|
);
|
||||||
|
|
||||||
|
let mut mode = connector.modes().get(0);
|
||||||
|
connector.modes().iter().for_each(|m| {
|
||||||
|
debug!("mode: {m:?}");
|
||||||
|
|
||||||
|
if m.mode_type().contains(ModeTypeFlags::PREFERRED) {
|
||||||
|
// Pick the highest refresh rate.
|
||||||
|
if mode
|
||||||
|
.map(|curr| curr.vrefresh() < m.vrefresh())
|
||||||
|
.unwrap_or(true)
|
||||||
|
{
|
||||||
|
mode = Some(m);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
let mode = mode.ok_or_else(|| anyhow!("no mode"))?;
|
||||||
|
info!("picking mode: {mode:?}");
|
||||||
|
|
||||||
|
let surface = connector
|
||||||
|
.encoders()
|
||||||
|
.iter()
|
||||||
|
.filter_map(|enc| match drm.get_encoder(*enc) {
|
||||||
|
Ok(info) => Some(info),
|
||||||
|
Err(err) => {
|
||||||
|
warn!("error probing encoder: {err}");
|
||||||
|
None
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.flat_map(|enc| {
|
||||||
|
// Get all CRTCs compatible with the encoder.
|
||||||
|
let mut crtcs = resources.filter_crtcs(enc.possible_crtcs());
|
||||||
|
|
||||||
|
// Sort by maximum number of overlay planes.
|
||||||
|
crtcs.sort_by_cached_key(|crtc| match drm.planes(crtc) {
|
||||||
|
Ok(planes) => -(planes.overlay.len() as isize),
|
||||||
|
Err(err) => {
|
||||||
|
warn!("error probing planes for CRTC: {err}");
|
||||||
|
0
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
crtcs
|
||||||
|
})
|
||||||
|
.find_map(
|
||||||
|
|crtc| match drm.create_surface(crtc, *mode, &[connector.handle()]) {
|
||||||
|
Ok(surface) => Some(surface),
|
||||||
|
Err(err) => {
|
||||||
|
warn!("error creating DRM surface: {err}");
|
||||||
|
None
|
||||||
|
}
|
||||||
|
},
|
||||||
|
);
|
||||||
|
let surface = surface.ok_or_else(|| anyhow!("no surface"))?;
|
||||||
|
|
||||||
|
// Create GBM allocator.
|
||||||
|
let gbm_flags = GbmBufferFlags::RENDERING | GbmBufferFlags::SCANOUT;
|
||||||
|
let allocator = GbmAllocator::new(gbm.clone(), gbm_flags);
|
||||||
|
|
||||||
|
// Update the output mode.
|
||||||
|
let (physical_width, physical_height) = connector.size().unwrap_or((0, 0));
|
||||||
|
let output_name = format!(
|
||||||
|
"{}-{}",
|
||||||
|
connector.interface().as_str(),
|
||||||
|
connector.interface_id(),
|
||||||
|
);
|
||||||
|
|
||||||
|
let (make, model) = EdidInfo::for_connector(drm, connector.handle())
|
||||||
|
.map(|info| (info.manufacturer, info.model))
|
||||||
|
.unwrap_or_else(|| ("Unknown".into(), "Unknown".into()));
|
||||||
|
|
||||||
|
let output = Output::new(
|
||||||
|
output_name,
|
||||||
|
PhysicalProperties {
|
||||||
|
size: (physical_width as i32, physical_height as i32).into(),
|
||||||
|
subpixel: Subpixel::Unknown,
|
||||||
|
model,
|
||||||
|
make,
|
||||||
|
},
|
||||||
|
);
|
||||||
|
let wl_mode = Mode::from(*mode);
|
||||||
|
output.change_current_state(Some(wl_mode), None, None, Some((0, 0).into()));
|
||||||
|
output.set_preferred(wl_mode);
|
||||||
|
|
||||||
|
// FIXME: store this somewhere to remove on disconnect, etc.
|
||||||
|
let _global = output.create_global::<Niri>(&niri.display_handle);
|
||||||
|
niri.space.map_output(&output, (0, 0));
|
||||||
|
niri.output = Some(output.clone());
|
||||||
|
// windows.set_output();
|
||||||
|
|
||||||
|
// Create the compositor.
|
||||||
|
let compositor = DrmCompositor::new(
|
||||||
|
OutputModeSource::Auto(output),
|
||||||
|
surface,
|
||||||
|
None,
|
||||||
|
allocator,
|
||||||
|
gbm.clone(),
|
||||||
|
SUPPORTED_COLOR_FORMATS,
|
||||||
|
formats,
|
||||||
|
drm.cursor_size(),
|
||||||
|
Some(gbm.clone()),
|
||||||
|
)?;
|
||||||
|
Ok(compositor)
|
||||||
|
}
|
||||||
|
}
|
||||||
+65
-78
@@ -4,21 +4,49 @@ use smithay::backend::renderer::damage::OutputDamageTracker;
|
|||||||
use smithay::backend::renderer::element::surface::WaylandSurfaceRenderElement;
|
use smithay::backend::renderer::element::surface::WaylandSurfaceRenderElement;
|
||||||
use smithay::backend::renderer::gles::GlesRenderer;
|
use smithay::backend::renderer::gles::GlesRenderer;
|
||||||
use smithay::backend::winit::{self, WinitError, WinitEvent, WinitEventLoop, WinitGraphicsBackend};
|
use smithay::backend::winit::{self, WinitError, WinitEvent, WinitEventLoop, WinitGraphicsBackend};
|
||||||
|
use smithay::desktop::space::SpaceRenderElements;
|
||||||
use smithay::output::{Mode, Output, PhysicalProperties, Subpixel};
|
use smithay::output::{Mode, Output, PhysicalProperties, Subpixel};
|
||||||
use smithay::reexports::calloop::timer::{TimeoutAction, Timer};
|
use smithay::reexports::calloop::timer::{TimeoutAction, Timer};
|
||||||
use smithay::reexports::calloop::EventLoop;
|
use smithay::reexports::calloop::LoopHandle;
|
||||||
use smithay::utils::{Rectangle, Transform};
|
use smithay::utils::{Rectangle, Transform};
|
||||||
|
|
||||||
use crate::{CalloopData, Smallvil};
|
use crate::backend::Backend;
|
||||||
|
use crate::{LoopData, Niri};
|
||||||
|
|
||||||
pub fn init_winit(
|
pub struct Winit {
|
||||||
event_loop: &EventLoop<CalloopData>,
|
output: Output,
|
||||||
data: &mut CalloopData,
|
backend: WinitGraphicsBackend<GlesRenderer>,
|
||||||
) -> Result<(), Box<dyn std::error::Error>> {
|
winit_event_loop: WinitEventLoop,
|
||||||
let display = &mut data.display;
|
damage_tracker: OutputDamageTracker,
|
||||||
let state = &mut data.state;
|
}
|
||||||
|
|
||||||
let (mut backend, mut winit) = winit::init()?;
|
impl Backend for Winit {
|
||||||
|
fn seat_name(&self) -> String {
|
||||||
|
"winit".to_owned()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn renderer(&mut self) -> &mut GlesRenderer {
|
||||||
|
self.backend.renderer()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn render(
|
||||||
|
&mut self,
|
||||||
|
_niri: &mut Niri,
|
||||||
|
elements: &[SpaceRenderElements<GlesRenderer, WaylandSurfaceRenderElement<GlesRenderer>>],
|
||||||
|
) {
|
||||||
|
let size = self.backend.window_size().physical_size;
|
||||||
|
let damage = Rectangle::from_loc_and_size((0, 0), size);
|
||||||
|
|
||||||
|
self.damage_tracker
|
||||||
|
.render_output(self.backend.renderer(), 0, elements, [0.1, 0.1, 0.1, 1.0])
|
||||||
|
.unwrap();
|
||||||
|
self.backend.submit(Some(&[damage])).unwrap();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Winit {
|
||||||
|
pub fn new(event_loop: LoopHandle<LoopData>) -> Self {
|
||||||
|
let (backend, winit_event_loop) = winit::init().unwrap();
|
||||||
|
|
||||||
let mode = Mode {
|
let mode = Mode {
|
||||||
size: backend.window_size().physical_size,
|
size: backend.window_size().physical_size,
|
||||||
@@ -34,7 +62,6 @@ pub fn init_winit(
|
|||||||
model: "Winit".into(),
|
model: "Winit".into(),
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
let _global = output.create_global::<Smallvil>(&display.handle());
|
|
||||||
output.change_current_state(
|
output.change_current_state(
|
||||||
Some(mode),
|
Some(mode),
|
||||||
Some(Transform::Flipped180),
|
Some(Transform::Flipped180),
|
||||||
@@ -43,47 +70,37 @@ pub fn init_winit(
|
|||||||
);
|
);
|
||||||
output.set_preferred(mode);
|
output.set_preferred(mode);
|
||||||
|
|
||||||
state.space.map_output(&output, (0, 0));
|
let damage_tracker = OutputDamageTracker::from_output(&output);
|
||||||
|
|
||||||
let mut damage_tracker = OutputDamageTracker::from_output(&output);
|
|
||||||
|
|
||||||
std::env::set_var("WAYLAND_DISPLAY", &state.socket_name);
|
|
||||||
|
|
||||||
let mut full_redraw = 0u8;
|
|
||||||
|
|
||||||
let timer = Timer::immediate();
|
let timer = Timer::immediate();
|
||||||
event_loop
|
event_loop
|
||||||
.handle()
|
|
||||||
.insert_source(timer, move |_, _, data| {
|
.insert_source(timer, move |_, _, data| {
|
||||||
winit_dispatch(
|
let winit = data.winit.as_mut().unwrap();
|
||||||
&mut backend,
|
winit.dispatch(&mut data.niri);
|
||||||
&mut winit,
|
|
||||||
data,
|
|
||||||
&output,
|
|
||||||
&mut damage_tracker,
|
|
||||||
&mut full_redraw,
|
|
||||||
)
|
|
||||||
.unwrap();
|
|
||||||
TimeoutAction::ToDuration(Duration::from_millis(16))
|
TimeoutAction::ToDuration(Duration::from_millis(16))
|
||||||
})?;
|
})
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
Ok(())
|
Self {
|
||||||
|
output,
|
||||||
|
backend,
|
||||||
|
winit_event_loop,
|
||||||
|
damage_tracker,
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn winit_dispatch(
|
pub fn init(&mut self, niri: &mut Niri) {
|
||||||
backend: &mut WinitGraphicsBackend<GlesRenderer>,
|
let _global = self.output.create_global::<Niri>(&niri.display_handle);
|
||||||
winit: &mut WinitEventLoop,
|
niri.space.map_output(&self.output, (0, 0));
|
||||||
data: &mut CalloopData,
|
niri.output = Some(self.output.clone());
|
||||||
output: &Output,
|
}
|
||||||
damage_tracker: &mut OutputDamageTracker,
|
|
||||||
full_redraw: &mut u8,
|
|
||||||
) -> Result<(), Box<dyn std::error::Error>> {
|
|
||||||
let display = &mut data.display;
|
|
||||||
let state = &mut data.state;
|
|
||||||
|
|
||||||
let res = winit.dispatch_new_events(|event| match event {
|
fn dispatch(&mut self, niri: &mut Niri) {
|
||||||
|
let res = self
|
||||||
|
.winit_event_loop
|
||||||
|
.dispatch_new_events(|event| match event {
|
||||||
WinitEvent::Resized { size, .. } => {
|
WinitEvent::Resized { size, .. } => {
|
||||||
output.change_current_state(
|
niri.output.as_ref().unwrap().change_current_state(
|
||||||
Some(Mode {
|
Some(Mode {
|
||||||
size,
|
size,
|
||||||
refresh: 60_000,
|
refresh: 60_000,
|
||||||
@@ -93,48 +110,18 @@ pub fn winit_dispatch(
|
|||||||
None,
|
None,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
WinitEvent::Input(event) => state.process_input_event(event),
|
WinitEvent::Input(event) => niri.process_input_event(event),
|
||||||
_ => (),
|
_ => (),
|
||||||
});
|
});
|
||||||
|
|
||||||
if let Err(WinitError::WindowClosed) = res {
|
if let Err(WinitError::WindowClosed) = res {
|
||||||
// Stop the loop
|
niri.stop_signal.stop();
|
||||||
state.loop_signal.stop();
|
return;
|
||||||
|
|
||||||
return Ok(());
|
|
||||||
} else {
|
} else {
|
||||||
res?;
|
res.unwrap();
|
||||||
}
|
}
|
||||||
|
|
||||||
*full_redraw = full_redraw.saturating_sub(1);
|
self.backend.bind().unwrap();
|
||||||
|
niri.redraw(self);
|
||||||
let size = backend.window_size().physical_size;
|
}
|
||||||
let damage = Rectangle::from_loc_and_size((0, 0), size);
|
|
||||||
|
|
||||||
backend.bind()?;
|
|
||||||
smithay::desktop::space::render_output::<_, WaylandSurfaceRenderElement<GlesRenderer>, _, _>(
|
|
||||||
output,
|
|
||||||
backend.renderer(),
|
|
||||||
1.0,
|
|
||||||
0,
|
|
||||||
[&state.space],
|
|
||||||
&[],
|
|
||||||
damage_tracker,
|
|
||||||
[0.1, 0.1, 0.1, 1.0],
|
|
||||||
)?;
|
|
||||||
backend.submit(Some(&[damage]))?;
|
|
||||||
|
|
||||||
state.space.elements().for_each(|window| {
|
|
||||||
window.send_frame(
|
|
||||||
output,
|
|
||||||
state.start_time.elapsed(),
|
|
||||||
Some(Duration::ZERO),
|
|
||||||
|_, _| Some(output.clone()),
|
|
||||||
)
|
|
||||||
});
|
|
||||||
|
|
||||||
state.space.refresh();
|
|
||||||
display.flush_clients()?;
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user