从 Firebase 传输数据到对象类。

huangapple go评论88阅读模式
英文:

Pass data from firebase to object class

问题

问题是当我设置文本视图时,总是会出现空指针异常,因此我无法将文本设置为我的视图。

我认为对象没有从getData方法中填充字段。如何修复这个问题?

我正在按照以下步骤进行操作:https://firebase.google.com/docs/firestore/query-data/listen#listen_to_multiple_documents_in_a_collection 和 https://stackoverflow.com/questions/52172309/parcelable-object-passing-from-android-activity-to-fragment

这是来自Android Studio控制台的错误输出:

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

编辑:添加构造函数以从其他对象添加对象,我遵循了https://stackoverflow.com/questions/869033/how-do-i-copy-an-object-in-java

这是有关字段数据库和Parcelable的对象:

  1. public class Layanan implements Parcelable {
  2. // ...(省略其他代码)
  3. //Constructor to add value from another object
  4. public Layanan(Layanan another) {
  5. this.Nama = another.Nama;
  6. this.Syarat = another.Syarat;
  7. this.Langkah = another.Langkah;
  8. this.Lampiran = another.Lampiran;
  9. }
  10. // ...(省略其他代码)
  11. }

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

  1. public class MainActivity extends AppCompatActivity {
  2. // ...(省略其他代码)
  3. Layanan UP;
  4. Layanan GU;
  5. Layanan LS;
  6. protected void onCreate(Bundle savedInstanceState) {
  7. super.onCreate(savedInstanceState);
  8. setContentView(R.layout.activity_main);
  9. if (savedInstanceState == null) {
  10. // ...(省略其他代码)
  11. getData("UP");
  12. Log.d(TAG, "This is the value name of " + UP.getNama()); //Output: This is the value name of null
  13. extras.putParcelable(UPParcelable, UP);
  14. if (UP.getSyarat() != null) Log.d(TAG, "Value Added");
  15. if (UP.getSyarat() == null) Log.d(TAG, "Value not Added"); //Output: Value not Added
  16. homeFragment.setArguments(extras);
  17. getSupportFragmentManager().beginTransaction().add(R.id.main_activity, homeFragment).commit();
  18. }
  19. // ...(省略其他代码)
  20. }
  21. // ...(省略其他代码)
  22. public void getData(final String p) {
  23. mFirebase.collection("panduan_layanan")
  24. .whereEqualTo("nama", p)
  25. .addSnapshotListener(new EventListener<QuerySnapshot>() {
  26. // ...(省略其他代码)
  27. });
  28. }
  29. // ...(省略其他代码)
  30. }

非常感谢。

英文:

The issue I have is there're always Null Pointer Exception when I settext textview, so I cannot setText to my view.

I think the object didn't fill the field from getData method. How to fix this?

I am following this step https://firebase.google.com/docs/firestore/query-data/listen#listen_to_multiple_documents_in_a_collection and this https://stackoverflow.com/questions/52172309/parcelable-object-passing-from-android-activity-to-fragment.

This is the error output from android studio console

  1. E/AndroidRuntime: FATAL EXCEPTION: main
  2. Process: com.my.plkbi, PID: 24337
  3. java.lang.NullPointerException: Attempt to invoke virtual method &#39;java.lang.String com.my.plkbi.Layanan.getSyarat()&#39; on a null object reference
  4. at com.my.plkbi.SubMainFragment.onCreateView(SubMainFragment.java:78)
  5. at androidx.fragment.app.Fragment.performCreateView(Fragment.java:2600)
  6. at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:881)
  7. at androidx.fragment.app.FragmentManagerImpl.moveFragmentToExpectedState(FragmentManagerImpl.java:1238)
  8. at androidx.fragment.app.FragmentManagerImpl.moveToState(FragmentManagerImpl.java:1303)
  9. at androidx.fragment.app.BackStackRecord.executeOps(BackStackRecord.java:439)
  10. at androidx.fragment.app.FragmentManagerImpl.executeOps(FragmentManagerImpl.java:2079)
  11. at androidx.fragment.app.FragmentManagerImpl.executeOpsTogether(FragmentManagerImpl.java:1869)
  12. at androidx.fragment.app.FragmentManagerImpl.removeRedundantOperationsAndExecute(FragmentManagerImpl.java:1824)
  13. at androidx.fragment.app.FragmentManagerImpl.execPendingActions(FragmentManagerImpl.java:1727)
  14. at androidx.fragment.app.FragmentManagerImpl$2.run(FragmentManagerImpl.java:150)
  15. at android.os.Handler.handleCallback(Handler.java:751)
  16. at android.os.Handler.dispatchMessage(Handler.java:95)
  17. at android.os.Looper.loop(Looper.java:154)
  18. at android.app.ActivityThread.main(ActivityThread.java:6119)
  19. at java.lang.reflect.Method.invoke(Native Method)
  20. at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886)
  21. at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776)

EDIT: Add constructor to add object from other object, I follow this https://stackoverflow.com/questions/869033/how-do-i-copy-an-object-in-java
This is the object about the field database and Parcelable

  1. public class Layanan implements Parcelable {
  2. private String Nama;
  3. private String Syarat;
  4. private String Langkah;
  5. private String Lampiran;
  6. public Layanan(){
  7. //this(&quot;connect to internet&quot;, &quot;connect to internet&quot;, &quot;connect to internet&quot;, &quot;connect to internet&quot;);
  8. }
  9. //Constructor to add value from another object
  10. public Layanan(Layanan another) {
  11. this.nama = another.nama;
  12. this.syarat = another.syarat;
  13. this.langkah = another.langkah;
  14. this.lampiran = another.lampiran;
  15. this.deskripsi = another.deskripsi;
  16. }
  17. protected Layanan(Parcel in) {
  18. Nama = in.readString();
  19. Syarat = in.readString();
  20. Langkah = in.readString();
  21. Lampiran = in.readString();
  22. }
  23. public static final Creator&lt;Layanan&gt; CREATOR = new Creator&lt;Layanan&gt;() {
  24. @Override
  25. public Layanan createFromParcel(Parcel in) {
  26. return new Layanan(in);
  27. }
  28. @Override
  29. public Layanan[] newArray(int size) {
  30. return new Layanan[size];
  31. }
  32. };
  33. public static Layanan newInstance() {
  34. Bundle args = new Bundle();
  35. Layanan fragment = new Layanan();
  36. fragment.setArguments(args);
  37. return fragment;
  38. }
  39. private void setArguments(Bundle args) {
  40. }
  41. public String getNama() {
  42. return Nama;
  43. }
  44. public String getSyarat() {
  45. return Syarat;
  46. }
  47. public void setSyarat(String syarat) {
  48. Syarat = syarat;
  49. }
  50. public String getLangkah() {
  51. return Langkah;
  52. }
  53. public void setNama(String nama) {
  54. Nama = nama;
  55. }
  56. public void setLangkah(String langkah) {
  57. Langkah = langkah;
  58. }
  59. public String getLampiran() {
  60. return Lampiran;
  61. }
  62. public void setLampiran(String lampiran) {
  63. Lampiran = lampiran;
  64. }
  65. @Override
  66. public int describeContents() {
  67. return 0;
  68. }
  69. @Override
  70. public void writeToParcel(Parcel dest, int flags) {
  71. dest.writeString(Nama);
  72. dest.writeString(Syarat);
  73. dest.writeString(Langkah);
  74. dest.writeString(Lampiran);
  75. }
  76. }

This is how i get data from Firebase, it's inside in activity

  1. Layanan UP;
  2. Layanan GU;
  3. Layanan LS;
  4. protected void onCreate(Bundle savedInstanceState) {
  5. super.onCreate(savedInstanceState);
  6. setContentView(R.layout.activity_main);
  7. if(savedInstanceState == null) {
  8. //initMF();
  9. MainFragment homeFragment = MainFragment.newInstance();
  10. Bundle extras = new Bundle();
  11. getData(&quot;UP&quot;);
  12. Log.d(TAG, &quot;This is the value name of &quot; + UP.getNama()); //Output: This is the value name of null
  13. extras.putParcelable(UPParcelable, UP);
  14. if (UP.getSyarat()!=null) Log.d(TAG, &quot;Value Added&quot;);
  15. if (UP.getSyarat()==null) Log.d(TAG, &quot;Value not Added&quot;); //Output: Value not Added
  16. homeFragment.setArguments(extras);
  17. getSupportFragmentManager().beginTransaction().add(R.id.main_activity, homeFragment).commit();
  18. }
  19. ...
  20. ...
  21. public void getData(final String p){
  22. mFirebase.collection(&quot;panduan_layanan&quot;)
  23. .whereEqualTo(&quot;nama&quot;, p)
  24. .addSnapshotListener(new EventListener&lt;QuerySnapshot&gt;() {
  25. @Override
  26. public void onEvent(@Nullable QuerySnapshot value, @Nullable FirebaseFirestoreException e) {
  27. if (e != null){
  28. Log.w(TAG, &quot;onEvent:error&quot;, e);
  29. return;
  30. }
  31. Layanan newLayanan = new Layanan();
  32. for (QueryDocumentSnapshot doc : value) {
  33. if (doc.get(&quot;nama&quot;) != null &amp;&amp; doc.get(&quot;syarat&quot;) != null &amp;&amp; doc.get(&quot;langkah&quot;) != null &amp;&amp; doc.get(&quot;lampiran&quot;)!= null){
  34. newLayanan.setNama(doc.getString(&quot;nama&quot;));
  35. newLayanan.setLampiran(doc.getString(&quot;lampiran&quot;));
  36. newLayanan.setLangkah(doc.getString(&quot;langkah&quot;));
  37. newLayanan.setSyarat(doc.getString(&quot;syarat&quot;));
  38. Log.d(TAG, &quot;Update data: Success&quot; + p);
  39. Log.d(TAG, &quot;This is the &quot; + p + &quot; syarat&quot; + newLayanan.getSyarat());
  40. if (newLayanan.getSyarat() != null) Log.d(TAG, &quot;new layanan is&quot; + newLayanan.getNama()); //new layanan isUP, it is work too
  41. }
  42. }
  43. if (p.equals(&quot;UP&quot;)) UP = new Layanan(newLayanan);
  44. Log.d(TAG, &quot;the&quot; + UP.getNama()); //Output theUP so it is work in here
  45. if (p.equals(&quot;GU&quot;)) GU = new Layanan(newLayanan);
  46. if (p.equals(&quot;LS&quot;)) LS = new Layanan(newLayanan);
  47. }
  48. });
  49. }
  50. ...

Thank you so much

答案1

得分: 0

因为 Firebase 会异步执行该代码块,所以你不能这样做。因此,该字段不会立即获得值,就像 Frank 的评论所说的那样。

英文:

You can't do that because firebase execute that block asynchronously. So the field doesn't get value immediately just like Frank's comment said

huangapple
  • 本文由 发表于 2020年5月5日 20:13:22
  • 转载请务必保留本文链接:https://go.coder-hub.com/61612879.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定