mirror of
https://gitlab.freedesktop.org/pipewire/wireplumber.git
synced 2026-01-06 02:10:13 +01:00
state-routes.lua: Add new 'bluetooth.keep-volume-on-profile-changed' setting
If enabled, this setting will use the same volume levels as the previous profile. This is useful on some bluetooth devices if the bluetooth profile audioswitch is enabled.
This commit is contained in:
parent
94aabdb370
commit
d55680b929
4 changed files with 74 additions and 4 deletions
10
po/conf.pot
10
po/conf.pot
|
|
@ -13,6 +13,16 @@ msgstr ""
|
|||
msgid "Auto-switch to headset profile"
|
||||
msgstr ""
|
||||
|
||||
#. /wireplumber.settings.schema/bluetooth.keep-volume-on-profile-changed/description
|
||||
#: wireplumber.conf
|
||||
msgid "Keep same volume levels between Bluetooth profile changes"
|
||||
msgstr ""
|
||||
|
||||
#. /wireplumber.settings.schema/bluetooth.keep-volume-on-profile-changed/name
|
||||
#: wireplumber.conf
|
||||
msgid "Keep volume"
|
||||
msgstr ""
|
||||
|
||||
#. /wireplumber.settings.schema/bluetooth.use-persistent-storage/description
|
||||
#: wireplumber.conf
|
||||
msgid "Remember and restore Bluetooth headset mode status"
|
||||
|
|
|
|||
|
|
@ -847,6 +847,12 @@ wireplumber.settings.schema = {
|
|||
type = "bool"
|
||||
default = true
|
||||
}
|
||||
bluetooth.keep-volume-on-profile-changed = {
|
||||
name = "Keep volume"
|
||||
description = "Keep same volume levels between Bluetooth profile changes"
|
||||
type = "bool"
|
||||
default = false
|
||||
}
|
||||
|
||||
## Device
|
||||
device.restore-profile = {
|
||||
|
|
|
|||
|
|
@ -21,6 +21,15 @@ log = Log.open_topic ("s-device")
|
|||
state = nil
|
||||
state_table = nil
|
||||
|
||||
-- utilities
|
||||
function fillCycle (dest, src)
|
||||
local size = #dest
|
||||
local srcSize = #src
|
||||
for i = 1, size do
|
||||
dest[i] = src[((i - 1) % srcSize) + 1]
|
||||
end
|
||||
end
|
||||
|
||||
-- hook to restore routes selection for a newly selected profile
|
||||
find_stored_routes_hook = SimpleEventHook {
|
||||
name = "device/find-stored-routes",
|
||||
|
|
@ -128,6 +137,24 @@ apply_route_props_hook = SimpleEventHook {
|
|||
|
||||
-- convert arrays to Json
|
||||
if props.channelVolumes then
|
||||
|
||||
-- fill the channel volumes with the ones from the previous profile if
|
||||
-- this is a BT device and the setting is enabled
|
||||
if device.properties["device.api"] == "bluez5" and
|
||||
Settings.get_boolean ("bluetooth.keep-volume-on-profile-changed") then
|
||||
local prev_profile = dev_info.route_param_prev_profile
|
||||
local route_dir = route_info.direction
|
||||
if dev_info.route_param_profile_changed and
|
||||
dev_info.route_param_channel_volumes[device.id] ~= nil and
|
||||
dev_info.route_param_channel_volumes[device.id][prev_profile] ~= nil then
|
||||
local vols = dev_info.route_param_channel_volumes[device.id][prev_profile][route_dir]
|
||||
if vols ~= nil then
|
||||
log:info (device, "using previous profile channel volumes on route " .. route_info.name)
|
||||
fillCycle (props.channelVolumes, vols)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
props.channelVolumes = Json.Array (props.channelVolumes)
|
||||
end
|
||||
if props.channelMap then
|
||||
|
|
@ -169,6 +196,7 @@ store_or_restore_routes_hook = AsyncEventHook {
|
|||
device:enum_params ("EnumRoute", function (enum_route_it, e)
|
||||
local selected_routes = {}
|
||||
local push_select_routes = false
|
||||
local profile = nil
|
||||
|
||||
-- check for error
|
||||
if e then
|
||||
|
|
@ -189,6 +217,18 @@ store_or_restore_routes_hook = AsyncEventHook {
|
|||
return
|
||||
end
|
||||
|
||||
-- Update current and previous profiles, and check if they changed
|
||||
for p in device:iterate_params ("Profile") do
|
||||
profile = cutils.parseParam (p, "Profile")
|
||||
if dev_info.route_param_curr_profile ~= profile.index then
|
||||
dev_info.route_param_prev_profile = dev_info.route_param_curr_profile
|
||||
dev_info.route_param_curr_profile = profile.index
|
||||
dev_info.route_param_profile_changed = true
|
||||
else
|
||||
dev_info.route_param_profile_changed = false
|
||||
end
|
||||
end
|
||||
|
||||
local new_route_infos = {}
|
||||
|
||||
-- look at all the routes and update/reset cached information
|
||||
|
|
@ -227,6 +267,18 @@ store_or_restore_routes_hook = AsyncEventHook {
|
|||
goto skip_route
|
||||
end
|
||||
|
||||
-- cache the device input and output route channel volumes for current profile
|
||||
local curr_profile = dev_info.route_param_curr_profile
|
||||
local route_dir = route.direction
|
||||
if dev_info.route_param_channel_volumes [device.id] == nil then
|
||||
dev_info.route_param_channel_volumes [device.id] = {}
|
||||
end
|
||||
if dev_info.route_param_channel_volumes [device.id][curr_profile] == nil then
|
||||
dev_info.route_param_channel_volumes [device.id][curr_profile] = {}
|
||||
end
|
||||
dev_info.route_param_channel_volumes [device.id][curr_profile][route_dir] =
|
||||
route.props.properties.channelVolumes
|
||||
|
||||
-- get cached route info and at the same time
|
||||
-- ensure that the route is also in EnumRoute
|
||||
local route_info = devinfo.find_route_info (dev_info, route, false)
|
||||
|
|
@ -264,10 +316,8 @@ store_or_restore_routes_hook = AsyncEventHook {
|
|||
end
|
||||
|
||||
-- save selected routes for the active profile
|
||||
for p in device:iterate_params ("Profile") do
|
||||
local profile = cutils.parseParam (p, "Profile")
|
||||
saveProfileRoutes (dev_info, profile.name)
|
||||
end
|
||||
assert (profile)
|
||||
saveProfileRoutes (dev_info, profile.name)
|
||||
|
||||
-- push a select-routes event to re-apply the routes with new properties
|
||||
if push_select_routes then
|
||||
|
|
|
|||
|
|
@ -44,6 +44,10 @@ function module.get_device_info (self, device)
|
|||
name = device_name,
|
||||
active_profile = -1,
|
||||
route_infos = {},
|
||||
route_param_curr_profile = -1,
|
||||
route_param_prev_profile = -1,
|
||||
route_param_profile_changed = false,
|
||||
route_param_channel_volumes = {}
|
||||
}
|
||||
self.dev_infos [device_id] = dev_info
|
||||
end
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue