【问题标题】:Problem with the asynchronous behavior of Firebase API when using Firebase Realtime Database and Android (Java)使用 Firebase 实时数据库和 Android (Java) 时 Firebase API 的异步行为问题
【发布时间】:2021-11-21 05:53:16
【问题描述】:

我目前正在做我的最后一个项目,但我卡住了。

我有 Firebase 实时数据库,它与我用 Android (Java) 编写的移动应用程序相连。 The database on which I am working has the following structure:

解决方案的想法是,我在 7 天(当前日期)中从数据库中获取 ukpromet 并将其保存到 ArrayList 中,该 ArrayList 在片段中生成bar chart

现在的代码:

public class TjednoIzvjesceFragment extends Fragment {

    final List<Float> tjednoIzvjesce = new ArrayList<>();
    public ArrayList<BarEntry> entries = new ArrayList<>();

    String korisnik, year, month, day;
    Float ukpromet;
    Integer dayx;
    Integer monthx;
    Integer yearx;
    // Baza
    FirebaseDatabase rootNode;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment
        View view = inflater.inflate(R.layout.fragment_tjedno_izvjesce, container, false);


        BarChart barChart = view.findViewById(R.id.barChart);
        
        // Testing ArrayList and Bar Chart 
        //entries.add(new BarEntry(0,2));
        
        korisnik = ((HomeActivity) requireActivity()).korisnickoIme;


        // Current date
        String sadasnjiDatum = new SimpleDateFormat("dd/MM/yyyy", Locale.getDefault()).format(new Date());

        //Current date in string
        String[] separated = sadasnjiDatum.split("/");
        dan = separated[0];
        month = separated[1];
        year = separated[2];

        //Current date in integer
        int danasdd = Integer.parseInt(dan);
        int monthdd = Integer.parseInt(month);
        int yeardd = Integer.parseInt(year);

        String korisnik = ((HomeActivity) requireActivity()).korisnickoIme;
        // Putanja do baze smjena vozaca
        rootNode = FirebaseDatabase.getInstance();
        DatabaseReference reference = rootNode.getReference("Vozaci");

        // Current date for work in integer
        dayx = todaydd;
        monthx = monthdd;
        yearx = yeardd;

        // 7 days
        int counter = 7;

        for(int i = 0; i < counter; i++){

            if (dayx <= 0) {
                ...
            }


            // DatabaseReference danPutanja = reference.child(korisnik).child("smjene").child(String.valueOf(yearx)).child("09").child(String.valueOf(dayx));
            DatabaseReference danPutanja = reference.child(korisnik).child("smjene").child("2021").child("09").child("13");

            readData(danPutanja,i, entries -> {
            });

            dayx--;
        }


        ArrayList<String> datumi = new ArrayList<>();

        datumi.add("13.09");
        datumi.add("14.09");
        datumi.add("15.09");
        datumi.add("16.09");
        datumi.add("17/09");
        datumi.add("18./09");
        datumi.add("19./09");

        // Chart Data
        BarDataSet bardataset = new BarDataSet(entries, "DateSet1");
        bardataset.setColors(ColorTemplate.COLORFUL_COLORS);

        BarData data = new BarData(bardataset);
        data.setBarWidth(0.9f);

        // Chart layout
        barChart.setDrawBarShadow(false);
        barChart.setDrawValueAboveBar(true);
        barChart.setPinchZoom(false);
        barChart.setDrawGridBackground(true);
        barChart.setData(data); // set the data and list of labels into chart
        barChart.animateY(2000);
        barChart.invalidate();
        barChart.getDescription().setEnabled(false);


        // Legend
        Legend legend = barChart.getLegend();
        legend.setEnabled(false);

        // X axis
        XAxis xAxis = barChart.getXAxis();
        //xAxis.setCenterAxisLabels(true);
        xAxis.setEnabled(true);
        //xAxis.setDrawGridLines(false);
        xAxis.setPosition(XAxis.XAxisPosition.BOTTOM);
        xAxis.setValueFormatter(new com.github.mikephil.charting.formatter.IndexAxisValueFormatter(datumi));

        return view;
    }


    private void readData(DatabaseReference danPutanja, float counter, FirebaseCallback firebaseCallback){
        danPutanja.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
                String getUkpromet;
                if (dataSnapshot.exists()) {
                    getUkpromet = dataSnapshot.child("ukPromet").getValue(String.class);
                } else {
                    getUkpromet = "0";
                }
                ukpromet = Float.parseFloat(getUkpromet);
                System.out.println(ukpromet);
                tjednoIzvjesce.add(ukpromet);
                entries.add(new BarEntry(counter,ukpromet));
                Log.e("!__@::>", counter + " " + ukpromet);

                firebaseCallback.onCallBack(entries);
            }

            @Override
            public void onCancelled(@NonNull DatabaseError error) {
                Log.d("Error: ", error.getMessage());
            }
        });
    }

    private interface FirebaseCallback{
        void onCallBack(ArrayList<BarEntry> entries);
    }
}

问题是数组中没有添加任何内容。

E/AndroidRuntime: FATAL EXCEPTION: main
    Process: hr.vsite.map.taxivodstvo, PID: 1314
    java.lang.ArrayIndexOutOfBoundsException: length=0; index=0
        at com.github.mikephil.charting.buffer.BarBuffer.addBar(BarBuffer.java:37)
        at com.github.mikephil.charting.buffer.BarBuffer.feed(BarBuffer.java:80)
        at com.github.mikephil.charting.renderer.BarChartRenderer.drawDataSet(BarChartRenderer.java:144)
        at com.github.mikephil.charting.renderer.BarChartRenderer.drawData(BarChartRenderer.java:82)
        at com.github.mikephil.charting.charts.BarLineChartBase.onDraw(BarLineChartBase.java:237)
        at android.view.View.draw(View.java:21421)
        at android.view.View.updateDisplayListIfDirty(View.java:20298)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.View.draw(View.java:21153)
        at android.view.ViewGroup.drawChild(ViewGroup.java:4388)
        at androidx.drawerlayout.widget.DrawerLayout.drawChild(DrawerLayout.java:1426)
        at android.view.ViewGroup.dispatchDraw(ViewGroup.java:4149)
        at android.view.View.draw(View.java:21424)
        at android.view.View.updateDisplayListIfDirty(View.java:20298)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ViewGroup.recreateChildDisplayList(ViewGroup.java:4372)
        at android.view.ViewGroup.dispatchGetDisplayList(ViewGroup.java:4345)
        at android.view.View.updateDisplayListIfDirty(View.java:20258)
        at android.view.ThreadedRenderer.updateViewTreeDisplayList(ThreadedRenderer.java:575)
        at android.view.ThreadedRenderer.updateRootDisplayList(ThreadedRenderer.java:581)
        at android.view.ThreadedRenderer.draw(ThreadedRenderer.java:654)
        at android.view.ViewRootImpl.draw(ViewRootImpl.java:3610)
        at android.view.ViewRootImpl.performDraw(ViewRootImpl.java:3418)
        at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:2755)
        at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1721)
E/AndroidRuntime:     at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:7598)
        at android.view.Choreographer$CallbackRecord.run(Choreographer.java:966)
        at android.view.Choreographer.doCallbacks(Choreographer.java:790)
        at android.view.Choreographer.doFrame(Choreographer.java:725)
        at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:951)
        at android.os.Handler.handleCallback(Handler.java:883)
        at android.os.Handler.dispatchMessage(Handler.java:100)
        at android.os.Looper.loop(Looper.java:214)
        at android.app.ActivityThread.main(ActivityThread.java:7356)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:492)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:930)

我怎么理解,问题出现是因为the asynchronous behavior of Firebase API

我查看了 Alex Mamo 先生的教程和几篇关于该问题的文章。我不确定它可能是什么????任何人都知道如何使它工作?

【问题讨论】:

  • 你的 onDataChange() 甚至被触发了吗?数据库的位置,欧洲?
  • 是的,它被触发了。我可以在日志中看到它:` E/!__@::>: 0.0 705.0 I/System.out: 705.0 E/!__@::>: 1.0 705.0 I/System.out: 705.0 E/!__@: :>: 2.0 705.0 I/System.out: 705.0 E/!__@::>: 3.0 705.0 I/System.out: 705.0 E/!__@::>: 4.0 705.0 I/System.out: 705.0 E/ !__@::>: 5.0 705.0 I/System.out: 705.0 E/!__@::>: 6.0 705.0 D/AndroidRuntime: 关闭 VM E/AndroidRuntime: 致命异常: 主进程: hr.vsite.map。 taxivodstvo,PID:1314 java.lang.ArrayIndexOutOfBoundsException:长度=0; index=0 ` 数据库位置:美国 (us-central1)。
  • 您在哪一行代码中遇到了这个错误?

标签: java android firebase-realtime-database mpandroidchart


【解决方案1】:
java.lang.ArrayIndexOutOfBoundsException: length=0; index=0
        at com.github.mikephil.charting.buffer.BarBuffer.addBar(BarBuffer.java:37)
        at com.github.mikephil.charting.buffer.BarBuffer.feed(BarBuffer.java:80)
        at com.github.mikephil.charting.renderer.BarChartRenderer.drawDataSet(BarChartRenderer.java:144)
        at com.github.mikephil.charting.renderer.BarChartRenderer.drawData(BarChartRenderer.java:82)
        at com.github.mikephil.charting.charts.BarLineChartBase.onDraw(BarLineChartBase.java:237)
        at android.view.View.draw(View.java:21421)

从下往上读取堆栈。

Android 正在尝试绘制您的自定义视图。 当它尝试绘制时,它正在寻找一些数据。

这很可能发生在 Firebase 数据库回复预期的数据之前。 (您在 onCreate 方法中的代码调用了 firebase,firebase 使用异步方法来检索数据,因此 Android UI 会在后台继续尝试绘制屏幕)。

您还没有共享 BarBufferBarLineChartBase 所以不能推荐修复,除了说,您的 onDraw 方法应该检查它是否真的有数据要绘制(即如果数组为空,然后跳过绘图(或绘制一个空视图)。

这可能很有趣:Do we need to use background thread for retrieving data using firebase?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2023-03-06
    • 2021-07-01
    • 2021-04-09
    • 1970-01-01
    • 2017-06-03
    • 1970-01-01
    • 2022-10-14
    相关资源
    最近更新 更多