FileDocCategorySizeDatePackage
NativeActivity.javaAPI DocAndroid 5.1 API11851Thu Mar 12 22:22:10 GMT 2015android.app

NativeActivity

public class NativeActivity extends Activity implements SurfaceHolder.Callback2, android.view.ViewTreeObserver.OnGlobalLayoutListener, InputQueue.Callback
Convenience for implementing an activity that will be implemented purely in native code. That is, a game (or game-like thing). There is no need to derive from this class; you can simply declare it in your manifest, and use the NDK APIs from there.

A typical manifest would look like: {@sample development/ndk/platforms/android-9/samples/native-activity/AndroidManifest.xml manifest}

A very simple example of native code that is run by NativeActivity follows. This reads input events from the user and uses OpenGLES to draw into the native activity's window. {@sample development/ndk/platforms/android-9/samples/native-activity/jni/main.c all}

Fields Summary
public static final String
META_DATA_LIB_NAME
Optional meta-that can be in the manifest for this component, specifying the name of the native shared library to load. If not specified, "main" is used.
public static final String
META_DATA_FUNC_NAME
Optional meta-that can be in the manifest for this component, specifying the name of the main entry point for this native activity in the {@link #META_DATA_LIB_NAME} native code. If not specified, "ANativeActivity_onCreate" is used.
private static final String
KEY_NATIVE_SAVED_STATE
private NativeContentView
mNativeContentView
private android.view.inputmethod.InputMethodManager
mIMM
private long
mNativeHandle
private android.view.InputQueue
mCurInputQueue
private android.view.SurfaceHolder
mCurSurfaceHolder
final int[]
mLocation
int
mLastContentX
int
mLastContentY
int
mLastContentWidth
int
mLastContentHeight
private boolean
mDispatchingUnhandledKey
private boolean
mDestroyed
Constructors Summary
Methods Summary
private static java.lang.StringgetAbsolutePath(java.io.File file)

        return (file != null) ? file.getAbsolutePath() : null;
    
voidhideIme(int mode)

        mIMM.hideSoftInputFromWindow(mNativeContentView.getWindowToken(), mode);
    
private native longloadNativeCode(java.lang.String path, java.lang.String funcname, android.os.MessageQueue queue, java.lang.String internalDataPath, java.lang.String obbPath, java.lang.String externalDataPath, int sdkVersion, android.content.res.AssetManager assetMgr, byte[] savedState)

public voidonConfigurationChanged(android.content.res.Configuration newConfig)

        super.onConfigurationChanged(newConfig);
        if (!mDestroyed) {
            onConfigurationChangedNative(mNativeHandle);
        }
    
private native voidonConfigurationChangedNative(long handle)

private native voidonContentRectChangedNative(long handle, int x, int y, int w, int h)

protected voidonCreate(android.os.Bundle savedInstanceState)

        String libname = "main";
        String funcname = "ANativeActivity_onCreate";
        ActivityInfo ai;
        
        mIMM = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);

        getWindow().takeSurface(this);
        getWindow().takeInputQueue(this);
        getWindow().setFormat(PixelFormat.RGB_565);
        getWindow().setSoftInputMode(
                WindowManager.LayoutParams.SOFT_INPUT_STATE_UNSPECIFIED
                | WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE);

        mNativeContentView = new NativeContentView(this);
        mNativeContentView.mActivity = this;
        setContentView(mNativeContentView);
        mNativeContentView.requestFocus();
        mNativeContentView.getViewTreeObserver().addOnGlobalLayoutListener(this);
        
        try {
            ai = getPackageManager().getActivityInfo(
                    getIntent().getComponent(), PackageManager.GET_META_DATA);
            if (ai.metaData != null) {
                String ln = ai.metaData.getString(META_DATA_LIB_NAME);
                if (ln != null) libname = ln;
                ln = ai.metaData.getString(META_DATA_FUNC_NAME);
                if (ln != null) funcname = ln;
            }
        } catch (PackageManager.NameNotFoundException e) {
            throw new RuntimeException("Error getting activity info", e);
        }
        
        String path = null;
        
        File libraryFile = new File(ai.applicationInfo.nativeLibraryDir,
                System.mapLibraryName(libname));
        if (libraryFile.exists()) {
            path = libraryFile.getPath();
        }
        
        if (path == null) {
            throw new IllegalArgumentException("Unable to find native library: " + libname);
        }
        
        byte[] nativeSavedState = savedInstanceState != null
                ? savedInstanceState.getByteArray(KEY_NATIVE_SAVED_STATE) : null;

        mNativeHandle = loadNativeCode(path, funcname, Looper.myQueue(),
                getAbsolutePath(getFilesDir()), getAbsolutePath(getObbDir()),
                getAbsolutePath(getExternalFilesDir(null)),
                Build.VERSION.SDK_INT, getAssets(), nativeSavedState);

        if (mNativeHandle == 0) {
            throw new IllegalArgumentException("Unable to load native library: " + path);
        }
        super.onCreate(savedInstanceState);
    
protected voidonDestroy()

        mDestroyed = true;
        if (mCurSurfaceHolder != null) {
            onSurfaceDestroyedNative(mNativeHandle);
            mCurSurfaceHolder = null;
        }
        if (mCurInputQueue != null) {
            onInputQueueDestroyedNative(mNativeHandle, mCurInputQueue.getNativePtr());
            mCurInputQueue = null;
        }
        unloadNativeCode(mNativeHandle);
        super.onDestroy();
    
public voidonGlobalLayout()

        mNativeContentView.getLocationInWindow(mLocation);
        int w = mNativeContentView.getWidth();
        int h = mNativeContentView.getHeight();
        if (mLocation[0] != mLastContentX || mLocation[1] != mLastContentY
                || w != mLastContentWidth || h != mLastContentHeight) {
            mLastContentX = mLocation[0];
            mLastContentY = mLocation[1];
            mLastContentWidth = w;
            mLastContentHeight = h;
            if (!mDestroyed) {
                onContentRectChangedNative(mNativeHandle, mLastContentX,
                        mLastContentY, mLastContentWidth, mLastContentHeight);
            }
        }
    
public voidonInputQueueCreated(android.view.InputQueue queue)

        if (!mDestroyed) {
            mCurInputQueue = queue;
            onInputQueueCreatedNative(mNativeHandle, queue.getNativePtr());
        }
    
private native voidonInputQueueCreatedNative(long handle, long queuePtr)

public voidonInputQueueDestroyed(android.view.InputQueue queue)

        if (!mDestroyed) {
            onInputQueueDestroyedNative(mNativeHandle, queue.getNativePtr());
            mCurInputQueue = null;
        }
    
private native voidonInputQueueDestroyedNative(long handle, long queuePtr)

public voidonLowMemory()

        super.onLowMemory();
        if (!mDestroyed) {
            onLowMemoryNative(mNativeHandle);
        }
    
private native voidonLowMemoryNative(long handle)

protected voidonPause()

        super.onPause();
        onPauseNative(mNativeHandle);
    
private native voidonPauseNative(long handle)

protected voidonResume()

        super.onResume();
        onResumeNative(mNativeHandle);
    
private native voidonResumeNative(long handle)

protected voidonSaveInstanceState(android.os.Bundle outState)

        super.onSaveInstanceState(outState);
        byte[] state = onSaveInstanceStateNative(mNativeHandle);
        if (state != null) {
            outState.putByteArray(KEY_NATIVE_SAVED_STATE, state);
        }
    
private native byte[]onSaveInstanceStateNative(long handle)

protected voidonStart()

        super.onStart();
        onStartNative(mNativeHandle);
    
private native voidonStartNative(long handle)

protected voidonStop()

        super.onStop();
        onStopNative(mNativeHandle);
    
private native voidonStopNative(long handle)

private native voidonSurfaceChangedNative(long handle, android.view.Surface surface, int format, int width, int height)

private native voidonSurfaceCreatedNative(long handle, android.view.Surface surface)

private native voidonSurfaceDestroyedNative(long handle)

private native voidonSurfaceRedrawNeededNative(long handle, android.view.Surface surface)

public voidonWindowFocusChanged(boolean hasFocus)

        super.onWindowFocusChanged(hasFocus);
        if (!mDestroyed) {
            onWindowFocusChangedNative(mNativeHandle, hasFocus);
        }
    
private native voidonWindowFocusChangedNative(long handle, boolean focused)

voidsetWindowFlags(int flags, int mask)

        getWindow().setFlags(flags, mask);
    
voidsetWindowFormat(int format)

        getWindow().setFormat(format);
    
voidshowIme(int mode)

        mIMM.showSoftInput(mNativeContentView, mode);
    
public voidsurfaceChanged(android.view.SurfaceHolder holder, int format, int width, int height)

        if (!mDestroyed) {
            mCurSurfaceHolder = holder;
            onSurfaceChangedNative(mNativeHandle, holder.getSurface(), format, width, height);
        }
    
public voidsurfaceCreated(android.view.SurfaceHolder holder)

        if (!mDestroyed) {
            mCurSurfaceHolder = holder;
            onSurfaceCreatedNative(mNativeHandle, holder.getSurface());
        }
    
public voidsurfaceDestroyed(android.view.SurfaceHolder holder)

        mCurSurfaceHolder = null;
        if (!mDestroyed) {
            onSurfaceDestroyedNative(mNativeHandle);
        }
    
public voidsurfaceRedrawNeeded(android.view.SurfaceHolder holder)

        if (!mDestroyed) {
            mCurSurfaceHolder = holder;
            onSurfaceRedrawNeededNative(mNativeHandle, holder.getSurface());
        }
    
private native voidunloadNativeCode(long handle)