我正在尝试通过recyclerView从数据库检索数据。但是它运行不正常。应用程序需要通过检索Firebase数据库中的所有数据转到第二页(这是详细信息页面)。但我收到此错误。 原因:java.lang.NullPointerException:尝试调用虚拟方法“ com.google.firebase.database.ChildEventListener com.google.firebase.database.Query.addChildEventListener(com.google.firebase.database.ChildEventListener)”在空对象引用上 ..会出现什么问题。
在我的mainActivity类中,我正在编码如何向数据库添加数据。当我单击按钮时,它运行正常并且数据正在添加到表中。但是当我单击按钮时,它应该重定向到详细信息界面。但它没有发生。数据已正确添加到数据库,然后应用程序开始停止。然后我得到了上面的错误。
这是我的mainActivity类。
package com.example.medisafe;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import android.content.Intent;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import com.firebase.ui.database.FirebaseRecyclerAdapter;
import com.firebase.ui.database.FirebaseRecyclerOptions;
import com.google.firebase.database.DatabaseReference;
import com.google.firebase.database.FirebaseDatabase;
public class MainActivity extends AppCompatActivity {
EditText txtCname, txtSpecial,txtDocName, txtadd, txtphone, date, time;
Button button;
DatabaseReference dbRef;
Appointment appointment;
FirebaseDatabase firebaseDatabase;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
txtCname = (EditText)findViewById(R.id.eTTCenterName);
txtSpecial = (EditText)findViewById(R.id.eTTSpeciality);
txtDocName= (EditText)findViewById(R.id.eTTdocName);
txtadd = (EditText)findViewById(R.id.eTTAddress);
txtphone = (EditText)findViewById(R.id.eTTPhone);
date = (EditText)findViewById(R.id.editTextDate);
time = (EditText)findViewById(R.id.editTextTime);
button = (Button) findViewById(R.id.button);
appointment = new Appointment();
dbRef = FirebaseDatabase.getInstance().getReference().child("Appointment");
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
int phone = Integer.parseInt(txtphone.getText().toString().trim());
appointment.setName(txtCname.getText().toString().trim());
appointment.setSpecial(txtSpecial.getText().toString().trim());
appointment.setDocName(txtDocName.getText().toString().trim());
appointment.setAddress(txtadd.getText().toString().trim());
appointment.setPhone(phone);
appointment.setDate(date.getText().toString().trim());
appointment.setTime(time.getText().toString().trim());
String id = dbRef.push().getKey();
dbRef.child(id).setValue(appointment);
Toast.makeText(MainActivity.this, "saved successfully",Toast.LENGTH_LONG).show();
opennewpage();
}
});
}
public void opennewpage (){
Intent intent = new Intent(this, AppointmentDetail.class);
startActivity(intent);
}
}
这是我的viewHolder类。
package com.example.medisafe;
import android.content.Context;
import android.view.View;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import java.util.ConcurrentModificationException;
public class ViewHolder extends RecyclerView.ViewHolder {
public ViewHolder(@NonNull View itemView) {
super(itemView);
itemView.setOnLongClickListener(new View.OnLongClickListener() {
@Override
public boolean onLongClick(View view) {
mClickListener.onItemLongClick(view,getAdapterPosition());
return false;
}
});
}
public void setData(Context context, String cname, String sp, String docName, String Add, int cphone, String adate, String aTime){
TextView textView = itemView.findViewById(R.id.txtViewRow);
textView.setText("Center Name: "+cname+ "\n" + "Specialization"+ sp + "\n"+ "Doctor Name: "+docName+ "\n"
+ "Location: "+Add+ "\n"+ "Phone"+ "\n" + "Date: "+adate+ "\n" + "Time: "+aTime);
}
private ViewHolder.Clicklistener mClickListener;
public interface Clicklistener{
void onItemLongClick(View view, int position);
}
public void setOnClickListener(ViewHolder.Clicklistener clickListener)
{
mClickListener = clickListener;
}
}
这是我的AppointmentDetail类。
package com.example.medisafe;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Toast;
import com.firebase.ui.database.FirebaseRecyclerAdapter;
import com.firebase.ui.database.FirebaseRecyclerOptions;
import com.google.firebase.database.DataSnapshot;
import com.google.firebase.database.DatabaseError;
import com.google.firebase.database.DatabaseReference;
import com.google.firebase.database.FirebaseDatabase;
import com.google.firebase.database.Query;
import com.google.firebase.database.ValueEventListener;
public class AppointmentDetail extends AppCompatActivity {
DatabaseReference dbRef;
String name;
RecyclerView recyclerView;
FirebaseDatabase firebaseDatabase;
Appointment appointment;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_appointment_detail);
recyclerView = findViewById(R.id.detailView);
recyclerView.setHasFixedSize(true);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
}
protected void onStart(){
super.onStart();
FirebaseRecyclerOptions<Appointment> options = new FirebaseRecyclerOptions.Builder<Appointment>()
.setQuery(dbRef,Appointment.class).build();
FirebaseRecyclerAdapter<Appointment, ViewHolder> firebaseRecyclerAdapter = new FirebaseRecyclerAdapter<Appointment, ViewHolder>(options){
@Override
protected void onBindViewHolder(@NonNull ViewHolder holder, int position, @NonNull Appointment model) {
holder.setData(getApplicationContext(), model.getName(), model.getSpecial(), model.getDocName(),
model.getAddress(), model.getPhone(), model.getDate(), model.getTime());
holder.setOnClickListener(new ViewHolder.Clicklistener() {
@Override
public void onItemLongClick(View view, int position) {
name = getItem(position).getName();
showDeleteDialog(name);
}
});
}
@NonNull
@Override
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.row, parent, false);
return new ViewHolder(view);
}
};
firebaseRecyclerAdapter.startListening();
recyclerView.setAdapter(firebaseRecyclerAdapter);
}
private void showDeleteDialog(final String name){
AlertDialog .Builder builder = new AlertDialog.Builder(AppointmentDetail.this);
builder.setTitle("Delete");
builder.setMessage("Sure You want to delete this?");
builder.setPositiveButton("yes", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int i) {
Query query = dbRef.orderByChild("name").equalTo(name);
query.addListenerForSingleValueEvent(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot snapshot) {
for (DataSnapshot ds : snapshot.getChildren()) {
ds.getRef().removeValue();
}
Toast.makeText(AppointmentDetail.this, "Data deleted", Toast.LENGTH_SHORT).show();
}
@Override
public void onCancelled(@NonNull DatabaseError error) {
}
});
}
});
builder.setNegativeButton("No", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int i) {
dialog.dismiss();
}
});
AlertDialog alertDialog = builder.create();
alertDialog.show();
}
}
他们说错误出在此行的详细信息类的第76行。
firebaseRecyclerAdapter.startListening();
此行位于 viewHolder 方法之后的Appointmentmentdetail类中。