1/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
5 * use this file except in compliance with the License. You may obtain a copy of
6 * the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13 * License for the specific language governing permissions and limitations under
14 * the License.
15 */
16package android.speech.tts;
17
18import android.content.Context;
19import android.media.MediaPlayer;
20import android.net.Uri;
21import android.os.ConditionVariable;
22import android.speech.tts.TextToSpeechService.UtteranceProgressDispatcher;
23import android.util.Log;
24
25class AudioPlaybackQueueItem extends PlaybackQueueItem {
26    private static final String TAG = "TTS.AudioQueueItem";
27
28    private final Context mContext;
29    private final Uri mUri;
30    private final int mStreamType;
31
32    private final ConditionVariable mDone;
33    private MediaPlayer mPlayer;
34    private volatile boolean mFinished;
35
36    AudioPlaybackQueueItem(UtteranceProgressDispatcher dispatcher,
37            Object callerIdentity,
38            Context context, Uri uri, int streamType) {
39        super(dispatcher, callerIdentity);
40
41        mContext = context;
42        mUri = uri;
43        mStreamType = streamType;
44
45        mDone = new ConditionVariable();
46        mPlayer = null;
47        mFinished = false;
48    }
49    @Override
50    public void run() {
51        final UtteranceProgressDispatcher dispatcher = getDispatcher();
52
53        dispatcher.dispatchOnStart();
54        mPlayer = MediaPlayer.create(mContext, mUri);
55        if (mPlayer == null) {
56            dispatcher.dispatchOnError();
57            return;
58        }
59
60        try {
61            mPlayer.setOnErrorListener(new MediaPlayer.OnErrorListener() {
62                @Override
63                public boolean onError(MediaPlayer mp, int what, int extra) {
64                    Log.w(TAG, "Audio playback error: " + what + ", " + extra);
65                    mDone.open();
66                    return true;
67                }
68            });
69            mPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
70                @Override
71                public void onCompletion(MediaPlayer mp) {
72                    mFinished = true;
73                    mDone.open();
74                }
75            });
76            mPlayer.setAudioStreamType(mStreamType);
77            mPlayer.start();
78            mDone.block();
79            finish();
80        } catch (IllegalArgumentException ex) {
81            Log.w(TAG, "MediaPlayer failed", ex);
82            mDone.open();
83        }
84
85        if (mFinished) {
86            dispatcher.dispatchOnDone();
87        } else {
88            dispatcher.dispatchOnError();
89        }
90    }
91
92    private void finish() {
93        try {
94            mPlayer.stop();
95        } catch (IllegalStateException ex) {
96            // Do nothing, the player is already stopped
97        }
98        mPlayer.release();
99    }
100
101    @Override
102    void stop(boolean isError) {
103        mDone.open();
104    }
105}
106