feat: add PipeWire muter functionality and service files for Sendspin audio player
This commit is contained in:
@@ -62,6 +62,32 @@ func listAllNodes() ([]Node, error) {
|
||||
return nodes, nil
|
||||
}
|
||||
|
||||
// FindNodeIDByName scans every PipeWire node (not just Audio/*) and returns
|
||||
// the numeric ID of the first one whose node.name matches. Used by the
|
||||
// loopback muter, where the target may be a stream/loopback rather than a
|
||||
// sink/source. Returns -1 with an error when no match is found.
|
||||
func FindNodeIDByName(name string) (int, error) {
|
||||
out, err := exec.Command("pw-dump").Output()
|
||||
if err != nil {
|
||||
return -1, fmt.Errorf("pw-dump: %w", err)
|
||||
}
|
||||
|
||||
var objects []pwObject
|
||||
if err := json.Unmarshal(out, &objects); err != nil {
|
||||
return -1, fmt.Errorf("parse pw-dump: %w", err)
|
||||
}
|
||||
|
||||
for _, o := range objects {
|
||||
if o.Type != "PipeWire:Interface:Node" {
|
||||
continue
|
||||
}
|
||||
if o.Info.Props.NodeName == name {
|
||||
return o.ID, nil
|
||||
}
|
||||
}
|
||||
return -1, fmt.Errorf("no PipeWire node with node.name=%q", name)
|
||||
}
|
||||
|
||||
func ListSinks() ([]Node, error) {
|
||||
all, err := listAllNodes()
|
||||
if err != nil {
|
||||
|
||||
Reference in New Issue
Block a user