19730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson/* 29730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * Copyright (C) 2011 The Android Open Source Project 39730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * 49730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * Licensed under the Apache License, Version 2.0 (the "License"); 59730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * you may not use this file except in compliance with the License. 69730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * You may obtain a copy of the License at 79730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * 89730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * http://www.apache.org/licenses/LICENSE-2.0 99730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * 109730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * Unless required by applicable law or agreed to in writing, software 119730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * distributed under the License is distributed on an "AS IS" BASIS, 129730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 139730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * See the License for the specific language governing permissions and 149730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson * limitations under the License. 159730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson */ 169730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 179730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonpackage com.android.ex.variablespeed; 189730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 199730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonimport android.media.MediaPlayer; 209730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 219730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonimport java.util.concurrent.BlockingQueue; 229730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonimport java.util.concurrent.LinkedBlockingQueue; 239730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonimport java.util.concurrent.TimeUnit; 249730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonimport java.util.concurrent.TimeoutException; 259730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 269730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonimport javax.annotation.concurrent.ThreadSafe; 279730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 289730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson/** Implementation of {@link MediaPlayer.OnCompletionListener} that we can wait for in tests. */ 299730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson@ThreadSafe 309730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudsonpublic class AwaitableErrorListener implements MediaPlayer.OnErrorListener { 319730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson private final BlockingQueue<Object> mQueue = new LinkedBlockingQueue<Object>(); 329730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson private volatile boolean mOnErrorReturnValue = true; 339730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 349730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson @Override 359730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson public boolean onError(MediaPlayer mp, int what, int extra) { 369730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson addAnObjectToTheQueue(); 379730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson return mOnErrorReturnValue; 389730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 399730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 409730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson public void setOnErrorReturnValue(boolean value) { 419730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson mOnErrorReturnValue = value; 429730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 439730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 449730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson private void addAnObjectToTheQueue() { 459730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson try { 469730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson mQueue.put(new Object()); 479730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } catch (InterruptedException e) { 489730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson // This should not happen in practice, the queue is unbounded so this method will not 499730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson // block. 509730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson // If this thread is using interrupt to shut down, preserve interrupt status and return. 519730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson Thread.currentThread().interrupt(); 529730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 539730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 549730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 559730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson public void awaitOneCallback(long timeout, TimeUnit unit) throws InterruptedException, 569730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson TimeoutException { 579730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson if (mQueue.poll(timeout, unit) == null) { 589730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson throw new TimeoutException(); 599730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 609730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 619730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson 629730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson public void assertNoMoreCallbacks() { 639730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson if (mQueue.peek() != null) { 649730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson throw new IllegalStateException("there was an unexpected callback on the queue"); 659730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 669730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson } 679730f15ebbf4b64cd48e0777850e56cb516a9ed4Hugo Hudson} 68