How to change fragment when a onClick event is triggerred?

J.erome :

I want to change from HomeFragment to AperoDetailFragment when I click on a list item in this HomeFragment.

I can already trigger the event and it seems to work since the logs appears. This is my HomeFragment:

public class HomeFragment extends Fragment {

    private HomeViewModel homeViewModel;
    private View root;

    public View onCreateView(@NonNull final LayoutInflater inflater,
                             final ViewGroup container, Bundle savedInstanceState) {
        homeViewModel =
                ViewModelProviders.of(this).get(HomeViewModel.class);
        root = inflater.inflate(R.layout.fragment_home, container, false);
        final TextView textView = root.findViewById(R.id.text_home);
        homeViewModel.getText().observe(getViewLifecycleOwner(), new Observer<String>() {
            @Override
            public void onChanged(@Nullable String s) {
                textView.setText(s);
            }
        });

        ArrayList<AperoVersion> incomingApero = new ArrayList<AperoVersion>();
        initList(incomingApero);
        AperoIncomingAdapter adapterIncomingApero = new AperoIncomingAdapter(this.getContext(),R.layout.apero_coming_cell_layout, incomingApero);
        final ListView listIncomingApero = (ListView)root.findViewById(R.id.list_apero);
        listIncomingApero.setAdapter(adapterIncomingApero);
        listIncomingApero.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> adapter, View v, int position, long id) {
                AperoVersion selectedItem = (AperoVersion) adapter.getItemAtPosition(position);
                Log.v("Root now", "Root: " + root);

                //root = inflater.inflate(R.layout.apero_detail_layout, container, false);
                Fragment newFragment = new AperoDetailFragment();
                FragmentTransaction transaction = getFragmentManager().beginTransaction();
                transaction.replace(R.id.list_apero, newFragment);
                transaction.addToBackStack(null);
                transaction.commit();

                Log.v("CustomAdapterExemple", "Selected element: " + selectedItem.getName());
                Log.v("Root now", "Root: " + root);
            }
        });
        return root;
    }

I tried with the root = inflater... and the root changed in the log but the display wasn't changing. Then I tried with the transaction but I get the error:

2020-03-02 21:23:41.401 6781-6781/com.example.lapero E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.example.lapero, PID: 6781
    java.lang.UnsupportedOperationException: addView(View) is not supported in AdapterView
        at android.widget.AdapterView.addView(AdapterView.java:489)
        at androidx.fragment.app.FragmentStateManager.createView(FragmentStateManager.java:326)
        at androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1187)
        at androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1356)
        at androidx.fragment.app.FragmentManager.moveFragmentToExpectedState(FragmentManager.java:1434)
        at androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1497)
        at androidx.fragment.app.BackStackRecord.executeOps(BackStackRecord.java:447)
        at androidx.fragment.app.FragmentManager.executeOps(FragmentManager.java:2169)
        at androidx.fragment.app.FragmentManager.executeOpsTogether(FragmentManager.java:1992)
        at androidx.fragment.app.FragmentManager.removeRedundantOperationsAndExecute(FragmentManager.java:1947)
        at androidx.fragment.app.FragmentManager.execPendingActions(FragmentManager.java:1849)
        at androidx.fragment.app.FragmentManager$4.run(FragmentManager.java:413)
        at android.os.Handler.handleCallback(Handler.java:883)
        at android.os.Handler.dispatchMessage(Handler.java:100)
        at android.os.Looper.loop(Looper.java:214)
        at android.app.ActivityThread.main(ActivityThread.java:7356)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)  

I can provide any xml file if needed. So how can I change my displayed layout/fragment ?

[edit]
Here is my AperoDetailFragment.java :

public class AperoDetailFragment extends Fragment {

    private View root;

    public AperoDetailFragment() {
        // Required empty public constructor
    }

    @Override
    public View onCreateView(@NonNull final LayoutInflater inflater,
                             final ViewGroup container, Bundle savedInstanceState) {
        root = inflater.inflate(R.layout.fragment_detail_apero, container, false);

        //------------------------------------- la liste simple des apéros à venir-------------------
        ArrayList<AperoVersion> aperoList = new ArrayList<AperoVersion>();
        initList(aperoList);
    //    AperoAdapter adapter = new AperoAdapter(this.getContext(),R.layout.apero_detail_layout, aperoList);
     //   final ListView list = (ListView)root.findViewById(R.id.list_apero);
     //    list.setAdapter(adapter);

        return root;
    }

    private void initList(ArrayList<AperoVersion> androidList) {
...
    }
}
Oscar Emilio Perez Martinez :

The problems is the following line

transaction.replace(R.id.list_apero, newFragment);

You're trying to create a fragment transaction using your listView's ID.

Do this inside your Fragment Resource file where your list view is, add an id called content(or any other name) to your layout like thisandroid:id="@+id/content"

then in the code where your are doing your fragment replacement, edit this line of code transaction.replace(R.id.list_apero, nextFrag); to be transaction.replace(R.id.content, nextFrag);

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=20910&siteId=1