refactor: remove browser NS toggle, default RNNoise on, rework voice settings
- RNNoise (AI Noise Suppression) now enabled by default for all users - Remove redundant browser Noise Suppression toggle from VoiceControls and UserSettings — AudioManager handles it automatically as fallback - Add AI Noise Suppression toggle to UserSettings panel - Rename toggleRnnoise → setRnnoiseEnabled for clearer API - Store migration v3→v4: enable RNNoise for existing users - Keep Echo Cancellation and Auto Gain Control (orthogonal features)
This commit is contained in:
@@ -130,11 +130,10 @@ export const useVoiceStore = create()(persist((set, get) => ({
|
||||
noiseSuppression: true,
|
||||
echoCancellation: true,
|
||||
autoGainControl: false,
|
||||
rnnoiseEnabled: false,
|
||||
toggleNoiseSuppression: () => set((state) => ({ noiseSuppression: !state.noiseSuppression })),
|
||||
rnnoiseEnabled: true,
|
||||
setEchoCancellation: (enabled) => set({ echoCancellation: enabled }),
|
||||
setAutoGainControl: (enabled) => set({ autoGainControl: enabled }),
|
||||
toggleRnnoise: () => set((state) => ({ rnnoiseEnabled: !state.rnnoiseEnabled })),
|
||||
setRnnoiseEnabled: (enabled) => set({ rnnoiseEnabled: enabled }),
|
||||
deafenedUserIds: new Set(),
|
||||
setUserDeafened: (userId, deafened) => {
|
||||
set((state) => {
|
||||
@@ -206,7 +205,7 @@ export const useVoiceStore = create()(persist((set, get) => ({
|
||||
}),
|
||||
}), {
|
||||
name: 'opencord-voice-settings',
|
||||
version: 3,
|
||||
version: 4,
|
||||
migrate: (persistedState, version) => {
|
||||
if (version === 0) {
|
||||
persistedState.streamAttenuationEnabled = false;
|
||||
@@ -215,13 +214,16 @@ export const useVoiceStore = create()(persist((set, get) => ({
|
||||
persistedState.echoCancellation = true;
|
||||
persistedState.autoGainControl = false;
|
||||
}
|
||||
if (version < 3) {
|
||||
persistedState.rnnoiseEnabled = false;
|
||||
if (version < 4) {
|
||||
// v4: RNNoise on by default, browser NS is no longer user-configurable
|
||||
persistedState.rnnoiseEnabled = true;
|
||||
persistedState.noiseSuppression = true;
|
||||
}
|
||||
return persistedState;
|
||||
},
|
||||
storage: createJSONStorage(() => localStorage),
|
||||
// Only persist these keys. Maps and Sets are complex to serialize.
|
||||
// noiseSuppression intentionally excluded — always true, managed by AudioManager.
|
||||
partialize: (state) => ({
|
||||
currentVoiceChannelId: state.currentVoiceChannelId,
|
||||
isMuted: state.isMuted,
|
||||
@@ -231,7 +233,6 @@ export const useVoiceStore = create()(persist((set, get) => ({
|
||||
inputDeviceId: state.inputDeviceId,
|
||||
outputDeviceId: state.outputDeviceId,
|
||||
videoQuality: state.videoQuality,
|
||||
noiseSuppression: state.noiseSuppression,
|
||||
echoCancellation: state.echoCancellation,
|
||||
autoGainControl: state.autoGainControl,
|
||||
rnnoiseEnabled: state.rnnoiseEnabled,
|
||||
|
||||
@@ -65,10 +65,9 @@ interface VoiceState {
|
||||
echoCancellation: boolean;
|
||||
autoGainControl: boolean;
|
||||
rnnoiseEnabled: boolean;
|
||||
toggleNoiseSuppression: () => void;
|
||||
setEchoCancellation: (enabled: boolean) => void;
|
||||
setAutoGainControl: (enabled: boolean) => void;
|
||||
toggleRnnoise: () => void;
|
||||
setRnnoiseEnabled: (enabled: boolean) => void;
|
||||
deafenedUserIds: Set<string>;
|
||||
setUserDeafened: (userId: string, deafened: boolean) => void;
|
||||
// WebSocket-based voice user status (visible without joining LiveKit)
|
||||
@@ -226,11 +225,10 @@ export const useVoiceStore = create<VoiceState>()(
|
||||
noiseSuppression: true,
|
||||
echoCancellation: true,
|
||||
autoGainControl: false,
|
||||
rnnoiseEnabled: false,
|
||||
toggleNoiseSuppression: () => set((state) => ({ noiseSuppression: !state.noiseSuppression })),
|
||||
rnnoiseEnabled: true,
|
||||
setEchoCancellation: (enabled) => set({ echoCancellation: enabled }),
|
||||
setAutoGainControl: (enabled) => set({ autoGainControl: enabled }),
|
||||
toggleRnnoise: () => set((state) => ({ rnnoiseEnabled: !state.rnnoiseEnabled })),
|
||||
setRnnoiseEnabled: (enabled) => set({ rnnoiseEnabled: enabled }),
|
||||
deafenedUserIds: new Set(),
|
||||
setUserDeafened: (userId, deafened) => {
|
||||
set((state) => {
|
||||
@@ -305,7 +303,7 @@ export const useVoiceStore = create<VoiceState>()(
|
||||
}),
|
||||
{
|
||||
name: 'opencord-voice-settings',
|
||||
version: 3,
|
||||
version: 4,
|
||||
migrate: (persistedState: any, version: number) => {
|
||||
if (version === 0) {
|
||||
persistedState.streamAttenuationEnabled = false;
|
||||
@@ -314,13 +312,18 @@ export const useVoiceStore = create<VoiceState>()(
|
||||
persistedState.echoCancellation = true;
|
||||
persistedState.autoGainControl = false;
|
||||
}
|
||||
if (version < 3) {
|
||||
persistedState.rnnoiseEnabled = false;
|
||||
if (version < 4) {
|
||||
// v4: RNNoise on by default, browser NS is no longer user-configurable
|
||||
// (AudioManager uses it as automatic fallback when RNNoise is off)
|
||||
persistedState.rnnoiseEnabled = true;
|
||||
persistedState.noiseSuppression = true;
|
||||
}
|
||||
return persistedState;
|
||||
},
|
||||
storage: createJSONStorage(() => localStorage),
|
||||
// Only persist these keys. Maps and Sets are complex to serialize.
|
||||
// noiseSuppression is intentionally excluded — always true internally,
|
||||
// managed automatically by AudioManager based on RNNoise state.
|
||||
partialize: (state) => ({
|
||||
currentVoiceChannelId: state.currentVoiceChannelId,
|
||||
isMuted: state.isMuted,
|
||||
@@ -330,7 +333,6 @@ export const useVoiceStore = create<VoiceState>()(
|
||||
inputDeviceId: state.inputDeviceId,
|
||||
outputDeviceId: state.outputDeviceId,
|
||||
videoQuality: state.videoQuality,
|
||||
noiseSuppression: state.noiseSuppression,
|
||||
echoCancellation: state.echoCancellation,
|
||||
autoGainControl: state.autoGainControl,
|
||||
rnnoiseEnabled: state.rnnoiseEnabled,
|
||||
|
||||
Reference in New Issue
Block a user