Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using FragmentManager and FragmentTransaction in a DialogFragment

The gist of the issue is this: I'm trying to Launch a DialogFragment from a FragmentActivity. This DialogFragment's view contains a FrameLayout which I would like to populate with a Fragment. Basically the FragmentActivity launches the DialogFragment, then the DialogFragment populates it's FrameLayout with a Fragment. I've scoured the internet for tutorials and I've pieced together something that (in my mind) should work. However, no matter what I try I continuously get errors. This is what I have so far:

This is my FragmentActivity's layout (file name is "activity_interact"):

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
style="@style/activity" >
<Button
        android:id="@+id/btnLaunchDialog"
        style="@style/btn" />

This is my DialogFragment's layout (file name is "dialog_overview"):

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
style="@style/dialog" >
<FrameLayout
    android:id="@+id/frameDisplay"
    style="@style/frame" />

This is my Fragment's layout (file name is "fragment_stats"):

<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
style="@style/table" >
<TableRow style="@style/table" >
    <TextView
        style="@style/display"
        android:gravity="right"
        android:text="@string/textStr" />
</TableRow>

Here is the java code for my FragmentActivity:

public class ActivityInteract extends FragmentActivity implements
    OnClickListener {

Button btnLaunchDialog;

@Override
protected void onCreate(Bundle b) {
    super.onCreate(b);
    setContentView(R.layout.activity_interact);
    btnLaunchDialog = (Button) findViewById(R.id.btnLaunchDialog);
    btnLaunchDialog.setOnClickListener(this);
}

public void onClick(View v) {
    switch (v.getId()) {
        case R.id.btnLaunchDialog:
            FragmentManager fm = getSupportFragmentManager();
            DialogOverview dialogOverview = new DialogOverview();
            dialogOverview.show(fm, "dialog_overview");
            break;
    }
}

}

Here is my DialogFragment's code:

public class DialogOverview extends DialogFragment implements OnClickListener {

public DialogOverview() {

}
@Override
public View onCreateView(LayoutInflater li, ViewGroup vg, Bundle b) {
    View view = li.inflate(R.layout.dialog_overview, vg);
    FragmentManager fm = getFragmentManager();
    FragmentTransaction ft = fm.beginTransaction();
    ft.add(R.id.frameDisplay, new FragmentStats());
    ft.commit();
    return view;
}

}

Here is my Fragment's code:

public class FragmentStats extends Fragment {

@Override
public View onCreateView(LayoutInflater li, ViewGroup vg, Bundle b) {
    View view = li.inflate(R.layout.fragment_stats, vg);
    return view;
}

}

And finally, here is the logcat error:

06-11 10:07:29.382: E/AndroidRuntime(30013): java.lang.IllegalArgumentException: No view found for id 0x7f060003 for fragment FragmentStats{4169c928 #1 id=0x7f060003}

I can see that it's saying that I don't have a view for the Fragment, but I do...(or do I?) I'm lost here, any help would be appreciated. Also, am I going about this the right way? Would it be more efficient to re-use a FragmentManager? (i.e. pass it from the FragmentActivity into the DialogFragment)

Update: I removed the code to load my Fragment into the DialogFragment and the DialogFragment displays without issue now. So obviously (as the logcat error suggests) there is something wrong with my Fragment itself...however, it matches examples that I've seen on the internet. Which is making me wonder: Is there an issue with nesting fragments in this way? A FragmentActivity displaying a DialogFragment that displays a Fragment makes me want to quip that "we can't go any deeper" but I don't know. Could I nest more fragments?

like image 498
user1449018 Avatar asked Jun 11 '12 14:06

user1449018


1 Answers

Actually, you CAN add nested fragment to a DialogFragment, BUT it cannot be based on a wrapped Dialog.

Instead of overriding onCreateDialog, inflate the View that contains the ViewGroup that will use the Fragment in onCreateView.

A consequence of this is that you cannot use a DialogFragment that wraps an AlertDialog - so if you want positive and negative buttons you need to manually create them in the content view.

Also, keep in mind that you cannot set the fragment in the XML. You need to declare the container view in XML and perform the fragment transaction programmatically.

public class MyDialogFragment extends DialogFragment { [...]

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {



    final View view = inflater.inflate(R.layout.dialog_layout, container);

    if (savedInstanceState == null) {
        final ChildFragment fragment = [...];
        getChildFragmentManager()
                .beginTransaction()
                .replace(R.id.fragment_container, fragment)
                .commit();
    }

    return view;
    }
}
like image 116
GaRRaPeTa Avatar answered Oct 15 '22 14:10

GaRRaPeTa