Enhance audio settings: Added loudness controls and headphone model synchronization. Updated PeqState interface to include peq filters. Improved EQPage to dynamically load headphone models based on device state.
This commit is contained in:
+60
-14
@@ -13,7 +13,7 @@
|
||||
import { useDevice } from "@/contexts/DeviceContext";
|
||||
import { ChevronLeft, ChevronDown, Minus, Plus, Edit3, Headphones } from "lucide-react";
|
||||
import { useLocation } from "wouter";
|
||||
import { useState, useMemo } from "react";
|
||||
import { useState, useMemo, useEffect } from "react";
|
||||
import { cn } from "@/lib/utils";
|
||||
import BottomNav from "@/components/BottomNav";
|
||||
import { toast } from "sonner";
|
||||
@@ -47,14 +47,6 @@ function CyanSlider({ value, min, max, step = 1, onChange }: {
|
||||
|
||||
/* ── Constants ── */
|
||||
const FILTER_TYPES = ["PEAK", "LSHELF", "HSHELF", "NOTCH", "LPF", "HPF"];
|
||||
const HEADPHONE_MODELS = [
|
||||
"Sennheiser HD 650",
|
||||
"Sennheiser HD 800",
|
||||
"Sony WH-1000XM5",
|
||||
"AKG K701",
|
||||
"Beyerdynamic DT 990",
|
||||
"Audio-Technica ATH-M50x",
|
||||
];
|
||||
|
||||
/* ── Frequency Response Chart ── */
|
||||
function FreqChart({
|
||||
@@ -211,15 +203,69 @@ function freqLabel(f: number) {
|
||||
/* ── Main Component ── */
|
||||
export default function EQPage() {
|
||||
const [, setLocation] = useLocation();
|
||||
const { deviceState, updateSetting } = useDevice();
|
||||
const { deviceState, updateSetting, api, isDemoMode } = useDevice();
|
||||
const eqOn = (deviceState?.peqEnable ?? 0) === 1;
|
||||
|
||||
const [bands, setBands] = useState(DEFAULT_BANDS);
|
||||
const [selectedBand, setSelectedBand] = useState(3);
|
||||
const [headphoneIdx, setHeadphoneIdx] = useState(0);
|
||||
const [headphoneIdx, setHeadphoneIdx] = useState(deviceState?.peqSelect ?? 0);
|
||||
const [headphoneModels, setHeadphoneModels] = useState<string[]>([]);
|
||||
const [abMode, setAbMode] = useState<"A" | "B">("A");
|
||||
const [autoGain, setAutoGain] = useState(false);
|
||||
|
||||
// 同步 peqSelect 变化
|
||||
useEffect(() => {
|
||||
if (deviceState?.peqSelect !== undefined) {
|
||||
setHeadphoneIdx(deviceState.peqSelect);
|
||||
}
|
||||
}, [deviceState?.peqSelect]);
|
||||
|
||||
// 加载耳机列表
|
||||
useEffect(() => {
|
||||
async function loadHeadphones() {
|
||||
if (isDemoMode || !api) {
|
||||
// 演示模式使用默认列表
|
||||
setHeadphoneModels([
|
||||
"Sennheiser HD 650",
|
||||
"Sennheiser HD 800",
|
||||
"Sony WH-1000XM5",
|
||||
"AKG K701",
|
||||
"Beyerdynamic DT 990",
|
||||
"Audio-Technica ATH-M50x",
|
||||
]);
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const peqState = await api.getPeqState();
|
||||
if (peqState.peq && peqState.peq.length > 0) {
|
||||
setHeadphoneModels(peqState.peq.map(h => h.name));
|
||||
} else {
|
||||
// 如果没有数据,使用默认列表
|
||||
setHeadphoneModels([
|
||||
"Sennheiser HD 650",
|
||||
"Sennheiser HD 800",
|
||||
"Sony WH-1000XM5",
|
||||
"AKG K701",
|
||||
"Beyerdynamic DT 990",
|
||||
"Audio-Technica ATH-M50x",
|
||||
]);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Failed to load headphone models:", error);
|
||||
// 出错时使用默认列表
|
||||
setHeadphoneModels([
|
||||
"Sennheiser HD 650",
|
||||
"Sennheiser HD 800",
|
||||
"Sony WH-1000XM5",
|
||||
"AKG K701",
|
||||
"Beyerdynamic DT 990",
|
||||
"Audio-Technica ATH-M50x",
|
||||
]);
|
||||
}
|
||||
}
|
||||
loadHeadphones();
|
||||
}, [api, isDemoMode]);
|
||||
|
||||
const band = bands[selectedBand];
|
||||
|
||||
const updateBand = (idx: number, patch: Partial<typeof bands[0]>) => {
|
||||
@@ -271,10 +317,10 @@ export default function EQPage() {
|
||||
<button
|
||||
className="flex items-center gap-2 active:opacity-70 transition-opacity"
|
||||
onClick={() => {
|
||||
navigateToSelect("选择耳机型号", HEADPHONE_MODELS, headphoneIdx, "/eq", "headphone");
|
||||
navigateToSelect("选择耳机型号", headphoneModels, headphoneIdx, "/eq", "headphone");
|
||||
setLocation("/select");
|
||||
}}>
|
||||
<span className="text-[20px] font-bold text-white">{HEADPHONE_MODELS[headphoneIdx]}</span>
|
||||
<span className="text-[20px] font-bold text-white">{headphoneModels[headphoneIdx]}</span>
|
||||
<ChevronDown size={18} className="text-white/50" />
|
||||
</button>
|
||||
<div className="flex items-center gap-2">
|
||||
@@ -287,7 +333,7 @@ export default function EQPage() {
|
||||
<button
|
||||
className="w-9 h-9 rounded-full flex items-center justify-center text-white/60 active:text-white transition-colors"
|
||||
style={{ background: "rgba(44,44,46,0.8)", border: "1px solid rgba(255,255,255,0.1)" }}
|
||||
onClick={() => setHeadphoneIdx((i) => Math.min(HEADPHONE_MODELS.length - 1, i + 1))}>
|
||||
onClick={() => setHeadphoneIdx((i) => Math.min(headphoneModels.length - 1, i + 1))}>
|
||||
<Plus size={15} />
|
||||
</button>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user