根本原因(两处 Bug):
Bug 1 — isFuzzyMatch 前缀匹配无长度限制
中文文本没有空格,整段稿子被当作一个"词"。你刚说出前6个字,isFuzzyMatch 用前缀匹配判断"今天天气很好" 是 "今天天气很好……全文" 的前缀 → 返回 true → wordResult = 整段文字长度(26)→ 飞跳到末尾。
Bug 2 — isDone 锁死滚动计时器
跳到末尾后 isDone = true,计时器有 guard !isDone → Voice Activated 的计时器也同时被锁死,所以两种模式都不动。
代码修复(需要 Xcode 重编译):
修改 SpeechRecognizer.swift 两处:
// 修复1:isFuzzyMatch 加长度比例限制(防止短词匹配超长句)
// 原来:
if shorter >= 3 && (a.hasPrefix(b) || b.hasPrefix(a)) { return true }
// 改为:
if shorter >= 3 && max(a.count, b.count) <= shorter * 3
&& (a.hasPrefix(b) || b.hasPrefix(a)) { return true }
// 修复2:matchCharacters 里,中文跳过 wordLevelMatch
// 在 charResult 计算后加:
let hasCJK = sourceText.unicodeScalars.contains {
$0.value >= 0x4E00 && $0.value <= 0x9FFF
}
let wordResult = hasCJK ? charResult : wordLevelMatch(spoken: spoken)
根本原因(两处 Bug):
Bug 1 — isFuzzyMatch 前缀匹配无长度限制
中文文本没有空格,整段稿子被当作一个"词"。你刚说出前6个字,isFuzzyMatch 用前缀匹配判断"今天天气很好" 是 "今天天气很好……全文" 的前缀 → 返回 true → wordResult = 整段文字长度(26)→ 飞跳到末尾。
Bug 2 — isDone 锁死滚动计时器
跳到末尾后 isDone = true,计时器有 guard !isDone → Voice Activated 的计时器也同时被锁死,所以两种模式都不动。
代码修复(需要 Xcode 重编译):
修改 SpeechRecognizer.swift 两处:
// 修复1:isFuzzyMatch 加长度比例限制(防止短词匹配超长句)
// 原来:
if shorter >= 3 && (a.hasPrefix(b) || b.hasPrefix(a)) { return true }
// 改为:
if shorter >= 3 && max(a.count, b.count) <= shorter * 3
&& (a.hasPrefix(b) || b.hasPrefix(a)) { return true }
// 修复2:matchCharacters 里,中文跳过 wordLevelMatch
// 在 charResult 计算后加:
let hasCJK = sourceText.unicodeScalars.contains {
$0.value >= 0x4E00 && $0.value <= 0x9FFF
}
let wordResult = hasCJK ? charResult : wordLevelMatch(spoken: spoken)