【问题标题】:NoSuchMethodError in Fragment with Cardview and RecyclerView connected to Firebase片段中的 NoSuchMethodError 与 Cardview 和 RecyclerView 连接到 Firebase
【发布时间】:2018-11-19 02:25:19
【问题描述】:

我正在尝试创建一个连接到 firebase 的事件报告应用程序,每当我在应用程序中创建事件时,它都会显示在 Firebase 数据库中,并以 Cardview 和 RecyclerView 的形式显示在应用程序本身中。我的应用程序已经可以在 Firebase 中显示输出,现在我正在尝试完成 CardView 和 RecyclerView。

但是,当我现在运行我的应用程序时,每当我尝试单击允许我输入事件的片段时,应用程序就会崩溃并显示此错误:

java.lang.NoSuchMethodError:Lcom/google/firebase/FirebaseApp 类中没有虚拟方法 zzbox()Z;或其超类(“com.google.firebase.FirebaseApp”的声明出现在 /data/app/com.example.samuel.a4-CppiMKcbuMktQgH7RUO1XA==/split_lib_dependencies_apk.apk 中)

假定的错误是我片段中的这一行:

mDatabase = FirebaseDatabase.getInstance().getReference().child("Incidents");

请记住,这是在片段中,而我观看的教程是在普通课堂上。

这是我输入事件的片段

package com.example.samuel.a4;

import android.content.Intent;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentTransaction;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.Toolbar;

import com.firebase.ui.database.FirebaseRecyclerAdapter;
import com.github.clans.fab.FloatingActionButton;
import com.github.clans.fab.FloatingActionMenu;
import com.google.firebase.database.DatabaseReference;
import com.google.firebase.database.FirebaseDatabase;

import org.w3c.dom.Text;


public class IncmanFragment extends Fragment {

private RecyclerView mBlogList;
private DatabaseReference mDatabase;

FloatingActionButton fab;

@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable 
ViewGroup container, @Nullable Bundle savedInstanceState) {
//        return inflater.inflate(R.layout.fragment_incman, container, 
false);
     //i moved this up from just ontop of fab to here
    View myView = inflater.inflate(R.layout.fragment_incman, container, 
false);
   // getFragmentManager().findFragmentById(R.id.fragment_container);
    mDatabase = 
FirebaseDatabase.getInstance().getReference().child("Incidents");
    mDatabase.keepSynced(true);

    mBlogList=(RecyclerView) myView.findViewById(R.id.recyclerview);
    mBlogList.setHasFixedSize(true);
    mBlogList.setLayoutManager(new LinearLayoutManager(getActivity()));


    fab = (FloatingActionButton) myView.findViewById(R.id.fabIncident);
    fab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            FragmentTransaction fragmentTransaction = 
getFragmentManager().beginTransaction();
            fragmentTransaction.replace(R.id.fragment_container, new 
ReportFragment());
            fragmentTransaction.addToBackStack(null);
          /*  Toast.makeText(getActivity(), "toast successful", 
Toast.LENGTH_SHORT).show();*/
            fragmentTransaction.commit();

        }

    });

    return myView;
}

@Override
public void onStart() {
    super.onStart();
    FirebaseRecyclerAdapter<IncmanFirebaseName, IncmanViewHolder> 
    firebaseRecyclerAdapter = new 
    FirebaseRecyclerAdapter<IncmanFirebaseName, 
    IncmanViewHolder>
            (IncmanFirebaseName.class, R.layout.incidentdesign, 
      IncmanViewHolder.class, mDatabase) {
        @Override
        protected void populateViewHolder(IncmanViewHolder viewHolder, 

            viewHolder.setTitle(model.getTitle());
            viewHolder.setDetails(model.getDetailsId());
            viewHolder.setRemarks(model.getRemarksId());
            viewHolder.setLocation(model.getLocationId());
            viewHolder.setDate(model.getDate());
            viewHolder.setUrgency(model.getUrgencyId());

        }
    };

    mBlogList.setAdapter(firebaseRecyclerAdapter);

}

    public static class IncmanViewHolder extends RecyclerView.ViewHolder
    {
        View mView;
        public IncmanViewHolder(View itemView)
        {
            super(itemView);
            mView = itemView;
        }
        public void setTitle(String title)
        {
            TextView tvtitledesign = 
    (TextView)mView.findViewById(R.id.tvtitledesign);
            tvtitledesign.setText(title);
        }
        public void setDetails(String detailsId)
        {
            TextView tvdetailsdesign = 
    (TextView)mView.findViewById(R.id.tvdetailsdesign);
            tvdetailsdesign.setText(detailsId);
        }
        public void setRemarks(String remarksId)
        {
            TextView tvremarksdesign = 
    (TextView)mView.findViewById(R.id.tvremarksdesign);
            tvremarksdesign.setText(remarksId);
        }
        public void setLocation(String locationId)
        {
            TextView tvlocationdesign = (TextView) 
    mView.findViewById(R.id.tvlocationdesign);
            tvlocationdesign.setText(locationId);

        }
        public void setDate (String date)
        {
            TextView tvdatedesign = 
     (TextView)mView.findViewById(R.id.tvdatedesign);
            tvdatedesign.setText(date);
        }
        public void setUrgency(String urgencyId)
        {
            TextView tvurgencydesign = 
     (TextView)mView.findViewById(R.id.tvurgencydesign);
            tvurgencydesign.setText(urgencyId);
        }
    }
}

这是构造函数以及get和set方法所在的类

 package com.example.samuel.a4;

    public class IncmanFirebaseName {

    private String date;
    private String detailsId;
    private String locationId;
    private String remarksId;
    private String reportedById;
    private String splocationId;
    private String typeId;
    private String urgencyId;
    private String title;

    public IncmanFirebaseName(String date, String detailsId, String 
    remarksId/*String reportedById*/ /* String typeId*/, String urgencyId, 
    String 
    title) {
        this.date = date;
        this.detailsId = detailsId;
      /*  this.locationId = locationId;*/
        this.remarksId = remarksId;
        /*this.reportedById = reportedById;*/
        this.splocationId = splocationId;
        /*this.typeId = typeId;*/
        this.urgencyId = urgencyId;
        this.title=title;
    }

    public String getDate() {
        return date;
    }

    public void setDate(String date) {
        this.date = date;
    }

    public String getDetailsId() {
        return detailsId;
    }

    public void setDetailsId(String detailsId) {
        this.detailsId = detailsId;
    }

    public String getLocationId() {
        return locationId;
    }

    public void setLocationId(String locationId) {
        this.locationId = locationId;
    }

    public String getRemarksId() {
        return remarksId;
    }

    public void setRemarksId(String remarksId) {
        this.remarksId = remarksId;
    }

    /*public String getReportedById() {
        return reportedById;
    }

    public void setReportedById(String reportedById) {
        this.reportedById = reportedById;
    }*/

    /* public String getSplocationId() {
        return splocationId;
    }

    public void setSplocationId(String splocationId) {
        this.splocationId = splocationId;
    }*/

     /*   public String getTypeId() {
        return typeId;
    }

    public void setTypeId(String typeId) {
        this.typeId = typeId;
    }*/

    public String getUrgencyId() {
        return urgencyId;
    }

    public void setUrgencyId(String urgencyId) {
        this.urgencyId = urgencyId;
    }

    public String getTitle(){
        return title;
    }
    public void setTitle() {
        this.title = title;
    }
    public IncmanFirebaseName()
    {

    }
    }

Database Structure

现在我不确定为什么 logcat 在我的代码中将该行显示为错误,因为我在另一个片段中有类似的行并且它工作得非常好;这是片段:“ package com.example.samuel.a4;

    import android.app.DatePickerDialog;
    import android.app.ProgressDialog;
    import android.content.Intent;
    import android.graphics.Bitmap;
    import android.graphics.Color;
    import android.graphics.drawable.ColorDrawable;
    import android.media.Image;
    import android.net.Uri;
    import android.os.Bundle;
    import android.provider.MediaStore;
    import android.support.annotation.NonNull;
    import android.support.annotation.Nullable;
    import android.support.v4.app.Fragment;
    import android.text.TextUtils;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.AdapterView;
    import android.widget.ArrayAdapter;
    import android.widget.Button;
    import android.widget.DatePicker;
    import android.widget.EditText;
    import android.widget.ImageView;
    import android.widget.Spinner;
    import android.widget.TextView;
    import android.widget.Toast;

    import com.google.android.gms.tasks.OnCompleteListener;
    import com.google.android.gms.tasks.OnFailureListener;
    import com.google.android.gms.tasks.OnSuccessListener;
    import com.google.android.gms.tasks.Task;
    import com.google.firebase.database.DatabaseReference;
    import com.google.firebase.database.FirebaseDatabase;
    import com.google.firebase.storage.FirebaseStorage;
    import com.google.firebase.storage.OnProgressListener;
    import com.google.firebase.storage.StorageReference;
    import com.google.firebase.storage.UploadTask;

    import org.w3c.dom.Text;

    import java.io.IOException;
    import java.util.Calendar;
    import java.util.Date;
    import java.util.UUID;

    import static android.app.Activity.RESULT_OK;

    public class ReportFragment extends Fragment implements 
    AdapterView.OnItemSelectedListener{

    private Button btnChoose,btnUpload;
    private ImageView imageView;
    private Uri filePath;
    private final int PICK_IMAGE_REQUEST = 71;
    private TextView mDisplayDate;
    private DatePickerDialog.OnDateSetListener mDateSetListener;

    private EditText reportedBy;
    private TextView date; //upstairs declare alr as mDisplayDate
    private Spinner spinner; //downstairs declare alr as spinner3
    private EditText location;
    private Spinner spinner2; //downstairs declare alr as spinner2
    private EditText details;
    private Spinner spinner3; //downstairs declare alr as spinner1
    private EditText remarks;
    private EditText title;
    private Button submitIncident;

    DatabaseReference databaseIncidents;
    FirebaseStorage storage;
    StorageReference storageReference;

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, @Nullable 
    ViewGroup container, @Nullable Bundle savedInstanceState) {
        View v = inflater.inflate(R.layout.fragment_report, container, 
false);

          databaseIncidents = 
    FirebaseDatabase.getInstance().getReference("Incidents");
        storage = FirebaseStorage.getInstance();
        storageReference = storage.getReference();

        btnChoose = (Button) v.findViewById(R.id.btnChoose);
        btnUpload = (Button) v.findViewById(R.id.btnUpload);
        imageView = (ImageView) v.findViewById(R.id.imgView);

        reportedBy = (EditText) v.findViewById(R.id.etreportedby);
    //        Below have already line 151
    //        date = (TextView) v.findViewById(R.id.tvdate);
        location = (EditText) v.findViewById(R.id.etlocation);
        details = (EditText) v.findViewById(R.id.etdetails);
        remarks = (EditText) v.findViewById(R.id.etremarks);
        title = (EditText) v.findViewById(R.id.ettitle);
        submitIncident = (Button) v.findViewById(R.id.btnSubmit);


        btnChoose.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                chooseImage();
            }
        });
        btnUpload.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                uploadImage();
            }
        });

        submitIncident.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                incidentSubmit();
            }
        });

        return v;


    }

    private void incidentSubmit(){
        String reportedname = reportedBy.getText().toString().trim();
        String location1 = location.getText().toString();
        String details1 = details.getText().toString();
        String remarks1 = remarks.getText().toString();
        String urgency1 = spinner.getSelectedItem().toString();
        String type1 = spinner2.getSelectedItem().toString();
        String splocation1 = spinner3.getSelectedItem().toString();
        String date1 = mDisplayDate.getText().toString();
        String title1 = title.getText().toString();

        if(!TextUtils.isEmpty(reportedname)) {

            String incidentId = databaseIncidents.push().getKey();
            Incident incident = new 

  Incident(reportedname,location1,details1,remarks1,urgency1,type1,splocation1,date1,title1);
            databaseIncidents.child(incidentId).setValue(incident);

            Toast.makeText(getActivity(), "Incident Added", 
    Toast.LENGTH_LONG).show();
        } else {
            Toast.makeText(getActivity(), "All fields must be 
    entered",Toast.LENGTH_LONG).show();
        }

    }


    @Override
    public void onItemSelected(AdapterView<?> parent, View view, int position, 
    long id) {
        String text = parent.getItemAtPosition(position).toString();
        Toast.makeText(parent.getContext(), text, Toast.LENGTH_SHORT).show();
    }

    @Override
    public void onNothingSelected(AdapterView<?> parent) {

    }

    }

真诚感谢任何帮助。谢谢!

【问题讨论】:

  • 请仅添加您认为导致问题的最少且可验证的代码量。
  • 抱歉,我已经尝试删除一些代码。我对编码还是很陌生,因此不太了解
  • 如果错误就在您所说的那一行,那么您的 Firebase 数据库结构有问题。
  • 您可能知道我们的数据库结构有什么问题吗?因为在我们开始的 3-4 周内,我和我的朋友都没有见过这个错误
  • 删除您的 XML 并发布您的数据库结构,以便我可以查看错误。

标签: android firebase android-fragments firebase-realtime-database


【解决方案1】:

好的,从您的评论和代码来看,我认为您在设置对数据库的引用和实际检索值之间感到困惑。

下面的代码行,只是在您的 Firebase 数据库中设置了对 Incidents 子项的引用。

mDatabase = FirebaseDatabase.getInstance().getReference().child("Incidents");

要从数据库中检索值,您必须使用eventListeners,在this answer 中阅读有关eventListeners 的更多信息。

我给你一个示例代码来检索你的数据库的locationId 节点的第一个唯一ID 的值。它看起来像这样:

mDatabase.child("LR9j...").addListenerForSingleValueEvent(new ValueEventListener() {
// in the child("LR9j..") you have to put the whole first id from your image
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                String locId = dataSnapshot.child("locationId").getValue(String.class);
            }

            @Override
            public void onCancelled(DatabaseError databaseError) {
                Log.d(TAG, "onCancelled", databaseError.toException());
            }


        });

上面的代码会将第一个唯一 ID 的 locationId 的值存储在变量 locId 中。此外,您必须了解 Firebase 异步检索值,因此它只能在 eventListener 内部工作。

this answer 中了解有关 Firebase 异步行为的更多信息。

还可以在文档中阅读有关 Firebase 的更多信息。

【讨论】:

  • 嗨,实际上对于 id,它是在我从应用程序中添加的每个新事件时自动生成的。所以我想问是否有任何替代第一行“mDatabase.child("LR9j...").addListenerForSingleValueEvent(new ValueEventListerner()" 因为如果我要创建一个新事件是否意味着我必须继续写更多这些代码?如果我要删除这些事件是否意味着我也必须删除这些代码?
  • 出于这个确切原因,有push()getKey()。在此处阅读更多相关信息firebase.google.com/docs/database/admin/…,也可以通过单击答案旁边的 V 型刻度标记按钮将答案标记为正确,这有助于问题的未来读者,我也会很感激。干杯! :)
  • 我刚刚尝试添加示例,它仍然显示相同的错误!我不确定我是否将示例代码放置在正确的区域,但我将其放置在标题为“Incman Fragment”(第一个代码区域)的“return myView”上方的片段中。我放错了,还是我应该先填写所有其他输入?还是有其他问题?非常感谢您的帮助!
  • 嗨,经过更多研究,我发现这可能是由于 gradle 问题,我现在有点让我的应用程序可以工作了!非常感谢!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-05-23
  • 1970-01-01
  • 1970-01-01
  • 2018-08-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多