如何让TextToSpeech说得更快?

时间:2015-11-14 08:13:29

标签: java android queue text-to-speech

我正在使用TextToSpeech开发一个节拍器应用程序。而且我有点Metronome课来处理所有这些事情(这是完整的代码。但我会告诉你以后要关注的地方):

public class Metronome {
    private static final int DEFAULT_BPM = 115;
    private Timer timer;
    private int tempo;
    private int maxBeats;
    private int currentBeat;
    private BeatDivider inBeat;
    private BeatType beatType;

    private TextToSpeech tts;

    public void setMaxBeats(int maxBeats) {
        this.maxBeats = maxBeats;
    }

    public void setTempo (int tempo) {
        timer.setInterval (getMillisecondsFromBpm (tempo, beatType));
        this.tempo = tempo;
    }

    public void setBeatType (BeatType type) {
        beatType = type;
        setTempo (tempo);
    }

    public int getMaxBeats() {
        return maxBeats;
    }

    public BeatDivider getInBeat() {
        return inBeat;
    }

    public int getTempo () {
        return tempo;
    }

    public void reset () {
        if (!timer.isPaused ())
            throw new IllegalStateException ("Timer cannot be running when reset");

        inBeat = BeatDivider.ON_BEAT;
        currentBeat = 1;
    }

    public void start () {
        timer.startTimer ();
    }

    public void stop () {
        timer.stopTimer ();
        reset ();
    }

    public boolean isRunning () {
        return !timer.isPaused ();
    }

    public Metronome (Context c) {
        timer = new Timer (new Runnable () {
            @Override
            public void run() {
                beep ();
                increment ();
            }
        }, getMillisecondsFromBpm (DEFAULT_BPM, BeatType.QUARTER), false);
        tts = new TextToSpeech (c, new TextToSpeech.OnInitListener () {
            @Override
            public void onInit(int status) {

            }
        });
        tts.setSpeechRate (2);
        setBeatType (BeatType.QUARTER);
        setMaxBeats (4);
        setTempo (DEFAULT_BPM);
    }

    private int getMillisecondsFromBpm (int bpm, BeatType type) {
        int ms = (int)Math.pow (bpm / 60.0, -1) * 1000;

        switch (type) {
            case QUARTER:
                return ms;
            case EIGHTH:
                return ms / 2;
            case SIXTEENTH:
                return ms / 4;
        }

        return ms;
    }

    private void increment () {
        if (beatType == BeatType.QUARTER) {
            incrementBeat ();
        } else if (beatType == BeatType.EIGHTH) {
            incrementEighth ();
        } else if (beatType == BeatType.SIXTEENTH) {
            incrementSixteenth ();
        }
    }

    private void incrementSixteenth() {
        switch (inBeat) {
            case E:
                inBeat = BeatDivider.AND;
                break;
            case A:
                inBeat = BeatDivider.ON_BEAT;
                incrementBeat ();
                break;
            case ON_BEAT:
                inBeat = BeatDivider.E;
                break;
            case AND:
                inBeat = BeatDivider.A;
        }
    }

    private void incrementEighth() {
        switch (inBeat) {
            case E:
            case ON_BEAT:
                inBeat = BeatDivider.AND;
                break;
            case A:
            case AND:
                inBeat = BeatDivider.ON_BEAT;
                incrementBeat ();
                break;
        }
    }

    private void incrementBeat() {
        inBeat = BeatDivider.ON_BEAT;
        if (currentBeat < maxBeats) {
            currentBeat++;
        } else {
            currentBeat = 1;
        }
    }

    private void beep () {
        tts.speak (getBeatString (), TextToSpeech.QUEUE_FLUSH, null);
    }

    private String getBeatString () {
        switch (inBeat) {
            case ON_BEAT:
                default:
                return Integer.toString (currentBeat);
            case E:
                return "e";
            case AND:
                return "and";
            case A:
                return "Ah";
        }
    }

    public enum BeatDivider {
        ON_BEAT,
        E,
        AND,
        A
    }

    public enum BeatType {
        QUARTER,
        EIGHTH,
        SIXTEENTH
    }
}

说明:

Timer课程正如它所说的那样。这是我的自定义实现。那里应该没有问题。这个想法是,用户可以设置速度(tempo),时间签名(maxBeats)和笔记类型(BeatType)。有四分音符,它就像1 2 3 4和八分音符一样,它分别为1和2以及3和4等等。 TextToSpeech会说出这些话。

问题:

当我将bpm增加到80或90时,tts不会说话!不知怎的,当我减少bpm时,它就像1 3 1 3 1 3.原因是它说得太慢了。

我试图解决它:

因为我认为它说得很慢,所以我将语速提高到了4.但同样的事情又发生了!然后我尝试使用QUEUE_ADD代替QUEUE_FLUSH。当我将bpm从60增加到150时,tts仍然以初始速度说话!然后我试着按下停止按钮,但在那之后,tts仍然保持说话,说话和说话,直到我finish()活动!

我真的想知道如何解决这个问题。我想减少演讲之间的时间是我需要做的。但是怎么样?或者,如果我用&#34; beep&#34;声音和使用MediaPlayer,会发生这种情况吗?

1 个答案:

答案 0 :(得分:0)

您可以通过tts.setPitch(1)更改速度;和tts.setSpeechRate(2);