I have implemented a custom dialog for my application. I want to implement that when the user clicks outside the dialog, the dialog will be dismissed. What do I have to do for this?
14 Answers
You can use dialog.setCanceledOnTouchOutside(true);
which will close the dialog if you touch outside of the dialog.
Something like,
Dialog dialog = new Dialog(context)
dialog.setCanceledOnTouchOutside(true);
Or if your Dialog in non-model then,
1 - Set the flag-FLAG_NOT_TOUCH_MODAL
for your dialog's window attribute
Window window = this.getWindow();
window.setFlags(WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL,
WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL);
2 - Add another flag to windows properties,, FLAG_WATCH_OUTSIDE_TOUCH
- this one is for dialog to receive touch event outside its visible region.
3 - Override onTouchEvent()
of dialog and check for action type. if the action type is
'MotionEvent.ACTION_OUTSIDE
' means, user is interacting outside the dialog region. So in this case, you can dimiss your dialog or decide what you wanted to perform.
view plainprint?
public boolean onTouchEvent(MotionEvent event)
{
if(event.getAction() == MotionEvent.ACTION_OUTSIDE){
System.out.println("TOuch outside the dialog ******************** ");
this.dismiss();
}
return false;
}
For more info look at How to dismiss a custom dialog based on touch points? and How to dismiss your non-modal dialog, when touched outside dialog region

- 108,599
- 23
- 164
- 151
-
9This works great except that the activity underneath also reacts to the touch event. Is there some way to prevent this? – howettl Jan 31 '12 at 20:29
-
Yeah. window.setFlags(WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL, WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL); causes this problem. I've posted a solution below :) – Unknownweirdo Jun 26 '14 at 16:02
-
Is it possible to propagate 'on-touch-outside' events to the underneath activity using a non-custom dialog too? – j.c Jul 03 '14 at 10:37
-
2@howettl I have solved your problem in my solution **which I have posted below** where I don't need to set any flags to window. – Roman Nazarevych Jul 07 '14 at 13:57
-
@MuhammedRefaat - Please look at this thread https://groups.google.com/forum/#!topic/android-developers/VhaiIMl6E_w . They nicely described it. – user370305 Nov 26 '14 at 19:29
-
When dialog is dismiss i give slide down animation but when i opened dialog at and without closing dialog I am pressing minimize button of my phone at that time my dialog is auto matically dismiss and some effect with slide down which is not good so how to prevent to dismiss dialog at that time. Thanks in advance. – Ganpat Kaliya Dec 16 '16 at 12:35
Simply use
dialog.setCanceledOnTouchOutside(true);

- 1,291
- 1
- 13
- 15
-
4I know that this should the right answer, but doesn't work for me, and I just don't know why. – IgniteCoders Nov 19 '19 at 12:58
You can use this implementation of onTouchEvent. It prevent from reacting underneath activity to the touch event (as mentioned howettl).
@Override
public boolean onTouchEvent ( MotionEvent event ) {
// I only care if the event is an UP action
if ( event.getAction () == MotionEvent.ACTION_UP ) {
// create a rect for storing the window rect
Rect r = new Rect ( 0, 0, 0, 0 );
// retrieve the windows rect
this.getWindow ().getDecorView ().getHitRect ( r );
// check if the event position is inside the window rect
boolean intersects = r.contains ( (int) event.getX (), (int) event.getY () );
// if the event is not inside then we can close the activity
if ( !intersects ) {
// close the activity
this.finish ();
// notify that we consumed this event
return true;
}
}
// let the system handle the event
return super.onTouchEvent ( event );
}
Source: http://blog.twimager.com/2010/08/closing-activity-by-touching-outside.html

- 1,149
- 11
- 11
Or, if you're customizing the dialog using a theme defined in your style xml, put this line in your theme:
<item name="android:windowCloseOnTouchOutside">true</item>

- 4,506
- 6
- 31
- 38
-
This does not work for me on Samsung Galaxy Tab 2 WiFi. `dialog.setCanceledOnTouchOutside(true);` does work wonderfully. – doplumi May 03 '14 at 20:17
This method should completely avoid activities below the grey area retrieving click events.
Remove this line if you have it:
window.setFlags(WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL, WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL);
Put this on your activity created
getWindow().setFlags(LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH, LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH);
then override the touch event with this
@Override
public boolean onTouchEvent(MotionEvent ev)
{
if(MotionEvent.ACTION_DOWN == ev.getAction())
{
Rect dialogBounds = new Rect();
getWindow().getDecorView().getHitRect(dialogBounds);
if (!dialogBounds.contains((int) ev.getX(), (int) ev.getY())) {
// You have clicked the grey area
displayYourDialog();
return false; // stop activity closing
}
}
// Touch events inside are fine.
return super.onTouchEvent(ev);
}

- 485
- 6
- 16
You can try this :-
AlterDialog alterdialog;
alertDialog.setCanceledOnTouchOutside(true);
or
alertDialog.setCancelable(true);
And if you have a AlterDialog.Builder
Then you can try this:-
alertDialogBuilder.setCancelable(true);

- 1,353
- 2
- 18
- 35
This code is use for when use click on dialogbox that time hidesoftinput and when user click outer side of dialogbox that time both softinput and dialogbox are close.
dialog = new Dialog(act) {
@Override
public boolean onTouchEvent(MotionEvent event) {
// Tap anywhere to close dialog.
Rect dialogBounds = new Rect();
getWindow().getDecorView().getHitRect(dialogBounds);
if (!dialogBounds.contains((int) event.getX(),
(int) event.getY())) {
// You have clicked the grey area
InputMethodManager inputMethodManager = (InputMethodManager) act
.getSystemService(act.INPUT_METHOD_SERVICE);
inputMethodManager.hideSoftInputFromWindow(dialog
.getCurrentFocus().getWindowToken(), 0);
dialog.dismiss();
// stop activity closing
} else {
InputMethodManager inputMethodManager = (InputMethodManager) act
.getSystemService(act.INPUT_METHOD_SERVICE);
inputMethodManager.hideSoftInputFromWindow(dialog
.getCurrentFocus().getWindowToken(), 0);
}
return true;
}
};

- 9,564
- 146
- 81
- 122

- 532
- 4
- 14
Another solution, this code was taken from android source code of Window
You should just add these Two methods to your dialog source code.
@Override
public boolean onTouchEvent(MotionEvent event) {
if (isShowing() && (event.getAction() == MotionEvent.ACTION_DOWN
&& isOutOfBounds(getContext(), event) && getWindow().peekDecorView() != null)) {
hide();
}
return false;
}
private boolean isOutOfBounds(Context context, MotionEvent event) {
final int x = (int) event.getX();
final int y = (int) event.getY();
final int slop = ViewConfiguration.get(context).getScaledWindowTouchSlop();
final View decorView = getWindow().getDecorView();
return (x < -slop) || (y < -slop)
|| (x > (decorView.getWidth()+slop))
|| (y > (decorView.getHeight()+slop));
}
This solution doesnt have this problem :
This works great except that the activity underneath also reacts to the touch event. Is there some way to prevent this? – howettl

- 7,513
- 4
- 62
- 67
-
Cant you just make your dialog touch modal if you dont want other windows recieving events? – Nov 22 '19 at 08:54
Following has worked for me:
myDialog.setCanceledOnTouchOutside(true);

- 1,160
- 13
- 24
I tried some answers still I faced a problem like when I press outside the dialog dialog was hiding but a dimmed view was showing, and pressing again would go to the parent activity. But actually I wanted to go the parent activity after first click. So what I did was
dialog.setOnCancelListener(this);
and changed my activity to implement DialogInterface.OnCancelListener
with
@Override
public void onCancel(DialogInterface dialog) {
finish();
}
And boom, it worked.

- 365
- 3
- 16
You can make a background
occupying all the screen size transparent
and listen to the onClick
event to dismiss
it.

- 4,052
- 2
- 36
- 37

- 1,883
- 12
- 20
-
10Very bad answer! Of course this can be done, but please do it the right way! – j.c Jul 03 '14 at 10:31
Here is the code
dialog.getWindow().getDecorView().setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent ev) {
if(MotionEvent.ACTION_DOWN == ev.getAction())
{
Rect dialogBounds = new Rect();
dialog. getWindow().getDecorView().getHitRect(dialogBounds);
if (!dialogBounds.contains((int) ev.getX(), (int) ev.getY())) {
// You have clicked the grey area
UiUtils.hideKeyboard2(getActivity());
return false; // stop activity closing
}
}
getActivity().dispatchTouchEvent(ev);
return false;
}
});
Try this one . you can hide the keyboard when you touch outside

- 125
- 2
- 4