Improve microphone level sensitivity using logarithmic (dB) scaling
This commit is contained in:
@@ -4,7 +4,7 @@ import (
|
||||
"math"
|
||||
)
|
||||
|
||||
// CalculateRMSLevel calculates the RMS level of PCM samples and returns 0-100
|
||||
// CalculateRMSLevel calculates the RMS level of PCM samples and returns 0-100 (Logarithmic/dB)
|
||||
func CalculateRMSLevel(samples []int16) int {
|
||||
if len(samples) == 0 {
|
||||
return 0
|
||||
@@ -16,15 +16,33 @@ func CalculateRMSLevel(samples []int16) int {
|
||||
}
|
||||
|
||||
rms := math.Sqrt(sum / float64(len(samples)))
|
||||
// Normalize to 0-100 (max int16 is 32767)
|
||||
level := int(rms / 32767.0 * 100.0)
|
||||
|
||||
// Normalize to 0.0 - 1.0
|
||||
val := rms / 32768.0
|
||||
if val < 0.000001 { // Avoid log(0)
|
||||
return 0
|
||||
}
|
||||
|
||||
// Convert to dB
|
||||
db := 20 * math.Log10(val)
|
||||
|
||||
// Map -50dB (silence floor) to 0dB (max) to 0-100
|
||||
const minDB = -50.0
|
||||
|
||||
if db < minDB {
|
||||
return 0
|
||||
}
|
||||
|
||||
// Scale
|
||||
level := int((db - minDB) * (100.0 / (0 - minDB)))
|
||||
|
||||
if level > 100 {
|
||||
level = 100
|
||||
}
|
||||
return level
|
||||
}
|
||||
|
||||
// CalculatePeakLevel returns the peak level of PCM samples as 0-100
|
||||
// CalculatePeakLevel returns the peak level of PCM samples as 0-100 (Logarithmic/dB)
|
||||
func CalculatePeakLevel(samples []int16) int {
|
||||
if len(samples) == 0 {
|
||||
return 0
|
||||
@@ -40,7 +58,26 @@ func CalculatePeakLevel(samples []int16) int {
|
||||
}
|
||||
}
|
||||
|
||||
return int(float64(peak) / 32767.0 * 100.0)
|
||||
// Normalize
|
||||
val := float64(peak) / 32768.0
|
||||
if val < 0.000001 {
|
||||
return 0
|
||||
}
|
||||
|
||||
db := 20 * math.Log10(val)
|
||||
const minDB = -50.0
|
||||
|
||||
if db < minDB {
|
||||
// Linear falloff for very low signals to avoid clutter
|
||||
return 0
|
||||
}
|
||||
|
||||
level := int((db - minDB) * (100.0 / (0 - minDB)))
|
||||
if level > 100 {
|
||||
level = 100
|
||||
}
|
||||
|
||||
return level
|
||||
}
|
||||
|
||||
// LevelToBar converts a 0-100 level to a visual bar string
|
||||
|
||||
Reference in New Issue
Block a user