Show dialog alert from a non-activity class in android

后端 未结 7 1979
慢半拍i
慢半拍i 2020-12-06 02:37

I want to show an Alert Dialog via AlertDialogManager class to a non-activity class DeviceAdminReceiverSample\'s method onDisabl

相关标签:
7条回答
  • 2020-12-06 02:49

    The problem is 'You can show AlertDialogs from Activity only'. This is not an issue of context.

    Although this is not a good idea to show dialog from receiver (better is to use Notification), But if you want to do so you can create an Activity as dialog and show

    0 讨论(0)
  • 2020-12-06 02:54

    Just add this before your alertDialog.show();

    alertDialog.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
    

    or try following if above didn't work:

    alertDialog.getWindow().setType(WindowManager.LayoutParams.TYPE_APPLICATION_PANEL); 
    

    and use this permission:

    <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
    
    0 讨论(0)
  • 2020-12-06 02:57

    Here's what I made and use:

    myDialog.java:

    import android.app.Activity;
    import android.content.DialogInterface;
    import android.support.v7.app.AlertDialog;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.widget.TextView;
    
    public class myDialog {
        private Activity mActivity;
    
        myDialog(Activity a) {
            this.mActivity = a;
        }
    
        @SuppressWarnings("InflateParams")
        public void build(String title, String msg) {
            LayoutInflater inflater = LayoutInflater.from(mActivity);
            View subView = inflater.inflate(R.layout.dialog_box_text, null);
            final TextView message = subView.findViewById(R.id.message);
            message.setText(msg);
            AlertDialog.Builder builder = new AlertDialog.Builder(mActivity);
            builder.setTitle(title);
            builder.setView(subView);
            builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    dialog.dismiss();
                }
            });
            AlertDialog alert = builder.create();
            alert.show();
        }
    }
    

    dialog_box_text.xml:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:weightSum="1"
        android:orientation="horizontal">
        <TextView
            android:id="@+id/message"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="  "
            android:maxLines="1"
            android:textColor="@color/colorBlack" />
    </LinearLayout>
    

    Example code:

    public class MainActivity extends AppCompatActivity {
        private myDialog md;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            md = new myDialog(this);
    
    ...
    
            md.build("Title", "Message");
    
    0 讨论(0)
  • 2020-12-06 02:58

    You can define a public Context var in the MainActivity with initial value (this); As show here:

    public class MainActivity< alertdail > extends AppCompatActivity {
    
        ////////////////////////////////////////////////////////////
        //Public var refers to Main Activity:
        Context mainActivity = this;
        ////////////////////////////////////////////////////////////
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate ( savedInstanceState );
            setContentView ( R.layout.activity_main );
            AlertDialogManager alert  =new AlertDialogManager ();
    alert.showAlertDialog ( this,"Title","Message",true );
    
    
         }
    
    
        public class AlertDialogManager {
    
            public void showAlertDialog(Context context, String title, String message,
                                        Boolean status) {
                final AlertDialog alertDialog = new AlertDialog.Builder ( mainActivity ).create ( );
                alertDialog.setTitle ( title );
                alertDialog.setMessage ( message );
    
                if (status != null)
                    alertDialog.setButton ( "OK", new DialogInterface.OnClickListener ( ) {
                        public void onClick(DialogInterface dialog, int which) {
                            alertDialog.dismiss ( );
                        }
                    } );
                alertDialog.show ( );
            }
    
            public void showAlertDialog(Context c) {
            }
        }
    
    
        public class DeviceAdminReceiverSample extends DeviceAdminReceiver {
            static final String TAG = "DeviceAdminReceiver";
            AlertDialogManager alert = new AlertDialogManager ( );
    
            /**
             * Called when this application is no longer the device administrator.
             */
            @Override
            public void onDisabled(Context context, Intent intent) {
                super.onDisabled ( context, intent );
                Toast.makeText ( context, R.string.device_admin_disabled,
                        Toast.LENGTH_LONG ).show ( );
                // intent.putExtra("dialogMessage", "Device admin has been disabled");
                // intent.setClass(context, DialogActivity.class);
                // intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                // context.startActivity(intent);
                alert.showAlertDialog ( context, "Alert",
                        "Device admin has been disabled", true );
            }
        }
    }
    
    0 讨论(0)
  • 2020-12-06 03:02

    If you always want to get the current activity from anywhere in the app you can register an ActivityLifecycleCallback on your Application instance.

    Here's an untested implementation that might get you closer.

    public class TestApp extends Application {
    
        private WeakReference<Activity> mActivity = null;
    
        @Override
        public void onCreate() {
            super.onCreate();
            registerActivityLifecycleCallbacks(new ActivityLifecycleCallbacks() {
                @Override
                public void onActivityCreated(Activity activity, Bundle savedInstanceState) {
                    mActivity = new WeakReference<Activity>(activity);
                }
    
                @Override
                public void onActivityDestroyed(Activity activity) {
                    mActivity.clear();
                }
    
                /** Unused implementation **/
                @Override
                public void onActivityStarted(Activity activity) {}
    
                @Override
                public void onActivityResumed(Activity activity) {}
                @Override
                public void onActivityPaused(Activity activity) {}
    
                @Override
                public void onActivityStopped(Activity activity) {}
    
                @Override
                public void onActivitySaveInstanceState(Activity activity, Bundle outState) {}
            });
        }
    
        public Activity getCurrentActivity() {
            return mActivity.get();
        }
    
    }
    

    Then to use this throughout your app you would do some call like this ...

    Activity activity = ((TestApp)getApplicationContext()).getCurrentActivity(); 
    

    The advantages are you can always keep track of your current activity, however its a little too overkill for just handling Dialogs from within the Activity.

    0 讨论(0)
  • 2020-12-06 03:02

    Here's a quick method of properly performing this task that has done the job for me. Basically, what you would do is just create a new thread.


    1. Declare a public and static variable with a type that matches the original activity class.

      public static Activity1 activity;

    Activity1 is the class that the variable resides in.


    1. Upon calling the method onCreate();, set the variable to be equal to the context of the activity, otherwise known as this.

    Example:

    @Override 
        protected void onCreate( Bundle savedInstanceState ) {
        super.onCreate( savedInstanceState );
        activity = this;
    }
    


    3. Since we now have the context of the activity, we can use it to create a function with an alert dialog by using the runOnUiThread(); method inside of the function that will call the alert dialog. We would use a new Runnable() for the runnable action required for runOnUiThread();, and to have the alert dialog actually open, we would override the run function of a runnable item and place the code for the alert dialog in there.

    Example function:

    public static void exampleDialog(){
    Activity1.activity.runOnUiThread(new Runnable){
    @Override
        public void run(){
        //alert dialog code goes here.  For the context, use the activity variable from Activity1.
            }
        }
    }
    

    Hope this helps :)

    0 讨论(0)
提交回复
热议问题