IPlaybackRate.c revision d2a7f0d6883a6d3835642e7b282f05ed1c54fe63
161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten/*
261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * Copyright (C) 2010 The Android Open Source Project
361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten *
461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * Licensed under the Apache License, Version 2.0 (the "License");
561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * you may not use this file except in compliance with the License.
661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * You may obtain a copy of the License at
761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten *
861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten *      http://www.apache.org/licenses/LICENSE-2.0
961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten *
1061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * Unless required by applicable law or agreed to in writing, software
1161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * distributed under the License is distributed on an "AS IS" BASIS,
1261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * See the License for the specific language governing permissions and
1461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten * limitations under the License.
1561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten */
1661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
1761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten/* PlaybackRate implementation */
1861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
1961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten#include "sles_allinclusive.h"
2061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
2161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kastenstatic SLresult IPlaybackRate_SetRate(SLPlaybackRateItf self, SLpermille rate)
2261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
2361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate *this = (IPlaybackRate *) self;
24d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // const, so no lock needed
25d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    if (!(this->mMinRate <= rate && rate <= this->mMaxRate))
26d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten        return SL_RESULT_PARAMETER_INVALID;
2761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    interface_lock_poke(this);
2861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    this->mRate = rate;
2961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    interface_unlock_poke(this);
30497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#ifdef USE_ANDROID
31497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    return sles_to_android_audioPlayerSetPlayRate(this, rate);
32497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#endif
3361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    return SL_RESULT_SUCCESS;
3461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
3561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
3661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kastenstatic SLresult IPlaybackRate_GetRate(SLPlaybackRateItf self, SLpermille *pRate)
3761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
38497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    if (NULL == pRate) {
3961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten        return SL_RESULT_PARAMETER_INVALID;
40497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    }
4161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate *this = (IPlaybackRate *) self;
4261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    interface_lock_peek(this);
4361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLpermille rate = this->mRate;
4461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    interface_unlock_peek(this);
4561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pRate = rate;
4661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    return SL_RESULT_SUCCESS;
4761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
4861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
49d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kastenstatic SLresult IPlaybackRate_SetPropertyConstraints(SLPlaybackRateItf self, SLuint32 constraints)
5061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
5161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate *this = (IPlaybackRate *) self;
52497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    SLresult result = SL_RESULT_SUCCESS;
5361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    this->mProperties = constraints;
54497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#ifdef USE_ANDROID
55497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    // verify property support before storing
56497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    result = sles_to_android_audioPlayerSetPlaybackRateBehavior(this, constraints);
57497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#endif
58497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    interface_lock_poke(this);
59497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    if (result == SL_RESULT_SUCCESS) {
60497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi        this->mProperties = constraints;
61497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    }
62497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    interface_unlock_poke(this);
63497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    return result;
6461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
6561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
66d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kastenstatic SLresult IPlaybackRate_GetProperties(SLPlaybackRateItf self, SLuint32 *pProperties)
6761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
68497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    if (NULL == pProperties) {
6961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten        return SL_RESULT_PARAMETER_INVALID;
70497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    }
7161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate *this = (IPlaybackRate *) self;
72497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    interface_lock_peek(this);
7361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLuint32 properties = this->mProperties;
74497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    interface_unlock_peek(this);
7561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pProperties = properties;
7661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    return SL_RESULT_SUCCESS;
7761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
7861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
7961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kastenstatic SLresult IPlaybackRate_GetCapabilitiesOfRate(SLPlaybackRateItf self,
8061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLpermille rate, SLuint32 *pCapabilities)
8161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
82497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    if (NULL == pCapabilities) {
8361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten        return SL_RESULT_PARAMETER_INVALID;
84497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    }
85497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    IPlaybackRate *this = (IPlaybackRate *) self;
86d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // const, so no lock needed
87d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    if (!(this->mMinRate <= rate && rate <= this->mMaxRate))
88d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten        return SL_RESULT_PARAMETER_INVALID;
89497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    SLuint32 capabilities = 0;
90497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#ifdef USE_ANDROID
91497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    sles_to_android_audioPlayerGetCapabilitiesOfRate(this, &capabilities);
92d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten#else
93d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    capabilities = this->mCapabilities;
94497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#endif
9561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pCapabilities = capabilities;
9661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    return SL_RESULT_SUCCESS;
9761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
9861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
9961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kastenstatic SLresult IPlaybackRate_GetRateRange(SLPlaybackRateItf self, SLuint8 index,
100d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    SLpermille *pMinRate, SLpermille *pMaxRate, SLpermille *pStepSize, SLuint32 *pCapabilities)
10161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
10261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    if (NULL == pMinRate || NULL == pMaxRate || NULL == pStepSize || NULL == pCapabilities)
10361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten        return SL_RESULT_PARAMETER_INVALID;
104d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // only one range
105d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    if (0 < index)
106d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten        return SL_RESULT_PARAMETER_INVALID;
10761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate *this = (IPlaybackRate *) self;
10861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    interface_lock_shared(this);
10961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLpermille minRate = this->mMinRate;
11061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLpermille maxRate = this->mMaxRate;
11161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLpermille stepSize = this->mStepSize;
11261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    SLuint32 capabilities = this->mCapabilities;
11361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    interface_unlock_shared(this);
11461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pMinRate = minRate;
11561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pMaxRate = maxRate;
11661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pStepSize = stepSize;
11761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    *pCapabilities = capabilities;
11861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    return SL_RESULT_SUCCESS;
11961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
12061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
12161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kastenstatic const struct SLPlaybackRateItf_ IPlaybackRate_Itf = {
12261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate_SetRate,
12361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate_GetRate,
12461ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate_SetPropertyConstraints,
12561ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate_GetProperties,
12661ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate_GetCapabilitiesOfRate,
12761ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate_GetRateRange
12861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten};
12961ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten
13061ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kastenvoid IPlaybackRate_init(void *self)
13161ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten{
13261ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    IPlaybackRate *this = (IPlaybackRate *) self;
13361ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten    this->mItf = &IPlaybackRate_Itf;
134d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    this->mProperties = SL_RATEPROP_NOPITCHCORAUDIO;
1350b167267bda99b68346045ccab14e810121d5de4Glenn Kasten    this->mRate = 1000;
136d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // const
1370b167267bda99b68346045ccab14e810121d5de4Glenn Kasten    this->mMinRate = 500;
1380b167267bda99b68346045ccab14e810121d5de4Glenn Kasten    this->mMaxRate = 2000;
139d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    this->mStepSize = 0;
140497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#ifdef USE_ANDROID
141497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    this->mStepSize = 0;
142497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    // for an AudioPlayer, mCapabilities will be initialized in sles_to_android_audioPlayerCreate
143497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi#endif
144d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // The generic implementation sets no capabilities because the generic
145d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // implementation alone doesn't support any.
146497c71251661f9096f77d0a9bc08fe7a5eb49079Jean-Michel Trivi    this->mCapabilities = 0;
147d2a7f0d6883a6d3835642e7b282f05ed1c54fe63Glenn Kasten    // SL_RATEPROP_SILENTAUDIO | SL_RATEPROP_STAGGEREDAUDIO | SL_RATEPROP_NOPITCHCORAUDIO | SL_RATEPROP_PITCHCORAUDIO
14861ac0ade16f84d877dfd8d0e984eb203d4a2901dGlenn Kasten}
149