2011-10-05 3 views
2

우리는 현재 IOS 응용 프로그램에서 사용중인 C++로 작성된 일부 이미지 처리 소프트웨어를 보유하고 있습니다. Android NDK를 사용하여 만든 Android 프로젝트에이 이미지 처리 코드를 통합하려고합니다.Android ndk에서 .cpp 파일을 작성하려면 어떻게해야합니까?

나는 내 안드로이드 프로젝트와 SDK를 모두 설치하고 갈 준비가되어있다. 나 또한 ndk 설정을하고 갈 준비가되었습니다.

거의

void Java_com_mamlambo_sample_ndk1_AndroidNDK1SampleActivity_helloLog(JNIEnv * env, jobject this, jstring logThis) 

그것은, 내가 (최고입니다) this tutorial을 뚫고 다음되었고, 나는이 같은 함수 이름을했기 때문에 그가 native.c의 코드를 정의하는 부분에서 난처한 상황에 빠진있어 내가 기존의 모든 C++ 함수를 살펴보고 NDK가 코드를 인식 할 수 있도록 코드를 변경해야하는 것처럼 보입니다.

그래서 여기 내 질문은,

  1. 나는 그것이 NDK 빌더와 함께 작동하기 위해서는 기존 C++ 코드를 변경해야합니까? 그렇다면이 작업을 위해 코드에서 변경해야 할 사항은 무엇입니까?
  2. Android.mk 파일에 전체 디렉토리를 만들 수있는 방법이 있습니까? 파일이 너무 많아서 빌드하기 위해 모든 파일 하나 하나를 나열하고 싶지 않았습니다.

답변

4

1) 당신은 변경없이 빌드 할 수 있어야한다, 그러나 당신은 자바에서 호출하는 그 JNI 래퍼 기능의 일부를 작성해야합니다. 다행스럽게도 소수의 최상위 클래스를 보유하고 있으므로이를 래핑하면됩니다. 예 : 이 내 com.rarepebble.game3.Game 클래스에서 이러한 기능을 선언하고 응용 프로그램의 수명주기에 적절한 시간에 그들을 호출 할 수있는 자바 측면에서

// android.cpp 
#include "game.h" 
#include <jni.h> 

namespace { 
    Game* toGame(jlong gamePtr) { 
     return reinterpret_cast<Game*>(gamePtr); 
    } 
} 

extern "C" { 

    jlong Java_com_rarepebble_game3_Game_create(JNIEnv* env, jobject jobj) { 
     Game* g = new Game(); 
     return reinterpret_cast<jlong>(g); 
    } 

    void Java_com_rarepebble_game3_Game_destroy(JNIEnv* env, jobject jobj, jlong gamePtr) { 
     delete toGame(gamePtr); 
    } 

    void Java_com_rarepebble_game3_Game_update(JNIEnv* env, jobject jobj, jlong gamePtr, jboolean isTouching, jfloat touchX, jfloat touchY) { 
     toGame(gamePtr)->update(isTouching, touchX, touchY); 
    } 

    void Java_com_rarepebble_game3_Game_render(JNIEnv* env, jobject jobj, jlong gamePtr) { 
     toGame(gamePtr)->render(); 
    } 

    // ... and a few others. Only one class, though. 
} 

: 저는 여기에 게임 난 (천천히) 쓰기를 위해있는거야. (++ 자바 패키지, 클래스와 함수 이름이 C에서 함수 이름에 해당하는 방법을 참고) :

//Game.java 
package com.rarepebble.game3; 

// (imports) 

public class Game { 
    static { 
     System.loadLibrary("game3lib"); 
    } 
    // These are the functions you defined in C++ 
    private native long create(); 
    private native void destroy(long gamePtr);  
    private native void update(long gamePtr, boolean isTouched, float x, float y); 
    private native void render(long gamePtr); 

    private long gamePtr = 0; 

    Game() { 
     gamePtr = create(); 
    } 

    @Override 
    protected void finalize() throws Throwable { 
     if (gamePtr != 0) { 
      destroy(gamePtr); 
     } 
     super.finalize(); 
    } 

    // etc... 
} 

2) 당신은

LOCAL_SRC_FILES을 사용할 수 있습니다 : = $ (와일드 카드 * cpp를) $ (와일드 카드 하위 디렉토리 /*.cpp) #etc ...

편집 : 요청으로, 내 C++ 게임 클래스 헤더, "game.h"

// game.h 
#ifndef GAME_INCLUDED 
#define GAME_INCLUDED 

// Various game and standard library includes. 
// *NO* JNI or Android includes. 

namespace game { 

    class Game { 
    public: 
     Game(); 
     ~Game(); 

     void update(bool isTouching, float touchX, float touchY); 
     void render(); 

     // other funcs... 

    private: 
     // etc... 
    }; 

} 

#endif //def GAME_INCLUDED 

마찬가지로, "game.cpp"할 JNI를 포함시키지 마십시오.

+0

Martin이 도움을 주셔서 감사합니다. 그 예제는 아직 NDK 튜토리얼에서 본 일부 베스트입니다. 그래서 "Java_com_rarepebble_game3_Game_update"와 같은 함수는 C++ 함수의 이름이 필요합니다. "Java_packages_function"과 같은 것입니까? – Metropolis

+0

예, 정확하게. 'Java_' 이후의 모든 것은 자바처럼 보이기를 원하는 전체 패키지, 클래스, 함수 이름과 일치해야합니다. Java에서 클래스를 정의하고 그 안에'private native etc ... '선언을 추가해야합니다. (나는이 대답을 더 명확하게하기 위해 편집하고있다.) –

+0

굉장하다. 그래서 나는 기본적으로 모든 C++ 파일을 검토하고 "Java_package_function"과 일치하는 이름을 변경해야한다. 또한 헤더 파일을 ndk 빌드에 포함시켜야합니까? 또는 .cpp 파일 만? – Metropolis

관련 문제