process method
Ingests a new TranscriptionResult from the ASR recognizer, updates filtered tokens and recomputes continuous acoustic durations.
Implementation
ProcessedAudioStream process(TranscriptionResult result) {
final int maxCount = min(result.tokens.length, result.timestamps.length);
int commonLen = 0;
final int minLen = min(_lastRawTokens.length, maxCount);
for (int i = 0; i < minLen; i++) {
if (_lastRawTokens[i] == result.tokens[i]) {
commonLen++;
} else {
break;
}
}
if (commonLen < _lastRawTokens.length) {
reset();
commonLen = 0;
}
_lastRawTokens = result.tokens.sublist(0, maxCount);
final bool hasNewTokens = commonLen < maxCount;
// Ingest newly arrived non-blank tokens into filtered arrays
for (int i = commonLen; i < maxCount; i++) {
final String tok = result.tokens[i];
final double rawTs = result.timestamps[i];
// Defensively filter empty or special CTC blank / epsilon tokens.
if (tok.isEmpty ||
tok == '<blank>' ||
tok == '<blk>' ||
tok == '<eps>' ||
tok == 'eps') {
continue;
}
_filteredTokens.add(tok);
_filteredSpikeTimes.add(rawTs);
}
// Recompute accurate acoustic durations across all filtered tokens
_recomputeDurations();
// Debug prints:
if (hasNewTokens && _filteredTokens.isNotEmpty) {
final int startPrint = max(0, _filteredTokens.length - (maxCount - commonLen + 1));
for (int i = startPrint; i < _filteredTokens.length; i++) {
// ignore: avoid_print
print(
'⏱️ [SHERPA TOKEN] #$i "${_filteredTokens[i]}" | Pure Sherpa Ts: ${_filteredSpikeTimes[i].toStringAsFixed(3)}s | Grading Dur: ${_tokenDurations[i].toStringAsFixed(3)}s [start: ${_tokenStarts[i].toStringAsFixed(3)}s -> end: ${_tokenEnds[i].toStringAsFixed(3)}s]',
);
}
}
return ProcessedAudioStream(
tokens: _filteredTokens,
durations: _tokenDurations,
starts: _tokenStarts,
ends: _tokenEnds,
spikeTimes: _filteredSpikeTimes,
);
}