【问题标题】:Nested Child Fragment with Viewpager带有 Viewpager 的嵌套子片段
【发布时间】:2017-07-17 13:44:25
【问题描述】:

目前,我正在尝试使用片段创建嵌套视图寻呼机,如何访问顶级父函数来刷新视图?

假设我有:

 public class ParentFragment extends Fragment {

    ...{
    ...
    viewPagerAdapter = new ViewPagerParentAdapter(getChildFragmentManager(), listOfItem);
    viewPager.setAdapter(viewPagerAdapter);
    }

public void refreshView(){
    loadData();
}


private class ViewPagerParentAdapter extends FragmentStatePagerAdapter{
    private List<String> tabTitle;
    private List<Item> listOfItem;
    public ViewPagerParentAdapter(FragmentManager fm, @NonNull List<Item> listOfItem) {
        super(fm);

        this.tabTitle = new ArrayList<>();
        this.listOfItem = new ArrayList<>();

        if (listOfItem.size() > 0) {
            this.listOfItem = listOfItem;

            for (Item item : this.listOfItem) {
                tabTitle.add(Item.getCLASSIFICATION());
            }
        }
        notifyDataSetChanged();
    }

    @Override
    public Fragment getItem(int position) {
        return DetailFragment.newInstance(getItemAtPosition(position).getDETAILS());
    }

     public Item getItemAtPosition(int position) {
        return listOfItem != null ? listOfItem.get(position) : null;
    }
}
}

这里是我的对象

public class Item{
    //POJO
    private String CLASSIFICATION;
    private Details details;
}

细节片段

public class DetailFragment extends Fragment{

...{
    ...
    Details details = getArguments().getParcelable("details");

    viewPagerAdapter = new DetailViewPagerAdapter(getChildFragmentManager(), details);
    viewPagerDetails.setAdapter(viewPagerAdapter);
}

public void refreshParentView(){
    ((ParentFragment) getParentFragment()).refreshView(); //getting Null
}

public class DetailViewPagerAdapter extends FragmentStatePagerAdapter {

    String[] tabTitle = {"Components", "Materials", "Descriptions"};
    Details details;


    public DetailViewPagerAdapter(FragmentManager fm, @NonNull Details details) {
        super(fm);
        this.details = details;
        notifyDataSetChanged();
    }

    @Override
    public Fragment getItem(int position) {
        switch (position) {
            case 0:
                return DetailsChildFragment.newInstance(details.getCOMPONENT());
            case 1:
                return DetailsChildFragment.newInstance(details.getMATERIAL());
            case 2:
                return DetailsChildFragment.newInstance(details.getDESC());
        }
        return null;
    }

    @Override
    public int getCount() {
        return tabTitle.length;
    }
}
}

最后一个子片段

public class DetailsChildFragment extends Fragment implements View.OnClickListener{

...{
...
...

Button buttonRefresh = (Button)getView().findViewById(R.id.button_refresh);
buttonRefresh.setOnClickListener(this);
}

@Override
public void onClick(View view){
    switch(view.getId()){
        case R.id.button_refresh:
            ((DetailFragment)getParentFragment()).refreshParentView();
        break;
    }
}

}

目前我在细节片段 refreshParentView

上得到 Null

有什么建议吗?提前致谢

【问题讨论】:

    标签: android android-fragments fragment android-nested-fragment


    【解决方案1】:

    您可以使用interface 作为Listener 来处理发生在孩子身上的事件

    public interface Listener{
      void onRefreshButtonClicked();
    }
    

    子fragment需要有一个Listener作为字段,然后在获取子fragment的实例时可以设置Listener

    public class ChildFragment extends Fragment{
    
    private Listener listener;
    
    public void setListener(Listener listener)//setter
    ...
    
    //now on button click you call the listener
    refreshButton.setOnClickListener(new View.OnClickListener(){
    
        @Override onClick(){
            if(listener!=null){
                listener.onRefreshButtonClicked();
            }
        }
    }
    
    
    
    
    public class ParentFragment extends Fragment{
        ...
    
    
        ChildFragment child = ChildFragment.getInstance()
        child.setListener(new Listener(){
            @Override
            void onRefreshButtonClicked(){
    // implement your logic
            }
        }
    

    这样做的一个好处是您不需要将父级从Fragment 转换为ParentFragment,这使得您的代码可以在您需要时重复使用

    【讨论】:

    • 谢谢这对我有帮助:D
    【解决方案2】:

    当您添加 DetailFragment 时,请使用标签进行操作,以便您可以在需要时检索它的实例。示例:

    getSupportFragmentManager().beginTransaction().add(R.id.fragment_container, detailFragment,"detailFragmentTag").commit();
    

    现在,任何时候你需要访问这个片段,你只需要调用

    DetailFragment parentFragment = (DetailFragment) getActivity().getSupportFragmentManager().findFragmentByTag("detailFragmentTag");
    if(detailFragment != null && detailFragment.isAdded()){ //check if it is not null and it is added to the view so you dont end up in some NPE
        detailFragment.refreshParentView()
    

    【讨论】:

    • 感谢您的回答,如果访问第二个父级是正确的,但我需要访问父级的顶部(ParentFragment(this) -> DetailFragment(not this) ->DetailChildFragment),谢谢跨度>
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-09-14
    • 1970-01-01
    • 2014-01-17
    • 1970-01-01
    • 2015-05-18
    • 2013-11-17
    • 1970-01-01
    相关资源
    最近更新 更多