| // Copyright (c) 2013 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #ifndef BASE_ANDROID_JNI_GENERATOR_SAMPLE_FOR_TESTS_H_ |
| #define BASE_ANDROID_JNI_GENERATOR_SAMPLE_FOR_TESTS_H_ |
| |
| #include <jni.h> |
| #include <map> |
| #include <string> |
| |
| #include "base/android/jni_android.h" |
| #include "base/basictypes.h" |
| |
| namespace base { |
| namespace android { |
| |
| // This file is used to: |
| // - document the best practices and guidelines on JNI usage. |
| // - ensure sample_for_tests_jni.h compiles and the functions declared in it |
| // as expected. |
| // |
| // Methods are called directly from Java (except RegisterJNI). More |
| // documentation in SampleForTests.java |
| // |
| // For C++ to access Java methods: |
| // - GYP Build must be configured to generate bindings: |
| // # ... |
| // 'targets': [ |
| // { |
| // # An example target that will rely on JNI: |
| // 'target_name': 'foo', |
| // 'type': '<(component)', |
| // # ... normal sources, defines, deps. |
| // # For each jni generated .java -> .h header file in foo_jni_headers |
| // # target there will be a single .cc file here that includes it. |
| // # |
| // # Add deps for JNI: |
| // 'conditions': [ |
| // ['OS == "android"', { |
| // 'dependencies': [ |
| // 'foo_java', |
| // 'foo_jni_headers', |
| // ], |
| // }], |
| // ], |
| // }, |
| // ], |
| // # ... |
| // # Create targets for JNI: |
| // 'conditions': [ |
| // ['OS == "android"', { |
| // 'targets': [ |
| // { |
| // 'target_name': 'foo_jni_headers', |
| // 'type': 'none', |
| // 'sources': [ |
| // 'java/src/org/chromium/example/jni_generator/SampleForTests.java', |
| // ], |
| // 'variables': { |
| // 'jni_gen_package': 'foo', |
| // }, |
| // 'includes': [ '../../../build/jni_generator.gypi' ], |
| // }, |
| // { |
| // 'target_name': 'foo_java', |
| // 'type': 'none', |
| // 'dependencies': [ |
| // '../../../base/base.gyp:base', |
| // ], |
| // 'variables': { |
| // 'java_in_dir': 'java', |
| // }, |
| // 'includes': [ '../../../build/java.gypi' ], |
| // }, |
| // ], |
| // }], |
| // ], |
| // |
| // - GN Build must be configured to generate bindings: |
| // # Add import at top of file: |
| // if (is_android) { |
| // import("//build/config/android/rules.gni") # For generate_jni(). |
| // } |
| // # ... |
| // # An example target that will rely on JNI: |
| // component("foo") { |
| // # ... normal sources, defines, deps. |
| // # For each jni generated .java -> .h header file in jni_headers |
| // # target there will be a single .cc file here that includes it. |
| // # |
| // # Add a dep for JNI: |
| // if (is_android) { |
| // deps += [ ":foo_jni" ] |
| // } |
| // } |
| // # ... |
| // # Create target for JNI: |
| // if (is_android) { |
| // generate_jni("jni_headers") { |
| // sources = [ |
| // "java/src/org/chromium/example/jni_generator/SampleForTests.java", |
| // ] |
| // jni_package = "foo" |
| // } |
| // android_library("java") { |
| // java_files = [ |
| // "java/src/org/chromium/example/jni_generator/SampleForTests.java", |
| // "java/src/org/chromium/example/jni_generator/NonJniFile.java", |
| // ] |
| // } |
| // } |
| // |
| // For C++ methods to be exposed to Java: |
| // - The generated RegisterNativesImpl method must be called, this is typically |
| // done by having a static RegisterJNI method in the C++ class. |
| // - The RegisterJNI method is added to a module's collection of register |
| // methods, such as: example_jni_registrar.h/cc files which call |
| // base::android::RegisterNativeMethods. |
| // An example_jni_registstrar.cc: |
| // |
| // namespace { |
| // const base::android::RegistrationMethod kRegisteredMethods[] = { |
| // // Initial string is for debugging only. |
| // { "ExampleName", base::ExampleNameAndroid::RegisterJNI }, |
| // { "ExampleName2", base::ExampleName2Android::RegisterJNI }, |
| // }; |
| // } // namespace |
| // |
| // bool RegisterModuleNameJni(JNIEnv* env) { |
| // return RegisterNativeMethods(env, kRegisteredMethods, |
| // arraysize(kRegisteredMethods)); |
| // } |
| // |
| // - Each module's RegisterModuleNameJni must be called by a larger module, |
| // or application during startup. |
| // |
| class CPPClass { |
| public: |
| CPPClass(); |
| ~CPPClass(); |
| |
| // Register C++ methods exposed to Java using JNI. |
| static bool RegisterJNI(JNIEnv* env); |
| |
| // Java @CalledByNative methods implicitly available to C++ via the _jni.h |
| // file included in the .cc file. |
| |
| class InnerClass { |
| public: |
| jdouble MethodOtherP0(JNIEnv* env, jobject caller); |
| }; |
| |
| void Destroy(JNIEnv* env, jobject caller); |
| |
| jint Method(JNIEnv* env, jobject caller); |
| |
| void AddStructB(JNIEnv* env, jobject caller, jobject structb); |
| |
| void IterateAndDoSomethingWithStructB(JNIEnv* env, jobject caller); |
| |
| base::android::ScopedJavaLocalRef<jstring> ReturnAString( |
| JNIEnv* env, jobject caller); |
| |
| private: |
| std::map<long, std::string> map_; |
| |
| DISALLOW_COPY_AND_ASSIGN(CPPClass); |
| }; |
| |
| } // namespace android |
| } // namespace base |
| |
| #endif // BASE_ANDROID_JNI_GENERATOR_SAMPLE_FOR_TESTS_H_ |