
SpeechSynthesizer对象可以注册Speech_SpeakProgress事件,当被触发时,可以返回当前的阅读进度,每次新建speech之后,可以绑定。下面稍做测试
private void txtChange(string text)
{txt.Text = text;speech = new SpeechSynthesizer();speech.SpeakProgress += Speech_SpeakProgress;
}
private void Speech_SpeakProgress(object? sender, SpeakProgressEventArgs e)
{Dispatcher.Invoke(() => { txtInfo.Text = $"{e.Text}, {e.CharacterPosition}, {e.AudioPosition}"; });
}
由于需要调用窗口对象,所以用到了Dispatcher.Invoke函数。
其中,e.Text表示当前朗读的单词;e.CharacterPosition表示当前朗读字符所在位置;e.AudioPosition表示当前播放时间,其效果如下
既然能够反馈文本位置,就可以设置更多的功能,比如快速定位当前阅读位置,将Speech_SpeakProgress内容改为
private void Speech_SpeakProgress(object? sender, SpeakProgressEventArgs e)
{Dispatcher.Invoke(() => {txt.CaretIndex = e.CharacterPosition;txt.SelectionStart = e.CharacterPosition;txt.SelectionLength = e.Text.Length;});
}
其中,CaretIndex用于控制滚动条随着光标移动;txt.SelectionStart控制被选中文本的起始点;Txt.SelectionLength表示选中文本的长度。
但仅仅是这样还不够,尽管我们选中了文本,但txt控件并不是窗口的焦点,所以窗口会认为我们没在关注txt,所以并不会展示选区的变化。所以,在speechTask运行前后,需要添加一行txt.Focus,从而结果如下
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-17V3tIE9-1685763546165)(csharp/wpf_txt_12.gif)]
如果觉得文字的表现力不够,还可以再加一个进度条,其xaml代码写在txt前面,内容如下
<ProgressBar DockPanel.Dock="Bottom" x:Name="pgBarText" Height="2"/>
然后在Speech_SpeakProgress的Dispatcher中添加进度条调控的代码,修改之后内容如下
private void Speech_SpeakProgress(object? sender, SpeakProgressEventArgs e)
{Dispatcher.Invoke(() => {txt.CaretIndex = e.CharacterPosition;txt.SelectionStart = e.CharacterPosition;txt.SelectionLength = e.Text.Length;pgBarText.Value = 100.0 * e.CharacterPosition / txt.Text.Length;});
}
其中新添加的这行就用于调控进度条,进度条最大值为100,所以用100.0乘上当前阅读的进度。
本文发布于:2024-01-30 14:50:13,感谢您对本站的认可!
本文链接:https://www.4u4v.net/it/170659741620785.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
| 留言与评论(共有 0 条评论) |