Method to refresh Fragment content when data changed ( like recall onCreateView)

不问归期 提交于 2019-12-03 15:04:06

Detach and attach it with

Fragment currentFragment = getFragmentManager().findFragmentByTag("YourFragmentTag");
FragmentTransaction fragmentTransaction = getFragmentManager().beginTransaction();
fragmentTransaction.detach(currentFragment);
fragmentTransaction.attach(currentFragment);
fragmentTransaction.commit();

or search fragment with

Fragment currentFragment = getActivity().getSupportFragmentManager().findFragmentById(R.id.container);

There is one very useful method of Fragment, which can be used for refreshing fragment.

@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
    super.setUserVisibleHint(isVisibleToUser);
    if (isVisibleToUser) {
        //Write down your refresh code here, it will call every time user come to this fragment. 
       //If you are using listview with custom adapter, just call notifyDataSetChanged(). 
    }
}

Combined two answers and removed if (isVisibleToUser), because it makes the setUserVisibleHint be called in an unpredicted asynchroneous order and fragment can either be refreshed or not. I found this piece of code stable (in your Fragment):

@Override
public void setUserVisibleHint(boolean isVisibleToUser) {

super.setUserVisibleHint(isVisibleToUser);

  // Refresh tab data:

  if (getFragmentManager() != null) {

    getFragmentManager()
      .beginTransaction()
      .detach(this)
      .attach(this)
      .commit();
  }
}

If you have problems with some of the methods listed above (as I had after uprgrading...), I recommend to make some kind of public refresh method in fragment and then simply call it, it is even less code, nicer and faster because fragment doesn't need to be reinitialized...

FragmentManager fm = getSupportFragmentManager();

//if you added fragment via layout xml
Fragment fragment = fm.findFragmentById(R.id.your_fragment_id);
if(fragment instanceof YourFragmentClass) // avoid crash if cast fail
{
    ((YourFragmentClass)fragment).showPrayer();
}

If you added fragment via code and used a tag string when you added your fragment, use findFragmentByTag instead:

Fragment fragment = fm.findFragmentByTag("yourTag");
if(fragment instanceof YourFragmentClass)
{
    ((YourFragmentClass)fragment).showPrayer();
}

When the data in a fragment changes, its always a good idea to detach and reattach the fragment into the framelayout. In my case, I have a listview which shows the favorite items of my users. Once the user unlike a product, I have to remove it from the list and reload the Favorites fragment.

So I did something like this to reload the fragment into the frame layout:

FragmentTransaction ft = getFragmentManager().beginTransaction();
ft.replace(R.id.frm,new FavoritesFragment()).addToBackStack(null).commit();

Here, frm is the frame layout in the MainActivity that hold the fragment and FavoritesFragment() is the fragment that needs to be reloaded.

The above code should be executed everytime the user press unlike button

Mike

According to FragmentTransaction#replace it's the same as calling remove and then add. So you can use .replace with the fragment manager when you're starting the fragment or when you want to reload it. So use the same function from the onCreate as well as the place where you'd want to reload it...

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    if (savedInstanceState == null) {
        loadContentFragment();
    }
}

private void someFunctionThatChangesValue(String value) {
    mValue = value;
    loadContentFragment();
}

private void loadContentFragment() {
    ContentListFragment newFrag = ContentListFragment.newInstance();
    // passing value from activity
    Bundle args = new Bundle();
    args.putString(Constants.ARG_ACCOUNT_NAME, mValue);
    newFrag.setArguments(args);
    getSupportFragmentManager().beginTransaction()
            .replace(R.id.content_frag_container,
                    newFrag,
                    Constants.CONTENT_FRAGMENT)
            .commitNow();
}

This way there's only one function that loads the content and passes data. This assumes you have an entry in your layout with the ID content_frag_container. I used a FrameLayout.

Akshay Shah

This method works for me:

MyCameraFragment f2 = new MyCameraFragment();
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.frame_container, f2);
transaction.addToBackStack(null);
transaction.commit();

Following code refreshes A fragment from withIn an Adapter

DownloadsAdapter code:

public class DownloadsAdapter extends RecyclerView.Adapter<DownloadsAdapter.ViewHolder> {

private Context mCtx;

//getting the context and product list with constructor
public DownloadsAdapter(Context mCtx, List<DataModel> fileUrlLinkList) {
    this.mCtx = mCtx;
    this.fileUrlList = fileUrlLinkList;

}

**... and in onBindViewHolder**

 FragmentManager manager = ((AppCompatActivity) mCtx).getSupportFragmentManager();
 Fragment currentFragment = manager.findFragmentByTag("DOWNLOADS");
 FragmentTransaction fragmentTransaction = manager.beginTransaction();
 fragmentTransaction.detach(currentFragment);
 fragmentTransaction.attach(currentFragment);
 fragmentTransaction.commit();

...

}
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!