81

I need to disable Home and other system buttons in my Android application.

Example: MX Player (see at Google Play) - you can press "lock" icon at player screen and it locks all hardware and software system buttons.

It works fine WITHOUT ROOTING.

I tested it on some devices with different Android versions. I tried to disassemble Kids Lock (plugin) but has no clue how it works yet.

I need same solution like the Kids Lock (plugin) for MX Player: - disable Home, Back and all other system buttons.

Any suggestions?

Bhavin Nattar
  • 3,105
  • 2
  • 18
  • 30
user1024
  • 1,052
  • 1
  • 9
  • 16
  • 1
    http://stackoverflow.com/questions/17183905/how-to-disable-home-button-in-android/17183967#17183967. you cannot disable home button. – Raghunandan Jul 09 '13 at 13:29
  • 2
    @user1024 have you found any solution for your question? As i also want to do same functionality as in MX Player. – Chirag Shah Sep 03 '13 at 12:28
  • 2
    The MX Player way is rather interesting. They are actually surpressing the navigation bar from returning. – nhaarman Jan 04 '14 at 14:23
  • Did you ever find a solution to this issue? I am also in need for figuring out how to disable these buttons. At the very least, how can I manage the multitasking button. – portfoliobuilder Nov 26 '14 at 19:08
  • You may check my answer, I think will help you achieve what you want http://stackoverflow.com/a/28603790/3300883 – Miguel Feb 19 '15 at 10:23

18 Answers18

92

First of, please think long and hard if you really want to disable the Home button or any other button for that matter (e.g. the Back button), this is not something that should be done (at least most of the times, this is a bad design). I can speak only for myself, but if I downloaded an app that doesn't let me do something like clicking an OS button, the next thing I do is uninstall that app and leave a very bad review. I also believe that your app will not be featured on the App Store.

Now...

Notice that MX Player is asking permission to draw on top of other applications:MX Player permissions
Since you cannot override the Home button on Android device (at least no in the latest OS versions). MX Player draws itself on top of your launcher when you "lock" the app and clicks on the Home button.
To see an example of that is a bit more simple and straight forward to understand, you can see the Facebook Messenger App.

As I was asked to provide some more info about MX Player Status Bar and Navigation Bar "overriding", I'm editing my answer to include these topics too.

First thing first, MX Player is using Immersive Full-Screen Mode (DevBytes Video) on KitKat.
Android 4.4 (API Level 19) introduces a new SYSTEM_UI_FLAG_IMMERSIVE flag for setSystemUiVisibility() that lets your app go truly "full screen." This flag, when combined with the SYSTEM_UI_FLAG_HIDE_NAVIGATION and SYSTEM_UI_FLAG_FULLSCREEN flags, hides the navigation and status bars and lets your app capture all touch events on the screen.

When immersive full-screen mode is enabled, your activity continues to receive all touch events. The user can reveal the system bars with an inward swipe along the region where the system bars normally appear. This clears the SYSTEM_UI_FLAG_HIDE_NAVIGATION flag (and the SYSTEM_UI_FLAG_FULLSCREEN flag, if applied) so the system bars become visible. This also triggers your View.OnSystemUiVisibilityChangeListener, if set. However, if you'd like the system bars to automatically hide again after a few moments, you can instead use the SYSTEM_UI_FLAG_IMMERSIVE_STICKY flag. Note that the "sticky" version of the flag doesn't trigger any listeners, as system bars temporarily shown in this mode are in a transient state.

Second: Hiding the Status Bar
Third: Hiding the Navigation Bar
Please note that although using immersive full screen is only for KitKat, hiding the Status Bar and Navigation Bar is not only for KitKat.

I don't have much to say about the 2nd and 3rd, You get the idea I believe, it's a fast read in any case. Just make sure you pay close attention to View.OnSystemUiVisibilityChangeListener.

I added a Gist that explains what I meant, it's not complete and needs some fixing but you'll get the idea. https://gist.github.com/Epsiloni/8303531

Good luck implementing this, and have fun!

Assaf Gamliel
  • 11,639
  • 4
  • 36
  • 56
  • 1
    So how does it hide the navigation bar and *prevents* it from popping back up again when the screen is touched? And when you do a swipe movement to get out of immersive mode, the navigation bar shows and hides again immediately. Furthermore, it is not possible to pull out the notification panel when locked, even when the 'immersive swipe' forces the statusbar to show. How does it do that? – nhaarman Jan 06 '14 at 08:37
  • Yeah, I didn't add that to my answer. I'll edit it now. – Assaf Gamliel Jan 06 '14 at 08:54
  • Added, let me know if there is anything else needed. – Assaf Gamliel Jan 06 '14 at 13:52
  • 2
    Okay, this helps a lot, but we're not there quite yet. I'm gonna place two comments, one for KitKat, one for Jelly Bean. For KitKat, using the flags `TYPE_SYSTEM_ALERT`, `SYSTEM_UI_FLAG_HIDE_NAVIGATION` and `SYSTEM_UI_FLAG_IMMERSIVE_STICKY`, there is no way of exiting the app. Both system bars stay hidden. ***Unless*** the power menu is opened. Then the navigation bar appears again, en the home button becomes functional. *MX Player* manages to keep the navigation bar hidden in that case. So for devices running KitKat, we still need to fix this. – nhaarman Jan 06 '14 at 22:24
  • 1
    For Jelly Bean (16+), `IMMERSIVE_STICKY` doesn't work. Therefore, it is possible to show the navigation bar (statusbar stays hidden because of `SYSTEM_ALERT`). We can detect this using the `OnSystemUiVisibilityChangeListener`, and enable the flags again. However, by some reason, this only works after a second or so, which is more than enough time to press the home button. MX Player does not use `IMMERSIVE STICKY` (bars appear on kitkat), but the bars disappear again before you know it. – nhaarman Jan 06 '14 at 22:32
  • 1
    Github Gist for KitKat: https://gist.github.com/nhaarman/8291022. Github Gist for Jelly Bean: https://gist.github.com/nhaarman/8291070. – nhaarman Jan 06 '14 at 22:37
  • As I've said, the immersive is for KitKat, and as you know it's no problem to do different things depending on the API level. Moreover, I do think they use the immersive mode and catch the event in the listener so they can hide it again immediately. I hope I will have time today to create a demo app for you. – Assaf Gamliel Jan 07 '14 at 06:47
  • Hey, I didn't have much time but I made something to explain the idea. I think that on KitKat it should work much better. There is some fine tuning to do, but I'm sorry I just didn't have enough time. https://gist.github.com/Epsiloni/8303531 – Assaf Gamliel Jan 07 '14 at 17:57
  • Thanks for the example! Unfortunately, this has the same effect as my KitKat example: the navbar is visible for too long, so it is possible to press one of the buttons. – nhaarman Jan 07 '14 at 18:59
  • Yeah, sorry @Niek I will not have more time to work on this before maybe the weekend. But I think you can take it from here. :) – Assaf Gamliel Jan 09 '14 at 11:55
  • That's no problem, you totally deserve the bounty for your effort. It's just these small issues that I just can't get right though. Really looking forward to the solution! – nhaarman Jan 09 '14 at 15:54
  • Thanks for superb explanation. I just had some issues working on it thought u might help. When I long press power button, navigation bar displays, but I want that not to be displayed, can u please help me over this. – Pankaj Kushwaha Mar 12 '14 at 11:30
  • 7
    FYI Assaf, some apps NEED to be locked. For example, kiosk-type apps where the owner is allowing temporary access to the piece of hardware. I'm creating a photo booth app right now, and I don't want the user (person getting their picture taken) to be able to do anything besides take a picture (and a few other things). The owner can unlock via a software button, but otherwise needs to be shut down. I'm sorry, but your "motherly advise" at the beginning of your answer rubbed me (and I'm sure others including the OP) the wrong way. Thank you for your answer though, I'll look into it. – ntgCleaner Feb 09 '16 at 00:33
  • 1
    if disabling the home button is not possible then how the screen lock apps disable the home button. so they must be set to home screen temporarily . right ? how to do that ? – Sagar Nayak May 21 '16 at 06:18
  • @SagarNayak did u get any solution for disabling home button? – Mubashshir Mar 10 '17 at 17:30
13

You can use Android-HomeKey-Locker to disable HOME KEY and other system keys(such as BACK KEY and MENU KEY)

Hope this will help you in your application. Thanks.

shaobin0604
  • 1,119
  • 12
  • 13
13

I followed the shaobin0604's answer and I finally managed to lock the HOME button, by adding:

<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />

to AndroidManifest.xml All you have to do is to copy HomeKeyLocker.java from shaobin's lib to your project and implement it like in shaobin's example. BTW: My AVD's Android version is Android 4.0.3.

Community
  • 1
  • 1
Lê Quang Duy
  • 717
  • 7
  • 14
  • Is it working in Android 4.4.4? Because, it tried it in my Moto G which is running in 4.4.4. It didn't work for me. – venkat Dec 01 '14 at 20:22
  • 1
    This library just disable hard home button.Moto G has soft home button so it does not work.. @ venkat – Harry Sharma Mar 02 '15 at 12:34
  • An alert is a good solution, if not the best, but keep in mind, that on some devices (Nexus 4 ie.) this won't work and the home button is still usable! – JacksOnF1re Sep 10 '15 at 15:42
12

You can disable the home and recents button Android 5.0, using the screen pinning feature mentioned here:

Android 5.0 introduces a new screen pinning API that lets you temporarily restrict users from leaving your task or being interrupted by notifications. This could be used, for example, if you are developing an education app to support high stakes assessment requirements on Android, or a single-purpose or kiosk application. Once your app activates screen pinning, users cannot see notifications, access other apps, or return to the home screen, until your app exits the mode.

You can lock the device down to be a kiosk. The navigation bar is not hidden, but the home and recents buttons can be either removed or disabled depending how you activate the mode. I wrote some information after testing this feature here.

Community
  • 1
  • 1
tagy22
  • 1,343
  • 17
  • 25
6

Just a guess, but I think with the SYSTEM_ALERT_WINDOW permission (displayed as "Draw over other apps", see here) it could be possible: display your app as a fullscreen, system alert type window. This way it will hide any other apps, even the homescreen so if you press Home, it won't really be disabled, just without any visible effect.

MX Player has this permission declared, and Facebook Messenger has it too for displaying "chat heads" over anything - so it might be the solution.

Update (added from my comments): Next, use SYSTEM_UI_FLAG_HIDE_NAVIGATION in conjunction with capturing touch events/using OnSystemUiVisibilityChangeListener to override the default behaviour (navbar appearing on touch). Also, since you said exit immersive gesture does not work, you could try setting SYSTEM_UI_FLAG_IMMERSIVE_STICKY too (with SYSTEM_UI_FLAG_FULLSCREEN and SYSTEM_UI_FLAG_HIDE_NAVIGATION).

Community
  • 1
  • 1
molnarm
  • 9,585
  • 2
  • 41
  • 55
  • A quick test -- adding the permission and calling `getWindow().addFlags(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);` -- shows that this will hide the statusbar (and the swipe down movement as used to exit immersive fullscreen doesn't work), but not the navigation bar. The buttons on this bar are still functional. – nhaarman Jan 05 '14 at 13:31
  • I don't have the SDK now but my next idea would be using SYSTEM_UI_FLAG_HIDE_NAVIGATION in conjunction with capturing touch events/using OnSystemUiVisibilityChangeListener to override the default behaviour (navbar appearing on touch). – molnarm Jan 05 '14 at 13:49
  • Also, since you said exit immersive gesture does not work, you could try setting SYSTEM_UI_FLAG_IMMERSIVE_STICKY too (with SYSTEM_UI_FLAG_FULLSCREEN and SYSTEM_UI_FLAG_HIDE_NAVIGATION). – molnarm Jan 05 '14 at 13:57
4

It used to be possible to disable the Home button, but now it isn't. It's due to malicious software that would trap the user.

You can see more detailes here: Disable Home button in Android 4.0+

Finally, the Back button can be disabled, as you can see in this other question: Disable back button in android

Community
  • 1
  • 1
Alvaro Cavalcanti
  • 2,600
  • 4
  • 16
  • 29
  • 2
    I just tested MX player as him said on a Nexus 4, and it really locked the home button =S – Pozzo Apps Jul 09 '13 at 13:37
  • back button is meant to work the way it is designed for. I would suggest against disabling back button. – Raghunandan Jul 09 '13 at 13:37
  • I see your point, @Raghunandan, and agree with it. Still, the Back button **can** be disabled, and I trust the developer to take this on account. If he manages to break its app's usability his users will let him know. – Alvaro Cavalcanti Jul 09 '13 at 13:43
  • try to install MX Player and test it. It disables HOME button. It disables all system buttons. MX Player uses Kids Lock (plugin). I tried to disassemble Kids Lock (plugin) but has no clue how it works yet. This is why i ask this question. – user1024 Jul 10 '13 at 12:58
  • 1
    Note that this answer does *not* provide the way mx player implements this feature. – nhaarman Jan 06 '14 at 08:32
3

If you target android 5.0 and above. You could use:

Activity.startLockTask()
SMR
  • 6,320
  • 2
  • 32
  • 55
lowolfne
  • 31
  • 2
  • This does not provide an answer to the question. To critique or request clarification from an author, leave a comment below their post - you can always comment on your own posts, and once you have sufficient [reputation](http://stackoverflow.com/help/whats-reputation) you will be able to [comment on any post](http://stackoverflow.com/help/privileges/comment). - [From Review](/review/low-quality-posts/11154332) – user1140237 Feb 05 '16 at 06:18
  • 1
    @user1140237 Why not? – Trilarion Feb 05 '16 at 10:50
  • 1
    This can only be done if you're a device administrator, which a normal app should not be – Ron Jul 17 '18 at 11:03
3

First create a method :

public void hideNavigationBar() {
        final View decorView = this.getWindow().getDecorView();
        final int uiOptions =
                View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
                        | View.SYSTEM_UI_FLAG_FULLSCREEN
                        | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
                        | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
                        | View.SYSTEM_UI_FLAG_LAYOUT_STABLE;

        Timer timer = new Timer();
        TimerTask task = new TimerTask() {
            @Override
            public void run() {
                YourActivityName.this.runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        decorView.setSystemUiVisibility(uiOptions);

                    }
                });
            }
        };

        timer.scheduleAtFixedRate(task, 1, 2);

    }

Then you call it on onCreate() method of your activity. Call it again on the onResume() method. Then you may add another method in your activity like this:

@Override
    public void onWindowFocusChanged(boolean hasFocus) {
        super.onWindowFocusChanged(hasFocus);
        hideNavigationBar();
    }

That will be it. Do remember it will lock the screen till the next time user touches the screen, in Timer class you can change the delay and it will allow you change things for that instance.Then it will lock the screen again.

2

I too was searching for this for sometime, and finally was able to do it as I needed, ie Navigation Bar is inaccessible, status bar is inaccessible, even if you long press power button, neither the power menu nor navigation buttons are shown. Thanks to @Assaf Gamliel , his answer took me to the right path. I followed this tutorial with some slight modifications. While specifying Type, I specified WindowManager.LayoutParams.TYPE_SYSTEM_ERROR instead of WindowManager.LayoutParams.TYPE_PHONE, else our "overlay" won't hide the system bars. You can play around with the Flags, Height, Width etc so that it'll behave as you want it to.

aravindsagar
  • 2,942
  • 1
  • 13
  • 18
1

i dont know how to diable home button. as long as my knowledge i got folowing link.

refer the link:- http://developer.android.com/reference/android/view/KeyEvent.html#KEYCODE_HOME

Key code constant: Home key. This key is handled by the framework and is never delivered to applications.

But,we can diable back button. hope following code helps you out.

@Override
public void onBackPressed() {
    //return nothing 
    return;
}
Harshal Benake
  • 2,378
  • 1
  • 21
  • 41
1

Refreshing an old topic. I was able to achieve that my activity does not fold when the home button (physical or virtual) is pressed. Here is my code for activity onCreate() method:

super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_alarm_screen);
        context = getApplicationContext();
        int windowType;
        if (Build.VERSION.SDK_INT>=26) windowType = WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY;
        else windowType = WindowManager.LayoutParams.TYPE_TOAST;
        final WindowManager.LayoutParams params = new WindowManager.LayoutParams(
                windowType,
                WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON
                        | WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED
                        | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON
                        | WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD
                        | WindowManager.LayoutParams.FLAG_FULLSCREEN,
                PixelFormat.TRANSLUCENT
        );
        wm = (WindowManager) getApplicationContext()
                .getSystemService(Context.WINDOW_SERVICE);

        mTopView = (ViewGroup) getLayoutInflater().inflate(R.layout.activity_alarm_screen, null);
        getWindow().setAttributes(params);
        //Set up your views here
        testView = mTopView.findViewById(R.id.test);
        wm.addView(mTopView, params);

On API 26 and abovem you need to get screen overlay permission from the user. Tested on Android 7 and 8.

Dmitri Borohhov
  • 1,243
  • 14
  • 28
0

You can't disable Home button from ICS onwords but can disable other buttons as follows

@Override
public boolean dispatchKeyEvent(KeyEvent keyEvent){
   return true;
}
CR Sardar
  • 757
  • 1
  • 10
  • 20
0

Post ICS i.e. Android 4+, the overriding of the HomeButton has been removed for security reasons, to enable the user exit in case the application turns out to be a malware.

Plus, it is not a really good practice to not let the user navigate away from the application. But, since you are making a lock screen application, what you can do is declare the activity as a Launcher , so that when the HomeButton is pressed it will simply restart your application and remain there itself (the users would notice nothing but a slight flicker in the screen).

You can go through the following link:

http://dharmendra4android.blogspot.in/2012/05/override-home-button-in-android.html

Rishabh Srivastava
  • 3,593
  • 2
  • 27
  • 55
0

Frankly it is not possible to disable the home button at least on new api levels , that is from 4.0 onwards. It is also not advisable to do that. You can however, block the back button by overriding the

public void onBackPressed() {
    // do not call super onBackPressed.
}

in order to override the home button, you could use a timer for example, and after every time check if the main screen is your screen or not, or your package is on top or not, (i am sure you will get links to it), and display your activity using the flag single_top.

That way , even if the home button is pressed you will be able to bring your app to the top.

Also make sure that the app has a way to exit, because such kind of apps can really be annoying and should never be developed.

Happy coding.

P.S: It is not possible to intercept the home event, when the home button is pressed.

You can use on attach to window methods and also keyguard methods, but not for api levels from 4.0 onwards.

  • The question is to specifically mimic the MX player functionality. – nhaarman Jan 08 '14 at 09:27
  • @NiekHaarman, not really. The question is to "disable Home, Back and all other system buttons." Specifically LIKE MX player, not MIMIC. – Adam Aug 05 '14 at 17:55
  • @adam no, the bounty I put on the question that triggered this answer asked specifically to mimic the MX player functionality. – nhaarman Aug 05 '14 at 17:58
0

Using rotation causes an exception, So I've fixed my activity using this:

HomeKeyLocker locker;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    requestWindowFeature(Window.FEATURE_NO_TITLE);
    setContentView(R.layout.activity_splash);

    locker = new HomeKeyLocker();               
    locker.lock(this);
}

@Override
protected void onSaveInstanceState(Bundle savedInstanceState) {
    super.onSaveInstanceState(savedInstanceState);
    locker.unlock();
}

@Override
public void onConfigurationChanged(Configuration config) {
    super.onConfigurationChanged(config);
    locker.lock(this);
}

You will need to use the @Lê Quang Duy suggestion.

Oscar Romero
  • 131
  • 2
  • 10
0

I'm working on an application that needs to lock the tablet just for application. First I put my app as MainLauncher, then I lock the taskbar using an AndroidView. Finally I block the tablet. It is not a feature that I indicate to use across multiple tablet models, since each device model has a feature to block it.

But overall it works for everyone. You can use the commands

Java.Lang.Runtime.GetRuntime().Exec("su -c sed -i '/VOLUME_UP/s/^# //g' /system/usr/keylayout/Generic.kl");

as an example to disable the buttons. But everything is based on changing the system files, inside the folder "/ system / usr / keylayout / ...". NOTE: Only works on rooted devices.

Another way I'm trying though still developing is using StreamWrite and StreamReader to access the RootDirectory and rewrite the whole file to disable and enable the buttons.

Hope this helps.

And any questions remain available.

0

For anyone looking to completely remove the soft-nav on a rooted (or custom ROM) android device, you can modify the build.prop text file within the system folder.

Set the following variable/value:

gemu.hw.mainkeys=1

This is what vendors use to disable the soft nav, when they have physical buttons.

Le-roy Staines
  • 1,909
  • 1
  • 19
  • 38
-3

Sorry for answering after 2-3 years. but you can hide activity of all system buttons. Just check this my answers How to disable virtual home button in any activity?.

Community
  • 1
  • 1
hardwork
  • 761
  • 7
  • 14