Skip to content
This repository has been archived by the owner on Aug 8, 2023. It is now read-only.

Chained animations lead to StackOverFlowException #5836

Closed
ivovandongen opened this issue Jul 30, 2016 · 3 comments
Closed

Chained animations lead to StackOverFlowException #5836

ivovandongen opened this issue Jul 30, 2016 · 3 comments
Labels
Android Mapbox Maps SDK for Android bug

Comments

@ivovandongen
Copy link
Contributor

ivovandongen commented Jul 30, 2016

In creating an activity to reproduce the error in #5721 I ran into a situation where the test app crashes due to a StackOverflowException. The relevant code in question:

    private void animateToNextPosition(final int iterations) {
        //Setup the target camera position
        final CameraPosition cameraPosition = new CameraPosition.Builder()
                .target(getNextLatLng())
                .bearing(270)
                .tilt(20)
                .build();

        //Create a callback
        final MapboxMap.CancelableCallback callback = new MapboxMap.CancelableCallback() {
            @Override
            public void onCancel() {
                Log.i(TAG, String.format("Duration onCancel Callback called on Thread id: %s, name %s", Thread.currentThread().getId(), Thread.currentThread().getName()));
                //Toast.makeText(CameraAnimationChainingActivity.this, "Duration onCancel Callback called.", Toast.LENGTH_SHORT).show();
            }

            @Override
            public void onFinish() {
                Log.i(TAG, String.format("Duration onFinish Callback called on Thread id: %s, name %s", Thread.currentThread().getId(), Thread.currentThread().getName()));
                //Toast.makeText(CameraAnimationChainingActivity.this, "Duration onFinish Callback called.", Toast.LENGTH_SHORT).show();
                if (iterations > 0) {
                    animateToNextPosition(iterations - 1);
                }
            }
        };

        mapView.getMapAsync(new OnMapReadyCallback() {
            @Override
            public void onMapReady(MapboxMap mapboxMap) {
                mapboxMap.animateCamera(CameraUpdateFactory.newCameraPosition(cameraPosition), 7500, callback);
            }
        });
    }

Resulting in:

...
07-30 16:03:34.426  4707  4707 I CameraAnimationChainingActivity: Duration onFinish Callback called on Thread id: 1, name main
07-30 16:03:34.427  4707  4707 I CameraAnimationChainingActivity: Duration onFinish Callback called on Thread id: 1, name main
07-30 16:03:34.427  4707  4707 I CameraAnimationChainingActivity: Duration onFinish Callback called on Thread id: 1, name main
07-30 16:03:34.595  4707  4707 W art     : JNI WARNING: java.lang.StackOverflowError thrown while calling printStackTrace
07-30 16:03:34.625  4707  4707 W System.err: java.lang.StackOverflowError: stack size 8MB

The actual issue is caused when cancelTransitions() is called in MapView#flyto(), which eventually reaches Transform::cancelTransition() in core where the previous transitionFinishFn is still set:

    if (transitionFinishFn) {
        transitionFinishFn();
    }

    transitionFrameFn = nullptr;
    transitionFinishFn = nullptr;

Might be solved by clearing the transitionFn and then calling it. A similar situation exists in startTransition() which might instigate the loop.

Possibly related: #5833

cc @tmpsantos @zugaldia

@ivovandongen
Copy link
Contributor Author

So, clearing the function pointer before calling it does prevent the loop leading to the StackOverFlowException. Another issue surfaces thought where the second animation is started and executed (log statements indicate so), but the visual map is not actually updated. Starting another animation does work after that.

@bleege
Copy link
Contributor

bleege commented Aug 1, 2016

/sub

@bleege
Copy link
Contributor

bleege commented Aug 9, 2016

Great job @ivovandongen!

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Android Mapbox Maps SDK for Android bug
Projects
None yet
Development

No branches or pull requests

2 participants