【问题标题】:Pass data from firebase to object class将数据从 firebase 传递到对象类
【发布时间】:2020-05-05 12:13:22
【问题描述】:

我遇到的问题是当我设置文本文本视图时总是出现空指针异常,所以我无法将文本设置到我的视图中。

我认为对象没有填充 getData 方法的字段。如何解决这个问题?

我正在执行此步骤https://firebase.google.com/docs/firestore/query-data/listen#listen_to_multiple_documents_in_a_collection 和此Parcelable object passing from android activity to fragment

这是来自 android studio 控制台的错误输出

E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.my.plkbi, PID: 24337
    java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.String com.my.plkbi.Layanan.getSyarat()' on a null object reference
        at com.my.plkbi.SubMainFragment.onCreateView(SubMainFragment.java:78)
        at androidx.fragment.app.Fragment.performCreateView(Fragment.java:2600)
        at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:881)
        at androidx.fragment.app.FragmentManagerImpl.moveFragmentToExpectedState(FragmentManagerImpl.java:1238)
        at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:1303)
        at androidx.fragment.app.BackStackRecord.executeOps(BackStackRecord.java:439)
        at androidx.fragment.app.FragmentManagerImpl.executeOps(FragmentManagerImpl.java:2079)
        at androidx.fragment.app.FragmentManagerImpl.executeOpsTogether(FragmentManagerImpl.java:1869)
        at androidx.fragment.app.FragmentManagerImpl.removeRedundantOperationsAndExecute(FragmentManagerImpl.java:1824)
        at androidx.fragment.app.FragmentManagerImpl.execPendingActions(FragmentManagerImpl.java:1727)
        at androidx.fragment.app.FragmentManagerImpl$2.run(FragmentManagerImpl.java:150)
        at android.os.Handler.handleCallback(Handler.java:751)
        at android.os.Handler.dispatchMessage(Handler.java:95)
        at android.os.Looper.loop(Looper.java:154)
        at android.app.ActivityThread.main(ActivityThread.java:6119)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776)

编辑:添加构造函数以从其他对象添加对象,我遵循此How do I copy an object in Java? 这是关于字段数据库和 Parcelable 的对象

public class Layanan implements Parcelable {
    private String Nama;
    private String Syarat;
    private String Langkah;
    private String Lampiran;

    public Layanan(){
        //this("connect to internet", "connect to internet", "connect to internet", "connect to internet");
    }

//Constructor to add value from another object
    public Layanan(Layanan another) {
        this.nama = another.nama;
        this.syarat = another.syarat;
        this.langkah = another.langkah;
        this.lampiran = another.lampiran;
        this.deskripsi = another.deskripsi;
    }

    protected Layanan(Parcel in) {
        Nama = in.readString();
        Syarat = in.readString();
        Langkah = in.readString();
        Lampiran = in.readString();
    }

    public static final Creator<Layanan> CREATOR = new Creator<Layanan>() {
        @Override
        public Layanan createFromParcel(Parcel in) {
            return new Layanan(in);
        }

        @Override
        public Layanan[] newArray(int size) {
            return new Layanan[size];
        }
    };

    public static Layanan newInstance() {

        Bundle args = new Bundle();

        Layanan fragment = new Layanan();
        fragment.setArguments(args);
        return fragment;
    }

    private void setArguments(Bundle args) {

    }

    public String getNama() {
        return Nama;
    }

    public String getSyarat() {
        return Syarat;
    }

    public void setSyarat(String syarat) {
        Syarat = syarat;
    }

    public String getLangkah() {
        return Langkah;
    }

    public void setNama(String nama) {
        Nama = nama;
    }

    public void setLangkah(String langkah) {
        Langkah = langkah;
    }

    public String getLampiran() {
        return Lampiran;
    }

    public void setLampiran(String lampiran) {
        Lampiran = lampiran;
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        dest.writeString(Nama);
        dest.writeString(Syarat);
        dest.writeString(Langkah);
        dest.writeString(Lampiran);
    }
}

这就是我从 Firebase 获取数据的方式,它在活动中

Layanan UP;
Layanan GU;
Layanan LS;


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

        if(savedInstanceState == null) {
            //initMF();
            MainFragment homeFragment = MainFragment.newInstance();

            Bundle extras = new Bundle();


            getData("UP");
            Log.d(TAG, "This is the value name of " + UP.getNama()); //Output: This is the value name of null
            extras.putParcelable(UPParcelable, UP);
            if (UP.getSyarat()!=null) Log.d(TAG, "Value Added"); 
            if (UP.getSyarat()==null) Log.d(TAG, "Value not Added"); //Output: Value not Added

            homeFragment.setArguments(extras);
            getSupportFragmentManager().beginTransaction().add(R.id.main_activity, homeFragment).commit();
        }
...
...
    public void getData(final String p){
        mFirebase.collection("panduan_layanan")
                .whereEqualTo("nama", p)
                .addSnapshotListener(new EventListener<QuerySnapshot>() {

                    @Override
                    public void onEvent(@Nullable QuerySnapshot value, @Nullable FirebaseFirestoreException e) {
                        if (e != null){
                            Log.w(TAG, "onEvent:error", e);
                            return;
                        }
                        Layanan newLayanan = new Layanan();
                        for (QueryDocumentSnapshot doc : value) {
                            if (doc.get("nama") != null && doc.get("syarat") != null && doc.get("langkah") != null && doc.get("lampiran")!= null){
                                newLayanan.setNama(doc.getString("nama"));
                                newLayanan.setLampiran(doc.getString("lampiran"));
                                newLayanan.setLangkah(doc.getString("langkah"));
                                newLayanan.setSyarat(doc.getString("syarat"));
                                Log.d(TAG, "Update data: Success" + p);
                                Log.d(TAG, "This is the " + p + " syarat" + newLayanan.getSyarat());
                                if (newLayanan.getSyarat() != null) Log.d(TAG, "new layanan is" + newLayanan.getNama()); //new layanan isUP, it is work too
                            }
                        }
                        if (p.equals("UP")) UP = new Layanan(newLayanan);
                        Log.d(TAG, "the" + UP.getNama());  //Output theUP so it is work in here
                        if (p.equals("GU")) GU = new Layanan(newLayanan);
                        if (p.equals("LS")) LS = new Layanan(newLayanan);
                    }
                });
    }
...

非常感谢

【问题讨论】:

  • 如果您遇到异常,请从应用程序的 logcat 输出中获取确切的错误消息和堆栈跟踪并将它们添加到您的问题中。
  • 谢谢@FrankvanPuffelen 我会添加它
  • 谢谢。接下来,您的代码com.my.plkbi.SubMainFragment.onCreateView(SubMainFragment.java:78) 中的这一行是什么?顺便说一句,这些都是你应该立即做的事情,因为它增加了有人能够提供帮助的机会。
  • 您共享的代码似乎都没有包含此调用:Layanan.getSyarat()。但似乎无法从数据库中的数据中创建Layanan。我建议在您创建/填充Layanan 对象的位置设置断点,并在调试器中单步执行。
  • 感谢您的跟进。这是第 77 行和第 78 行的代码。Layanan UP = getArguments().getParcelable("UPParcelable");expandedCardText1.setText(UP.getSyarat());

标签: java android firebase google-cloud-firestore


【解决方案1】:

您不能这样做,因为 firebase 会异步执行该块。所以该字段不会像弗兰克的评论所说的那样立即获得价值

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-11-10
    • 2021-12-14
    • 1970-01-01
    • 2011-05-27
    • 1970-01-01
    • 1970-01-01
    • 2012-02-15
    • 1970-01-01
    相关资源
    最近更新 更多