|
@@ -21,6 +21,11 @@ export interface EqualizerPreset {
|
|
|
isCustom: boolean; // 是否为自定义预设
|
|
isCustom: boolean; // 是否为自定义预设
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+export interface EqualizerGainStats {
|
|
|
|
|
+ maxPositiveGain: number;
|
|
|
|
|
+ positiveGainSum: number;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
export class EqualizerManager {
|
|
export class EqualizerManager {
|
|
|
private static instance: EqualizerManager | null = null;
|
|
private static instance: EqualizerManager | null = null;
|
|
|
private static readonly TAG: string = 'heanup EqualizerManager';
|
|
private static readonly TAG: string = 'heanup EqualizerManager';
|
|
@@ -45,18 +50,18 @@ export class EqualizerManager {
|
|
|
{ frequency: 16000, label: '16kHz', gain: 0 }
|
|
{ frequency: 16000, label: '16kHz', gain: 0 }
|
|
|
];
|
|
];
|
|
|
|
|
|
|
|
- // 内置预设 - 增益值增大以获得更明显的效果
|
|
|
|
|
|
|
+ // 内置预设 - 以音色校正为主,避免多频段同时大幅正增益导致失真
|
|
|
public static readonly BUILT_IN_PRESETS: EqualizerPreset[] = [
|
|
public static readonly BUILT_IN_PRESETS: EqualizerPreset[] = [
|
|
|
{ id: 'normal', name: '正常', gains: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], isCustom: false },
|
|
{ id: 'normal', name: '正常', gains: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], isCustom: false },
|
|
|
- { id: 'pop', name: '流行', gains: [-2, 3, 6, 6, 3, 0, -2, -2, -2, -2], isCustom: false },
|
|
|
|
|
- { id: 'rock', name: '摇滚', gains: [6, 5, 2, 0, -2, 0, 3, 5, 6, 6], isCustom: false },
|
|
|
|
|
- { id: 'jazz', name: '爵士', gains: [5, 3, 2, 3, -3, -3, 0, 2, 3, 5], isCustom: false },
|
|
|
|
|
- { id: 'classical', name: '古典', gains: [6, 5, 3, 2, -2, -2, 0, 3, 5, 6], isCustom: false },
|
|
|
|
|
- { id: 'bass_boost', name: '低音增强', gains: [10, 8, 6, 3, 0, 0, 0, 0, 0, 0], isCustom: false },
|
|
|
|
|
- { id: 'treble_boost', name: '高音增强', gains: [0, 0, 0, 0, 0, 2, 4, 6, 8, 10], isCustom: false },
|
|
|
|
|
- { id: 'vocal', name: '人声增强', gains: [-4, -2, 0, 4, 6, 6, 4, 0, -2, -4], isCustom: false },
|
|
|
|
|
- { id: 'dance', name: '舞曲', gains: [8, 6, 3, 0, 0, -3, -2, 3, 5, 6], isCustom: false },
|
|
|
|
|
- { id: 'acoustic', name: '原声', gains: [5, 4, 2, 2, 3, 3, 3, 5, 4, 2], isCustom: false }
|
|
|
|
|
|
|
+ { id: 'pop', name: '流行', gains: [-1.5, -0.5, 1.5, 2.5, 1.5, 0.5, -0.5, -1, -1, -1.5], isCustom: false },
|
|
|
|
|
+ { id: 'rock', name: '摇滚', gains: [2.5, 1.5, 0.5, -0.5, -1, 0, 1.5, 2.5, 3, 2.5], isCustom: false },
|
|
|
|
|
+ { id: 'jazz', name: '爵士', gains: [1.5, 1, 0.5, 1, -0.5, -1, 0.5, 1.5, 2, 1.5], isCustom: false },
|
|
|
|
|
+ { id: 'classical', name: '古典', gains: [0.5, 0, -0.5, -1, -1.5, 0.5, 1.5, 2.5, 2, 1], isCustom: false },
|
|
|
|
|
+ { id: 'bass_boost', name: '低音增强', gains: [4.5, 3.5, 2.5, 1.5, 0.5, -0.5, -1, -1, -1, -1], isCustom: false },
|
|
|
|
|
+ { id: 'treble_boost', name: '高音增强', gains: [-1, -1, -0.5, 0, 0.5, 1, 2, 3, 4, 4.5], isCustom: false },
|
|
|
|
|
+ { id: 'vocal', name: '人声增强', gains: [-2, -1, -0.5, 1, 2.5, 3, 2.5, 1, -0.5, -1.5], isCustom: false },
|
|
|
|
|
+ { id: 'dance', name: '舞曲', gains: [3.5, 2.5, 1.5, 0, -0.5, 0.5, 1.5, 2.5, 2, 1], isCustom: false },
|
|
|
|
|
+ { id: 'acoustic', name: '原声', gains: [1, 0.5, 0, 0.5, 1, 1.5, 1.5, 1, 0.5, 0], isCustom: false }
|
|
|
];
|
|
];
|
|
|
|
|
|
|
|
// 当前状态
|
|
// 当前状态
|
|
@@ -170,6 +175,20 @@ export class EqualizerManager {
|
|
|
return this._customGains.slice();
|
|
return this._customGains.slice();
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ private clampGainValue(gain: number): number {
|
|
|
|
|
+ let clampedGain = gain;
|
|
|
|
|
+ if (!Number.isFinite(clampedGain)) {
|
|
|
|
|
+ clampedGain = 0;
|
|
|
|
|
+ }
|
|
|
|
|
+ if (clampedGain < -12) {
|
|
|
|
|
+ clampedGain = -12;
|
|
|
|
|
+ }
|
|
|
|
|
+ if (clampedGain > 12) {
|
|
|
|
|
+ clampedGain = 12;
|
|
|
|
|
+ }
|
|
|
|
|
+ return Math.round(clampedGain * 10) / 10;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
// 获取所有预设(内置 + 自定义)
|
|
// 获取所有预设(内置 + 自定义)
|
|
|
getAllPresets(): EqualizerPreset[] {
|
|
getAllPresets(): EqualizerPreset[] {
|
|
|
const result: EqualizerPreset[] = [];
|
|
const result: EqualizerPreset[] = [];
|
|
@@ -205,6 +224,25 @@ export class EqualizerManager {
|
|
|
return [0, 0, 0, 0, 0, 0, 0, 0, 0, 0];
|
|
return [0, 0, 0, 0, 0, 0, 0, 0, 0, 0];
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ getCurrentGainStats(): EqualizerGainStats {
|
|
|
|
|
+ const gains = this.getCurrentGains();
|
|
|
|
|
+ let maxPositiveGain = 0;
|
|
|
|
|
+ let positiveGainSum = 0;
|
|
|
|
|
+ for (let i = 0; i < gains.length; i++) {
|
|
|
|
|
+ const gain = gains[i];
|
|
|
|
|
+ if (gain > 0) {
|
|
|
|
|
+ positiveGainSum += gain;
|
|
|
|
|
+ if (gain > maxPositiveGain) {
|
|
|
|
|
+ maxPositiveGain = gain;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ return {
|
|
|
|
|
+ maxPositiveGain: Math.round(maxPositiveGain * 10) / 10,
|
|
|
|
|
+ positiveGainSum: Math.round(positiveGainSum * 10) / 10
|
|
|
|
|
+ };
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
// 设置预设
|
|
// 设置预设
|
|
|
setPreset(presetId: string): void {
|
|
setPreset(presetId: string): void {
|
|
|
this._currentPresetId = presetId;
|
|
this._currentPresetId = presetId;
|
|
@@ -217,15 +255,7 @@ export class EqualizerManager {
|
|
|
if (bandIndex < 0 || bandIndex >= 10) {
|
|
if (bandIndex < 0 || bandIndex >= 10) {
|
|
|
return;
|
|
return;
|
|
|
}
|
|
}
|
|
|
- // 限制增益范围 -12 到 +12
|
|
|
|
|
- let clampedGain = gain;
|
|
|
|
|
- if (clampedGain < -12) {
|
|
|
|
|
- clampedGain = -12;
|
|
|
|
|
- }
|
|
|
|
|
- if (clampedGain > 12) {
|
|
|
|
|
- clampedGain = 12;
|
|
|
|
|
- }
|
|
|
|
|
- this._customGains[bandIndex] = clampedGain;
|
|
|
|
|
|
|
+ this._customGains[bandIndex] = this.clampGainValue(gain);
|
|
|
this._currentPresetId = 'custom';
|
|
this._currentPresetId = 'custom';
|
|
|
this.saveState();
|
|
this.saveState();
|
|
|
}
|
|
}
|
|
@@ -236,14 +266,7 @@ export class EqualizerManager {
|
|
|
return;
|
|
return;
|
|
|
}
|
|
}
|
|
|
for (let i = 0; i < 10; i++) {
|
|
for (let i = 0; i < 10; i++) {
|
|
|
- let g = gains[i];
|
|
|
|
|
- if (g < -12) {
|
|
|
|
|
- g = -12;
|
|
|
|
|
- }
|
|
|
|
|
- if (g > 12) {
|
|
|
|
|
- g = 12;
|
|
|
|
|
- }
|
|
|
|
|
- this._customGains[i] = g;
|
|
|
|
|
|
|
+ this._customGains[i] = this.clampGainValue(gains[i]);
|
|
|
}
|
|
}
|
|
|
this._currentPresetId = 'custom';
|
|
this._currentPresetId = 'custom';
|
|
|
this.saveState();
|
|
this.saveState();
|