gaming: arctis-sound-manager + quickshell ANC switcher
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
parent
1df7ebb302
commit
027858ff1e
4 changed files with 143 additions and 1 deletions
23
flake.lock
generated
23
flake.lock
generated
|
|
@ -1,5 +1,27 @@
|
|||
{
|
||||
"nodes": {
|
||||
"arctis-sound-manager": {
|
||||
"inputs": {
|
||||
"nixpkgs": [
|
||||
"nixpkgs"
|
||||
]
|
||||
},
|
||||
"locked": {
|
||||
"dir": "nix",
|
||||
"lastModified": 1785229953,
|
||||
"narHash": "sha256-5oezrSj8OxNeMUN0IxjdKh4t2D9jn1BOainmBRNeXgE=",
|
||||
"owner": "loteran",
|
||||
"repo": "Arctis-Sound-Manager",
|
||||
"rev": "aaa05fd62b7ac037d59802ce9c46b69c5bc84a33",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
"dir": "nix",
|
||||
"owner": "loteran",
|
||||
"repo": "Arctis-Sound-Manager",
|
||||
"type": "github"
|
||||
}
|
||||
},
|
||||
"base16": {
|
||||
"inputs": {
|
||||
"fromYaml": "fromYaml"
|
||||
|
|
@ -372,6 +394,7 @@
|
|||
},
|
||||
"root": {
|
||||
"inputs": {
|
||||
"arctis-sound-manager": "arctis-sound-manager",
|
||||
"home-manager": "home-manager",
|
||||
"nix-cachyos-kernel": "nix-cachyos-kernel",
|
||||
"nixpkgs": "nixpkgs_2",
|
||||
|
|
|
|||
|
|
@ -20,6 +20,11 @@
|
|||
|
||||
proton-cachyos-nix.url = "github:powerofthe69/proton-cachyos-nix";
|
||||
|
||||
arctis-sound-manager = {
|
||||
url = "github:loteran/Arctis-Sound-Manager?dir=nix";
|
||||
inputs.nixpkgs.follows = "nixpkgs";
|
||||
};
|
||||
|
||||
stylix.url = "github:nix-community/stylix/release-26.05";
|
||||
};
|
||||
outputs =
|
||||
|
|
@ -49,7 +54,7 @@
|
|||
in
|
||||
{
|
||||
nixosConfigurations = {
|
||||
FredOS-Gaming = mkHost "FredOS-Gaming" [];
|
||||
FredOS-Gaming = mkHost "FredOS-Gaming" [ inputs.arctis-sound-manager.nixosModules.default ];
|
||||
FredOS-Mediaserver = mkHost "FredOS-Mediaserver" [];
|
||||
FredOS-Macbook = mkHost "FredOS-Macbook" [];
|
||||
};
|
||||
|
|
|
|||
|
|
@ -24,6 +24,10 @@
|
|||
|
||||
programs.geary.enable = true;
|
||||
|
||||
# SteelSeries Nova Pro control (ANC switching via quickshell talks to its
|
||||
# asm-daemon over D-Bus)
|
||||
services.arctis-sound-manager.enable = true;
|
||||
|
||||
# Force heavy builds off the gaming PC onto the media server so nix updates
|
||||
# never compete with games for CPU/RAM. Pairs with the distributed build
|
||||
# config in common.nix. builders-use-substitutes lets the server pull from
|
||||
|
|
|
|||
|
|
@ -418,6 +418,7 @@ in
|
|||
readonly property string systemctl: "${pkgs.systemd}/bin/systemctl"
|
||||
readonly property string weatherFetch: "${weatherFetchScript}"
|
||||
readonly property string ssh: "${pkgs.openssh}/bin/ssh"
|
||||
readonly property string gdbus: "${pkgs.glib}/bin/gdbus"
|
||||
// Unprivileged ping works via ICMP dgram sockets — NixOS sets
|
||||
// net.ipv4.ping_group_range for everyone (no wrapper exists).
|
||||
readonly property string ping: "${pkgs.iputils}/bin/ping"
|
||||
|
|
@ -2932,6 +2933,115 @@ in
|
|||
}
|
||||
}
|
||||
|
||||
${lib.optionalString (!isMacbook) ''
|
||||
// Nova Pro noise cancelling — talks to asm-daemon
|
||||
// (Arctis Sound Manager) over the session bus.
|
||||
// SetSetting("noise_cancelling", "0|1|2"), status read
|
||||
// back as off/transparent/on. Card hides when the
|
||||
// daemon or headset is gone.
|
||||
Card {
|
||||
id: ancCard
|
||||
visible: ancMode !== ""
|
||||
width: parent.width
|
||||
property string ancMode: ""
|
||||
|
||||
function setMode(key, value) {
|
||||
if (key === ancMode) return;
|
||||
ancMode = key; // optimistic; next poll corrects if the device disagrees
|
||||
ancSet.mode = value;
|
||||
ancSet.running = true;
|
||||
}
|
||||
|
||||
Process {
|
||||
id: ancSet
|
||||
property string mode: "0"
|
||||
command: [Commands.gdbus, "call", "--session",
|
||||
"--dest", "name.giacomofurlan.ArctisManager.Next",
|
||||
"--object-path", "/name/giacomofurlan/ArctisManager/Next/Settings",
|
||||
"--method", "name.giacomofurlan.ArctisManager.Next.Settings.SetSetting",
|
||||
"noise_cancelling", mode]
|
||||
}
|
||||
|
||||
Process {
|
||||
id: ancStatus
|
||||
command: [Commands.gdbus, "call", "--session",
|
||||
"--dest", "name.giacomofurlan.ArctisManager.Next",
|
||||
"--object-path", "/name/giacomofurlan/ArctisManager/Next/Status",
|
||||
"--method", "name.giacomofurlan.ArctisManager.Next.Status.GetStatus"]
|
||||
stdout: StdioCollector {
|
||||
onStreamFinished: {
|
||||
// gdbus prints a GVariant tuple: ('{"headset": ...}',)
|
||||
const a = text.indexOf("('");
|
||||
const b = text.lastIndexOf("',");
|
||||
if (a < 0 || b <= a) { ancCard.ancMode = ""; return; }
|
||||
try {
|
||||
const st = JSON.parse(text.slice(a + 2, b));
|
||||
const nc = st.headset ? st.headset.noise_cancelling : undefined;
|
||||
ancCard.ancMode = (nc && nc.value) ? nc.value : "";
|
||||
} catch (e) { ancCard.ancMode = ""; }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Poll only while the dropdown is up; keeps ticking
|
||||
// with the card hidden so a headset appearing
|
||||
// mid-open reveals it.
|
||||
Timer {
|
||||
interval: 3000
|
||||
repeat: true
|
||||
triggeredOnStart: true
|
||||
running: volDropdown.visible
|
||||
onTriggered: ancStatus.running = true
|
||||
}
|
||||
|
||||
Row {
|
||||
spacing: 6
|
||||
SIcon { anchors.verticalCenter: parent.verticalCenter; text: "headphones" }
|
||||
SText {
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
text: "Noise Cancelling"
|
||||
font.weight: Font.Medium
|
||||
}
|
||||
}
|
||||
|
||||
Row {
|
||||
width: parent.width
|
||||
spacing: 6
|
||||
|
||||
Repeater {
|
||||
model: [
|
||||
{ key: "off", label: "Off", val: "0" },
|
||||
{ key: "transparent", label: "Transparent", val: "1" },
|
||||
{ key: "on", label: "ANC", val: "2" }
|
||||
]
|
||||
|
||||
Rectangle {
|
||||
required property var modelData
|
||||
property bool active: ancCard.ancMode === modelData.key
|
||||
width: (parent.width - 12) / 3
|
||||
height: 26
|
||||
radius: 6
|
||||
color: active ? Theme.base0D : "transparent"
|
||||
border.color: active ? Theme.base0D : Theme.base03
|
||||
border.width: 1
|
||||
|
||||
SText {
|
||||
anchors.centerIn: parent
|
||||
text: modelData.label
|
||||
font.pixelSize: 11
|
||||
color: active ? Theme.base00 : Theme.base05
|
||||
}
|
||||
|
||||
MouseArea {
|
||||
anchors.fill: parent
|
||||
cursorShape: Qt.PointingHandCursor
|
||||
onClicked: ancCard.setMode(modelData.key, modelData.val)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
''}
|
||||
// Applications card
|
||||
Card {
|
||||
visible: appStreamsCol.childrenRect.height > 0
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue