summaryrefslogtreecommitdiffstats
path: root/core/jni/android_media_AudioTrack.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'core/jni/android_media_AudioTrack.cpp')
-rw-r--r--core/jni/android_media_AudioTrack.cpp67
1 files changed, 42 insertions, 25 deletions
diff --git a/core/jni/android_media_AudioTrack.cpp b/core/jni/android_media_AudioTrack.cpp
index b8d6586..42ada54 100644
--- a/core/jni/android_media_AudioTrack.cpp
+++ b/core/jni/android_media_AudioTrack.cpp
@@ -335,7 +335,7 @@ android_media_AudioTrack_start(JNIEnv *env, jobject thiz)
jniThrowException(env, "java/lang/IllegalStateException",
"Unable to retrieve AudioTrack pointer for start()");
}
-
+
lpTrack->start();
}
@@ -433,6 +433,45 @@ static void android_media_AudioTrack_native_release(JNIEnv *env, jobject thiz)
// ----------------------------------------------------------------------------
+jint writeToTrack(AudioTrack* pTrack, jint audioFormat, jbyte* data,
+ jint offsetInBytes, jint sizeInBytes) {
+ // give the data to the native AudioTrack object (the data starts at the offset)
+ ssize_t written = 0;
+ // regular write() or copy the data to the AudioTrack's shared memory?
+ if (pTrack->sharedBuffer() == 0) {
+ written = pTrack->write(data + offsetInBytes, sizeInBytes);
+ } else {
+ if (audioFormat == javaAudioTrackFields.PCM16) {
+ // writing to shared memory, check for capacity
+ if ((size_t)sizeInBytes > pTrack->sharedBuffer()->size()) {
+ sizeInBytes = pTrack->sharedBuffer()->size();
+ }
+ memcpy(pTrack->sharedBuffer()->pointer(), data + offsetInBytes, sizeInBytes);
+ written = sizeInBytes;
+ } else if (audioFormat == javaAudioTrackFields.PCM8) {
+ // data contains 8bit data we need to expand to 16bit before copying
+ // to the shared memory
+ // writing to shared memory, check for capacity,
+ // note that input data will occupy 2X the input space due to 8 to 16bit conversion
+ if (((size_t)sizeInBytes)*2 > pTrack->sharedBuffer()->size()) {
+ sizeInBytes = pTrack->sharedBuffer()->size() / 2;
+ }
+ int count = sizeInBytes;
+ int16_t *dst = (int16_t *)pTrack->sharedBuffer()->pointer();
+ const int8_t *src = (const int8_t *)(data + offsetInBytes);
+ while(count--) {
+ *dst++ = (int16_t)(*src++^0x80) << 8;
+ }
+ // even though we wrote 2*sizeInBytes, we only report sizeInBytes as written to hide
+ // the 8bit mixer restriction from the user of this function
+ written = sizeInBytes;
+ }
+ }
+ return written;
+
+}
+
+// ----------------------------------------------------------------------------
static jint android_media_AudioTrack_native_write(JNIEnv *env, jobject thiz,
jbyteArray javaAudioData,
jint offsetInBytes, jint sizeInBytes,
@@ -461,35 +500,13 @@ static jint android_media_AudioTrack_native_write(JNIEnv *env, jobject thiz,
return 0;
}
- // give the data to the native AudioTrack object (the data starts at the offset)
- ssize_t written = 0;
- // regular write() or copy the data to the AudioTrack's shared memory?
- if (lpTrack->sharedBuffer() == 0) {
- written = lpTrack->write(cAudioData + offsetInBytes, sizeInBytes);
- } else {
- if (javaAudioFormat == javaAudioTrackFields.PCM16) {
- memcpy(lpTrack->sharedBuffer()->pointer(), cAudioData + offsetInBytes, sizeInBytes);
- written = sizeInBytes;
- } else if (javaAudioFormat == javaAudioTrackFields.PCM8) {
- // cAudioData contains 8bit data we need to expand to 16bit before copying
- // to the shared memory
- int count = sizeInBytes;
- int16_t *dst = (int16_t *)lpTrack->sharedBuffer()->pointer();
- const int8_t *src = (const int8_t *)(cAudioData + offsetInBytes);
- while(count--) {
- *dst++ = (int16_t)(*src++^0x80) << 8;
- }
- // even though we wrote 2*sizeInBytes, we only report sizeInBytes as written to hide
- // the 8bit mixer restriction from the user of this function
- written = sizeInBytes;
- }
- }
+ jint written = writeToTrack(lpTrack, javaAudioFormat, cAudioData, offsetInBytes, sizeInBytes);
env->ReleasePrimitiveArrayCritical(javaAudioData, cAudioData, 0);
//LOGV("write wrote %d (tried %d) bytes in the native AudioTrack with offset %d",
// (int)written, (int)(sizeInBytes), (int)offsetInBytes);
- return (int)written;
+ return written;
}