android_media_ToneGenerator.cpp revision bda7469d9b1ec6d9c9d6da40ddf64dc39ff271a9
1/* //device/libs/android_runtime/android_media_AudioSystem.cpp
2 **
3 ** Copyright 2008, The Android Open Source Project
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 **     http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17
18#define LOG_TAG "ToneGenerator"
19
20#include <stdio.h>
21#include <unistd.h>
22#include <fcntl.h>
23
24#include "jni.h"
25#include "JNIHelp.h"
26#include "android_runtime/AndroidRuntime.h"
27
28#include "utils/Log.h"
29#include "media/AudioSystem.h"
30#include "media/ToneGenerator.h"
31
32// ----------------------------------------------------------------------------
33
34using namespace android;
35
36struct fields_t {
37    jfieldID context;
38};
39static fields_t fields;
40
41static jboolean android_media_ToneGenerator_startTone(JNIEnv *env, jobject thiz, jint toneType, jint durationMs) {
42    LOGV("android_media_ToneGenerator_startTone: %x\n", (int)thiz);
43
44    ToneGenerator *lpToneGen = (ToneGenerator *)env->GetIntField(thiz,
45            fields.context);
46    if (lpToneGen == NULL) {
47        jniThrowException(env, "java/lang/RuntimeException", "Method called after release()");
48        return false;
49    }
50
51    return lpToneGen->startTone(toneType, durationMs);
52}
53
54static void android_media_ToneGenerator_stopTone(JNIEnv *env, jobject thiz) {
55    LOGV("android_media_ToneGenerator_stopTone: %x\n", (int)thiz);
56
57    ToneGenerator *lpToneGen = (ToneGenerator *)env->GetIntField(thiz,
58            fields.context);
59
60    LOGV("ToneGenerator lpToneGen: %x\n", (unsigned int)lpToneGen);
61    if (lpToneGen == NULL) {
62        jniThrowException(env, "java/lang/RuntimeException", "Method called after release()");
63        return;
64    }
65    lpToneGen->stopTone();
66}
67
68static void android_media_ToneGenerator_release(JNIEnv *env, jobject thiz) {
69    ToneGenerator *lpToneGen = (ToneGenerator *)env->GetIntField(thiz,
70            fields.context);
71    LOGV("android_media_ToneGenerator_release lpToneGen: %x\n", (int)lpToneGen);
72
73    env->SetIntField(thiz, fields.context, 0);
74
75    if (lpToneGen) {
76        delete lpToneGen;
77    }
78}
79
80static void android_media_ToneGenerator_native_setup(JNIEnv *env, jobject thiz,
81        jint streamType, jint volume) {
82    ToneGenerator *lpToneGen = new ToneGenerator(streamType, AudioSystem::linearToLog(volume), true);
83
84    env->SetIntField(thiz, fields.context, 0);
85
86    LOGV("android_media_ToneGenerator_native_setup jobject: %x\n", (int)thiz);
87
88    if (lpToneGen == NULL) {
89        LOGE("ToneGenerator creation failed \n");
90        jniThrowException(env, "java/lang/OutOfMemoryError", NULL);
91        return;
92    }
93    LOGV("ToneGenerator lpToneGen: %x\n", (unsigned int)lpToneGen);
94
95    if (!lpToneGen->isInited()) {
96        LOGE("ToneGenerator init failed \n");
97        jniThrowException(env, "java/lang/RuntimeException", "Init failed");
98        return;
99    }
100
101    // Stow our new C++ ToneGenerator in an opaque field in the Java object.
102    env->SetIntField(thiz, fields.context, (int)lpToneGen);
103
104    LOGV("ToneGenerator fields.context: %x\n", env->GetIntField(thiz, fields.context));
105}
106
107static void android_media_ToneGenerator_native_finalize(JNIEnv *env,
108        jobject thiz) {
109    LOGV("android_media_ToneGenerator_native_finalize jobject: %x\n", (int)thiz);
110
111    ToneGenerator *lpToneGen = (ToneGenerator *)env->GetIntField(thiz,
112            fields.context);
113
114    if (lpToneGen) {
115        LOGV("delete lpToneGen: %x\n", (int)lpToneGen);
116        delete lpToneGen;
117    }
118}
119
120// ----------------------------------------------------------------------------
121
122static JNINativeMethod gMethods[] = {
123    { "startTone", "(II)Z", (void *)android_media_ToneGenerator_startTone },
124    { "stopTone", "()V", (void *)android_media_ToneGenerator_stopTone },
125    { "release", "()V", (void *)android_media_ToneGenerator_release },
126    { "native_setup", "(II)V", (void *)android_media_ToneGenerator_native_setup },
127    { "native_finalize", "()V", (void *)android_media_ToneGenerator_native_finalize }
128};
129
130
131int register_android_media_ToneGenerator(JNIEnv *env) {
132    jclass clazz;
133
134    clazz = env->FindClass("android/media/ToneGenerator");
135    if (clazz == NULL) {
136        LOGE("Can't find %s", "android/media/ToneGenerator");
137        return -1;
138    }
139
140    fields.context = env->GetFieldID(clazz, "mNativeContext", "I");
141    if (fields.context == NULL) {
142        LOGE("Can't find ToneGenerator.mNativeContext");
143        return -1;
144    }
145    LOGV("register_android_media_ToneGenerator ToneGenerator fields.context: %x", (unsigned int)fields.context);
146
147    return AndroidRuntime::registerNativeMethods(env,
148            "android/media/ToneGenerator", gMethods, NELEM(gMethods));
149}
150