如何将数据从 BottomSheetDialogFragment 返回到父片段
Posted
技术标签:
【中文标题】如何将数据从 BottomSheetDialogFragment 返回到父片段【英文标题】:How to return data from BottomSheetDialogFragment to Parent Fragment 【发布时间】:2019-06-14 04:51:50 【问题描述】:我在底部表中填充 RecyclerView 并将底部表显示为底部表对话框片段。当点击 RecyclerView 中的项目时,我想使用该项目的详细信息自动填写表单。
如何将包含来自 BottomSheetDialogFragment 的数据的类(模型)对象传递给我在其中实例化 BottomSheetDialogFragment 的片段。这是我的代码
我想自动填充字段的片段
public class FormFragment extends Fragment implements onItemSelected public class fetchSimilarContacts extends AsyncTask<Void, Void, String>
String result, res, search;
fetchSimilarContacts(String sear)
search = sear;
@Override
protected void onPostExecute(String aVoid)
try
if (res.equals("200"))
try
// bring up bottom sheet
bottomSheetDialogFragment = new formBottomSheet();
Bundle bun = new Bundle();
bun.putParcelableArrayList("data", contItems);
bottomSheetDialogFragment.setArguments(bun);
bottomSheetDialogFragment.show(getActivity().getSupportFragmentManager(), bottomSheetDialogFragment.getTag());
catch (Exception ex)
ex.printStackTrace();
else
Toast.makeText(getActivity().getApplicationContext(), "Could not connect to server", Toast.LENGTH_LONG).show();
我使用上面的 asynctask 函数获取数据并填充 RecyclerView。这是 formBottomSheet 类
public class formBottomSheet extends BottomSheetDialogFragment
similarContactAdapter mAdapter;
RecyclerView rec;
ArrayList<hash> contItems;
View v;
onItemSelected itemSelected;
@Override
public void onCreate(@Nullable Bundle savedInstanceState)
super.onCreate(savedInstanceState);
//contItems = new ArrayList<hash>();
if(getArguments() != null)
contItems = getArguments().getParcelableArrayList("data");
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState)
/*return super.onCreateView(inflater, container, savedInstanceState);*/
v = inflater.inflate(R.layout.form_bottomsheet_recyclerview, container, false);
rec = (RecyclerView) v.findViewById(R.id.recycler);
itemSelected = (onItemSelected) getParentFragment();
//contItems = new ArrayList<hash>();
mAdapter = new similarContactAdapter(contItems, getActivity().getApplicationContext(), new similarContactAdapter.onItemClickListener()
@Override
public void onItemClick(hash hsh)
//after clicking on an item in the RecyclerView, i get the item's data here, how to i pass the data from here to the Form Fragment where i instantiated the bottom sheet fragment dialog?
Toast.makeText(getActivity().getApplicationContext(), "", Toast.LENGTH_LONG).show();
);
final RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getActivity().getApplicationContext());
rec.setLayoutManager(mLayoutManager);
rec.setItemAnimator(new DefaultItemAnimator());
rec.setAdapter(mAdapter);
mAdapter.notifyDataSetChanged();
return v;
@Override
public void setupDialog(Dialog dialog, int style)
super.setupDialog(dialog, style);
public interface onItemSelected
void SendHashItem(hash hsh);
单击 RecyclerView 中的项目后,我在此处获取该项目的数据,如何将数据从此处传递到我实例化 BottomSheetFragmentDialog 的表单片段?
这是我的活动
protected void onCreate(Bundle savedInstanceState)
try
super.onCreate(savedInstanceState);
// Hide the status bar.
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN);
setContentView(R.layout.activity_dashboard);
//initialize
toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
viewPager = (ViewPager) findViewById(R.id.viewp);
setupViewPager(viewPager);
title = findViewById(R.id.title);
tabLayout = (TabLayout) findViewById(R.id.tabs);
tabLayout.setupWithViewPager(viewPager);
tabLayout.setSelectedTabIndicatorColor(ContextCompat.getColor(getApplicationContext(), R.color.transparent));
setupTabIcons();
tabLayout.addOnTabSelectedListener(new TabLayout.OnTabSelectedListener()
@Override
public void onTabSelected(TabLayout.Tab tab)
View tabView = tab.getCustomView();
// get inflated children Views the icon and the label by their id
TextView tab_label = (TextView) tabView.findViewById(R.id.tab);
// change the label color, by getting the color resource value
tab_label.setTextColor(ContextCompat.getColor(getApplicationContext(), R.color.colorPrimary));
// change the image Resource
// i defined all icons in an array ordered in order of tabs appearances
// call tab.getPosition() to get active tab index.
tab_label.setCompoundDrawablesWithIntrinsicBounds(0, tabIconsActive[tab.getPosition()], 0, 0);
//"#4CAF50");
@Override
public void onTabUnselected(TabLayout.Tab tab)
View tabView = tab.getCustomView();
// get inflated children Views the icon and the label by their id
TextView tab_label = (TextView) tabView.findViewById(R.id.tab);
// change the label color, by getting the color resource value
tab_label.setTextColor(ContextCompat.getColor(getApplicationContext(), R.color.white));
// change the image Resource
// i defined all icons in an array ordered in order of tabs appearances
// call tab.getPosition() to get active tab index.
tab_label.setCompoundDrawablesWithIntrinsicBounds(0, tabIcons[tab.getPosition()], 0, 0);
@Override
public void onTabReselected(TabLayout.Tab tab)
);
viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener()
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels)
@Override
public void onPageSelected(int position)
tabLayout.setScrollPosition(position, 0 , true);
tabLayout.setSelected(true);
@Override
public void onPageScrollStateChanged(int state)
);
viewPager.setCurrentItem(0);
tabLayout.getTabAt(0).select();
setToolbarTitle();
catch(Exception e)
e.printStackTrace();
private void setupViewPager(ViewPager viewPager)
ViewPagerAdapter adapter = new ViewPagerAdapter(getSupportFragmentManager());
adapter.addFragment(new VideoFragment(), "Video");
adapter.addFragment(new ThreeSixtyFragment(), "360");
adapter.addFragment(new FormFragment(), "Form");
adapter.addFragment(new SettingsFragment(), "Settings");
viewPager.setAdapter(adapter);
private void setupTabIcons()
TextView tabThree = (TextView) LayoutInflater.from(this).inflate(R.layout.cust_tab, null);
tabThree.setText("Video");
tabThree.setTextColor(ContextCompat.getColor(getApplicationContext(), R.color.colorPrimary));
tabThree.setCompoundDrawablesWithIntrinsicBounds(0, R.drawable.ic_video_red, 0, 0);
tabLayout.getTabAt(0).setCustomView(tabThree);
TextView tabTwo = (TextView) LayoutInflater.from(this).inflate(R.layout.cust_tab, null);
tabTwo.setText("360");
tabTwo.setCompoundDrawablesWithIntrinsicBounds(0, R.drawable.ic_360_white, 0, 0);
tabLayout.getTabAt(1).setCustomView(tabTwo);
TextView tabOne = (TextView) LayoutInflater.from(this).inflate(R.layout.cust_tab, null);
tabOne.setText("Form");
tabOne.setCompoundDrawablesWithIntrinsicBounds(0, R.drawable.ic_form_white, 0, 0);
tabLayout.getTabAt(2).setCustomView(tabOne);
TextView tabFive = (TextView) LayoutInflater.from(this).inflate(R.layout.cust_tab, null);
tabFive.setText("Settings");
tabFive.setCompoundDrawablesWithIntrinsicBounds(0, R.drawable.ic_settings_white, 0, 0);
tabLayout.getTabAt(3).setCustomView(tabFive);
@Override
public void onFragmentInteraction(Uri uri)
class ViewPagerAdapter extends FragmentPagerAdapter
private final List<Fragment> mFragmentList = new ArrayList<>();
private final List<String> mFragmentTitleList = new ArrayList<>();
public ViewPagerAdapter(FragmentManager manager)
super(manager);
@Override
public Fragment getItem(int position)
return mFragmentList.get(position);
@Override
public int getCount()
return mFragmentList.size();
public void addFragment(Fragment fragment, String title)
mFragmentList.add(fragment);
mFragmentTitleList.add(title);
@Override
public CharSequence getPageTitle(int position)
return mFragmentTitleList.get(position);
【问题讨论】:
【参考方案1】:您的FormFragment
和formBottomSheet
都是位于同一个Activity 实例中的片段。
有时片段会有“父”或“子”片段,但这里不是这种情况,因为您的FormFragment
使用getActivity().getSupportFragmentManager()
来显示底部工作表,而不是getChildFragmentManager()
。这完全没问题,但要记住这一点。
这意味着formBottomSheet
与FormFragment
“对话”的最佳方式是与 Activity 对话,然后让 Activity 将其传递给 FormFragment
。
formBottomSheet
-> Activity
-> FormFragment
与 Activity 对话非常简单。您只需调用 getActivity()
并将其转换为您的 Activity 的类名即可:
mAdapter = new similarContactAdapter(contItems, getActivity().getApplicationContext(), new similarContactAdapter.onItemClickListener()
@Override
public void onItemClick(hash hsh)
MyActivity activity = (MyActivity) getActivity();
activity.onHashItem(hsh);
);
在您的 Activity 中,您可以使用 FragmentManager 获取您的 FormFragment
,然后将消息发送给它。这依赖于 FormFragment
要么具有 id
(如果您在 XML 中设置 android:id
属性,或者如果您使用 replace(R.id.some_id, ...)
则可以使用 id)或 tag
(如果您设置android:tag
属性在它的 XML 中或者如果你使用 replace(..., "TAG")
那么你可以使用标签)。
public void onHashItem(hash hsh)
FragmentManager fm = getSupportFragmentManager();
// use only one of the two following lines
FormFragment fragment = (FormFragment) fm.findFragmentById(R.id.some_id); // if using id
FormFragment fragment = (FormFragment) fm.findFragmentByTag("TAG"); // if using tag
fragment.onHashItem(hsh);
最后,您可以在FormFragment
中创建onHashItem()
方法:
public void onHashItem(hash hsh)
// do whatever you want
【讨论】:
我在尝试通过 id 或标签获取 FormFragment 时得到空引用。在我的活动中,我使用了视图寻呼机,所以我尝试获取当前片段,但我认为我的片段列表返回零,因为 BottomSheetDialogFragment 处于活动状态 这是一条很长的路。他可以在需要它的片段中实现一个接口,而无需引用 Host Activity。以上是关于如何将数据从 BottomSheetDialogFragment 返回到父片段的主要内容,如果未能解决你的问题,请参考以下文章