2017-06-07 53 views
0

我正在使用自然包含片段的Viewpager。 里面我有一个子片段(子片段)的片段之一 每个孩子片段包含一个按钮,调用以下替换子片段本身从儿童片段本身动态替换子片段

FragmentManager manager = getChildFragmentManager(); 
FragmentTransaction transaction = manager.beginTransaction(); 
transaction.replace(R.id.containerProfileDetails, new ProfileDetailsAddressFragment()); 
transaction.commit(); 

只是为了让更多的视觉:

1)是父片段

2)是子片段。 我需要按子片段本身内部的按钮替换子片段

┌--------┐ 
| 1 | 
| ┌-----┐| 
| | 2 || 
| |  || 
| └-----┘| 
└--------┘ 

注:我知道这是可能取代使用这种方法的片段,但是,它似乎是不可能做这与随着错误抛出的子片段一起。

java.lang.IllegalArgumentException: No view found for id 0x7f0f0104 (com.example.app:id/containerProfileDetails) for fragment ProfileDetailsAddressFragment

更新

父片段XML:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
xmlns:tools="http://schemas.android.com/tools" 
android:layout_width="match_parent" 
android:layout_height="match_parent" 
android:orientation="vertical" 
android:gravity="center" 
tools:context="com.example.app.fragments.ProfileDetailsFragment"> 

<TextView 
    android:id="@+id/lbl_page" 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:gravity="center" 
    android:textSize="42sp" 
    tools:text="2" 
    android:visibility="gone"/> 

<FrameLayout 
    android:id="@+id/containerProfileDetails" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    ></FrameLayout> 
</LinearLayout> 

儿童片段XML:

<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" 
xmlns:tools="http://schemas.android.com/tools" 
android:layout_width="match_parent" 
android:layout_height="match_parent" 
tools:context="com.example.app.fragments.ProfileDetailsUserFragment"> 

<TextView 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:text="Fragment Profile User Details" /> 

<Button 
    android:id="@+id/btnProfileDetailsUserNext" 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:layout_gravity="bottom|center"/> 

</FrameLayout> 

父片段的Java:

public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { 
    View view = inflater.inflate(R.layout.fragment_profile_details, container, false); 
    lblPage = (TextView) view.findViewById(R.id.lbl_page); 

    FragmentManager manager = getChildFragmentManager(); 
    FragmentTransaction transaction = manager.beginTransaction(); 
    transaction.add(R.id.containerProfileDetails, new ProfileDetailsUserFragment()); 
    transaction.commit(); 
    return view; 
} 

儿童片段的Java:

public View onCreateView(LayoutInflater inflater, ViewGroup container, 
         Bundle savedInstanceState) { 
    // Inflate the layout for this fragment 
    View v = inflater.inflate(R.layout.fragment_profile_details_user, container, false); 

    Button _btnProfileDetailsUserNext = (Button) v.findViewById(R.id.btnProfileDetailsUserNext); 
    _btnProfileDetailsUserNext.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      FragmentManager manager = getChildFragmentManager(); 
      FragmentTransaction transaction = manager.beginTransaction(); 
      transaction.replace(R.id.containerProfileDetails, new ProfileDetailsAddressFragment()); 
      transaction.commit(); 
     } 
    }); 
    return v; 
} 
+0

通常视图寻呼机没有容器,你传递的id是R.id.containerProfileDetails? –

+0

@AniruddhParihar我使用'transaction.add(R.id。containerProfileDetails,new firstchildfragment());'添加父片段中的第一个子片段 – Poorya

+0

你能分享你的xml布局代码吗? –

回答

2

更换你的父母片段和子片段代码下面

Parent_Fragment.Java

public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { 
    View view = inflater.inflate(R.layout.fragment_profile_details, container, false); 
    lblPage = (TextView) view.findViewById(R.id.lbl_page); 

    FragmentManager manager = getChildFragmentManager(); 
    FragmentTransaction transaction = manager.beginTransaction(); 
    transaction.add(R.id.containerProfileDetails, new ProfileDetailsUserFragment()); 
    transaction.commit(); 
    return view; 
} 

Child_Fragment.Java

public View onCreateView(LayoutInflater inflater, ViewGroup container, 
         Bundle savedInstanceState) { 
    // Inflate the layout for this fragment 
    View v = inflater.inflate(R.layout.fragment_profile_details_user, container, false); 

    Button _btnProfileDetailsUserNext = (Button) v.findViewById(R.id.btnProfileDetailsUserNext); 
    _btnProfileDetailsUserNext.setOnClickListener(new View.OnClickListener() { 
     @Override 
     public void onClick(View v) { 
      FragmentManager manager = getFragmentManager(); 
      FragmentTransaction transaction = manager.beginTransaction(); 
      transaction.replace(R.id.containerProfileDetails, new ProfileDetailsAddressFragment()); 
      transaction.commit(); 
     } 
    }); 
    return v; 
} 

我没有测试过代码,它可能会产生一些编译错误,但方法是正确的实现。

+0

,但是创建一个'public static FragmentManager manager'是个好主意吗?创建回调并从父代片段中替换子片段不是更好吗? – Poorya

+0

我认为getFragmentManager()也将代替getChildFragmentManager()在Child_Fragment.java 尝试它,如果它的作品,那么我也更新我的答案。 –

+0

@ Aniruddh Parihar你其实是对的!我不明白为什么,但它的工作。你有这方面的任何参考?我希望更多的细节。我会将它标记为答案,如果你更新帖子 – Poorya

1

这会不会在孩子碎片,因为工作,片段交易寻找与ID R.id.containerProfileDetails的容器。此容器不在子片段中,但它在父片段中。

你需要做的是创建一个从Child Fragment到Parent Fragment的回调。在您的子片段中的Onclick中,将回调调用到Parent Fragment,然后在Parent Fragment中,将Child Fragment替换为所需的片段。

+0

我不知道你在说什么。但我正在跳跃寻找更好的方式。所以你说没有办法从内部替换一个孩子的片段。因为在子片段本身内部没有办法获得对父级childefragmentmanager()的引用? – Poorya

+0

没有,除非你要保持父母FragmentManager在一个静态变量,如下面的答案,但我个人更喜欢回调方法。 – JaapM

+0

他在评论中的第二个建议实际上是有效的。你觉得有什么缺点吗?或可能的问题?他还更新了答案。 基本上使用普通片段管理器可以替换片段。 – Poorya