Skip to content

Instantly share code, notes, and snippets.

@zeh
Last active August 6, 2020 07:55
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save zeh/f0462204dd6c08cb9821 to your computer and use it in GitHub Desktop.
Save zeh/f0462204dd6c08cb9821 to your computer and use it in GitHub Desktop.
// On Android, every Activity can respond differently to the software keyboard: scrolling to fit, just resizing, overlaying, etc.
// http://developer.android.com/training/keyboard-input/visibility.html
// The C# code below adjusts Unity's current Android Activity to make the keyboard overlay the game, with no size adjustments.
// It is equivalent to calling getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING) in Java.
// Helped method needed for proper UI thread calls (required when accessing context views)
private static void runOnAndroidUiThread(Action target) {
using (var unityPlayer = new AndroidJavaClass("com.unity3d.player.UnityPlayer")) {
using (var activity = unityPlayer.GetStatic("currentActivity")) {
activity.Call("runOnUiThread", new AndroidJavaRunnable(target));
}
}
}
// Wrap it
private static void setSoftInputModeOverlay() {
runOnAndroidUiThread(setSoftInputModeOverlayInThread);
}
// Actual logic
private static void setSoftInputModeOverlayInThread() {
int SOFT_INPUT_ADJUST_NOTHING = 0x00000030; // WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING
using (var unityPlayer = new AndroidJavaClass("com.unity3d.player.UnityPlayer")) {
using (var activity = unityPlayer.GetStatic("currentActivity")) {
using (var window = activity.Call("getWindow")) {
window.Call("setSoftInputMode", SOFT_INPUT_ADJUST_NOTHING);
}
}
}
}
// Finally, call it
setSoftInputModeOverlay();
@braindroplabs
Copy link

I tested virtually the same thing (inferring from your ApplicationChrome class) to no avail with the call:

window.Call("setSoftInputMode", 0x00000030);

I figured I may have implemented it wrong and just tried your sample above. I had to update two things due to errors from:

...
using (var activity = unityPlayer.GetStatic("currentActivity")) {
using (var window = activity.Call("getWindow")) {
...

to

...
using (var activity = unityPlayer.GetStatic<AndroidJavaObject>("currentActivity")) {
using (var window = activity.Call<AndroidJavaObject>("getWindow")) {
...

Unfortunately, it still doesn't work. If I don't use the call ApplicationChrome.statusBarState = ApplicationChrome.States.Visible;, then the soft keyboard simply overlays the game screen as desired. However if I make that call, then the keyboard forces the rest of the window to resize as opposed to overlaying. Any other thoughts? Or can you confirm on your end when you have access to Unity?

As a side, do you know how edit the AndroidManifest.xml in Unity 5.0+? It seems like the AndroidManifest.xml is more of a black box in Unity 5.0+.

@zeh
Copy link
Author

zeh commented Feb 14, 2016

Thanks man. You're right - Unity 5 forces those generic types. Forgot about those.

I'll test out alternatives when I have access to Unity later today.

To answer the question.. I haven't tried manifest editing recently. I know one alternative is exporting it as a project (rather than an apk), editing the project, and recompiling. But it's really really cumbersome and I'm not 100% it still works with Unity 5.

@zeh
Copy link
Author

zeh commented Feb 17, 2016

Ah, I think I understand the problem better now.

When you said it was resizing, I assumed the whole game canvas was resizing to fit the smaller area provided by the keyboard. That's what the code snippet (instructing it to overlay) was set to fix. But when I tested it seemed to be fine:

But now that I've played around with it, I believe I misunderstood you. I think I know what you mean: when you hide the navigation completely, AND open the keyboard, it does force a small resize.

It works like this: when the software keyboard is shown, the navigation bar is always enforced. It is used to close the keyboard, I suppose. But it also means that if the navigation bar is set to "invisible", then instead of just showing it above the contenbt, it forces it to completely visible, thus resizing.

There's two ways to fix it.

  1. Set the navigation bar to "translucent over content" or "visible over content" instead. This makes the keyboard display without resizing. When the keyboard closes, you need to set it to invisible again.

Or

  1. Naturally listen to events and circumvent the system to always reset that flag. Haven't done this yet, but there's a discussion about this here at StackOverflow.

Let me see if there's a quick/easy fix that makes sense to add to this library.

Edit: nevermind that. I finally got it the way I originally thought you described. It's the full software resize. Sorry about the misunderstanding. Let me investigate it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment