I have a BaseActivity that opens Dialogs on it's code, but I can't change this class code, so I extended it, on my subclass, how to know when a Dialog is being open?
You could try to override onCreateDialog(). This passes a reference ID that is used when the Activity calls showDialog(id). If you just need to know if any Dialog is going to be shown, then I suppose you could call the super which will return the dialog that will be shown.
#Override
protected Dialog onCreateDialog(int id){
Dialog dialogToBeShown = super.onCreateDialog(id);
if(dialogToBeShown != null){
***Do whatever you have to with the dialog***
}
return dialogToBeShown;
}
EDIT:
This will only work the first time the Dialog is first created. You can do something similar with onPrepareDialog(int id, Dialog dialog, Bundle args) which is always called when a dialog is opening.
Dialog has an isShowing() method that should return if the dialog is currently visible. So you can use that to see if a dialog is showing and hide it with dismissDialog(). You just have to keep a reference to the Dialogs you create in onCreateDialog().
Related
I have a dialog with onDismiss handler:
public class TextReaderDialog extends DialogFragment {
...
public void onDismiss() {
}
I show this dialog and add some styles to a part of text from the fragment:
TextReaderDialog d = new TextReaderDialog();
d.show(getFragmentManager(), "sample");
Spannable spannableText = new SpannableString(tv.getText());
spannableText.setSpan(new BackgroundColorSpan(Color.LTGRAY), startOffset, startOffset + w.word.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
tv.setText(spannableText);
Whenever a dialog is dismissed, I want to remove styles from the text. How can I do that? What is the correct way to do that?
The simplest way to go about this would be to add a method to your fragment like so:
public void dismissStyles(){
//do your style dismissing here
}
Now, I assume in the dialog you are overriding DialogFragment.onDismiss(DialogInterface dialog). As long as that is the case, once you have completed that method, in your dialog's onDismiss function, you can do something to the effect of:
#Override
public void onDismiss(DialogInterface dialog) {
super.onDismiss(dialog);
MyFragment fragment = (MyFragment) activity
.getFragmentManager()
.findFragmentByID(R.id.containerOfYourFragment);
if(fragment != null){
fragment.dismissStyles();
}
}
Here, activity should be the current activity that your fragment and dialog are hosted in. You can pass this to the dialog in a constructor, or depending on where the dialog is located. You could also just pass the current fragment to the dialog in the constructor as well, and then it would simply be called by myFragment.dismissStyles();.
I have activity A which have a ListView with custom adapter.
The custom adapter (which aplies to each list view item) have a button which invokes a custom dialog.
in this dialog an action is being performed which in response i want to invoke UI update on activity A.
This is my activity on resume code:
#Override
public void onResume()
{
super.onResume();
setUI();
}
But when the i call
dialog.dismiss();
The dialog closes without the Activity A OnResume method benig invoked.
How can i catch and update the activity ui?
You can set an OnDismissListener to your dialog to achieve this:
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
builder.setOnDismissListener(listener);
...
Dialog dialog = builder.create();
You can let your Activity impelement DialogInterface.OnDismissListener and set them as the listener, so they get notified in the method onDismiss(DialogInterface dialog). In there, you can update your UI.
Actually its very easy - you can cast the Context inside the adapter to the calling containing activity:
ActivityName activity = (ActivityName )con;
activity.setUI();
I recently created a standard list DialogFragment to build an AlertDialog in my Activity as can be seen as the answer here:
What is the best way to recreate an AlertDialog when the screen is rotated?
Now I would like to re-use this fragment for 3 different "Pop Up" selection lists in my activity. For each of the three buttons I need to identify the calling button to determine what action to take when the item from the list is selected.
What is the best way to achieve this?
Currently I am thinking that I need to pass the calling button ID to the DialogFragment and then pass it back to the activity with the result when the dialog completes. Is there a better way to achieve this goal?
I think probably the easiest way to achieve what you're going for is to just have three different listeners inside of your DialogFragment, and then have setters for each. Then when you build the alert dialog as a fragment, you can define what the onClick method for each listener will do in the calling method. So something like this:
protected DialogInterface.OnClickListener mListener1;
protected DialogInterface.OnClickListener mListener2;
protected DialogInterface.OnClickListener mListener3;
public void setListener1(final YourDialogFragment.OnClickListener passedListener) {
mListener1 = new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
listener.onClick(getActivity(), dialog, which);
}
};
}
Then inside of the code that calls the DialogFragment, call something like:
// Building the Dialog Fragment here
YourDialogFragment.setListener1(new YourDialogFragment.OnClickListener() {
#Override
public void onClick(FragmentActivity activity, DialogInterface dialog, int which) {
// Whatever you want to happen when you click goes here
}
});
Ideally you make some sort of helper to just take parameters so you're not explicitly calling the set methods from an activity, but that's the gist of it.
I would recommend you to show the dialog fragment from another fragment where you can implement the onClick listeners and use setTargetFragment() to tell the dialog fragment that who it is working with..
dialogFragment.setTargetFragment(this, 0);
and use getTargetFragment() to get the parent fragment from DialogFragment.
here is some code snippets from sample programs..
// Retrieve the progress bar from the target's view hierarchy.
mProgressBar = (ProgressBar)getTargetFragment().getView().findViewById(
R.id.progress_horizontal);
And also you can use setRetainInstance(true) in onCreate() method to tell the framework to try to keep this fragment around during a configuration changes
See this answer to get more idea, hope this helps..
The following code displays date picker(as a popup dialog) when the user clicks on an EditText . showDialog() calls onCreateDialog(). The code works fine except when it is implemented in a Fragment. In Fragment , the dialog is not getting displayed.
edtTxtDateTime.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
showDialog(DATE_DIALOG_ID);
}
});
#Override
protected Dialog onCreateDialog(int id) {
switch (id) {
case DATE_DIALOG_ID:
// Displaying Date & Time as a dialog
}
return null;
}
I have tried to implement the same behaviour using DialogFragment API , but am unable to get the dialog when EditText is clicked.
Any suggestions / hints will be helpful.
Make sure you're using the correct context to display the dialog within your Fragment code. You need to be using the parent Activity's context. Within your Fragment, you can get the Activity (and correct context) by calling:
getActivity();
Our application uses nested dialogs, and we've been successfully making one dialog that sits on top of another dialog by constructing it from the first dialog's getContext() method. So:
Activity:
//...
Dialog1 dialog = new Dialog1(this);
dialog.show();
//...
Dialog1:
//...
Dialog1(Context context) {
super(context);
//etc.
}
public void onSomeCondition() {
Dialog2 dialog2 = new Dialog2(getContext());
dialog2.show();
//etc.
}
However, there is a circumstance where we want to launch Dialog2 directly from the Activity while Dialog1 is still visible. So we put this method in the Activity:
public void onSomeOtherCondition() {
Dialog2 dialog = new Dialog2(this); //crunch
dialog.show();
//etc.
}
The window manager doesn't like this at all. So is it that getContext() is actually NOT exactly the same as the ContextWrapper-ness in the Activity? If so exactly how does this secondary context differ from the primary one, and if (for example) you passed back getContext() from a dialog to a calling Activity, would that create the same leak risk as holding on to a Context reference elsewhere can do?
If it's not the context, what's causing the problem?
I suspect the problem with starting Dialog 2 from Activity 1 when Dialog 1 is visible is because Dialog 1 (not Activity 1) is on the top of the activity stack. I'm by no means an expert, but I suspect that only the Activity at the top of the Activity stack can start new Activities.
I'm not entirely certain if the contexts are different (it would appear they are), but I suspect the problem is that you are not dismissing Dialog1 before attempting to start Dialog2 from your Activity. The WindowManager is probably angry because you are attempting to start a dialog on top of your Activity, but Dialog1 is already there.
Long story short, I think you need:
public void onSomeOtherCondition() {
this.dismiss();
mActivity.onSomeOtherCondition(); //we have a reference to the activity
}
EDIT
The solution I proposed in the comments is to pass Dialog1's context to mActivity.onSomeOtherCondition so that you can create Dialog2 with the context that is at the top of the stack.