fix: improve voice quality and add distortion troubleshooting

- Fix RNNoise configuration: use mono instead of stereo, increase VAD threshold to 95%
- Adjust quantum settings: increase min-quantum to 64 for stability
- Add comprehensive voice distortion troubleshoot script
- Create optional disable-auto-rnnoise.nix for problematic setups
- The automatic RNNoise filter can cause artifacts, script helps diagnose and fix
This commit is contained in:
Geir Okkenhaug Jerstad 2025-06-18 21:46:31 +02:00
parent 52a9d544fc
commit 406acb3daf
3 changed files with 318 additions and 5 deletions

View file

@ -0,0 +1,25 @@
{
config,
lib,
pkgs,
...
}: {
# Optional configuration to disable automatic RNNoise filter
# This can be imported if the automatic filter causes distortion
services.pipewire = {
extraConfig.pipewire."15-disable-auto-rnnoise" = {
"context.modules" = [
# Commenting out the automatic RNNoise filter
# Users should use EasyEffects for manual noise suppression instead
# {
# name = "libpipewire-module-filter-chain";
# args = {
# "node.description" = "Noise Canceling Source";
# # ... rest of RNNoise config
# };
# }
];
};
};
}

View file

@ -24,8 +24,8 @@
"context.properties" = { "context.properties" = {
"default.clock.rate" = 48000; "default.clock.rate" = 48000;
"default.clock.quantum" = 1024; "default.clock.quantum" = 1024;
"default.clock.min-quantum" = 32; "default.clock.min-quantum" = 64;
"default.clock.max-quantum" = 2048; "default.clock.max-quantum" = 8192;
}; };
"context.modules" = [ "context.modules" = [
@ -40,10 +40,10 @@
type = "ladspa"; type = "ladspa";
name = "rnnoise"; name = "rnnoise";
plugin = "${pkgs.rnnoise-plugin}/lib/ladspa/librnnoise_ladspa.so"; plugin = "${pkgs.rnnoise-plugin}/lib/ladspa/librnnoise_ladspa.so";
label = "noise_suppressor_stereo"; label = "noise_suppressor_mono";
control = { control = {
"VAD Threshold (%)" = 50.0; "VAD Threshold (%)" = 95.0;
"VAD Grace Period (ms)" = 200; "VAD Grace Period (ms)" = 100;
"Retroactive VAD Grace (ms)" = 0; "Retroactive VAD Grace (ms)" = 0;
}; };
} }
@ -84,6 +84,9 @@
# Validation script # Validation script
(writeShellScriptBin "validate-audio" (builtins.readFile ./validate-audio.sh)) (writeShellScriptBin "validate-audio" (builtins.readFile ./validate-audio.sh))
# Troubleshoot script for voice distortion
(writeShellScriptBin "troubleshoot-voice-distortion" (builtins.readFile ./troubleshoot-voice-distortion.sh))
# Optional: Professional audio tools # Optional: Professional audio tools
# qjackctl # JACK control GUI (for JACK applications) # qjackctl # JACK control GUI (for JACK applications)

View file

@ -0,0 +1,285 @@
#!/usr/bin/env bash
# Voice Distortion Troubleshoot Script
# This script helps diagnose and fix voice distortion issues in PipeWire
set -euo pipefail
echo "🎤 Voice Distortion Troubleshoot Tool"
echo "===================================="
echo ""
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
CYAN='\033[0;36m'
NC='\033[0m' # No Color
success() {
echo -e "${GREEN}$1${NC}"
}
warning() {
echo -e "${YELLOW}⚠️ $1${NC}"
}
error() {
echo -e "${RED}$1${NC}"
}
info() {
echo -e "${BLUE} $1${NC}"
}
highlight() {
echo -e "${CYAN}🔧 $1${NC}"
}
echo "Let's diagnose your voice distortion issue step by step..."
echo ""
# 1. Check current audio settings
echo "1. Current Audio Configuration"
echo "=============================="
if command -v wpctl >/dev/null 2>&1; then
echo "Default devices:"
wpctl status | head -20
echo ""
# Get default source
DEFAULT_SOURCE=$(wpctl inspect @DEFAULT_AUDIO_SOURCE@ 2>/dev/null | grep "node.name" | head -1 | sed 's/.*"\(.*\)".*/\1/' || echo "unknown")
info "Current default source: $DEFAULT_SOURCE"
# Check sample rate
CURRENT_RATE=$(pw-metadata -n settings | grep "clock.rate" | awk '{print $3}' || echo "unknown")
info "Current sample rate: $CURRENT_RATE Hz"
# Check buffer size
CURRENT_QUANTUM=$(pw-metadata -n settings | grep "clock.quantum" | awk '{print $3}' || echo "unknown")
info "Current buffer size: $CURRENT_QUANTUM samples"
else
error "wpctl not available"
fi
echo ""
# 2. Check for common distortion causes
echo "2. Distortion Diagnosis"
echo "======================"
# Check if using RNNoise filter
if pw-dump 2>/dev/null | jq -r '.[] | select(.info.props."node.name" == "rnnoise_source")' | grep -q "rnnoise"; then
warning "You're using the RNNoise filter chain - this might be causing distortion"
echo " The automatic filter chain can sometimes cause artifacts"
else
info "Not using automatic RNNoise filter"
fi
# Check for high CPU usage
if command -v pw-top >/dev/null 2>&1; then
highlight "Checking PipeWire performance (5 seconds)..."
timeout 5 pw-top --batch-mode 2>/dev/null | tail -10 || warning "Could not check performance"
fi
# Check input levels
if command -v wpctl >/dev/null 2>&1; then
echo ""
echo "Current microphone volume levels:"
wpctl get-volume @DEFAULT_AUDIO_SOURCE@ || warning "Could not get volume info"
fi
echo ""
# 3. Quick fixes
echo "3. Quick Fixes to Try"
echo "===================="
echo ""
echo "Choose a solution to try:"
echo ""
echo "A) Disable automatic RNNoise filter (recommended first step)"
echo "B) Lower microphone input gain"
echo "C) Reduce buffer size for lower latency"
echo "D) Use EasyEffects instead of filter chain"
echo "E) Reset to safe audio settings"
echo "F) Test different sample rates"
echo "G) Monitor audio in real-time"
echo "H) All of the above (comprehensive fix)"
echo ""
read -p "Enter your choice (A-H): " choice
case $choice in
A|a)
echo ""
highlight "Disabling automatic RNNoise filter..."
if pw-dump 2>/dev/null | jq -r '.[] | select(.info.props."node.name" == "rnnoise_source") | .id' | while read id; do
echo "Removing filter node $id"
pw-cli destroy "$id" 2>/dev/null || warning "Could not remove filter $id"
done; then
success "RNNoise filter disabled"
echo "Try speaking now. If distortion is gone, use EasyEffects for noise suppression instead."
else
warning "Could not disable RNNoise filter automatically"
fi
;;
B|b)
echo ""
highlight "Lowering microphone input gain to 50%..."
wpctl set-volume @DEFAULT_AUDIO_SOURCE@ 50%
success "Microphone gain reduced to 50%"
echo "Test your voice now. Adjust further if needed with: wpctl set-volume @DEFAULT_AUDIO_SOURCE@ X%"
;;
C|c)
echo ""
highlight "Setting lower buffer size for reduced latency..."
pw-metadata -n settings 0 clock.force-quantum 512
success "Buffer size set to 512 samples"
echo "This should reduce latency but may increase CPU usage"
;;
D|d)
echo ""
highlight "Launching EasyEffects for manual noise suppression..."
if command -v easyeffects >/dev/null 2>&1; then
easyeffects &
success "EasyEffects launched"
echo ""
echo "In EasyEffects:"
echo "1. Go to 'Input' tab"
echo "2. Add 'RNNoise' effect"
echo "3. Set 'VAD Threshold' to 95% (very conservative)"
echo "4. Set 'Wet' signal to 50-70% (not 100%)"
echo "5. Disable any other aggressive processing"
else
error "EasyEffects not available"
fi
;;
E|e)
echo ""
highlight "Resetting to safe audio settings..."
# Reset quantum
pw-metadata -n settings 0 clock.force-quantum 0
# Reset rate
pw-metadata -n settings 0 clock.force-rate 0
# Set reasonable volume
wpctl set-volume @DEFAULT_AUDIO_SOURCE@ 70%
# Restart audio services
systemctl --user restart pipewire pipewire-pulse wireplumber
success "Audio settings reset to defaults"
echo "Wait 5 seconds for services to restart, then test your voice"
;;
F|f)
echo ""
highlight "Testing different sample rates..."
echo "Current rate: $(pw-metadata -n settings | grep clock.rate | awk '{print $3}' || echo 'default')"
echo ""
echo "Trying 44100 Hz..."
pw-metadata -n settings 0 clock.force-rate 44100
sleep 2
echo "Test your voice now. Press Enter to continue..."
read
echo "Trying 48000 Hz..."
pw-metadata -n settings 0 clock.force-rate 48000
sleep 2
echo "Test your voice now. Press Enter to continue..."
read
echo "Back to automatic rate..."
pw-metadata -n settings 0 clock.force-rate 0
success "Rate testing complete"
;;
G|g)
echo ""
highlight "Starting real-time audio monitoring..."
echo "Press Ctrl+C to stop monitoring"
echo ""
if command -v pw-top >/dev/null 2>&1; then
pw-top
else
echo "Monitoring with wpctl status (updating every 2 seconds):"
while true; do
clear
echo "=== PipeWire Status ==="
wpctl status
echo ""
echo "=== Microphone Volume ==="
wpctl get-volume @DEFAULT_AUDIO_SOURCE@
echo ""
echo "Press Ctrl+C to stop"
sleep 2
done
fi
;;
H|h)
echo ""
highlight "Running comprehensive fix..."
# Step 1: Disable RNNoise filter
echo "1/6: Disabling automatic RNNoise filter..."
pw-dump 2>/dev/null | jq -r '.[] | select(.info.props."node.name" == "rnnoise_source") | .id' | while read id; do
pw-cli destroy "$id" 2>/dev/null || true
done
# Step 2: Reset audio settings
echo "2/6: Resetting audio settings..."
pw-metadata -n settings 0 clock.force-quantum 0
pw-metadata -n settings 0 clock.force-rate 0
# Step 3: Set conservative volume
echo "3/6: Setting conservative microphone gain..."
wpctl set-volume @DEFAULT_AUDIO_SOURCE@ 60%
# Step 4: Restart services
echo "4/6: Restarting audio services..."
systemctl --user restart pipewire pipewire-pulse wireplumber
# Step 5: Wait for restart
echo "5/6: Waiting for services to stabilize..."
sleep 5
# Step 6: Launch EasyEffects
echo "6/6: Launching EasyEffects for manual control..."
if command -v easyeffects >/dev/null 2>&1; then
easyeffects &
success "Comprehensive fix applied!"
echo ""
echo "Next steps:"
echo "1. Test your voice without any effects first"
echo "2. In EasyEffects, gradually add noise suppression:"
echo " - Start with RNNoise at 50% wet signal"
echo " - Use VAD threshold of 95% or higher"
echo " - Avoid aggressive compression or EQ"
echo "3. If still distorted, try lowering input gain further"
else
warning "EasyEffects not available for manual control"
fi
;;
*)
error "Invalid choice"
;;
esac
echo ""
echo "🎯 Additional Tips to Prevent Distortion:"
echo "========================================="
echo ""
echo "• Keep microphone gain below 80% to avoid clipping"
echo "• Use RNNoise conservatively (50-70% wet signal, not 100%)"
echo "• Check for background applications using audio"
echo "• Ensure your microphone hardware supports 48kHz"
echo "• Consider using a better quality microphone"
echo "• Avoid stacking multiple noise reduction effects"
echo ""
echo "Run this script again anytime with: troubleshoot-voice-distortion"