Home > Blockchain >  ItemClick on Fragment makes the android App crash
ItemClick on Fragment makes the android App crash

Time:04-17

I am trying to show that when an item is clicked on an item on one fragement- details of that item is shown on the other fragment. It seems my code has no error. However , whenever I click on an item,the android app crashes and closes down.

Below is my COMPLETE(100%) code for all activities and corresponding xml files. You can simply copy these codes and run. I am not being able to find out why is it that the app crashes each time an item is clicked.

Error LogCat:

2022-04-17 19:18:09.220 8609-8609/com.example.fragment D/AndroidRuntime: Shutting down VM
2022-04-17 19:18:09.222 8609-8609/com.example.fragment E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.example.fragment, PID: 8609
    java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.TextView.setText(java.lang.CharSequence)' on a null object reference
        at com.example.fragment.MainActivity.OnItemSelected(MainActivity.java:32)
        at com.example.fragment.ListFrag.onListItemClick(ListFrag.java:56)
        at androidx.fragment.app.ListFragment$2.onItemClick(ListFragment.java:64)
        at android.widget.AdapterView.performItemClick(AdapterView.java:330)
        at android.widget.AbsListView.performItemClick(AbsListView.java:1187)
        at android.widget.AbsListView$PerformClick.run(AbsListView.java:3179)
        at android.widget.AbsListView$3.run(AbsListView.java:4097)
        at android.os.Handler.handleCallback(Handler.java:938)
        at android.os.Handler.dispatchMessage(Handler.java:99)
        at android.os.Looper.loop(Looper.java:223)
        at android.app.ActivityThread.main(ActivityThread.java:7656)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:592)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:947)
2022-04-17 19:18:09.249 8609-8609/com.example.fragment I/Process: Sending signal. PID: 8609 SIG: 9

MainActivity.java

package com.example.fragment;

import androidx.appcompat.app.AppCompatActivity;



import android.os.Bundle;
import android.widget.TextView;

import java.util.ArrayList;

public class MainActivity extends AppCompatActivity implements ListFrag.ItemSelected {
  TextView tvDescrtiption;
    ArrayList<String> descriptions;

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

        tvDescrtiption=findViewById(R.id.tvDescription);

        descriptions=new ArrayList<String>();

        descriptions.add("Descriptions for Item 1");
        descriptions.add("Descriptions for Item 2");
        descriptions.add("Descriptions for Item 3");

    }

    public void OnItemSelected(int index) {
        tvDescrtiption.setText(descriptions.get(index));

    }
}

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="horizontal"
    tools:context=".MainActivity">

    <androidx.fragment.app.FragmentContainerView
        android:id="@ id/fragmentContainerView"
        android:name="com.example.fragment.ListFrag"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_weight="1"
        tools:layout="@layout/fragment_list" />

    <androidx.fragment.app.FragmentContainerView
        android:id="@ id/fragmentContainerView2"
        android:name="com.example.fragment.Detail"
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_weight="1"
        tools:layout="@layout/fragment_detail" />
</LinearLayout>

ListFrag.java

package com.example.fragment;

import android.content.Context;
import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.ListFragment;


import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.ListView;

import java.util.ArrayList;

public class ListFrag extends ListFragment {
    ItemSelected activity;
public interface ItemSelected
{
    void OnItemSelected(int index);
}

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

    @Override
    public void onAttach(Context context) {
        super.onAttach(context);

        activity=(ItemSelected) context;
    }

    @Override
    public void onActivityCreated(@Nullable Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);

        ArrayList<String> data= new ArrayList<>();
        data.add("1. This is Item 1");
        data.add("2. This is Item 2");
        data.add("3. This is Item 3");

        setListAdapter(new ArrayAdapter<String>(getActivity(), android.R.layout.simple_list_item_1,data));

    }

    @Override
    public void onListItemClick( ListView l, View v, int position, long id) {
    
        activity.OnItemSelected(position);
    }
}

fragment_list.xml

<?xml version="1.0" encoding="utf-8"?>
<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"
    tools:context=".ListFrag">

    <ListView

        android:id="@ id/lvList"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
</LinearLayout>

Detail.java

package com.example.fragment;

import android.os.Bundle;

import androidx.fragment.app.Fragment;

import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;

public class Detail extends Fragment {
    
    private static final String ARG_PARAM1 = "param1";
    private static final String ARG_PARAM2 = "param2";
    
    private String mParam1;
    private String mParam2;
    public Detail() {
       
    }

   
    public static Detail newInstance(String param1, String param2) {
        Detail fragment = new Detail();
        Bundle args = new Bundle();
        args.putString(ARG_PARAM1, param1);
        args.putString(ARG_PARAM2, param2);
        fragment.setArguments(args);
        return fragment;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        if (getArguments() != null) {
            mParam1 = getArguments().getString(ARG_PARAM1);
            mParam2 = getArguments().getString(ARG_PARAM2);
        }
    }
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.fragment_detail, container, false);
    }
}

fragment_detail.xml

<?xml version="1.0" encoding="utf-8"?>
<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"
    android:background="@color/yellow"
    tools:context=".Detail">

    <TextView
        android:id="@ id/tvDescription"
        android:layout_width="122dp"
        android:layout_height="wrap_content"
        android:text="TextView"
        android:textSize="20sp" />
</FrameLayout>

CodePudding user response:

tvDescrtiption is null because it's inside a Detail fragment not directly in MainActivity, you should try and update the fragment from within.

CodePudding user response:

You are receiving a NullPointerException because when .setText() is invoked, it is being invoked on tvDescrtiption, which is null. If you set a breakpoint on lines 19 (tvDescrtiption=findViewById(R.id.tvDescription);) and 30 (tvDescrtiption.setText(descriptions.get(index));), you will see that tvDescrtiption is indeed null.

Why is it null? I have not used findViewById() in the longest, but if I recall correctly, you can only retrieve a View this way if you inflated it in the Activity or Fragment. tvDescrtiption lives in fragment_detail.xml, but in MainActivity, you are inflating activity_main.xml. You can currently only use findViewById() in MainActivity to retrieve views declared in activity_main.xml.

  • Related